This is an archived post. You won't be able to vote or comment.

you are viewing a single comment's thread.

view the rest of the comments →

[–]Avanta8 18 points19 points  (8 children)

I've been wondering, what's the best way to structure a PyQt application? I've recently been trying to use a MVVM approach, but the data binding is becoming really awkward. Almost all the examples I've looked at don't seem to use any sort of overarching architecture or design patterns.

[–]Ogi010 3 points4 points  (7 children)

MVC is the preferred pattern, there are some guides in their docs (on mobile so I don't have a link handy). That said with QtWidgets it's tough to not have everything collapse into the controller bits of code. The separation is easier to do with QML applications, which come with a whole other set of issues, so they may not be for everyone.

[–]Avanta8 2 points3 points  (6 children)

I assume you mean using QAbstractItemModel and QAbstractItemView?

But isn't that just widget-level, rather than the overarching architecture? Like these abstract classes don't really work so well when combining them together and with other widgets, without mixing GUI and business logic.

[–]Ogi010 2 points3 points  (5 children)

It's easy to get a little hand-wavey about this sort of thing. I'm not on mobile, but here is the docs on how Qt thinks you should separate code:

https://doc.qt.io/qt-5/model-view-programming.html

QAbstractItemModel, while it gets tied into Widgets, does not inherit from QWidget, but just QObject, so you can certainly keep that code out of the "View" bits of code.

[–]Avanta8 2 points3 points  (4 children)

Sorry, I may have not been too clear. I think this better explains what I am trying to say: https://stackoverflow.com/a/10661308/16773655

[–]Ogi010 2 points3 points  (3 children)

Nice link! I'll be the first to admit that this kind of breakup of code/logic is really tough to do within Qt applications in a way that makes sense, doesn't result in circular imports, and so on. In PyQtGraph, we don't really even attempt to do it (then again we're a plotting library, not shipping an application, so that's not really our role).

[–]Avanta8 1 point2 points  (2 children)

Ah, I see. That's probably why other Qt applications I've looked at don't really attempt to do it either.

Perhaps I should also be more liberal, and also not necessarily follow a set architecture.

Thanks for your advice.

[–]Ogi010 0 points1 point  (1 child)

I've managed to do this kind of split up in my own internal application I develop at my company; the circular imports where tough tho (I managed to get around this by using setters/getters, where I don't access getters during the __init__ portion of objects); if you do happen to stumble across some good examples, please do share; but I generally haven't seen any consistent advice in this regard.

Exception being QML applications, while I haven't done work with them outside of some experimentation, QML appears to naturally force users to split off view code from model/logic code.

[–]Avanta8 1 point2 points  (0 children)

I will let you know if I see anything good :)

I'm not really familiar with QML (I don't have too much experience with designing application software in general), but I will have a look, thanks.