//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Biquad::ConjugateRootToQuadCoeffs() // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ void Biquad::ConjugateRootToQuadCoeffs( float inTheta, float inMag, float &out0, float &out1, float &out2 ) { float x; float y; PolarToRect(inTheta, inMag, x, y ); out0 = 1.0; out1 = -2.0 * x; out2 = x*x + y*y; }
bool Aircraft::Step(float FT, sf::Vector2f Wind) { bool Die = false; Time += FT; const sf::Vector2f &Me = Shape.getPosition(); TakeoffSound.setPosition(Me.x, Me.y, 0.f); FlySound.setPosition(Me.x, Me.y, 0.f); LandingSound.setPosition(Me.x, Me.y, 0.f); Shape.update(FT); float Turning = 0.f; switch (State) { case FlyingIn: { sf::Vector2f To(400.f, 300.f); Shape.setRotation(Angle(Me - To)); if (P.NumPoints() > 0) { State = FlyingPath; } else if (Me.x > 100 && Me.x < 700 && Me.y > 100 && Me.y < 500) { State = FlyingFree; Turning = 0.2f; } break; } case FlyingOut: { sf::Vector2f From(400.f, 300.f); Shape.rotate(AngleDiff(Shape.getRotation(), Angle(From - Me)) * FT); float Scale = Map(Speed / Template.Speed, 0.f, 1.f, 1.f, 0.9f); float ShadowRadius = Radius * Scale; sf::Vector2f Shadow = sf::Transform().scale(sf::Vector2f(Scale, Scale), sf::Vector2f(800 / 2, 600 * 0.8f)).transformPoint(Me); if ((Me.x < -Radius || Me.x > (800 + Radius) || Me.y < -Radius || Me.y > (600 + Radius)) && (Shadow.x < -ShadowRadius || Shadow.x > (800 + ShadowRadius) || Shadow.y < -ShadowRadius || Shadow.y > (600 + ShadowRadius))) { Die = true; } break; } case FlyingFree: { float Angle = AngleFix(Shape.getRotation()), AddAngle; if ((Me.x < 100 && Angle > 180) || (Me.x > 700 && Angle < 180) || (Me.y < 100 && (Angle > 90 && Angle < 270)) || (Me.y > 500 && (Angle > 270 || Angle < 90))) { AddAngle = Turn; Turning = Turn / 10; } else if ((Me.x < 100 && Angle <= 180) || (Me.x > 700 && Angle >= 180) || (Me.y < 100 && (Angle <= 90 || Angle >= 270)) || (Me.y > 500 && (Angle <= 270 && Angle >= 90))) { AddAngle = -Turn; Turning = -Turn / 10; } else { AddAngle = Turning; } Angle += AddAngle; Shape.setRotation(AngleFix(Angle)); if (P.NumPoints() > 0) { State = FlyingPath; } break; } case FlyingPath: { if (P.NumPoints() > 0) { const sf::Vector2f To = P[0]; // might crash if (InRange(Me, To, 5)) P.RemovePoint(0); float Target = Angle(Me - To); Shape.setRotation(Target); if (Land && P.NumPoints() == 0 && /*Land->OnMe(Me) &&*/ P.Highlight /*abs(AngleDiff(GetAngle(), Land->GetAngle())) <= Land->GetTemplate().LandAngle*/) { FlySound.stop(); LandingSound.play(); State = Landing; LandPoint = Me; } else if (P.NumPoints() == 0) { if (Direction == Out && ((OutDirection == OutUp && To.y < 50) || (OutDirection == OutDown && To.y > 550) || (OutDirection == OutLeft && To.x < 50) || (OutDirection == OutRight && To.x > 750))) { State = FlyingOut; } else { State = FlyingFree; } } } break; } case Landing: { sf::Vector2f Runway = Land->GetPos() + PolarToRect(sf::Vector2f(Land->GetLength() * 1.5f, Land->GetAngle())); float Dist = Distance(Me, LandPoint); Speed = Map(Dist, 0.f, Land->GetLength() * 1.1f, Template.Speed, 0.f); if (Land->GetTemplate().Directional) { Shape.rotate(AngleDiff(Shape.getRotation(), Angle(Me - Runway)) * 3 * FT); } float Scale = Map2(Dist, 0.f, Land->GetLength() * 1.1f, 1.f, 0.65f); Shape.setScale(Scale, Scale); Radius = Template.Radius * Scale; if (Dist > Land->GetLength()) { Die = true; } break; } case TakingOff: { sf::Vector2f Runway = Land->GetPos() + PolarToRect(sf::Vector2f(Land->GetLength() * 1.5f, Land->GetAngle())); float Dist = Distance(Me, Land->GetPos()); Speed = Map(Dist, 0.f, Land->GetLength() * 1.1f, 10.f, Template.Speed); if (Land->GetTemplate().Directional) { Shape.rotate(AngleDiff(Shape.getRotation(), Angle(Me - Runway)) * 3 * FT); } float Scale = Map2(Dist, 0.f, Land->GetLength() * 1.1f, 0.65f, 1.f); Shape.setScale(Scale, Scale); Radius = Template.Radius * Scale; if (Dist > Land->GetLength()) { FlySound.play(); State = FlyingFree; Land = 0; } break; } } Shape.move(PolarToRect(sf::Vector2f(Speed, Shape.getRotation())) * FT); Shape.move(Wind * FT * Magnitude(Shape.getScale()) / sqrt(2.f)); return Die; }
sf::Texture PerlinNoise() { const int Size2 = 800; const float Persistence = 0.5f; vector< vector<float> > F(Size2, vector<float>(Size2, 0.f)); for (int i = 4; i <= 7; i++) { int Freq = pow(2, i); float Amplitude = pow(Persistence, log(Size2) / log(2) - i); int Size = Size2 / Freq; vector< vector<sf::Vector2f> > G(Size + 1, vector<sf::Vector2f>(Size + 1)); for (int y = 0; y < Size + 1; y++) { for (int x = 0; x < Size + 1; x++) G[y][x] = PolarToRect(sf::Vector2f(1.f, Random(0.f, 360.f))); } for (int y = 0; y < Size2; y++) { for (int x = 0; x < Size2; x++) { sf::Vector2f p(x, y); p *= float(Size) / Size2; sf::Vector2i p0(p); sf::Vector2i p1 = p0 + sf::Vector2i(1, 1); sf::Vector2f pp0 = p - sf::Vector2f(p0); sf::Vector2f pp1 = p - sf::Vector2f(p1); float s = DotProduct(G[p0.y][p0.x], pp0); float t = DotProduct(G[p0.y][p1.x], sf::Vector2f(pp1.x, pp0.y)); float u = DotProduct(G[p1.y][p0.x], sf::Vector2f(pp0.x, pp1.y)); float v = DotProduct(G[p1.y][p1.x], pp1); sf::Vector2f S; S.x = 3 * pow(pp0.x, 2) - 2 * pow(pp0.x, 3); float a = s + S.x * (t - s); float b = u + S.x * (v - u); S.y = 3 * pow(pp0.y, 2) - 2 * pow(pp0.y, 3); float z = a + S.y * (b - a); F[y][x] += z * Amplitude; } } } float min, max; for (int y = 0; y < Size2; y++) { for (int x = 0; x < Size2; x++) { if (y == 0 && x == 0) min = max = F[y][x]; else { if (F[y][x] < min) min = F[y][x]; if (F[y][x] > max) max = F[y][x]; } } } sf::Image Img; Img.create(Size2, Size2, sf::Color::Red); for (int y = 0; y < Size2; y++) { for (int x = 0; x < Size2; x++) { int val = Map(F[y][x], min, max, 165, 255); Img.setPixel(x, y, sf::Color(val, val, val)); } } sf::Texture Tex; Tex.loadFromImage(Img); return Tex; }