1
votes

I have a QListWidget that is in a QGridLayout in my constructor of the Draw class.QGridLAyout contains other elements.

Draw::Draw(QWidget *parent):QDialog(parent){

gridlayout=new QGridLayout;
gridlayout->addLayout(hbox,0,0);
gridlayout->addLayout(hbox1,1,0);
gridlayout->addLayout(hbox2,2,0);
gridlayout->addWidget(listWidget,3,0);
gridlayout->addLayout(hbox4,4,0);
this->setLayout(gridlayout);

}

When clicking on a QPushButton. I'm calling a slot that filled the QListWidget.

//SLOT

void Draw::fillListWidget(){
//item is QListWidgetItem
item=new QListWidgetItem;
item->setSizeHint(QSize(0,50));
listWidget->addItem(item);
//WidgetfillListWidget is an other class with parameters for the QListWidget
listWidget->setItemWidget(item,new WidgetfillListWidget(label1,path));

}

In my other class I build the new QWidget to fill the QlistWidget. The QListWidget contains a label, a string and a QPushButton.

WidgetfillListWidget::WidgetfillListWidget(QString label, QString p){

instanceDraw=new Draw(this);
QString name = label;
QString path = p;

name1=new QLabel(name,this);
path1=new QLineEdit(path,this);
remove=new QPushButton("remove",this);

hboxlist=new QHBoxLayout;
hboxlist->addWidget(name1);
hboxlist->addWidget(path1);
hboxlist->addWidget(remove);

setLayout(hboxlist);
connect(remove,SIGNAL(clicked()),instanceDraw,SLOT(removeItem()));
}

In the Draw class I have the slot that has to delete an item but it does not work

void Draw::removeItem(){
listWidget->takeItem(listWidget->row(item));
}

Deleting the item does not work. I think it comes from my Draw object in the connect. But I do not understand how to solve the problem. Does someone have an idea?

1
takeItem removes and returns the item from the given row , then you will have to delete it by yourself delete listWidget->takeItem(listWidget->row(item));Simon
I have a segmentation error. I may have a problem with my instance of the Draw class?Tom13000
@Thomas1314 Why are you adding a QString as a Widget? path1=new QString(path,this); hboxlist->addWidget(path1);eyllanesc
@eyllanesc excuse me. I was wrong. It's a QLineEdit ....Tom13000
But the problem remains the same...Tom13000

1 Answers

0
votes

The problem is because the Draw created in WidgetfillListWidget is different from the original Draw, they are 2 different objects.

In this case the solution is to create a clicked signal in WidgetfillListWidget that is issued when the QPushButton is pressed.

Then that signal is connected to the removeItem() method. In it we must obtain the item, but that is not simple, one way to do it is through the geometric position as I show below:

widgetfilllistwidget.h

#ifndef WIDGETFILLLISTWIDGET_H
#define WIDGETFILLLISTWIDGET_H

#include <QWidget>

class QLabel;
class QPushButton;
class QHBoxLayout;
class QLineEdit;

class WidgetfillListWidget : public QWidget
{
    Q_OBJECT
public:
    explicit WidgetfillListWidget(const QString & name, const QString &path, QWidget *parent = nullptr);
signals:
    void clicked();
private:
    QLabel *lname;
    QLineEdit *lpath;
    QPushButton *premove;
    QHBoxLayout *hboxlist;
};

#endif // WIDGETFILLLISTWIDGET_H

widgetfilllistwidget.cpp

#include "widgetfilllistwidget.h"

#include <QHBoxLayout>
#include <QLabel>
#include <QLineEdit>
#include <QPushButton>

WidgetfillListWidget::WidgetfillListWidget(const QString &name, const QString & path, QWidget *parent) : QWidget(parent)
{
    lname=new QLabel(name);
    lpath=new QLineEdit(path);
    premove=new QPushButton("remove");

    hboxlist=new QHBoxLayout(this);
    hboxlist->addWidget(lname);
    hboxlist->addWidget(lpath);
    hboxlist->addWidget(premove);
    connect(premove, &QPushButton::clicked, this, &WidgetfillListWidget::clicked);
}

draw.h

#ifndef DRAW_H
#define DRAW_H

#include <QDialog>

class QGridLayout;
class QListWidget;
class QPushButton;

class Draw : public QDialog
{
    Q_OBJECT

public:
    Draw(QWidget *parent = 0);
    ~Draw();
private:
    void fillListWidget();
    void removeItem();

    QGridLayout *gridlayout;
    QListWidget *listWidget;
    QPushButton *button;
};

#endif // DRAW_H

draw.cpp

#include "draw.h"
#include "widgetfilllistwidget.h"

#include <QGridLayout>
#include <QListWidget>
#include <QPushButton>

Draw::Draw(QWidget *parent)
    : QDialog(parent)
{
    button = new QPushButton("Press Me");
    listWidget = new QListWidget;
    gridlayout=new QGridLayout(this);
    gridlayout->addWidget(listWidget, 0, 0);
    gridlayout->addWidget(button, 1, 0);
    connect(button, &QPushButton::clicked, this, &Draw::fillListWidget);
}

void Draw::fillListWidget()
{
    QListWidgetItem *item=new QListWidgetItem;
    item->setSizeHint(QSize(0,50));
    listWidget->addItem(item);
    //WidgetfillListWidget is an other class with parameters for the QListWidget
    QString label = "label1";
    QString path = "label2";
    WidgetfillListWidget *widget = new WidgetfillListWidget(label,path);
    listWidget->setItemWidget(item, widget);
    connect(widget, &WidgetfillListWidget::clicked, this, &Draw::removeItem);
}

void Draw::removeItem()
{
    WidgetfillListWidget *widget = qobject_cast<WidgetfillListWidget *>(sender());
    if(widget){
        QPoint gp = widget->mapToGlobal(QPoint());
        QPoint p = listWidget->viewport()->mapFromGlobal(gp);
        QListWidgetItem *item = listWidget->itemAt(p);
        item = listWidget->takeItem(listWidget->row(item));
        delete item;
    }
}

Draw::~Draw()
{

}