In my raster drawing program I need to create a layers interface like in Photoshop or Sketchbook Pro. I read the documentation and figured out that I have to use QTreeView. But I didn't find a lot of information in the documentation about creating QTreeView with custom widgets. So:
1) How to insert custom widgets into tree view?
2) What is the difference between QTreeView and QTreeWidget?
3) What is the difference between QAbstractItemModel and qitemdelegate?
4) Any examples/articles/guides?
5) Maybe I should use something else?
QTreeWidget is a model and a view in one class, it's called a convenience view. It works against the good practice of separatng the views and the models, and probably shouldn't be used in a system where the notion of document layers belongs in the document handling code.
QTreeView is just a view, without any bundled models. When you have a model, you can set it on a view, making the view display the model.
A QAbstractItemModel is the data model. It has nothing to do with views or delegates at all - the model can exist and be useful without a view at all.
A delegate provides display and editing widgets for items of data in a view. It is a property of the view, not of the model. Different views can show the same model using different delegates, all at the same time.
Although the delegate lets you provide the custom widgets you're after, its use may be unnecessary. If the item you display has static contents, you can simply provide a QImage or a QPixmap as the data.
Special for your case (5): DON'T use any of QTreeView, QStandardItemModel and other such classes. If you need interaction with widgets + if you need widgets to be animated then you should use simple QScrollArea with QVBoxLayout inside of it.
Qt MVC is designed to process big amount of cognate data. It is not designed to provide widget-based interaction. So, if you want to "assign" one widget to each item and to interact with them - you will have a lot of problems with implementing delegates (tracking mouse events, providing editor's factory). Ofc, you may create your own delegates with custom drawing and custom processing of mouse events, but it's much easy to use simple widgets.
Related
I created my own data model based on QAbstractListModel and connected it with QListView by simple ui->listView->setModel(prodModel) - it works fine.
Now I want to create custom view in QListView for each item. For example, I want to reach that every data row from model will be shown in style like Stack Overflow (question with rating). I want to use Qt widgets and arrange it on my own idea - using layouts etc.
Unfortunately, a Qt's guide about model/view doesn't have described how to use QItemDelegate to show my widgets - I'm not interested about editing data in view (but I want to interact like click - ideally if I could click and get signal/sth in each widget in my custom view).
I found some examples, but they describe drawing only one widget (QProgressBar) without any layouts.
Any help will be appreciable, thanks!
I have a collection of images, dynamically generated through QGraphicsView widgets, and i'd like my users to choose between them. For that purpose, i would display inside a custom widget available images in some kind of grid and have users click the one they are interested in.
Multiple questions arise :
is there an existing widget that already fits this purpose ?
should i find a way to disable all mouse event handling by QGraphicsView items, or could i add a transparent widget in front of graphic views which would intercept them ?
is there a performance issue displaying many QGraphicsView widgets (up to a few hundreds) ? Should i export them to plain images first ?
First off, no, there's no widget designed specifically for that purpose.
I don't think you are grasping what QGraphicsView is for. It's for displaying a QGraphicsScene, which is meant to hold many QGraphicsItems. Based on your post, I can't see why you would need multiple QGraphicsViews. You can simply have one QGraphicsView and display many images inside of its scene. For example, see QGraphicsPixmapItem.
You definitely should not have hundreds of QGraphicsViews. You probably just want one (although a few could be justified in certain circumstances), in which you display many QGraphicsItems in a QGraphicsScene. You can definitely have hundreds of QGraphicsItems visible at once. In your case, you probably want QGraphicsPixmapItems, which are a subclass of QGraphicsItem. You could even have multiple QGraphicsScenes, and display whichever one is relevant using QGraphicsView::setScene. If you want the user to be able to select an image from a grid, and then work with that image, I would look to the State Pattern.
I can't think of any reason to disable mouse handling in QGraphicsViews, QGraphicsScenes, or QGraphicsItems. Why should these not handle their own mouse events? You can (and should, where necessary) subclass them and reimplement mousePressEvent, mouseMoveEvent, mouseRelease event, etc. to obtain the functionality you want.
Good luck!
I have a few different QGlWidget based display widgets which I need to embed in either an MDI or QDockwidget based app. But I need to handle some of the MDI/Dock specific events (minimize/dock etc) in my display widget
Options are:
Multiply inherit the display widgets from QGlWidget and QMdiSubWindow/QDockWidget. Any issues with multiply inheriting and signals/slots?
Encapsulate the display inside a QMdiSubWindow/QDock derived widget but then I have to wrap all the display's external functions in the Mdi/Dock wrapper widget.
When I make a new window, create a temporary Mdi/Dock widget, connect all the special signals to slots in the display before attaching the display to it and showing it. But this doesn't work for events.
Some QSignalMapper magic where I can receive QMdiSubWindow/QDockWidget specific signals in a QGlWidget
MDI/dock widgets are containers for other widgets, so mixing their features with display widgets is not a very nice solution as you end up with a hideous hybrid widget that looks like a container - but cannot contain anything. Not that Qt would allow it as noted by Jeremy.
If your QGLWidget needs events from it's parent container (e.g. minimize, dock, etc.) why can't you create partner methods in the QGLWidget for them, and call them whenever the action is performed by the parent?
I would like to add an effect of moving rows, like a store, in a QListView using QAnimation.
I use a custom delegate to render things from a QStandardItemModel.
My delegate is a custom widget.
The paint method in the delegate creates the widget, paints it and destroys it. I have no direct access to each custom widget displayed.
Nevertheless, I would like to use setPos() within the animation to move this "not accessible" widget.
Any ideas ?
Thank you
Your description of what you want to achieve is not very clear.
Have you thought of moving the animation into the QListView?
It should have visibility of all items in it's model.
I understand more or less how does MPV works.
But I don't get what classes:
QAbstractItemModel
QAbstractItemView
QAbstractItemDelegate / QItemDelegate
Can do for me?
If that is relevant, I'm using
QGraphicsScene / QGraphicsView with some elements (visual representation of game board) that user can interact with while the interaction logic (game rules) are encapsulated in other class.
AbstractItemModel QAbstractItemView QAbstractItemDelegate
Are from the "Mode/View framework"
This is a very powerful framework for the data part of your application, here is a presentation of the framework.
QAbstractItemModel
Is the base class for the model of the MVC. Has a global interface for accessing and altering the data and takes care of the Observable part.
QAbstractItemView
Is the base class for the view of the MVC. Has aglobal interface for the view/selections part and it takes care of the Observer part. You don't have to worry about the observer pattern, the framework does it for you.
QAbstractItemDelegate
Is the base class for the controller of the MVC.
Is the Strategy pattern for painting, editing the elements, ...
QGraphicsScene / QGraphicsView
Are from the "The Graphics View Framework" and is independent of the Model/View framework.
This is also a very powerful framework for the graphics part.
The Scene
QGraphicsScene provides the Graphics
View scene. The scene has the
following responsibilities:
Providing a fast interface for
managing a large number of items
Propagating events to each item
Managing item state, such as selection
and focus handling Providing
untransformed rendering functionality;
mainly for printing
The View
QGraphicsView provides the view
widget, which visualizes the contents
of a scene. You can attach several
views to the same scene, to provide
several viewports into the same data
set
If you want a Model to be visible in a QGraphicsView than you will have to write your own view based on the QAbstractItemView.
Take a QGraphicsView as view port widget QAbstractScrollArea::setViewport(QWidget * widget)) and then you can
add QAbstractItemView::rowsInserted,
remove QAbstractItemView::rowsAboutToBeRemoved
and change QAbstractItemView::dataChanged
the items in the scene. Don't forget to take care of the reset an layout change events.