Important: Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

How to edit a QListwidgetItem by using custom context menu ? need some corrections



  • I have a QListWidget named xml_scripts_textbox with some items in my UI, and when i right click on an item in my qlistwidget, a custom context menu appears, and one of the option of this context menu is "Edit the List item", so when this is clicked , i want that particular item in qlistwidget to be editable for once,

    How can i do this ?

    The code i have tried so far is

    context menu code

    void MainWindow::on_xml_scripts_textbox_customContextMenuRequested(const QPoint& pos)
    {
        QMenu* rMenu = new QMenu(this);
        QAction* edit = new QAction(tr("Edit the List item"), this);
    
        rMenu->addAction(edit);
        connect(edit, SIGNAL(triggered()), this, SLOT(edithelp()));
        rMenu->exec(cursor().pos());
    }
    

    code for edithelp(), the slot function which will make the listitem editable

    void MainWindow::edithelp()
    {
        QListWidgetItem* item_1 = ui->xml_scripts_textbox->takeItem(ui->xml_scripts_textbox->currentRow());
        item_1->setFlags(Qt::ItemIsEditable);  //still not getting editable ?? why ??
    }
    


    1. Why do you use takeItem? It will remove the item from the list widget (but not deleting it).
    2. setFlags(Qt::ItemIsEditable) only set the flag, it won't make it become editing state. And using it like that will also clear other flags.
      "Editable" doesn't mean it is in editing state, it means that the item can be triggered to enter editing state.

    To edit a item, first, do not set the flag only when you want to edit it. Set the flag when it should be editable.
    If it should be editable from the beginning, then set the flag when you create it like

    QListWidgetItem* item = new QListWidgetItem(ui->xml_scripts_textbox);
    item->setFlags(item->flags() | Qt::ItemIsEditable);
    

    Then in the edit slot, do something like

    if(QListWidgetItem *item_1 = ui->xml_scripts_textbox->currentItem()) {
        ui->xml_scripts_textbox->editItem(item_1);
    }
    

    In addition:

    1. currentItem() / currentRow() is not the best choice in this situation. Better to consider getting the item from the pos of customContextMenuRequested(const QPoint &pos).
    2. There's memory leak. Every right click will create a new QMenu, and they won't be deleted until MainWindow destroys. Since you are using the blocking exec(), you could delete the menu right after exec().
    3. By default, double clicking an item will trigger editing when it is editable, if you don't want that, set the editTriggers of your list widget.


    1. Why do you use takeItem? It will remove the item from the list widget (but not deleting it).
    2. setFlags(Qt::ItemIsEditable) only set the flag, it won't make it become editing state. And using it like that will also clear other flags.
      "Editable" doesn't mean it is in editing state, it means that the item can be triggered to enter editing state.

    To edit a item, first, do not set the flag only when you want to edit it. Set the flag when it should be editable.
    If it should be editable from the beginning, then set the flag when you create it like

    QListWidgetItem* item = new QListWidgetItem(ui->xml_scripts_textbox);
    item->setFlags(item->flags() | Qt::ItemIsEditable);
    

    Then in the edit slot, do something like

    if(QListWidgetItem *item_1 = ui->xml_scripts_textbox->currentItem()) {
        ui->xml_scripts_textbox->editItem(item_1);
    }
    

    In addition:

    1. currentItem() / currentRow() is not the best choice in this situation. Better to consider getting the item from the pos of customContextMenuRequested(const QPoint &pos).
    2. There's memory leak. Every right click will create a new QMenu, and they won't be deleted until MainWindow destroys. Since you are using the blocking exec(), you could delete the menu right after exec().
    3. By default, double clicking an item will trigger editing when it is editable, if you don't want that, set the editTriggers of your list widget.


  • @Bonnie said in How to edit a QListwidgetItem by using custom context menu ? need some corrections:

    editTriggers

    Thanks,

    for point 2 i added this

      QMenu* rMenu = new QMenu(this);
        QAction* rmove = new QAction(tr("Remove"), this);
        QAction* redit = new QAction(tr("Edit"), this);
    
        rMenu->addAction(rmove);
        rMenu->addAction(redit);
        connect(redit, SIGNAL(triggered()), this, SLOT(edithelp()));
        connect(rmove, SIGNAL(triggered()), this, SLOT(removehelp()));
        rMenu->exec(cursor().pos());
    
        //Release the memory
        QList<QAction*> list = rMenu->actions();
        foreach(QAction * pAction, list) delete pAction;
    
        delete rMenu;
    

    but for point 3 ,which edit trigger should i use ??
    can you please elaborate



  • @learnist said in How to edit a QListwidgetItem by using custom context menu ? need some corrections:

    but for point 3 ,which edit trigger should i use ??
    can you please elaborate

    If you don't want double clicking or any key pressing to trigger the editing, just set it to QAbstractItemView::NoEditTriggers.