Log in

View Full Version : New autonomous outline tutorial


jacob9706
17-12-2012, 17:11
Hi everyone,

Today I will be showing you how to implement an easy autonomous system based on callbacks/events. If anyone has done JavaScript using the jQuery library you will be quite familiar with the concept of a callback. A callback is a function (or method depending on the language) that executes after a set of code is done running.

Here is a quick jQuery example...

$(document).load(loadFunction);

var loadFunction = function() {
alert(“Loaded”);
}

What we will be doing today will be a little bit different. We will be creating a “list” of actions we want to preform one after another. This list will be represented as a vector of functions. The first thing we have to do is define a function pointer that returns a boolean and has nothing as its paramaters.

typedef bool (Event*)(void);

That line defines a function pointer called Event that takes nothing(void) and returns a boolean(bool).

The next step will be to define a function that will execute all of our function pointers called Event.

// Function that takes a vector of Even
bool runStringOfEvents(std::vector<Event> events)
{
// Loop through every event
for (unsigned int i = 0 i < events.size(); i++)
{
// Get current event from vector
Event event = events.at(i);
// Execute the event and get the return value
bool success = event();
// If it failed return false
if (!success)
{
return false;
}
}
// If all succeeded return true
return true;
}

Now that the hard part is done we can create a function we will call two times through a list of events we pass to our runStringOfEvents function.

bool someEvent()
{
std::cout << “Event executed” << std::endl;
return true;
}

Now that we have our event function we can create a list in our program and execute the list of events.

int main(int argc, char** argv)
{
// Create the vector to hold our events
std::vector<Event> events;

// Add the function to the list twice
events.push_back(&someEvent);
events.push_back(&someEvent);

// Run the events
runStringOfEvens(events);
}

apalrd
17-12-2012, 23:26
Maybe I'm completely missing the point, but why not just call the commands in a list, procedurally? Like, if you had functions drive_straight(float dist, float speed) and fire_ball(void) you could just do

void autonomous_1()
{
drive_straight(10,30);
fire_ball();
wait(500);
fire_ball();
drive_straight(-10,30);
}

And you would make more functions for more autonomous modes. It seems like a more elegant and execution-efficient solution.


I'm not saying there aren't reasons for storing commands in a list. In fact, I myself wrote a system which is by all metrics complex in LabVIEW to do a similar thing. However, I was trying to gain the ability to store the command vector in a text file, and load it on demand. Had I only wanted to write the commands in LabVIEW, I would have just called the command blocks in sequence (which I did successfully in our 2010 season, which suffered only from a very long on-field iteration time due to LV compile time issues).

jacob9706
18-12-2012, 00:14
Maybe I'm completely missing the point, but why not just call the commands in a list, procedurally? Like, if you had functions drive_straight(float dist, float speed) and fire_ball(void) you could just do

void autonomous_1()
{
drive_straight(10,30);
fire_ball();
wait(500);
fire_ball();
drive_straight(-10,30);
}

And you would make more functions for more autonomous modes. It seems like a more elegant and execution-efficient solution.


I'm not saying there aren't reasons for storing commands in a list. In fact, I myself wrote a system which is by all metrics complex in LabVIEW to do a similar thing. However, I was trying to gain the ability to store the command vector in a text file, and load it on demand. Had I only wanted to write the commands in LabVIEW, I would have just called the command blocks in sequence (which I did successfully in our 2010 season, which suffered only from a very long on-field iteration time due to LV compile time issues).

The reason for this is to be able to spawn them in separate threads... I originally wrote this today just for fun.

apalrd
18-12-2012, 00:47
I see. You are able to launch the next command before the previous command finishes.


That makes a lot of sense. However, when do you really need to do that? I spent a very long time trying to get my script system to allow asynchronous command execution and decided that it was too difficult of a tradeoff in code complexity. I found that there was no reasonable case in which it was impossible to write autonomous code with only one autonomous commanded action executing at a time, with the blocks I wanted to write.

The tradeoff is always between simplicity in execution and flexibility in design.

jacob9706
18-12-2012, 02:35
I see. You are able to launch the next command before the previous command finishes.


That makes a lot of sense. However, when do you really need to do that? I spent a very long time trying to get my script system to allow asynchronous command execution and decided that it was too difficult of a tradeoff in code complexity. I found that there was no reasonable case in which it was impossible to write autonomous code with only one autonomous commanded action executing at a time, with the blocks I wanted to write.

The tradeoff is always between simplicity in execution and flexibility in design.

The other reason I would do something like this(Which I have not yet been able to try) is to allow errors. As you see if one of the functions returns false the rest do not execute.

Joe Ross
18-12-2012, 11:40
Have you looked at the Command based programming model introduced in 2012?

jacob9706
18-12-2012, 14:31
Have you looked at the Command based programming model introduced in 2012?

No I have not. Where could this be found?

Brian Selle
18-12-2012, 15:01
No I have not. Where could this be found?

The 2012 WPILib Cookbook explains how it works. Read the whole document first but CommandGroups described on page 50 may be of interest.

http://firstforge.wpi.edu/sf/docman/do/downloadDocument/projects.wpilib/docman.root.c_and_java_documentation/doc1297

Ether
18-12-2012, 15:23
No I have not. Where could this be found?

http://www.chiefdelphi.com/forums/showpost.php?p=1114679&postcount=7

http://www.chiefdelphi.com/forums/showpost.php?p=1196788&postcount=1

http://www.chiefdelphi.com/forums/showthread.php?t=109719

http://www.chiefdelphi.com/forums/showpost.php?p=1197151&postcount=25