PDA

View Full Version : Making my app scriptable



bibbinator
7th June 2015, 19:07
Hi,
So I have spent the past few weeks digging into adding scripting to my app, reading the doc, looking at posts, SO, etc. I have a couple of high level questions to make sure my direction is right. Any help appreciated.

I'm writing an image processing app that will allow scripted filters to be applied to the image. All operations will be on arrays of floats, so I'll be processing large arrays of floats from the native side in JS, calling into native code for some utilities and stuff, but I don't need a whole bunch of properties or methods exposed.

1. I'm attracted to the debugger and tools of the old QtScript/QScriptEngine compared to the new QJSEngine. Is it correct in thinking that as long as my needs stay straightforward and simple that I can start with the older system and switch to the newer one if needed later? Seems relatively easy to migrate? Or is the new QJSEngine that much better I should use it from the start?

2. What's the best way to make large float arrays available to script? Is there any way to make a memory buffer available to scripts so I don't have to pass too much data?

3. If I want to allow the modifier scripts to store local variables what's the most performant way to declare my methods? Should I use MyClass.prototype to declare the set of methods and properties, or some other JS construct? I'm not a JS expert and I have seen many different ways to declare methods/properties and not sure the differences between them.

Thanks,
Brett

d_stranz
7th June 2015, 22:15
I'm attracted to the debugger and tools of the old QtScript/QScriptEngine

Be aware that QtScript will be deprecated in Qt 5.5 (http://wiki.qt.io/New-Features-in-Qt-5.5) and eventually they may be removed from the Qt distro completely.

bibbinator
8th June 2015, 06:41
I see, thanks for that info.

Okay, if I go the QML route it looks like there's 2 ways to handle the array of floats:

http://doc.qt.io/qt-5/qtqml-cppintegration-data.html

Under "Sequence Type to JavaScript Array" it says:

"If the sequence is exposed as a Q_PROPERTY, accessing any value in the sequence by index will cause the sequence data to be read from the QObject's property, then a read to occur. Similarly, modifying any value in the sequence will cause the sequence data to be read, and then the modification will be performed and the modified sequence will be written back to the QObject's property."

"If the sequence is returned from a Q_INVOKABLE function, access and mutation is much cheaper, as no QObject property read or write occurs; instead, the C++ sequence data is accessed and modified directly."

Does this mean for absolute best performance I should keep my arrays in JS, modify them there, and then return them to C++? Or is having the array in C++ and modifying it directly via index still quite fast? Or is it trying to say that if I have a Q_INVOKABLE method that returns a sequence to JS then that's the fastest and avoids the property read?

I don't understand the "cause the sequence data to be read from the QObject's property, then a read to occur" part. Does that mean it reads it twice? Or is that a typo?

Thanks,
Brett

d_stranz
9th June 2015, 23:18
I don't understand the "cause the sequence data to be read from the QObject's property, then a read to occur" part. Does that mean it reads it twice? Or is that a typo?


No, I think what it is saying is if you try to read a single value ("by index") from a sequence, the implementation of a sequence Q_PROPERTY will cause the entire sequence to be transferred into JS, then the desired element will be extracted ("read") into the local JS variable and the rest of the sequence discarded. This will occur for every indexed access, so if your sequence has 1000 items and you iterate over all of them, the sequence will be transferred 1000 times.

If instead of making the sequence a Q_PROPERTY, you make access to it a Q_INVOKABLE method (e.g. MySequence & getSequence( ); ), then you access the sequence items from the C++ side and return only the elements of interest to JS.

At least that's my read of it. More experienced minds may know better.