LAB: Geo Controller
Under Construction... not fully complete yet.
In this lab, we will add the Geological Controller to your RC car. Please review this article to figure out the roles and responsibilities of different controllers in your RC car.
The high level idea is that:
- Geo Controller receives a destination in the form of latitude and longitude
- Geo Controller also has a link to the GPS module
- You can more or less use the Pythagorean theorem to compute the heading degree for the Driver Controller
This will take some research but the earth is not flat (it is really not flat), and so if you use Pythagorean theorem, your heading degree may not be fully accurate, but it will work on the scale of your RC car unless you are sending it from the US to Canada.
Another research item is that you will have to eventually align your GPS degree to the Compass degree. For example, your compass degree may have 90 degrees as North, whereas your GPS may or may not agree, but for this lab we can assume fake values of the compass and focus only on the GPS portion. When you eventually fix this logic, no other controller would need to know because they are abstracted away as they only focus on the destination and current heading, and how you compute these numbers is not a concern for other controllers as long as you do it right.
Part 0: DBC
In this part, you should define the following CAN messages in the DBC file:
- GPS destination message
- The Bridge Controller should send the destination to Geo Controller
- This should include longitude and latitude
- GPS heading message
- The Geo Controller should send this message
- Include 0-360 degrees of current heading (from the Compass)
- Include 0-360 degrees of destination heading (computed by Geo)
Part 1: Driver Obstacle Avoidance Code Module
Remember out last code module for the driver? We will extend it to also take in the Geo Controller message, and then we will use this information to figure out the motor controller commands.
// @file driver_logic.h // Assuming these data structures from the generated DBC struct dbc_SENSOR_data_s; struct dbc_MOTOR_command_s; struct dbc_GEO_headings_s; // This should copy the sensor data to its internal "static" struct instance of dbc_SENSOR_data_s void driver__process_input(dbc_SENSOR_data_s sensor_data); void driver__process_geo_controller_directions(dbc_GEO_heading_s geo_heading); // This should operate on the "static" struct instance of dbc_SENSOR_data_s to run the obstacle avoidance logic dbc_MOTOR_command_s driver__get_motor_commands(void);
Part 2: The power of TDD
The beauty of unit-tests is that when we add additional logic, we can still ensure that our previously written code is not going to break or malfunction. The Geo Controller message should have no impact on the output of the motor controller commands if there is an obstacle avoidance actively being used. Only if all sensors show that there is no obstacle should your RC car obey the Geo Controller commands, and steer the car in the right direction.
Part 3: Extras
You should invest in easy diagnostic functionality, so slap on a couple of bright LED indicators (driven by a higher current transistor or mosfet) to indicate things such as:
- An obstacle is in near vicinity and GPS heading is not being followed
- This will tell you if the RC car is following the GPS or avoiding an obstacle
- A ring LED device that indicates where the RC car is trying to go
- Sparkfun device link may be non trivial to drive this LED device but should be worth the effort
While this part is technically "extra credit", implementing these kinds of easy features will save you ton of time later in the project.