Multithreaded multi-MDI app



  • The app is using multiple windows with each window containing multiple documents. Each document is both graphically as well as computationally intensive and splitting it off to a separate process is a no-go. One top-level window per display, with MDI for individual documents - up to 12 documents is not uncommon on single display setups, many more on multi-display setups with as many as 9+ displays not uncommon either, so lots of documents).

    Qt's Graphics View framework fits perfectly for rendering and interacting with the graphics of a single document, but since there's typically many documents open at the same time I'm not sure how to proceed as far as multi-threading it. AFAIK QGraphicsScene and friends are not thread-safe, or even reentrant and keeping the app single-threaded is basically a deal-breaker as far as using Qt for the app goes, so any suggestions would be welcome.



  • One way could be to put the computations into a separate thread and have only the graphics view skeleton in the main thread. Without deeper knowledge about the details, that's all that comes into mind.



  • Yes, I've thought of that also. The problem is that 1. graphics must be updated with each new data (and it's a big scene), and 2. generating new data is usually much cheaper than presenting it, which makes the one graphics thread the bottleneck. That's why the idea is to offload the entire graphics+computations process for a single document to a single thread (or two threads in the much less common scenario where generating new data is much more expensive than presenting it, for which your suggestion works well) and scale with more cpus if need be.



  • Let me rephrase that for clarity:

    I can scale the computation part, no problem, by using more threads.
    The problem is that Qt's Graphics View framework doesn't scale, or at least doesn't seem to. So I'm looking for suggestions on making Qt Graphics View framework scale to more threads (any modern computer has 4+ cores, and I can get more cores if needed, but Qt only uses 1, and I can't make that one any faster, ugh).



  • Why isn't splitting up into multiple processes an option? I think that is really your only way out. You can make multiple applications (can still communicate using IPC, of course). I have also seen demo's a while back that showed a simple windowing system build in Qt: Qt applications that render into a QImage, which is then managed by another Qt application that provides a surface for them. Such a setup, althoug it would require quite a bit of work, could result in a system where multiple processes are rendering into a what to the user looks like and works like a single application.



  • I was afraid you'd say that. The beauty of Qt is that it's simple to work with which allows for rapid app development. If you need to implement what basically sums up to a good portion of X11 networked input event and update mechanism it kinda defeats that (each "document" is basically a big interactive scene with lots of items/objects).



  • So I take it then that "put that graphics view renderer into its own thread and be done with it" probably isn't doable with Qt currently?



  • In case your actual drawing is that time consuming, it does not help putting it into a separate process too - the drawing is done in your main program.

    In my opinion there's a major design fault: drawing your graphics items being so heavy-weighted that you want to put that into a separate thread. You should think over it and optimize or simplify your drawing routines. There were some pretty nice talks on optimizing graphics view speed in one of the last Qt DevDays, have a look at the "video collection":/videos#c-98.

    As you do not provide details about what you are actually doing and why the graphical representation of your documents is so CPU consuming, we cannot comment in more detail.

    Regarding putting the renderers into separate threads: how should that work? The items can overlap etc. You will need one single central instance that coordinates all that stuff.

    You may try to "paint" onto a [[Doc:QImage]] or a [[Doc:QPicture]] in a secondary thread and pass the fully rendered image or picture to the main thread. But I'm not sure, if that's supported at all, due to the "paint in main thread only" restriction.



  • Yes, rendering into a QImage at least is fully supported in a thread.



  • [quote author="Andre" date="1322415174"]Yes, rendering into a QImage at least is fully supported in a thread. [/quote]

    Can we use a QPainter on that too? Like this:

    @
    QImage img;
    QPainter painter(image);
    painter.drawLine(...);
    // etc.
    @



  • [quote author="Volker" date="1322420982"]
    [quote author="Andre" date="1322415174"]Yes, rendering into a QImage at least is fully supported in a thread. [/quote]

    Can we use a QPainter on that too? Like this:

    @
    QImage img;
    QPainter painter(image);
    painter.drawLine(...);
    // etc.
    @
    [/quote]

    You certainly can!

    André


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.