hscript script is a scripting language interpreted by Houdini. For quick evaluation, you can type the hscript commands in the Textport window in Houdini. The hscript has many useful commands that you may want to invoke in the C++ code, for example to source own script file (using source command) or to display a dialog box (using message command). There is an CMD_Manager class to facilitate the script invocation, and its CMD_Manager::execute() method can be used to run the command.The CMD_Manager::execute() signature looks like this:
void execute(const char * cmd, // command to run int add_to_history = 0, // add the command to history ostream * out=0, // stream to print output to ostream *err=0, // stream to print errors to int do_alias_expansion = 1, // perform command alias expansion bool create_block = true); // run commands in one go
hscript command, which will be executed. If you provide the output stream, any output produced by the command will be written there. Also, if you pass in an error stream pointer, any error messages will be printed there.The command manager instance is owned by the OP_Director and can be obtained by OP_Director::getCommandManager(). The OP_Director instance, in turn, is accessible via the global function OPgetDirector(). OP_Director class represents the root of the node hierarchy (ie, the node "/"), and therefore there is only one instance of this class. This class has several OP_Managers as its children.
hscript commands because some of them operate with respect to that directory. For example opadd will create a new node inside the current working directory. You can use pwd and cd commands to print and change the current directory. You can also use the C++ methods OP_Director::getCwd() and OP_Director::setCwd() to achieve the same thing.hscript command that displays the dialog is called message, and its -b switch defines the buttons (separated by a comma). The -d switch specifies the default button. UT_String command = "message " "-b \"Left,Middle,Right\" " "-d 0 " "Please press any button.";
We will run the message command and retrieve the button index from the output stream. To obtain the command manager object, we query the global director.
UT_OStrStream os; OPgetDirector()->getCommandManager()->execute( command, false, &os );
Now, we need to parse the output stream and determine what number was printed out. We obtain the string using UT_OStrStream::str() but, after that, we have to unlock the buffer using the freeze(0) method.
UT_String result_str; int result_int; result_str.harden( os.str() ); result_str.trimSpace(); os.freeze(0); if( result_str.isstring() && result_str.isInteger() ) result_int = result_str.toInt(); else result_int = -1;
And now we can provide feedback to test if the code works correctly.
const char * button; UT_String feedback_cmd; if( result_int == 0 ) button = "first"; else if( result_int == 1 ) button = "second"; else if( result_int == 2 ) button = "third"; else button = "invalid"; feedback_cmd.sprintf( "message You pressed the %s button", button ); OPgetDirector()->getCommandManager()->execute( feedback_cmd );
void hdkExecuteMessageCmd() { UT_OStrStream os; UT_String result_str; int result_int; const char * button; UT_String command; // construct and run the command command = "message " "-b \"Left,Middle,Right\" " "-d 0 " "Please press any button."; OPgetDirector()->getCommandManager()->execute( command, false, &os ); // retrieve the output stream string and convert it into an integer result_str.harden( os.str() ); result_str.trimSpace(); os.freeze(0); if( result_str.isstring() && result_str.isInteger() ) result_int = result_str.toInt(); else result_int = -1; // construct the feedback command and run it if( result_int == 0 ) button = "first"; else if( result_int == 1 ) button = "second"; else if( result_int == 2 ) button = "third"; else button = "invalid"; command.sprintf( "message You pressed the %s button", button ); OPgetDirector()->getCommandManager()->execute( command ); }
1.5.9