/[enigma]/enigma/src/world.cc
ViewVC logotype

Diff of /enigma/src/world.cc

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.2 by dheck, Mon Jan 6 12:30:34 2003 UTC revision 1.3 by dheck, Thu Jan 9 10:24:03 2003 UTC
# Line 146  namespace Line 146  namespace
146                  return V3();                  return V3();
147    
148              if (a->int_attrib("mouseforce"))              if (a->int_attrib("mouseforce"))
149                  return force*exp(-time*options::MouseDamping);                  return force; //*exp(-time*options::MouseDamping);
150              else              else
151                  return V3();                  return V3();
152          }          }
153    
154          void tick(double dtime) {          void tick(double dtime) {
155                
156              double damping=options::MouseDamping;              double damping=options::MouseDamping;
157              force *= exp(-dtime*damping);              force *= exp(-dtime*damping);
158    
159                force=V3();
160  //             if (length(force) < 0.01)  //             if (length(force) < 0.01)
161  //            force = V3();  //            force = V3();
162          }          }
# Line 235  namespace Line 237  namespace
237      ForceList forces;      ForceList forces;
238      MouseForce *mouseforce;      MouseForce *mouseforce;
239    
     FieldArray *fields;         // the grid of static objects  
240      ActorList actorlist;        // list of movable, dynamic objects      ActorList actorlist;        // list of movable, dynamic objects
 }  
241    
242  tools::Timer world::g_timer;      class Level {
243        public:
244            Level(int ww, int hh) : fields(ww,hh) {
245                w = ww;
246                h = hh;
247            }
248    
249            bool contains (GridPos p) {
250                return (p.x>=0 && p.y>=0 && p.x<w && p.y<h);
251            }
252    
253  static bool          Field *get_field (GridPos p) {
254  level_contains(GridPos p)              if (this->contains(p))
255  {                  return &fields(p.x,p.y);
256      return (p.x >= 0 && p.y >= 0 &&              else
257              p.x < int(fields->width()) && p.y < int(fields->height()));                  return 0;
258            }
259    
260    
261            // Variables.
262            FieldArray fields;         // Contains floors, items, etc.
263            int w, h;                  // Width and height of the level
264        };
265    
266        Level *level;
267  }  }
268    
269    tools::Timer world::g_timer;
270    
271    
272  //======================================================================  //======================================================================
273  // PHYSICS SIMULATION  // PHYSICS SIMULATION
# Line 447  maybe_join_contacts (StoneContact & a, S Line 466  maybe_join_contacts (StoneContact & a, S
466  }  }
467    
468  static void  static void
469  find_stone_contacts(Actor *a, StoneContactList &cl)  find_stone_contacts (Actor *a, StoneContactList &cl)
470  {  {
471      ActorInfo &ai = *a->get_actorinfo();      ActorInfo &ai = *a->get_actorinfo();
472      px::Rect r(int(ai.pos[0]-0.5), int(ai.pos[1]-0.5),      px::Rect r(int(ai.pos[0]-0.5), int(ai.pos[1]-0.5),
# Line 473  find_stone_contacts(Actor *a, StoneConta Line 492  find_stone_contacts(Actor *a, StoneConta
492                  cl.push_back(contacts[i][j]);                  cl.push_back(contacts[i][j]);
493  }  }
494    
495    
496    /*
497    This function is called for every contact between an actor and a
498    stone.  It is here that the stones are informed about that event.  Note
499    that a stone may kill itself during a call to actor_hit() or
500    actor_contact() so we must not refer to it after having called these
501    functions.  (Incidentally, this is why StoneContact only contains a
502    'stonepos' and no 'stone' entry.
503    */
504  static V3  static V3
505  handle_stone_contact(V3 normal, StoneContact &sc)  handle_stone_contact(V3 normal, StoneContact &sc)
506  {  {
# Line 480  handle_stone_contact(V3 normal, StoneCon Line 508  handle_stone_contact(V3 normal, StoneCon
508      ActorInfo *ai = a->get_actorinfo();      ActorInfo *ai = a->get_actorinfo();
509    
510      if (sc.is_collision) {      if (sc.is_collision) {
         // The stone may kill itself during a call to actor_hit(), so  
         // extract all relevant data before invoking this method!  
         // GridPos stone_pos = sc.stone->get_pos();  
511          if (Stone *stone = world::GetStone(sc.stonepos))          if (Stone *stone = world::GetStone(sc.stonepos))
512              stone->actor_hit(sc);              stone->actor_hit(sc);
513          if (!sc.fake_collision && sc.response != STONE_PASS) {          if (!sc.fake_collision && sc.response != STONE_PASS) {
514              normal += sc.normal;              normal += sc.normal;
515              normal /= length(normal);              normal /= length(normal);
516                            
517              if (length(ai->vel) > 0.1)              if (length(ai->vel) > 0.1) {
             {  
518                  AddSprite(display::SPRITE_EFFECT, sc.contact_point, "ring-anim");                  AddSprite(display::SPRITE_EFFECT, sc.contact_point, "ring-anim");
519                  sound::PlaySound(sc.sound.c_str()); //collision_sound.c_str());                  sound::PlaySound(sc.sound.c_str());
520              }              }
521          }          }
522      }      }
# Line 613  tick_actor(Actor *a, double dtime) Line 637  tick_actor(Actor *a, double dtime)
637  static void  static void
638  clear_world()  clear_world()
639  {  {
640      delete fields;      delete level;
641        level = 0;
642      delete mouseforce;      delete mouseforce;
     fields=0;  
643      mouseforce=0;      mouseforce=0;
644      px::delete_sequence(forces.begin(), forces.end());      px::delete_sequence(forces.begin(), forces.end());
645      forces.clear();      forces.clear();
# Line 628  void Line 652  void
652  world::Create(int w, int h)  world::Create(int w, int h)
653  {  {
654      clear_world();      clear_world();
655      fields = new FieldArray(w,h);      level = new Level(w,h);
656      mouseforce = new MouseForce;      mouseforce = new MouseForce;
657      display::NewWorld(w, h);      display::NewWorld(w, h);
658      player::NewWorld();      player::NewWorld();
# Line 715  world::RemoveForceField(ForceField *ff) Line 739  world::RemoveForceField(ForceField *ff)
739          forces.erase(i);          forces.erase(i);
740  }  }
741    
   
   
 namespace  
 {  
     Field &get_field(GridPos p) {  
         return fields->get(p.x, p.y);  
     }  
 }  
   
   
742  //----------------------------------------  //----------------------------------------
743  // Layer  // Layer
744  //  //
# Line 737  class Layer { Line 751  class Layer {
751  public:  public:
752      Layer(T* deflt = 0) : defaultval(deflt) {}      Layer(T* deflt = 0) : defaultval(deflt) {}
753      T *get(GridPos p) {      T *get(GridPos p) {
754          return (level_contains(p)) ? raw_get(p) : defaultval;          if (Field *f=level->get_field(p))
755                return raw_get(*f);
756            else
757                return defaultval;
758      }      }
759    
760      T *yield(GridPos p) {      T *yield(GridPos p) {
761          if (level_contains(p)) {          if (Field *f=level->get_field(p)) {
762              T *x = raw_get(p);              T *x = raw_get(*f);
763              if (x) {              if (x) {
764                  raw_set(p, 0);                  raw_set(*f, 0);
765                  x->removal();                  x->removal();
766              }              }
767              return x;              return x;
# Line 753  public: Line 770  public:
770      }      }
771    
772      void set(GridPos p, T *x) {      void set(GridPos p, T *x) {
773          if (x && level_contains(p)) {          if (x) {
774              dispose(raw_get(p));              if (Field *f=level->get_field(p)) {
775              raw_set(p, x);                  dispose(raw_get(*f));
776              x->creation(p);                  raw_set(*f, x);
777                    x->creation(p);
778                }
779                else
780                    dispose(x);
781          }          }
         else  
             dispose(x);  
782      }      }
783      void kill(GridPos p) { dispose(yield(p)); }      void kill(GridPos p) { dispose(yield(p)); }
784    
785      virtual T* raw_get(GridPos) = 0;      virtual T* raw_get (Field &) = 0;
786      virtual void raw_set(GridPos, T *) = 0;      virtual void raw_set (Field &, T *) = 0;
787    
788  private:  private:
789      void dispose(T *x) { DisposeObject(x); }      void dispose(T *x) { if (x) DisposeObject(x); }
790  };  };
791    
792  //----------------------------------------  //----------------------------------------
# Line 778  namespace Line 797  namespace
797  {  {
798      class FloorLayer : public Layer<Floor> {      class FloorLayer : public Layer<Floor> {
799      private:      private:
800          Floor *raw_get(GridPos p) { return get_field(p).floor; }          Floor *raw_get (Field &f) { return f.floor; }
801          void raw_set(GridPos p, Floor *x) {get_field(p).floor = x;}          void raw_set (Field &f, Floor *x) { f.floor = x;}
802      };      };
803      FloorLayer fl_layer;      FloorLayer fl_layer;
804  }  }
# Line 811  namespace Line 830  namespace
830      public:      public:
831          StoneLayer() : Layer<Stone>(&borderstone) {}          StoneLayer() : Layer<Stone>(&borderstone) {}
832      private:      private:
833          Stone *raw_get(GridPos p) { return get_field(p).stone; }          Stone *raw_get (Field &f) { return f.stone; }
834          void raw_set(GridPos p, Stone *st) {get_field(p).stone = st;}          void raw_set (Field &f, Stone *st) { f.stone = st;}
835      };      };
836    
837      StoneLayer st_layer;      StoneLayer st_layer;
# Line 893  namespace Line 912  namespace
912  {  {
913      class ItemLayer : public Layer<Item> {      class ItemLayer : public Layer<Item> {
914      private:      private:
915          Item *raw_get(GridPos p) { return get_field(p).item; }          Item *raw_get (Field &f) { return f.item; }
916          void raw_set(GridPos p, Item *x) {get_field(p).item = x;}          void raw_set (Field &f, Item *x) { f.item = x;}
917      };      };
918      ItemLayer it_layer;      ItemLayer it_layer;
919  }  }
920    
921  void world::KillItem(GridPos p) {it_layer.kill(p);}  void world::KillItem(GridPos p) {it_layer.kill(p);}
922  Item *world::GetItem(GridPos p) {return it_layer.get(p);}  Item *world::GetItem(GridPos p) {return it_layer.get(p);}
923  Item *world::YieldItem(GridPos p) {return it_layer.yield(p);}  Item *world::YieldItem(GridPos p) {
924        laser::MaybeRecalcLight(p);
925        return it_layer.yield(p);
926    }
927  void world::SetItem(GridPos p, Item* st) {it_layer.set(p,st);}  void world::SetItem(GridPos p, Item* st) {it_layer.set(p,st);}
928    
929  //----------------------------------------  //----------------------------------------

Legend:
Removed from v.1.2  
changed lines
  Added in v.1.3

savannah-hackers-public@gnu.org
ViewVC Help
Powered by ViewVC 1.1.26