Emptying a sql table model (or a table view)



  • Hi,
    I've got a QSqlTableModel bound to a QTableViewer, and all works fine. Under some circustance I want the table to become cleared/empty, and possibly even the model. The clear method on the model does not reach the aim, since it releases also the resources, and I need to reselect the data from the model later on. Doing a fake select, like with a wrong filtering, seems to me a waste of resources. I'm not able to find a way to empty the view and/or the model.
    Any idea?



  • your question is not much clear to me.
    do you want to unhide items? or you want to completely release items and model?
    if your model defined as a pointer it should be cleared from memory by
    @delete pointer;@
    and recreated when you want to push new data.



  • [quote author="mohsen" date="1320912678"]your question is not much clear to me.
    do you want to unhide items? or you want to completely release items and model?
    if your model defined as a pointer it should be cleared from memory by
    @delete pointer;@
    and recreated when you want to push new data.[/quote]

    Seriously?

    I believe you would need a Proxy Model.



  • Do you actually want to clear the data in the underlying database as well?
    If so, just issue the SQL command to clear the table, and then refresh the model by re-setting the query on it.



  • I don't want to empty the table, only the view connected to the model.
    In a certain point in my code I do something like:

    @tableModel->select();@

    and therefore the data in the table is again visible. I want then to clear the table view, as the select was never issued on the model. I will do the select later on on the model again.



  • You have to make the model say to the view that it has no elements.



  • [quote author="veeeee_d" date="1320919201"]You have to make the model say to the view that it has no elements.[/quote]

    Ok, do you have an idea about how to achieve it?



  • Would just setting 0 as the model for your view be enough?



  • Yes it works, even if not as I was expecting. I set to NULL the model in the table view, but then something happened to the model itself, that lost its table association (maybe a reparenting?). So when I wanted to use the same model again I have to specify the table on which the model operates before the select is performed.



  • No, that's not the way to go. These "Qt Specialits" are doubtful at times, really...
    You can just keep the model to yourself and make a model that you can set as not retrieving information, for instance. For that, you can read "this":http://doc.qt.nokia.com/latest/model-view-programming.html#creating-new-models
    The best way is to simply subclass the model you're currently using and [b]only[b/] changing the [b]data[/b] function.



  • [quote author="veeeee_d" date="1320934162"]No, that's not the way to go. These "Qt Specialits" are doubtful at times, really...
    You can just keep the model to yourself and make a model that you can set as not retrieving information, for instance. For that, you can read "this":http://doc.qt.nokia.com/latest/model-view-programming.html#creating-new-models
    The best way is to simply subclass the model you're currently using and [b]only[b/] changing the [b]data[/b] function.[/quote]
    Good to know your opinion on Qt Specialists, especially if you give wrong advice yourself. If you only reimplement the data method, then the model will not appear to be empty.



  • [quote author="veeeee_d" date="1320934162"]No, that's not the way to go. These "Qt Specialits" are doubtful at times, really...
    [/quote]

    First of all, people in this (and other) forums are giving their time to help other not specialist people like I am. I will not be so rude in replying, since I could have express my will in a bad form or they could have not fully understood it. That's has nothing to do with programming skills!

    Coming back to my problem, as I stated setting the model to null in the view worked, except that it seems that also the model is unbound from the table it has previously selected. Maybe this is a normal behavior of the model life cycle, but it seems quite strange to me.
    And yes, I'd like to find a solution simpler even than subclassing, because I think there is enough implemented code to do almost what I need in this case. Of course, if I'm wrong please correct me.



  • I'm in no way being rude, but this is the third time someone suggests getting the model detached from the view, which I find quite awkward. There's no simpler way to do that, since the view draws the items it shows from the model. Subclassing your model and replacing ONE function is a no-go?



  • If you don't want a view to display the contents of a model, then it seems obvious to me that you detach the two. Subclassing the model to give the impression that it is empty when it is not seems like a stranger solution than that, at least to my limited perspective.

    An alternative may be to manipulate the view itself to not display anything. You could probably achieve that by subclassing as well (reimplementing paintEvent comes to mind...) or by simply calling QTableView::hideRow for all rows (no idea how efficient that is).

    What I don't get, is that the model itself seems to be changing after it is no longer the model for a view. I don't see how that could be happening.



  • [quote author="Andre" date="1320941266"]
    What I don't get, is that the model itself seems to be changing after it is no longer the model for a view. I don't see how that could be happening.[/quote]

    The application works as follows: I've got two tableview attached to two sqltablemodel. One view (with its model) is a "master" view, which selection filters the model (and therefore the view) "slave". When I do a full refresh on the master view (and therefore the model) I want the slave view (and model) to clear because I'm also clearing the selection on the master view. But I don't like to do an empty query (i.e., a query that is not going to report any result) for the salve model just because I don't have a selection active on the master, since this means a roundtrip to the database to produce a well know result set (the empty one). On the other hand when a row is selected after the refresh on the master view, the slave model must continue to produce a filtered query and update its view. That is why I was searching for a solution that did not discard the slave model, but simply "detaches" it from the view temporarily, so that the view becomes empty while the user selects something on the master one.
    But maybe there is even a smart way of achieving this.



  • As a model can be attached to multiple views, I don't believe that the internals are reset after detaching it from one view. You could check that by attaching the model to a second, temporary view.

    But as a better solution to your problem: Did you try calling "QSqlQueryModel::clear() ":http://doc.qt.nokia.com/4.7/qsqlquerymodel.html#clear on your secondary model? I did not check myself, but just dug in the API docs and came across this.

    And with every advice from the specialists, take it with special care ;-)



  • This is what I found.
    If I set NULL the model in the table view all the table view is cleared, but then I have to remind the model which table it has to attach to. If I call clear() the table view is emptied, but the rows are cleared and not hidden, that is I can see all the rows and cells but empty. While it suffices for me, it is not good to see an empty table, it should be better to see an empty view. Anyway, if I don't remind the model which table its belong to (using setTable() ), I can no more select anything from the model. This is correct with regard to the documentation, that states that the clear method will release the resources (and I think it means the underlying database cursor).
    So the only thing that remains to resolve is to remove also the table grid when the model is cleared.
    Any idea?



  • Hm. By calling clear(), I would expect that at least the row count is reset. I'd recommend opening a bug report on "Jira":http://bugreports.qt.nokia.com.

    I don't know if it works with editing, but for a read only view, you could consider using a proxy model between the table view and the table model. If signalled "show nothing", that would just return a rowCount of 0 (and send some xxxchanged signals).



  • I found something interesting, I hope someone can explain me what am I doing wrong.
    Now, in a table I've a slot connected to currentRowChanged signal, so that when a row on the master table is selected, the slave table is updated (i.e., filtered). The slot attached to the signal is like the following:

    @if( modelIndex.isValid() ){
    // filter

        }
    }
    else{
            doSlaveClean();
        }
    

    @

    and the doSlaveClean method removes the model from the view and calls clear:

    @void BasePerspective::doSlaveClean()
    {
    tableView->setModel( NULL );
    tableModel->tableName();

    }@

    Now, this works fine if the doSlaveClean is called only once per slot execution. I mean, when a row is de-selected in the master table, the signal is emitted, the slot calls doSlaveClean and the table is cleaned without loosing the table name. If, within the same slot, I call another time doSlaveClean, the table model appears not to be bound to a table. Is this a kind of concurrency problem of the signal/slot mechanism? Now, why should I call twice the doSlaveClean? Because I forget that de-selecting a row emits currentRowChanged ...
    Anyone can give me an hint about this?


Log in to reply
 

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