Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/FICN/src/orxonox/Flocking.h @ 653

Last change on this file since 653 was 618, checked in by nicolasc, 17 years ago
  • changed comments to doxygen tags in flocking
  • reduced ogre depency in HUD and ParticleInterface
  • various
File size: 6.4 KB
RevLine 
[342]1
[596]2//Headerfile: Flocking.h
[342]3
4#ifndef Flocking_Class
5#define Flocking_Class
6
[618]7// #include <Ogre.h>
[342]8#include <OgreVector3.h>
9
[596]10
[342]11#include <iostream>
12
13
14#endif
15
16
17class Element // An element that flocks
18{
19
20  public:
[618]21    Ogre::Vector3 location;                       //!< locationvector of the element
22    Ogre::Vector3 speed;                          //!< speedvector of the element
23    Ogre::Vector3 acceleration;                   //!< accelerationvector of the element
24    bool movable;                                 //!< movability of the element, (false) gives the possiblity that an object can`t be moved by flocking but still gets into the calculation
25    static int const SEPERATIONDISTANCE = 300;    //!< detectionradius of seperation
26    static int const ALIGNMENTDISTANCE = 300;     //!< detectionradius of alignment
27    static int const COHESIONDISTANCE = 5000;     //!< detectionradius of cohesion
28    static int const ANZELEMENTS = 9;             //!< number of elements
[342]29
[618]30  //! default constructor
[342]31  Element() {
[618]32    acceleration = Ogre::Vector3(0,0,0);
33    speed = Ogre::Vector3(0,0,0);
34    location = Ogre::Vector3(0,0,0);
[596]35    movable = true;
[342]36  }
37
[618]38  /** constructor
39   *  @param location_ sets locationvector of the element
40   *  @param speed_ sets speedvector of the element
41   *  @param acceleration_ sets accelerationvector of the element
42   *  @param movable_ sets movability of the element
43   */
[609]44  Element(Ogre::Vector3 location_, Ogre::Vector3 speed_, Ogre::Vector3 acceleration_, bool movable_) {
[342]45    acceleration = acceleration_;
46    speed = speed_;
47    location = location_;
[596]48    movable = movable_;
[342]49  }
50
[618]51  //! function to chance values of an element
[609]52  void setValues(Ogre::Vector3 location_, Ogre::Vector3 speed_, Ogre::Vector3 acceleration_, bool movable_) {
[342]53    acceleration = acceleration_;
54    speed = speed_;
55    location = location_;
[596]56    movable = movable_;
[342]57  }
58
[618]59  /** calculates the distance between the element and an other point given by temp
60   * @param e remote object to calculate distance to
61   */
62  float getDistance(Element e) {
63    Ogre::Vector3 distance = e.location - location;
[342]64    return distance.length();
65  }
66
[618]67  //! updates the data of an element
[596]68  void update(Element arrayOfElements[]) {
69    if (this->movable == true) {calculateAcceleration(arrayOfElements);} //if element is movable, calculate acceleration
[342]70  }
71
[618]72  //! calculates the new acceleration of an element
[342]73  void calculateAcceleration(Element arrayOfElements[]) {
[596]74    acceleration = separation(arrayOfElements) + alignment(arrayOfElements) + cohesion(arrayOfElements);  //acceleration consisting of flocking-functions
[342]75  }
76
[618]77  //! separation-function (keep elements separated, avoid crashs)
[609]78  Ogre::Vector3 separation(Element arrayOfElements[]) {
79    using namespace Ogre;
[596]80    Vector3 steering = Vector3(0,0,0); //steeringvector
81    Vector3 inverseDistance = Vector3(0,0,0);  //vector pointing away from possible collisions
[342]82    int numberOfNeighbour = 0;  //number of observed neighbours
[596]83    float distance = 0;  // distance to the actual element
84    for(int i=0; i<ANZELEMENTS; i++) {  //go through all elements
[342]85      Element actual = arrayOfElements[i];  //get the actual element
[596]86      distance = getDistance(actual);  //get distance between this and actual
87      if ((distance > 0) && (distance < SEPERATIONDISTANCE)) {  //do only if actual is inside detectionradius
88        inverseDistance = (0,0,0);
89        inverseDistance = location-actual.location;  //calculate the distancevector heading towards this
90        //adaptation of the inverseDistance to the distance
91        if ((distance < 200) && (distance >= 120)) {inverseDistance = 2*inverseDistance;}
92        if ((distance < 120) && (distance >= 80)) {inverseDistance = 5*inverseDistance;}
93        if ((distance < 80) && (distance >= 40)) {inverseDistance = 10*inverseDistance;}
94        if ((distance < 40) && (distance > 0)) {inverseDistance = 10*inverseDistance;}
95        steering = steering + inverseDistance;  //add up all significant steeringvectors
[342]96        numberOfNeighbour++;  //counts the elements inside the detectionradius
97      }
98    }
[596]99    if(numberOfNeighbour > 0) { steering = steering / (float)numberOfNeighbour; }  //devide the sum of steeringvectors by the number of elements -> separation steeringvector
100    return steering;
[342]101  }
102
[618]103  //! alignment-function (lead elements to the same heading)
[609]104  Ogre::Vector3 alignment(Element arrayOfElements[]) {
105    using namespace Ogre;
[596]106    Vector3 steering = Vector3(0,0,0); //steeringvector
[342]107    int numberOfNeighbour = 0;  //number of observed neighbours
[596]108    float distance = 0;
[342]109    //go through all elements
[596]110    for(int i=0; i<ANZELEMENTS; i++) {  //just working with 3 elements at the moment
[342]111      Element actual = arrayOfElements[i];  //get the actual element
112      float distance = getDistance(actual);  //get distance between this and actual
[596]113      if ((distance > 0) && (distance < ALIGNMENTDISTANCE)) {  //check if actual element is inside detectionradius
114        steering = steering + actual.speed;  //add up all speedvectors inside the detectionradius
[342]115        numberOfNeighbour++;  //counts the elements inside the detectionradius
116      }
117    }
[596]118    if(numberOfNeighbour > 0) { steering = steering / (float)numberOfNeighbour; }  //devide the sum of steeringvectors by the number of elements -> alignment steeringvector
119    return steering;
[342]120  }
121
[618]122  //! cohseion-function (keep elements close to each other)
[609]123  Ogre::Vector3 cohesion(Element arrayOfElements[]) {
124    using namespace Ogre;
[596]125    Vector3 steering = Vector3(0,0,0); //steeringvector
[342]126    int numberOfNeighbour = 0;  //number of observed neighbours
[596]127    float distance = 0;
[342]128    //go through all elements
[596]129    for(int i=0; i<ANZELEMENTS; i++) {  //just working with 3 elements at the moment
[342]130      Element actual = arrayOfElements[i];  //get the actual element
131      float distance = getDistance(actual);  //get distance between this and actual
[596]132      if ((distance > 0) && (distance < COHESIONDISTANCE)) {  //check if actual element is inside detectionradius
133        steering = steering + actual.location;  //add up all locations of elements inside the detectionradius
[342]134        numberOfNeighbour++;  //counts the elements inside the detectionradius
135      }
[596]136    }
[342]137    if(numberOfNeighbour > 0) {
[596]138      steering = steering  / (float)numberOfNeighbour;  //devide the sum steeringvector by the number of elements -> cohesion steeringvector
139      steering = steering - this->location;  //transform the vector for the ship
[342]140    }
[596]141    return steering;
[342]142  }
[596]143};     //End of class Element
Note: See TracBrowser for help on using the repository browser.