Kupo = Entity:New(x,y)

 function Kupo:New(x,y)
 	local o = Entity:New(x,y)

  o.type = "kupo"

 	o.pos = {x = x, y = y}
  o.speed = 20
  o.range = 200
  o.target = {x = x, y = y}
	o.sprite_offset = {x = 8, y = 5}

  -- animations
  o.body = Animation:New(animation.kupo.body)
  o.bow = Animation:New(animation.kupo.bow)

  -- bow
  o.bow_flip = 1
  o.bow_rotation = 0
  o.bow_frame = 1
  o.bow_subframe = 1
  o.bow_aim_frame = 0
  o.bow_speed = 1/10
  o.bow_frames = 6
  o.bow_extraframes = 18
	o.bow_aim_frames = 8
  o.hostile = true

  o.lightRange = o.range/2
	o.light = CreateLight(o.pos.x,o.pos.y,o.lightRange)

  table.insert(LoadedObjects.Entities,o)
  o.id = #LoadedObjects.Entities

 	setmetatable(o, self)
 	self.__index = self
 	return o
 end

function Kupo:Smart()
  self.light.pos.x = self.pos.x-self.target_offset.x
  self.light.pos.y = self.pos.y-self.target_offset.y

  self.target.x = main_Player.pos.x - main_Player.target_offset.x
  self.target.y = main_Player.pos.y - main_Player.target_offset.y
  local distance_x = self.target.x - self.pos.x
  local distance_y = self.target.y - self.pos.y
  local distance = math.sqrt(distance_x ^ 2 + distance_y ^ 2)
  local angle = GetAngleFromVector(distance_x,distance_y)
  self.draw_bow = false
  if distance <= self.range then
    if self.hostile == true then
      self.draw_bow = true
      -- fix so it can rotate from 0 to 360
      if math.deg(self.bow_rotation - angle) < 0 then
        self.bow_rotation = self.bow_rotation + math.rad(360)
      end

      -- fix so it can rotate from 360 to 0
      if math.deg(self.bow_rotation - angle) > 180 then
        self.bow_rotation = self.bow_rotation - math.rad(360)
      end

      -- actual rotation
      if self.bow_rotation < angle then
        self.bow_rotation = self.bow_rotation + math.rad(2)
      else
        self.bow_rotation = self.bow_rotation - math.rad(2)
      end
      --set in place
      if math.abs(math.deg(self.bow_rotation) - math.deg(angle)) < 2 then
          self.bow_rotation = angle
      end

      -- holding tight dispersion -- also affects arrows
      if self.bow_rotation == angle then
        self.bow_rotation = self.bow_rotation + math.rad(math.random(math.abs(math.floor(self.bow_frame-self.bow_aim_frames-self.bow_frames)/2)))
      end

      -- AIMING AI

        self.bow_subframe = self.bow_subframe + current_dt

      if self.bow_subframe > self.bow_speed then
        self.bow_subframe = self.bow_subframe - self.bow_speed
        if self.bow_frame == 3 then
          self.bow_aim_frame = self.bow_aim_frame + 1
          if self.bow_aim_frame > self.bow_aim_frames then
            self.bow_aim_frame = self.bow_aim_frame - self.bow_aim_frames
            self.bow_frame = self.bow_frame + 1
            Arrow:New(self.pos.x,self.pos.y,self.bow_rotation,15)
          end
        else
          self.bow_frame = self.bow_frame + 1
        end
        if self.bow_frame > self.bow_frames + self.bow_extraframes then
          self.bow_frame = self.bow_frame - self.bow_frames - self.bow_extraframes
        end
      end
    end
  else
    self.bow_frame = 6
    -- rest bow animation
    if distance_x > 0 then
      if self.bow_rotation > math.rad(45) then
        self.bow_rotation = self.bow_rotation - math.rad(3)
      elseif self.bow_rotation < math.rad(45) then
        self.bow_rotation = self.bow_rotation + math.rad(3)
      end

      -- set in place
      if math.abs(math.deg(self.bow_rotation) - 45) < 3 then
          self.bow_rotation = math.rad(45)
      end
      self.sprite_flip.x = 1
    else
      if self.bow_rotation > math.rad(135) then
        self.bow_rotation = self.bow_rotation - math.rad(3)
      elseif self.bow_rotation < math.rad(135) then
        self.bow_rotation = self.bow_rotation + math.rad(3)
      end
      -- set in place
      if math.abs(math.deg(self.bow_rotation) - 135) < 3 then
        self.bow_rotation = math.rad(135)
      end
      self.sprite_flip.x = -1
    end
  end
  self.angle = angle
end

function Kupo:HandleAnimation()
  local distance_x = self.target.x - self.pos.x
  local distance_y = self.target.y - self.pos.y

  if distance_x > 0 then
    self.sprite_flip.x = 1
  else
    self.sprite_flip.x = -1
  end

  -- flip sprite to look in the direction is moving
  if self.vel.x ~= 0 then self.sprite_flip.x = math.sign(self.vel.x) end

  self.body:Animate()
  self:Draw(self.body)

  if self.draw_bow == true then
    self.bow:DrawFrame(
      math.min(self.bow_frame,self.bow_frames),
      self.pos.x + (    8 * math.sin(self.bow_rotation)),
      self.pos.y + (2 - 6 * math.cos(self.bow_rotation)),
      self.bow_rotation
    )
  end
end

function Kupo:DoPhysics()

  	-- horizontal collisions
  if not isThereAnyCollisionAt(self.pos.x + self.vel.x, self.pos.y) then
  	self.pos.x = self.pos.x + self.vel.x
  end
  if not isThereAnyCollisionAt(self.pos.x, self.pos.y + self.vel.y) then
    self.pos.y = self.pos.y + self.vel.y
  end
end
