home *** CD-ROM | disk | FTP | other *** search
/ PC Format (South-Africa) 2001 June / PCFJune.iso / Xenon / XenonSource.exe / xenon / source / actor.cpp next >
Encoding:
C/C++ Source or Header  |  2000-09-09  |  4.5 KB  |  220 lines

  1. //-------------------------------------------------------------
  2. //
  3. // Class:    CActor
  4. //
  5. // Author:    John M Phillips
  6. //
  7. // Started:    06/05/00
  8. //
  9. // Base:    None
  10. //
  11. // Derived:    CShip
  12. //            CAlien
  13. //            CBullet
  14. //            CPickup
  15. //
  16. //-------------------------------------------------------------
  17.  
  18. #include "game.h"
  19.  
  20. //-------------------------------------------------------------
  21.  
  22. CActor::CActor()
  23. {
  24.     m_scene = 0;
  25.     m_owner = 0;
  26.     m_is_active = false;
  27.     m_is_on_screen = false;
  28.     m_is_hit = false;
  29.     m_score_multiplier = 1.f;
  30. }
  31.  
  32. //-------------------------------------------------------------
  33.  
  34. CActor::~CActor()
  35. {
  36. }
  37.  
  38. //-------------------------------------------------------------
  39.  
  40. bool CActor::activate()
  41. {
  42.     if (!m_is_active) {
  43.     
  44.         const ActorInfo& info = getActorInfo();
  45.  
  46.         if (info.m_filename)
  47.             m_image = m_scene->getImage(info.m_filename);
  48.         else
  49.             m_image = 0;
  50.  
  51.         m_sprite.setImage(m_image);
  52.         m_sprite.setHotspot(gsCPoint(info.m_hotspot_x,
  53.                                      info.m_hotspot_y));
  54.         m_sprite.setActive(m_image != 0);
  55.  
  56.         m_shield = info.m_initial_shield;
  57.  
  58.         m_is_active = true;
  59.         m_is_on_screen = false;
  60.         m_is_hit = false;
  61.         }
  62.  
  63.     return true;
  64. }
  65.  
  66. //-------------------------------------------------------------
  67.  
  68. void CActor::kill()
  69. {
  70.     m_is_active = false;
  71. }
  72.  
  73. //-------------------------------------------------------------
  74.  
  75. void CActor::explode()
  76. {
  77.     if (m_image) {
  78.         gsCPoint size = m_image->getTileSize();
  79.  
  80.         int area = size.getX() * size.getY();
  81.  
  82.         CExplosion *x;
  83.  
  84.         if (area <= 32 * 32)
  85.             x = new CSmallExplosion;
  86.         else if (area <= 64 * 64)
  87.             x = new CMediumExplosion;
  88.         else
  89.             x = new CBigExplosion;
  90.  
  91.         m_scene->addActor(x);
  92.         x->setPosition(getPosition());
  93.         x->activate();
  94.         }
  95. }
  96.         
  97. //-------------------------------------------------------------
  98.  
  99. void CActor::registerHit(int energy,CActor *hitter)
  100. {
  101.     if (m_shield != INFINITE_SHIELD) {
  102.         if (m_shield > 0) {
  103.             m_shield -= energy;
  104.             if (m_shield <= 0) {
  105.                 m_shield = 0;
  106.                 onKilled();
  107.                 }
  108.             }
  109.  
  110.         m_is_hit = true;
  111.         m_hit_timer.start();
  112.         }
  113. }
  114.  
  115. //-------------------------------------------------------------
  116.  
  117. void CActor::onKilled()
  118. {
  119.     int bonus = getActorInfo().m_kill_bonus; 
  120.     
  121.     if (bonus > 0) {
  122.         int score = (int) (bonus * m_score_multiplier);
  123.  
  124.         CPlayGameState::getPlayer()->scoreBonus(score);
  125.         m_scene->createLabel(getPosition(),score);
  126.         }
  127. }
  128.  
  129. //-------------------------------------------------------------
  130.  
  131. bool CActor::draw()
  132. {
  133.     if (isActive() && m_image) {
  134.         m_sprite.setPosition(gsCPoint(m_position) + m_scene->getMap()->getPosition());
  135.  
  136.         if (m_is_hit) {
  137.             if (m_hit_timer.getTime() > ACTOR_HIT_TIME) {
  138.                 m_hit_timer.reset();
  139.                 m_is_hit = false;
  140.                 }
  141.             }
  142.  
  143.         if (m_is_hit) {
  144.             int level = (int) (255.f * (1.f - m_hit_timer.getTime() / ACTOR_HIT_TIME));
  145.             m_sprite.enableFillColour(gsCColour(level,level,level));
  146.             }
  147.         else
  148.             m_sprite.disableFillColour();
  149.  
  150.         bool was_on_screen = m_is_on_screen;
  151.  
  152.         m_is_on_screen = m_sprite.draw();
  153.  
  154.         if (was_on_screen && !m_is_on_screen)
  155.             onLeavingScreen();
  156.  
  157.         if (m_is_on_screen)
  158.             m_scene->addToCollisionList(this,getCollisionRect());
  159.         }
  160.  
  161.     return true;
  162. }
  163.  
  164. //-------------------------------------------------------------
  165. // animate over range of frames
  166.  
  167. bool CActor::animate(AnimationMode mode,int first_frame,int num_frames)
  168. {
  169.     bool finished = false;
  170.  
  171.     int frame;
  172.  
  173.     if (num_frames <= 1)
  174.         frame = 0;
  175.     else {
  176.         frame = (int) (m_timer.getTime() * getActorInfo().m_anim_rate);
  177.  
  178.         switch (mode) {
  179.             case ANIMATE_LOOP:
  180.                 frame = frame % (num_frames - 1);    // cycle repeatedly
  181.                 break;
  182.             case ANIMATE_ONESHOT:
  183.                 if (frame >= num_frames) {
  184.                     frame = num_frames - 1;            // stay on last frame
  185.                     finished = true;                // flag that we've finished
  186.                     }
  187.                 break;
  188.             }
  189.         }
  190.  
  191.     m_sprite.setFrame(first_frame + frame);
  192.  
  193.     return finished;
  194. }
  195.  
  196. //-------------------------------------------------------------
  197. // animate over entire range
  198.  
  199. bool CActor::animate(AnimationMode mode)
  200. {
  201.     return animate(mode,0,m_image->getNumTiles());
  202. }
  203.  
  204. //-------------------------------------------------------------
  205. // Convert velocity into a direction (0..num_dir-1)
  206.  
  207. int CActor::getDirection(int num_dir)
  208. {
  209.     if (m_velocity.length() == 0.f)
  210.         return 0;
  211.  
  212.     float angle = m_velocity.direction();
  213.  
  214.     float step = 360.f / (float) num_dir;
  215.     
  216.     return ((int) ((angle - step / 2.f + 360.f) / step)) & (num_dir - 1);
  217. }
  218.  
  219. //-------------------------------------------------------------
  220.