Stupid feature... running external commands from inside KTurtle

23 views
Skip to first unread message

Permutation Company

unread,
Sep 23, 2008, 4:25:08 AM9/23/08
to KTurtle; an eduactinal programming environment
Folks,

I'm getting a group of primary school kids from theoretical
(programming) to practical (motion control).

We have a Velleman USB interface board with motors, lights, etc...,
and I want to tie its commands (scripts in Bash) to KTurtle, such that
when KTurtle command "turnleft 3" is in the interpreter, a Bash
command (say, a script called "/usr/bin/turn_left 3") executes, as
well. Alternatively, if I could create new commands in KTurtle (such
as "real_turnleft 3") that do the same thing.

Not a programmer... just a scripter, but anything I make out of this
gets shared with the community, so would appreciate any advice
offered.

Thanks, Jim

Andrea Occhi

unread,
Sep 23, 2008, 4:58:31 AM9/23/08
to kdeedu-...@googlegroups.com
I think that the best for you is to "compile" Kturtle code into bash
scripting code.
With a translation table this is not too complicated.
The "compiler" can be done in any language you best know.
bye
Andrea

2008/9/23 Permutation Company <goo...@permutation.com>:

Niels Slot

unread,
Sep 25, 2008, 12:00:03 PM9/25/08
to kdeedu-...@googlegroups.com
Hi Jim,

This would in theory be possible. Can you tell me which version of KTurtle you're using? Is it the older KDE3 version of the newer KDE4 version? If you're using the KDE3 version, are you willing to switch? Also, is it a problem for you to apply patches to the KTurtle source and compile it? Using the QProcess class I might be able to write a small path for KTurtle.

Regards,

Niels

2008/9/23 Permutation Company <goo...@permutation.com>

cies

unread,
Sep 27, 2008, 11:45:06 AM9/27/08
to kdeedu-...@googlegroups.com
niels: yr king..

Permutation Company

unread,
Oct 29, 2008, 9:49:09 AM10/29/08
to KTurtle; an eduactinal programming environment
Folks,

Currently using Turtle 0.8.1 in KDE 4.0.3 on Ubuntu Hardy (8.04)
machines.

I've no problem modifying and compiling custom versions, though I
should stress that I'm an amateur scripter, not an experienced coder.

In essence, I'm just looking to have an existing or new command in the
KTurtle environment also execute an external BASH script. I've built
a 'real' turtle (from a model tank) that is controlled by BASH scripts
I've written, that loosely match existing Logo commands. I'm just
trying to link the on-screen experience of the virtual Turtle with a
realworld remote controlled Turtle, such that our kids can begin
understanding scripting, programming and motion control.

Happy to post pictures, designs and any patches, once I get them
working.

Thanks, Jim

cies

unread,
Oct 30, 2008, 10:05:11 PM10/30/08
to kdeedu-...@googlegroups.com
wasn't the kturtle in kde3 able to run bash commands?
hmm..

it would not be too hard to implement i guess.

$x = bash "ls -lh"
then $x contains the std out (and std err??) of the command.

cheers,
_c.

Walter Schreppers aka Walle

unread,
Nov 8, 2008, 11:30:45 PM11/8/08
to KTurtle; an eduactinal programming environment
Hello,

I've been away from kturtle a while but I think I can help you very
quickly with this feature request (if it's not there already).
Anyways it's because the interpreter class was based on wsbasic and
wsbasic itself does have this process command you want for your
real turtle (actually I've used this exact technique before with a
mindstorms robot and NQC : http://walter.schreppers.com/index.php?page=mindstorms
check the .tar.gz on the page ).

But as for your request. Wsbasic already contains such a feature. The
code looks like follows in wsbasic for instance lets say you want to
run
the ls command and process its output in wsbasic you do that like
this:
wALLe-MAC:~/cppWork/wsbasic/scripts wschrep$ cat runtest.b
#!../wsbasic

dir = run ("ls -m -1")
print "dir=",dir

And for something more complex like sending a mail:
wALLe-MAC:~/cppWork/wsbasic/scripts wschrep$ cat mailto.b
#!../wsbasic

if $# != 4
begin
print "USAGE: " + $1 + " <mail list file> <mail content file>"
break
end

mail_list = $2
mail_subject = run( "head -n 1 " + $3 )
lines = run( "wc -l " + $3 )*1-1
mail_content = run( "tail -n " + lines + " " + $3 )

print "mail_list="+mail_list
print "mail_subject="+mail_subject
print "mail_content="+mail_content


#####################################
# loop that calls 'mail' program

foreach email in run( "cat " + mail_list )
begin
print "mailing '", email ,"'...";

#uncomment below to actually mail it!
#
#ok=run( "echo \"" + mail_content + "\" | mail -s \"" + mail_subject
+"\" " + email )
#if( ok == "" ) print "done."
#else print "failed!"

print ""
end

Now you see the run command is what you need in kturtle.
I can insert this into the kturtle cvs code (if Cies Breijs or someone
gives me some info on the cvs repository and login etc since I did not
use those).
Actually to be honest the reason I completely ceased development on
wsbasic and therefore also kturtle was because my promotor A. Cuyt did
not
really approve of my many side projects (that they helped me to do
better development for my PhD project and helped me to figure out many
design patterns didn't seem to matter much).

Anyways here is some snippet of c++ which executes bash commands
without using the QProcess from Qt (in other words this needs to be
added to the executer class of kturtle):
string Executer::runCommand( const string& command ){
FILE *pstream;

if( ( pstream = popen( command.c_str(), "r" ) ) == NULL ) return
"";

string Line;
char buf[100];

while( fgets(buf, sizeof(buf), pstream) !=NULL){
Line += buf;
}
pclose(pstream);

return Line;
}


void Executer::execRun( TreeNode* node ){
execute( node->firstChild() );

Number* cmdVal = runStack.top();
string cmd = cmdVal->strVal;
runStack.pop();

runStack.push( new Number( runCommand(cmd) ) );
delete cmdVal;
}


Kind regards,
Walter Schreppers

Even if I don't get a reply, hope it helped...




On Oct 31, 3:05 am, cies <cies.bre...@gmail.com> wrote:
> wasn't the kturtle in kde3 able to run bash commands?
> hmm..
>
> it would not be too hard to implement i guess.
>
> $x = bash "ls -lh"
> then $x contains the std out (and std err??) of the command.
>
> cheers,
> _c.
>
> On 10/29/08, Permutation Company <goo...@permutation.com> wrote:
>
>
>
> > Folks,
>
> > Currently using Turtle 0.8.1 in KDE 4.0.3 on Ubuntu Hardy (8.04)
> > machines.
>
> > I've no problem modifying and compiling custom versions, though I
> > should stress that I'm an amateur scripter, not an experienced coder.
>
> > In essence, I'm just looking to have an existing or new command in the
> > KTurtle environment also execute an external BASH script.  I've built
> > a 'real' turtle (from a model tank) that is controlled by BASH scripts
> > I've written, that loosely match existing Logo commands.  I'm just
> > trying to link the on-screen experience of the virtual Turtle with a
> > realworld remote controlled Turtle, such that our kids can begin
> > understanding scripting, programming and motion control.
>
> > Happy to post pictures, designs and any patches, once I get them
> > working.
>
> > Thanks, Jim
>
> > On Sep 27, 3:45 pm, cies <cies.bre...@gmail.com> wrote:
> > > niels: yr king..
>

Niels Slot

unread,
Nov 9, 2008, 1:03:19 PM11/9/08
to kdeedu-...@googlegroups.com
Hi Walter,

Thanks for your effort. From a first look at your code, it should in theory work. If you want to give it a try, you can find the current KTurtle code on KDE's SVN in /trunk/KDE/kdeedu/kturtle. Instructions are in KDE's Techbase or on the KTurtle homepage.

I would like to know how your code behaves when used together with Qt. We shouldn't block the GUI when we're executing an external program.

I also like to let everybody know that I am working with Jim on a different approach. He controls the mechanical turtle using a wrapper around a C library. I've already got a basic C program which can control the real turtle. It wouldn't be much work to integrate this in KTurtle. I think that would be a much cleaner implementation for what Jim wants.

Niels

2008/11/9 Walter Schreppers aka Walle <schre...@gmail.com>

cies....@gmail.com

unread,
Nov 10, 2008, 2:23:53 AM11/10/08
to KTurtle; an eduactinal programming environment
as noted earlier the kde3 version of kturtle has this func'ty.

http://websvn.kde.org/branches/KDE/3.5/kdeedu/kturtle/src/executer.cpp

see the methods execRun and runCommand

when i was porting i just didn't port this one over.. i dont know why
(anymore).
maybe it was hard-to-port code, but i dont think so.

anyway, the code refered to above gives a decent starting point for
implementing it again (using qt/kde-style idiom)


cheers..

On Nov 10, 1:03 am, "Niels Slot" <nielss...@gmail.com> wrote:
> Hi Walter,
>
> Thanks for your effort. From a first look at your code, it should in theory
> work. If you want to give it a try, you can find the current KTurtle code on
> KDE's SVN in /trunk/KDE/kdeedu/kturtle. Instructions are in KDE's Techbase
> or on the KTurtle homepage.
>
> I would like to know how your code behaves when used together with Qt. We
> shouldn't block the GUI when we're executing an external program.
>
> I also like to let everybody know that I am working with Jim on a different
> approach. He controls the mechanical turtle using a wrapper around a C
> library. I've already got a basic C program which can control the real
> turtle. It wouldn't be much work to integrate this in KTurtle. I think that
> would be a much cleaner implementation for what Jim wants.
>
> Niels
>
> 2008/11/9 Walter Schreppers aka Walle <schrepp...@gmail.com>

Walter Schreppers aka Walle

unread,
Nov 19, 2008, 8:42:01 PM11/19/08
to KTurtle; an eduactinal programming environment
Good point about the blocking of the gui with this execRun code!

I had no problems with it because I seperated the interpreter from the
gui code by wrapping the entire interpreter part in a qprocess (work I
did on mpl).

For the kturtle case it will probably be better to use QProcess.
Anyway the problem is I got swamped with work again. Started working
in construction 2 months ago for my dad's company resulting in a
friend who called me the belgian good will hunting. I laughed
(thinking I'm not that smart ;) ) but when I was filling a container
with concrete rubble and trash this morning I did get the striking
ressemblance ;). Anyway, like I said, too much work on my plate to go
and find out how to checkout/compile kturtle on my totally aged linux
box now (its not been updated since I started working on my macbook
which I love;) ). But maybe vmware can be of help for me to get a
quick recent edubuntu on my macbook ;).

Anyway here is some QProcess code which can be easily plugged into
kturtle and will indeed not block the gui:
Let's say we want to run something like 'ls -lh /home/wschrep' without
blocking and get its output:

First add the private local QProcess* exeProc; to the executer.h class
definition.

Then inside the execRun method implementation put something like
this :

void executer::execRun( ){
exeProc=new QProcess(this);
exeProc->addArgument( "ls" ); //the executable name you want to
run (can be any executable, you can give the total path like /usr/bin/
ls to be safe)
exeProc->addArgument( "-lh" ); //any arguments to the executable,
the rule here is use an addArgument whenever you type a space in
bash ;)
exeProc->addArgument("/home/wschrep");

//now to get the output from the executable you need some signal/
slots:

connect( exeProc, SIGNAL(readyReadStdout()), this, SLOT
(readFromStdout()) ); //get errors and output
connect( exeProc, SIGNAL(readyReadStderr()), this, SLOT
(readFromStderr()) );
// connect( inputTxt, SIGNAL(returnPressed()), this, SLOT(input
()) ); //this is only if you need to input code to the external
executable , as in the external exe is using cin it it's code

connect( exeProc, SIGNAL(processExited()), this, SLOT(exeDone
()) ); //signals end of execution of the external program.


That's it really :). Ok to be fair you will wonder what is inside the
readFrom... slots? Well here ya go (but you won't need these if you
just want to run an exe without getting input/output back):

void Executer::readFromStdout(){
while( exeProc->canReadLineStdout() ){ //read entire lines
output->append( exeProc->readLineStdout() ); //output is a
QTextEdit widget in my gui, have no time to check what it is in
kturtle, anyway it will probably be something similar
}

QString strOut = exeProc->readStdout(); //readStdout returns
QByteArray -> copy to qstring.
output->append( strOut ); //show the partial lines, again replace
output here with the appropriate kturtle widget name
}

readFromStderr is exactly the same but use canReadLineStderr() and
exeProc->readLineStderr() .

Now one more important method the exeDone:
void Executer::exeDone(){
statusBar->message( "Execution done!", 3000 );
delete exeProc;
exeProc=0; // I do this so that my destructor is more clean.
}

And add this inside the destructor:

Executer::~Executer(){
//... other destructor code
if( exeProc!= 0 ){
exeProc->kill();
delete exeProc;
}
}

This way you kill the process that was forked before the executer is
destroyed. For instance someone starts kturtle, runs an external
command then decides to close the application before the external
command finishes (for example something like 'ping google.com' which
would keep on running forever in background on most distributions and
the user will be unaware it is running unless he checks his processes
with ps or something). In short the exeProc->kill() is important ;).

As for hard coding the 'hardware turtle c code' into kturtle I think
it would not be a clean way and only necessary if there where
performance or real time issues (which I did not have with the
mindstorms project). Just get the commands like
move forward, turn etc. put them in seperate executables. And call
them from kturtle using a qprocess.

Giving you a few oneliners inside the executer class if you wrap the
code shown in runExe into something like
runExecutable( const QString& command ), then replace "ls" with
command in the above code.
Then sprinkle the running of the external commands into the approprate
exeForward, exeTurn etc and you can even wrap in a define so you can
switch on/off the hardware turtle code verry easily. Should be no more
than a few hours work which unfortunately I don't even have that to
spare now or at least not in the next few weeks because of the
construction work I need to finish and some other RoR work I need to
get done for legendskate.com :S.

Kind regards and hope it helped,
Walter

Walter Schreppers aka Walle

unread,
Nov 19, 2008, 10:21:38 PM11/19/08
to KTurtle; an eduactinal programming environment
Almost forgot to ask.
I would love to see some pictures and maybe even some schematics of
the hardware turtle!

To summarize you can construct your program like so once you have the
exeRun in the executer class of kturtle. (Can't see from the kturtle
manual if user functions/procedures are available, but in wsbasic its
like this):

function real_turn(angle)
begin
run("/usr/bin/turn_left "+ str(angle) )
end

function real_forward(dist)
begin
run("/usr/bin/forward "+ str(dist) )
end

####### main code ####

real_turn( 4 ) #your shell script is executed with value 4 and real
robot turns
turn 4 #kturtle turns
real_forward( 10 ) # your shell script is executed, real robot moves
forward

...etc...


I think I just might built my own combining an attiny+433mhz
transciever and some motor circuit I built a while back (most likely
when I'm stuck at home in a weekend and can't skateboard due to some
stupid injury in my ankle that pops up now and then again due to old
age I guess, time sure does fly ;) ).

http://walter.schreppers.com/index.php?page=blogpost&pos=20

Do let us know how your 'hardware turtle' is evolving because I'm very
intrigued by it as you may have noticed ;)

Cya,
W.

Walter Schreppers aka Walle

unread,
Nov 19, 2008, 10:25:14 PM11/19/08
to KTurtle; an eduactinal programming environment
Almost forgot to ask. I would love to see some pictures/schematics of
the hardware turtle!

To summarize ( Can't see from the kturtle manual if user functions/
procedures are available ) after having exeRun implementation you can
do what you want like this:

function real_turn(angle)
begin
run("/usr/bin/turn_left "+ str(angle) )
end

function real_forward(dist)
begin
run("/usr/bin/forward "+ str(dist) )
end

####### main code ####

real_turn( 4 ) #your shell script is executed with value 4 and real
robot turns
turn 4 #kturtle turns
real_forward( 10 ) # your shell script is executed, real robot moves
forward

...etc...


I think I just might built my own combining an attiny+433mhz
transciever and some motor circuit I built a while back (most likely
when I'm stuck at home in a weekend and can't skateboard due to some
stupid injury in my ankle that pops up now and then again, its when I
built the dc motor board last time I was stuck with a tweaked
ankle :) ):
http://walter.schreppers.com/index.php?page=blogpost&pos=20

Do let us know how your 'hardware turtle' is evolving because I'm very
intrigued by it as you may notice ;)

Cya,
W.

On Sep 23, 9:25 am, Permutation Company <goo...@permutation.com>
wrote:
Reply all
Reply to author
Forward
0 new messages