What purpose would it serve?
Two fold; One it would let me eval the heavy load portions of a script in a thread and then pass the "this" to the main gui thread so it could do the light processing of displaying the results. Only other way would be to store them in an object and pass it around but the GUI is .ui defined and can change at any time as can the script. FYI the script could be processed from any number of separate threads depending on circumstances. All this works fine for console output the problem is communication with the main gui thread.
Two it would let me have a persistent state across script evals since some processing depends on how many time X, Y etc have occurred. Like before this processing could take place in an undetermined thread.
Bob
I don't see what the definition of a GUI has to do with passing objects between script engines. Your script returns something (it can even be a JSON formatted string) and you can pass this something as input of another script on another script engine in another thread.
You can have the same by doing it properly, i.e. by using the "Memento" (aka Hibernate) design pattern.Two it would let me have a persistent state across script evals since some processing depends on how many time X, Y etc have occurred. Like before this processing could take place in an undetermined thread.
GUI being the main thread the the UI was created in and cannot be referenced from the script in a separate thread. It is referenced because I can use stdout with no problems, it just when I need to display the result in the main thread (gui) that I run into problems.I don't see what the definition of a GUI has to do with passing objects between script engines..
This is probably the only way to do it at this time but it is going to create more script code to encode and decode the information passed rather then just passing "this" which comes already defined.Your script returns something (it can even be a JSON formatted string) and you can pass this something as input of another script on another script engine in another thread
This would require storing a return from the script as you suggested above. Formatted string being the only viable options I can see since it would have many values to track.You can have the same by doing it properly, i.e. by using the "Memento" (aka Hibernate) design pattern.
Not totally what I wanted to here since just moving around the context appears to be the most elegant and easy solution but your suggestions will get the end result and thats would ultimately matters.
Bob
But why do you want to "reference" the UI from the script? Something runs the script, right? So it can retrieve the result from the script and display it on the UI.
You don't have to do it this way, there are other ways, especially that you have access to the global object of the script.This is probably the only way to do it at this time but it is going to create more script code to encode and decode the information passed rather then just passing "this" which comes already defined.
Wrong, you can use objects.This would require storing a return from the script as you suggested above. Formatted string being the only viable options I can see since it would have many values to track.
Not really. A context sits inside another context. You'd have to move all contexts which effectively would mean moving the entire machine. So it's better to move the entire machine which is possible or just don't do anything which would be the same...Not totally what I wanted to here since just moving around the context appears to be the most elegant and easy solution
The script itself is updating the ui, similar to the Calculator example.But why do you want to "reference" the UI from the script? Something runs the script, right? So it can retrieve the result from the script and display it on the UI.
My understanding of scripting is limited, so you are saying I can create an object inside the script pass it back to my c++ as a QScriptValue and then pass that back to the other script as an argument?Wrong, you can use objects.
If that is true that would be exactly what I needed, will just need to figure out the creation syntax for an object inside a script and setting its variables and returning it.
Bob
Edit:
Looks like I could do something like
That should return the myObject as a QScriptValue that I can pass as an argument to the other script?Qt Code:
function foo() { myObject = new Object(); myObject.a = 1; myObject.b = 2; return myObject; }To copy to clipboard, switch view to plain text mode
Last edited by coderbob; 24th January 2010 at 19:09.
In the Calculator example the argument is passed the script like
Qt Code:
QScriptValue ctor = engine.evaluate("Calculator"); QScriptValue scriptUi = engine.newQObject(ui, QScriptEngine::ScriptOwnership); QScriptValue calc = ctor.construct(QScriptValueList() << scriptUi);To copy to clipboard, switch view to plain text mode
This doesn't work
I cannot find the syntax and playing with the code I am unable to figure out how to pass a QScriptValue as an argument to a script.Qt Code:
QScriptValue ctor = engine.evaluate("foo"); QScriptValue scriptObj = engine.newQObject(myScriptValueObject.toObject(), QScriptEngine::ScriptOwnership); QScriptValue calc = ctor.construct(QScriptValueList() << scriptObj);To copy to clipboard, switch view to plain text mode
EDIT: and past that how to pass both the ui and the script object.
Bob
That obviously can't be done from a worker thread.
Yes, more or less. You can't pass the same object but you can send a copy of the data.My understanding of scripting is limited, so you are saying I can create an object inside the script pass it back to my c++ as a QScriptValue and then pass that back to the other script as an argument?
There are many ways to do it but you can start with:If that is true that would be exactly what I needed, will just need to figure out the creation syntax for an object inside a script and setting its variables and returning it.
javascript Code:
var x = new Object; x.something = somethingelse; x.xyz = abc; return x;To copy to clipboard, switch view to plain text mode
Yes, that's one possibility. But you can't pass the same value to another engine, you have to copy the data from it to a new object that is bound to the other engine.Looks like I could do something like
That should return the myObject as a QScriptValue that I can pass as an argument to the other script?Qt Code:
function foo() { myObject = new Object(); myObject.a = 1; myObject.b = 2; return myObject; }To copy to clipboard, switch view to plain text mode
JavaScript Object and QObject are two different things. QObjects are modelled as Objects but you can't convert freely between the two (i.e. you can't "cast" Object to QObject).
You can't reference GUI from non-GUI threads. As for making objects visible to the script, consult the reference manual, there are at least three ways to do it.EDIT: and past that how to pass both the ui and the script object.
In the QScriptValue docs in reference to copy it says:Yes, that's one possibility. But you can't pass the same value to another engine, you have to copy the data from it to a new object that is bound to the other engine.
Doing it inside the script is irrelevant in this case so the QScriptValueIterator was used.Note that a QScriptValue for which isObject() is true only carries a reference to an actual object; copying the QScriptValue will only copy the object reference, not the object itself. If you want to clone an object (i.e. copy an object's properties to another object), you can do so with the help of a for-in statement in script code, or QScriptValueIterator in C++.
I still run into the problem of "QScriptValue::setProperty(newObject) failed: cannot set value created in a different engine". I have read, reread, and rerereread the docs on this and not sure what I need to reference.Qt Code:
QScriptValue newObject; QScriptValueIterator it(oldObject); while (it.hasNext()) { it.next(); newObject.setProperty(it.name(),it.value()); }To copy to clipboard, switch view to plain text mode
it.value().data() does not produce the error but also does not give me anything either.
Bob
You are not making a copyQScriptValueIterator::value() returns a QScriptValue so you can't assign it to a different engine. You have to convert the value to appropriate C++ type (which makes a copy of the data) and then set it on the other object.
Bookmarks