]> git.mxchange.org Git - flightgear.git/blobdiff - src/FDM/YASim/Wing.cpp
First cut at a turbulence model for YASim. It's a
[flightgear.git] / src / FDM / YASim / Wing.cpp
index 858e3b4cd66931f923633af9a0c1e3a0990125eb..368cb4ec915fefd9cbec41d550dc3c011909f956 100644 (file)
@@ -15,8 +15,10 @@ Wing::Wing()
     _stall = 0;
     _stallWidth = 0;
     _stallPeak = 0;
+    _twist = 0;
     _camber = 0;
     _incidence = 0;
+    _inducedDrag = 1;
     _dragScale = 1;
     _liftRatio = 1;
     _flap0Start = 0;
@@ -39,7 +41,8 @@ Wing::Wing()
 
 Wing::~Wing()
 {
-    for(int i=0; i<_surfs.size(); i++) {
+    int i;
+    for(i=0; i<_surfs.size(); i++) {
         SurfRec* s = (SurfRec*)_surfs.get(i);
         delete s->surface;
         delete s;
@@ -68,7 +71,8 @@ void Wing::setMirror(bool mirror)
 
 void Wing::setBase(float* base)
 {
-    for(int i=0; i<3; i++) _base[i] = base[i];
+    int i;
+    for(i=0; i<3; i++) _base[i] = base[i];
 }
 
 void Wing::setLength(float length)
@@ -111,6 +115,11 @@ void Wing::setStallPeak(float fraction)
     _stallPeak = fraction;
 }
 
+void Wing::setTwist(float angle)
+{
+    _twist = angle;
+}
+
 void Wing::setCamber(float camber)
 {
     _camber = camber;
@@ -119,7 +128,8 @@ void Wing::setCamber(float camber)
 void Wing::setIncidence(float incidence)
 {
     _incidence = incidence;
-    for(int i=0; i<_surfs.size(); i++)
+    int i;
+    for(i=0; i<_surfs.size(); i++)
         ((SurfRec*)_surfs.get(i))->surface->setIncidence(incidence);
 }
 
@@ -159,7 +169,8 @@ void Wing::setFlap0(float lval, float rval)
 {
     lval = Math::clamp(lval, -1, 1);
     rval = Math::clamp(rval, -1, 1);
-    for(int i=0; i<_flap0Surfs.size(); i++) {
+    int i;
+    for(i=0; i<_flap0Surfs.size(); i++) {
        ((Surface*)_flap0Surfs.get(i))->setFlap(lval);
        if(_mirror) ((Surface*)_flap0Surfs.get(++i))->setFlap(rval);
     }
@@ -169,7 +180,8 @@ void Wing::setFlap1(float lval, float rval)
 {
     lval = Math::clamp(lval, -1, 1);
     rval = Math::clamp(rval, -1, 1);
-    for(int i=0; i<_flap1Surfs.size(); i++) {
+    int i;
+    for(i=0; i<_flap1Surfs.size(); i++) {
        ((Surface*)_flap1Surfs.get(i))->setFlap(lval);
        if(_mirror) ((Surface*)_flap1Surfs.get(++i))->setFlap(rval);
     }
@@ -179,7 +191,8 @@ void Wing::setSpoiler(float lval, float rval)
 {
     lval = Math::clamp(lval, 0, 1);
     rval = Math::clamp(rval, 0, 1);
-    for(int i=0; i<_spoilerSurfs.size(); i++) {
+    int i;
+    for(i=0; i<_spoilerSurfs.size(); i++) {
        ((Surface*)_spoilerSurfs.get(i))->setSpoiler(lval);
        if(_mirror) ((Surface*)_spoilerSurfs.get(++i))->setSpoiler(rval);
     }
@@ -188,18 +201,35 @@ void Wing::setSpoiler(float lval, float rval)
 void Wing::setSlat(float val)
 {
     val = Math::clamp(val, 0, 1);
-    for(int i=0; i<_slatSurfs.size(); i++)
+    int i;
+    for(i=0; i<_slatSurfs.size(); i++)
        ((Surface*)_slatSurfs.get(i))->setSlat(val);
 }
 
 float Wing::getGroundEffect(float* posOut)
 {
-    for(int i=0; i<3; i++) posOut[i] = _base[i];
+    int i;
+    for(i=0; i<3; i++) posOut[i] = _base[i];
     float span = _length * Math::cos(_sweep) * Math::cos(_dihedral);
     span = 2*(span + Math::abs(_base[2]));
     return span;
 }
 
+void Wing::getTip(float* tip)
+{
+    tip[0] = -Math::tan(_sweep);
+    tip[1] = Math::cos(_dihedral);
+    tip[2] = Math::sin(_dihedral);
+    Math::unit3(tip, tip);
+    Math::mul3(_length, tip, tip);
+    Math::add3(_base, tip, tip);
+}
+
+bool Wing::isMirrored()
+{
+    return _mirror;
+}
+
 void Wing::compile()
 {
     // Have we already been compiled?
@@ -215,10 +245,12 @@ void Wing::compile()
     bounds[6] = _slatStart;    bounds[7] = _slatEnd;
 
     // Sort in increasing order
-    for(int i=0; i<8; i++) {
+    int i;
+    for(i=0; i<8; i++) {
         int minIdx = i;
        float minVal = bounds[i];
-        for(int j=i+1; j<8; j++) {
+        int j;
+        for(j=i+1; j<8; j++) {
             if(bounds[j] < minVal) {
                 minIdx = j;
                minVal = bounds[j];
@@ -231,7 +263,7 @@ void Wing::compile()
     // Uniqify
     float last = bounds[0];
     int nbounds = 1;
-    for(int i=1; i<8; i++) {
+    for(i=1; i<8; i++) {
         if(bounds[i] != last)
             bounds[nbounds++] = bounds[i];
         last = bounds[i];
@@ -239,7 +271,7 @@ void Wing::compile()
 
     // Calculate a "nominal" segment length equal to an average chord,
     // normalized to lie within 0-1 over the length of the wing.
-    float segLen = _chord * (0.5*(_taper+1)) / _length;
+    float segLen = _chord * (0.5f*(_taper+1)) / _length;
 
     // Generating a unit vector pointing out the left wing.
     float left[3];
@@ -270,19 +302,20 @@ void Wing::compile()
 
     if(_mirror) {
        // Derive the right side orientation matrix from this one.
-        for(int i=0; i<9; i++)  rightOrient[i] = orient[i];
+        int i;
+        for(i=0; i<9; i++)  rightOrient[i] = orient[i];
 
        // Negate all Y coordinates, this gets us a valid basis, but
        // it's left handed!  So...
-        for(int i=1; i<9; i+=3) rightOrient[i] = -rightOrient[i];
+        for(i=1; i<9; i+=3) rightOrient[i] = -rightOrient[i];
 
        // Change the direction of the Y axis to get back to a
        // right-handed system.
-       for(int i=3; i<6; i++)  rightOrient[i] = -rightOrient[i];
+       for(i=3; i<6; i++)  rightOrient[i] = -rightOrient[i];
     }
 
     // Now go through each boundary and make segments
-    for(int i=0; i<(nbounds-1); i++) {
+    for(i=0; i<(nbounds-1); i++) {
         float start = bounds[i];
         float end = bounds[i+1];
         float mid = (start+end)/2;
@@ -297,10 +330,13 @@ void Wing::compile()
         // and flap1 are set.  Right now flap1 overrides.
 
         int nSegs = (int)Math::ceil((end-start)/segLen);
+        if (_twist != 0 && nSegs < 8) // more segments if twisted
+            nSegs = 8;
         float segWid = _length * (end - start)/nSegs;
 
-        for(int j=0; j<nSegs; j++) {
-            float frac = start + (j+0.5) * (end-start)/nSegs;
+        int j;
+        for(j=0; j<nSegs; j++) {
+            float frac = start + (j+0.5f) * (end-start)/nSegs;
             float pos[3];
             interp(root, tip, frac, pos);
 
@@ -313,6 +349,7 @@ void Wing::compile()
             sr->surface = s;
             sr->weight = chord * segWid;
             s->setTotalDrag(sr->weight);
+            s->setTwist(_twist * frac);
             _surfs.add(sr);
 
             if(_mirror) {
@@ -323,10 +360,15 @@ void Wing::compile()
                 sr->surface = s;
                 sr->weight = chord * segWid;
                 s->setTotalDrag(sr->weight);
+                s->setTwist(_twist * Math::sqrt(frac));
                 _surfs.add(sr);
             }
         }
     }
+
+    // Last of all, re-set the incidence in case setIncidence() was
+    // called before we were compiled.
+    setIncidence(_incidence);
 }
 
 float Wing::getDragScale()
@@ -337,7 +379,8 @@ float Wing::getDragScale()
 void Wing::setDragScale(float scale)
 {
     _dragScale = scale;
-    for(int i=0; i<_surfs.size(); i++) {
+    int i;
+    for(i=0; i<_surfs.size(); i++) {
         SurfRec* s = (SurfRec*)_surfs.get(i);
         s->surface->setTotalDrag(scale * s->weight);
     }
@@ -346,7 +389,8 @@ void Wing::setDragScale(float scale)
 void Wing::setLiftRatio(float ratio)
 {
     _liftRatio = ratio;
-    for(int i=0; i<_surfs.size(); i++)
+    int i;
+    for(i=0; i<_surfs.size(); i++)
         ((SurfRec*)_surfs.get(i))->surface->setZDrag(ratio);
 }
 
@@ -376,8 +420,8 @@ Surface* Wing::newSurface(float* pos, float* orient, float chord,
     // The negative AoA stall is the same if we're using an uncambered
     // airfoil, otherwise a "little badder".
     if(_camber > 0) {
-        s->setStall(1, stallAoA * 0.8);
-        s->setStallWidth(1, _stallWidth * 0.5);
+        s->setStall(1, stallAoA * 0.8f);
+        s->setStallWidth(1, _stallWidth * 0.5f);
     } else {
         s->setStall(1, stallAoA);
         s->setStall(1, _stallWidth);
@@ -386,8 +430,9 @@ Surface* Wing::newSurface(float* pos, float* orient, float chord,
     // The "reverse" stalls are unmeasurable junk.  Just use 13deg and
     // "sharp".
     s->setStallPeak(1, 1);
-    for(int i=2; i<4; i++) {
-        s->setStall(i, 0.2267);
+    int i;
+    for(i=2; i<4; i++) {
+        s->setStall(i, 0.2267f);
         s->setStallWidth(i, 1);
     }
     
@@ -401,6 +446,8 @@ Surface* Wing::newSurface(float* pos, float* orient, float chord,
     if(slat)    _slatSurfs.add(s);
     if(spoiler) _spoilerSurfs.add(s);
 
+    s->setInducedDrag(_inducedDrag);
+
     return s;
 }