"""
This module is used to hold the Player class.  The Player represents the 
user-controlled sprite on the screen.
"""
import pygame
import constants
vec = pygame.math.Vector2

from spritesheet_functions import SpriteSheet

class Player(pygame.sprite.Sprite):
    """ This class represents the bar at the bottom that the player
        controls. """
 
    # -- Methods
    def __init__(self):
        """ Constructor function """
 
        # Call the parent's constructor
        super(Player, self).__init__()
 
        # Create an image of the block, and fill it with a color.
        # This could also be an image loaded from the disk.
        width = 20
        height = 40
        self.image = pygame.Surface([width, height])
        #self.image.fill(constants.RED)
 
        # Set speed vector of player
        self.change_x = 0
        self.change_y = 0

        # Set Velocity and Acceleration
        self.vel = vec(0, 0)
        self.acc = vec(0, 0)
 
        # This holds all the images for the animated walk left/right of the player
        self.walking_frames_l = []
        self.walking_frames_r = []

        # Which direction the player is facing
        self.direction = "R"

        # List of sprites we can bump against
        self.level = None

        sprite_sheet = SpriteSheet("graphics/robosheet.bmp")
        # Load all the right facing images into a list

        #image = sprite_sheet.get_image(10,5,40,81)
        #image = pygame.transform.scale(image, (35,65))
        #self.walking_frames_r.append(image)
        image = sprite_sheet.get_image(0, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        self.walking_frames_r.append(image)
        image = sprite_sheet.get_image(56, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        self.walking_frames_r.append(image)
        image = sprite_sheet.get_image(100, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        self.walking_frames_r.append(image)
        image = sprite_sheet.get_image(146, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        self.walking_frames_r.append(image)
        image = sprite_sheet.get_image(200, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        self.walking_frames_r.append(image)
        image = sprite_sheet.get_image(250, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        self.walking_frames_r.append(image)

        # Load all the right facing images into a list
        #image = sprite_sheet.get_image(10,5,40,81)
        #image = pygame.transform.scale(image, (35,65))
        #image = pygame.transform.flip(image,True, False)
        #self.walking_frames_l.append(image)
        image = sprite_sheet.get_image(0, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        image = pygame.transform.flip(image,True, False)
        self.walking_frames_l.append(image)
        image = sprite_sheet.get_image(56, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        image = pygame.transform.flip(image, True, False)
        self.walking_frames_l.append(image)
        image = sprite_sheet.get_image(100, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        image = pygame.transform.flip(image, True, False)
        self.walking_frames_l.append(image)
        image = sprite_sheet.get_image(146, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        image = pygame.transform.flip(image, True, False)
        self.walking_frames_l.append(image)
        image = sprite_sheet.get_image(200, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        image = pygame.transform.flip(image, True, False)
        self.walking_frames_l.append(image)
        image = sprite_sheet.get_image(250, 103, 50, 81)
        image = pygame.transform.scale(image, (35, 65))
        image = pygame.transform.flip(image, True, False)
        self.walking_frames_l.append(image)

        # Set the image the player starts with
        self.image = self.walking_frames_r[0]
        # Set a referance to the image rect.
        self.rect = self.image.get_rect()
 
    def update(self):
        """ Move the player. """
        # Gravity
        self.calc_grav()
 
        # Move left/right
        self.rect.x += self.change_x
        pos = self.rect.x + self.level.world_shift
        self.acc = vec(0, constants.PLAYER_GRAVITY)
        if self.direction == "R":
            frame = (pos // 15) % len(self.walking_frames_r)
            self.image = self.walking_frames_r[frame]
        else:
            frame = (pos // 15) % len(self.walking_frames_l)
            self.image = self.walking_frames_l[frame] 
        # See if we hit anything
        block_hit_list = pygame.sprite.spritecollide(
            self, self.level.platform_list, False)
        for block in block_hit_list:
            # If we are moving right,
            # set our right side to the left side of the item we hit
            if self.change_x > 0:
                self.rect.right = block.rect.left
            elif self.change_x < 0:
                # Otherwise if we are moving left, do the opposite.
                self.rect.left = block.rect.right
 
        # Move up/down
        self.rect.y += self.change_y
 
        # Check and see if we hit anything
        block_hit_list = pygame.sprite.spritecollide(
            self, self.level.platform_list, False)
        for block in block_hit_list:
 
            # Reset our position based on the top/bottom of the object.
            if self.change_y > 0:
                self.rect.bottom = block.rect.top
            elif self.change_y < 0:
                self.rect.top = block.rect.bottom
 
            # Stop our vertical movement
            self.change_y = 0
 
    def calc_grav(self):
        """ Calculate effect of gravity. """
        if self.change_y == 0:
            self.change_y = 1
        else:
            self.change_y += 2
 
        # See if we are on the ground.
        if self.rect.y >= constants.SCREEN_HEIGHT - self.rect.height \
                and self.change_y >= 0:
            self.change_y = 0
            self.rect.y = constants.SCREEN_HEIGHT - self.rect.height
 
    def jump(self):
        """ Called when user hits 'jump' button."""
 
        # move down a bit and see if there is a platform below us.
        # Move down 2 pixels because it doesn't work well if we only move down
        # 1 when working with a platform moving down.
        self.rect.y += 2
        platform_hit_list = pygame.sprite.spritecollide(
            self, self.level.platform_list, False)
        self.rect.y -= 2
 
        # If it is ok to jump, set our speed upwards
        if len(platform_hit_list) > 0 \
                or self.rect.bottom >= constants.SCREEN_HEIGHT:
            self.change_y = -30
 
    # Player-controlled movement:
    def go_left(self):
        """Called when the user hits the left arrow."""
        #self.change_x = -10
        self.change_x = -constants.PLAYER_ACC
        self.change_x += self.vel.x * constants.PLAYER_FRICTION
        print(self.vel.x)
        #self.vel += self.change_x
        #self.pos += self.vel + 0.5 * self.change_x
        self.direction = "L"
 
    def go_right(self):
        """Called when the user hits the right arrow."""
        self.change_x = 10
        #self.acc.x = constants.PLAYER_ACC
        self.direction = "R"
 
    def stop(self):
        """Called when the user lets off the keyboard."""
        self.change_x = 0

    def crouch(self):
        #player duck method
        self.rect.height = 20
        self.image = pygame.Surface([20, 20])
        self.image.fill(constants.GREEN)

    def normal(self):
        self.rect.height = 40
        self.image = pygame.Surface([20, 40])
        self.image.fill(constants.RED)
 
 