154 lines
5.7 KiB
C++
154 lines
5.7 KiB
C++
#include "path_tracker.h"
|
|
#include <iostream>
|
|
|
|
#define _USE_MATH_DEFINES
|
|
#include <cmath>
|
|
|
|
#ifndef M_PI
|
|
#define M_PI 3.14159265358979323846
|
|
#endif
|
|
|
|
int main() {
|
|
std::cout << "========================================" << std::endl;
|
|
std::cout << " Single Steering Wheel AGV Path Tracking Control System Demo" << std::endl;
|
|
std::cout << "========================================\n" << std::endl;
|
|
|
|
// 1. Create AGV model
|
|
double wheelbase = 1.0; // Wheelbase 1.0m
|
|
double max_velocity = 2.0; // Max velocity 2.0 m/s
|
|
double max_steering = M_PI / 4; // Max steering angle 45 degrees
|
|
AGVModel agv_model(wheelbase, max_velocity, max_steering);
|
|
|
|
std::cout << "AGV Parameters:" << std::endl;
|
|
std::cout << " Wheelbase: " << wheelbase << " m" << std::endl;
|
|
std::cout << " Max Velocity: " << max_velocity << " m/s" << std::endl;
|
|
std::cout << " Max Steering Angle: " << (max_steering * 180.0 / M_PI) << " degrees" << std::endl;
|
|
|
|
// 2. Create path tracker
|
|
PathTracker tracker(agv_model);
|
|
|
|
// 3. Define reference path
|
|
PathCurve path;
|
|
|
|
std::cout << "Please select path type:" << std::endl;
|
|
std::cout << "1. Straight line path" << std::endl;
|
|
std::cout << "2. Circular arc path" << std::endl;
|
|
std::cout << "3. Bezier curve path" << std::endl;
|
|
std::cout << "4. S-curve path (combined)" << std::endl;
|
|
std::cout << "Enter choice (1-4): ";
|
|
|
|
int choice;
|
|
std::cin >> choice;
|
|
|
|
switch (choice) {
|
|
case 1: {
|
|
// Straight line: from (0,0) to (10,10)
|
|
PathPoint start(0.0, 0.0);
|
|
PathPoint end(10.0, 10.0);
|
|
path.generateLine(start, end, 100);
|
|
std::cout << "\nGenerated straight line path: (0,0) -> (10,10)" << std::endl;
|
|
break;
|
|
}
|
|
case 2: {
|
|
// Circular arc: center (5,0), radius 5m, from 0 to 90 degrees
|
|
path.generateCircleArc(5.0, 0.0, 5.0, 0.0, M_PI / 2, 100);
|
|
std::cout << "\nGenerated circular arc path: center (5,0), radius 5m" << std::endl;
|
|
break;
|
|
}
|
|
case 3: {
|
|
// Bezier curve
|
|
PathPoint p0(0.0, 0.0);
|
|
PathPoint p1(3.0, 5.0);
|
|
PathPoint p2(7.0, 5.0);
|
|
PathPoint p3(10.0, 0.0);
|
|
path.generateCubicBezier(p0, p1, p2, p3, 100);
|
|
std::cout << "\nGenerated Bezier curve path" << std::endl;
|
|
break;
|
|
}
|
|
case 4: {
|
|
// S-curve (two connected arcs)
|
|
std::vector<PathPoint> points;
|
|
|
|
// First segment: arc to the right
|
|
PathCurve arc1;
|
|
arc1.generateCircleArc(2.5, 0.0, 2.5, M_PI, M_PI / 2, 50);
|
|
auto arc1_points = arc1.getPathPoints();
|
|
points.insert(points.end(), arc1_points.begin(), arc1_points.end());
|
|
|
|
// Second segment: arc to the left
|
|
PathCurve arc2;
|
|
arc2.generateCircleArc(2.5, 5.0, 2.5, -M_PI / 2, 0, 50);
|
|
auto arc2_points = arc2.getPathPoints();
|
|
points.insert(points.end(), arc2_points.begin(), arc2_points.end());
|
|
|
|
path.setPathPoints(points);
|
|
std::cout << "\nGenerated S-curve path" << std::endl;
|
|
break;
|
|
}
|
|
default:
|
|
std::cout << "Invalid choice, using default straight line path" << std::endl;
|
|
PathPoint start(0.0, 0.0);
|
|
PathPoint end(10.0, 10.0);
|
|
path.generateLine(start, end, 100);
|
|
break;
|
|
}
|
|
|
|
tracker.setReferencePath(path);
|
|
std::cout << "Path length: " << path.getPathLength() << " m" << std::endl;
|
|
std::cout << "Path points: " << path.getPathPoints().size() << std::endl;
|
|
|
|
// 4. Set initial state
|
|
AGVModel::State initial_state(0.0, 0.0, 0.0); // Start at (0,0), heading 0 degrees
|
|
tracker.setInitialState(initial_state);
|
|
std::cout << "\nInitial state: x=" << initial_state.x
|
|
<< ", y=" << initial_state.y
|
|
<< ", theta=" << (initial_state.theta * 180.0 / M_PI) << " degrees" << std::endl;
|
|
|
|
// 5. Select control algorithm
|
|
std::cout << "\nPlease select control algorithm:" << std::endl;
|
|
std::cout << "1. Pure Pursuit" << std::endl;
|
|
std::cout << "2. Stanley" << std::endl;
|
|
std::cout << "Enter choice (1-2): ";
|
|
|
|
int algo_choice;
|
|
std::cin >> algo_choice;
|
|
|
|
std::string algorithm = (algo_choice == 2) ? "stanley" : "pure_pursuit";
|
|
std::cout << "\nUsing algorithm: " << algorithm << std::endl;
|
|
|
|
// 6. Generate control sequence
|
|
std::cout << "\nGenerating control sequence..." << std::endl;
|
|
double dt = 0.1; // Time step 0.1s
|
|
double horizon = 20.0; // Prediction horizon 20s
|
|
|
|
if (!tracker.generateControlSequence(algorithm, dt, horizon)) {
|
|
std::cerr << "Control sequence generation failed!" << std::endl;
|
|
return 1;
|
|
}
|
|
|
|
std::cout << "Control sequence generation completed!" << std::endl;
|
|
|
|
// 7. Display control sequence
|
|
tracker.printControlSequence();
|
|
|
|
// 8. Save to file
|
|
std::cout << "\nSave control sequence to file? (y/n): ";
|
|
char save_choice;
|
|
std::cin >> save_choice;
|
|
|
|
if (save_choice == 'y' || save_choice == 'Y') {
|
|
tracker.saveControlSequence("control_sequence.csv");
|
|
tracker.saveTrajectory("trajectory.csv");
|
|
std::cout << "\nFiles saved!" << std::endl;
|
|
std::cout << " - control_sequence.csv (control sequence)" << std::endl;
|
|
std::cout << " - trajectory.csv (predicted trajectory)" << std::endl;
|
|
std::cout << "\nNote: You can visualize CSV files using Python/MATLAB/Excel" << std::endl;
|
|
}
|
|
|
|
std::cout << "\n========================================" << std::endl;
|
|
std::cout << " Demo Program Ended" << std::endl;
|
|
std::cout << "========================================" << std::endl;
|
|
|
|
return 0;
|
|
}
|