static void UpdateCamera(fplbase::InputSystem* input, Camera* camera) { const fplbase::InputPointer& pointer = input->get_pointers()[0]; if (!pointer.used) return; // Update latitude and longitude: left mouse drag. if (input->GetButton(fplbase::K_POINTER1).is_down() && pointer.mousedelta != mathfu::kZeros2i) { const float lat = camera->latitude.ToRadians() + pointer.mousedelta.y * kLatitudeSensitivity; camera->latitude = Angle(mathfu::Clamp(lat, -kMaxLatitude, kMaxLatitude)); camera->longitude += Angle(pointer.mousedelta.x * kLongitudeSensitivity); } // Update distance: right mouse drag. // (Unfortunately, InputSystem doesn't support scroll wheels yet) if (input->GetButton(fplbase::K_POINTER3).is_down() && pointer.mousedelta != mathfu::kZeros2i) { const float dist = camera->distance + (pointer.mousedelta.x + pointer.mousedelta.y) * kDistanceSensitivity; camera->distance = std::max(dist, camera->z_near); } // Update target: middle mouse drag. if (input->GetButton(fplbase::K_POINTER2).is_down() && pointer.mousedelta != mathfu::kZeros2i) { const vec3 right = CameraRight(*camera); const vec3 up = VectorSystemUp(camera->coordinate_system); const vec2 dist = kTargetSensitivity * vec2(pointer.mousedelta); camera->target += dist[0] * right + dist[1] * up; } }
int main() { //! [Own Processor Register] LinearInit::Register(); //! [Own Processor Register] MotiveEngine engine; //! [Own Processor Create Instance] // Move from 10 --> -5 in 100 internal time units. const MotiveTarget1f target = motive::CurrentToTarget1f(10, 0, -5, 0, 100); // Create the one dimensional motivator of type Linear by passing in // LinearInit. Motivator1f linear_motivator(LinearInit(), &engine, target); //! [Own Processor Create Instance] //! [Own Processor Advance Simulation] // Advance the simulation one tick at a time by calling engine.AdvanceFrame(). std::vector<vec2> points; points.reserve(target.EndTime() + 1); for (MotiveTime t = 0; t <= target.EndTime(); ++t) { points.push_back(vec2(static_cast<float>(t), linear_motivator.Value())); engine.AdvanceFrame(1); } printf("\n%s", motive::Graph2DPoints(&points[0], static_cast<int>(points.size())) .c_str()); //! [Own Processor Advance Simulation] return 0; }
int main() { // Since we use the ‘smooth’ animation algorithm, we must register it. motive::SmoothInit::Register(); // The engine is the central place for animation data. motive::MotiveEngine engine; // In this example, we animate a one-dimensional floating point value. motive::Motivator1f facing_angle; // Initialize facing_angle Motivator to animate as a 'Smooth' Motivator. // Alternatively, we could initialize as an 'Overshoot' Motivator. All // Motivator types have the same interface. Internally, they are animated // with different algorithms, and they will move differently towards their // targets. However, to switch between Motivator types it is a simple matter // of initializing with a different kind of MotiveInit struct. // // Angles wrap around with modular arithmetic. That is, -pi is equivalent to // pi. Valid range for angles is -pi..pi, inclusive of +pi and exclusive of // -pi. const motive::SmoothInit init(Range(-kPi, kPi), true); facing_angle.Initialize(init, &engine); // Set initial state of the Motivator, and the target parameters. // 'Smooth' Motivators animate to a target-value in a target-time. Not all // types of Motivators use all target data. const Angle start = Angle::FromDegrees(120.0f); const float start_angular_velocity = 0.0f; const Angle target = Angle::FromDegrees(-120.0f); const float target_angular_velocity = 0.0f; const motive::MotiveTime target_time = 100; const motive::MotiveTime delta_time = 1; facing_angle.SetTarget( motive::CurrentToTarget1f(start.ToRadians(), start_angular_velocity, target.ToRadians(), target_angular_velocity, target_time)); std::vector<vec2> points(target_time / delta_time + 1); for (motive::MotiveTime t = 0; t <= target_time; t += delta_time) { // All Motivators created with 'engine' are animated here. engine.AdvanceFrame(delta_time); // The current value of the variable being animated is always available. const Angle angle_at_t = Angle::FromWithinThreePi(facing_angle.Value()); points.push_back( vec2(static_cast<float>(t), angle_at_t.ToDegrees())); } printf("\n%s", Graph2DPoints(&points[0], points.size()).c_str()); return 0; }
int main() { // Since we will be using the ‘smooth’ animation algorithm, we must register it // with the engine. motive::SmoothInit::Register(); // The engine is the central place where animation data is stored and processed. motive::MotiveEngine engine; // In this example, we animate a one-dimensional floating point value. // It's also possible to animate a mathfu::vec2 with motive::Motivator2f, and // similarly for higher dimensional vectors. We can even animate a mathfu::mat4 // (a 4x4 matrix) with motive::MotivatorMatrix4f. // // If you have your own math library, you can also animate those instead of // mathfu types. See [Using Your Own Math Types][]. motive::Motivator1f facing_angle; // Initialize facing_angle Motivator to animate as a 'Smooth' Motivator. // Alternatively, we could initialize as an 'Overshoot' Motivator. All // Motivator types have the same interface. Internally, they are animated // with different algorithms, and they will move differently towards their // targets. However, to switch between Motivator types it is a simple matter // of initializing with a different kind of MotiveInit struct. // // Angles wrap around with modular arithmetic. That is, -pi is equivalent to // pi. Valid range for angles is -pi..pi, inclusive of +pi and exclusive of // -pi. const motive::SmoothInit init(Range(-kPi, kPi), true); facing_angle.Initialize(init, &engine); // Set initial state of the Motivator, and the target parameters. // 'Smooth' Motivators animate to a target-value in a target-time. Not all // types of Motivators use all target data. const Angle start = Angle::FromDegrees(120.0f); const float start_angular_velocity = 0.0f; const Angle target = Angle::FromDegrees(-120.0f); const float target_angular_velocity = 0.0f; const motive::MotiveTime target_time = 100; const motive::MotiveTime delta_time = 1; facing_angle.SetTarget( motive::CurrentToTarget1f(start.ToRadians(), start_angular_velocity, target.ToRadians(), target_angular_velocity, target_time)); std::vector<vec2> points(target_time / delta_time + 1); for (motive::MotiveTime t = 0; t <= target_time; t += delta_time) { // That is, all Motivators created with 'engine' are animated here. engine.AdvanceFrame(delta_time); // The current value of the variable being animated is always available. // Additionally, we can also access facing_angle.Velocity() for the angular // velocity. const Angle facing_angle_at_time_t(facing_angle.Value()); points.push_back( vec2(static_cast<float>(t), facing_angle_at_time_t.ToDegrees())); } printf("\n%s", Graph2DPoints(&points[0], points.size()).c_str()); return 0; }