GroG made a comment about giving InMoov a " personality " and how it got more attention at shows if it was always moving. I put together the following script that runs gestures or speech randomly.

def randomgestures():
    for y in range(0,20):  #determines how many gestures are done
        x = (random.randint(1,10))
        if x == 1:
           knocktoby()
           sleep(30)  # time between gestures 
        if x == 2:
           lookleft()
           sleep(3)
           lookforward()
           sleep(40)
        if x == 3:
           i01.mouth.speak("hey let's do something")
           sleep(20)
        if x == 4:
           gowrong()
           sleep(60)
        if x == 5:
           laugh()           
           sleep(45)
        if x == 6:
           lookright()
           sleep(7)
           lookforward()
           sleep(40)
        if x == 7:
           lookup()
           sleep(4)
           lookforward()
           sleep(20)
        if x == 8:
           pointfinger()
           sleep(40)
        if x == 9:
           speakfrench()
           sleep(30)
        if x == 10:
           horsejoke()
           sleep(40)

    rest() 

It works quite well. By increasing or decreasing the sleep time between each gesture and how many gestures are done, will determine how long the scrpt takes to run. Theroretically, it could run for hours. The sleep time for each gesture can not exceed the "power down on inactivity" setting (if that is in use).

Have fun

GroG

10 years ago

Thanks bhouston.

Great script - can you embed an example video - would be nice to see cause ---> effect (even for people who don't currently have an InMoov)

What you've done is getting very close to a FSM (finite state machine), if the state began interacting with one another - specifically supressing others and were composed of more states underneath - you would have something similar to Subsumption Architecture

Very cool...

MaVo

10 years ago

That looks cool!

Although just one thing crossed my mind:

When the function runs, it would run until it's finished and you can not use it in a other way in the main-time.

If this it meant as a "gap-filler" I would like to do "real-things" just when I want to do them and not waiting for the/this "gap-filler" to finish.

Depending on how long it runs, it could be (very) long.

A "break" or something like this would be nice

Don't know Python enaugh for this - don't know, if something like this exists:

useitnow = false

[some other things]

def ... :

  for ... :

    if useitnow:

      [break]

...

NOTE: I say this without having a functional part of an InMoov - just got that idea ...

I've often thought it would be nice to have a command that would stop a script from running and return InMoov to the rest position. This could also be helpful if something is happening you don't want, you could quickly cancel it. 

I'm sure that a script for this is possible but like you, I don't know how to write it for sure.

Someone other there knows how though.

kwatters

10 years ago

In reply to by bhouston

If we could terminate (from the gui) the current running python code, that would be excellent... sometimes I might have a script running in a long loop and i want to kill it early.  I don't see any way to do that currently aside from restarting MRL.

I think Mastablasta had some of his actions like playing music be able to stop.  He could tell his InMoov to start playing music and if it told it would keep listening for commands so that he could make it stop playing or change to a different song. Not sure if every action in the framework is interruptable.

Here's some example python code that uses the "exec()" method to invoke a random gesture.

Below, I have defined 2 functions  gest1() and gest2()

I then create a list object in python with 2 snippets of python code.  Each element in the list is the python code to invoke.  I then enter a loop where I generate a random number and pull that out of the list and execute it using the exec() method.   

Something like this might be a bit easier to maintain than hard coding the branches of the switch statement.

#####################################################

import random
 
# My first gesture goes here
def gest1():
  print "gesture 1"
 
# my second gesture goes here
def gest2():
  print "gesture 2"
 
 
# create a list of strings that represent the methods you want to be able to call
functionlist=[ "gest1()", "gest2()"]
# compute the lenght of the list
num_functions = len(functionlist)
 
# choose how many times to run through the loop
num_iterations = 5
for i in range(0,num_iterations):
  # create a random number which will look up into the fuctionlist
  function_id = random.randint(0,num_functions-1)
  # grab the element in the list based on the random id
  function_to_call = functionlist[function_id]
  # evaluate the string as python code and invoke the gesture.
  exec(function_to_call) 
 

Technically this isn't introspection..  sorry for the confusing title to the post...

globals() returns a list of the fuctions that are defined in the global scope. you could iterate this and build the functionlist in the example above... (that was where I was originally going with the introspection thing.)

kwatters, that is a step in the right direction ...

I don't know about Python's integration into MRL (I believe it's Jython), but maybe we could cancel/abort Python's execution from the Java-side (GroG, are you here? ; ))

@kmc: Masta uses the not blocking soundfile-play method ...

Another thought:

The "gap-filler" could be something like PowerDown/Up, but only with very little snippets, turning the head 20°, raising the arm a bit, say "Are you here?", etc.

The next one:

After a period of time it switches over (from "using-state") into the "gap-filler", then when it isn't used there for an specific time, it goes into "powered-down" - would be nice with customizable, etc.

 

Possibly, if it's implemented from Java's side, it could have "more-control".

-integrating with InMoov, hooks for Python for custom-things and partly ON/OFF-switchable

 

AND we need the "emergency-shutdown"-button for the execution of Python-Scripts ...

 

OK, now I'm drifting away ...                                 GroG, make your TODO-list ready! ; )

There should be a big map of InMoov's Finite State Machine diagram.  I remember posting on this before.  You don't need to be a programmer to contribute .. State is what we all have experience in :)

Anyway - it would be helpful for us all if we had a communal document all of us could have access too to begin mapping the states & events InMoov can consume and produce.

I've used Dia in the past for state diagrams since its free & open source - I think it runs on many platforms too.

Yeah .. need to get back to my work list so I can get back to my TODO list :)

Heh, looked like fun so I tried this:

import threading
import random
 
twitching_thread = None
idle = True
 
def start_twitching():
  global twitching_thread
  twitching_thread = threading.Timer(5.0, twitch).start()
  print "gonna start twitching"
 
def stop_twitching():
  global twitching_thread
  twitching_thread.stop()
  print "i am zen now"
 
def twitch():
  global idle, twitches
  print 'twitch'
  if (idle):
    # replace is i01.isIdle()
    x = random.randint(0, len(twitches)-1)
    exec(twitches[x])
  
# --- twitchy gestures begin ----
 
def scratchBottom():
  print "i'm scratching my bottom"
 
def pickNose():
  print "i'm picking my nose"
 
def itchHead():
  print "i'm itching my head"
 
twitches = ["scratchBottom", "pickNose", "itchHead"]
start_twitching()
 
not sure about the exec(twitches[x]) - doesn't explode but I don't see the print statements .. perhaps a different  std out handle?  Anyway there's a global idle, because If he's doing something like defusing a bomb - you don't want to suddenly scratch your bottom :)

Simple answer ... no...

There is a big button - kill everything script ...

python.stop() ...  kills the interpreter, input queue thread, interpreter thread ... kills a lot of things ..

A Bigger button is python.stopService .. this whacks the inbox & outbox thread...

not positive it will interrupt a script ..

to attempt to start again you'd do python.startService() ..

dunno if they are symmetric .. let us know :)

If you do gestures in another thread (a thread is a thingy which executes code) .. I think you can interrupt it ..

So the question should be :  "How do I execute code in a seperate thread so I can interrupt it and stop it from running" 

Answer would be - similar to my gesture example