Qt Drag & Drop со своими виджетами? - PullRequest
0 голосов
/ 20 сентября 2010

Я создал небольшой виджет самостоятельно, включая QProgressBar и QLabel в QVBoxLayout. Он также имеет функцию, которая возвращает текст метки (самостоятельно созданный). Теперь в моем MainWindow есть два других QHBoxLayouts, и я хочу перетащить свой виджет из одного в другой. Это также работает, когда я нажимаю на небольшое свободное пространство между QLabel и QProgressBar. Но когда я нажимаю на один из них напрямую, приложение падает и мучительно сгорает.
Я также знаю, где это терпит неудачу. Мой mousePressEvent выглядит так:

void DragDrop::mousePressEvent(QMouseEvent *event) {

// !!!!---- make sure ONLY MyWidgets are here, else: CRASH ----!!!!
    MyWidget *child = static_cast<MyWidget*>(childAt(event->pos()));
    if (!child)
    return;

qDebug() << child->returnLabelText();
...

}

Поэтому, когда я нажимаю на ProgressBar, он вызывает ProgressBar, а не мой собственный виджет. И потому что QProgressBar не имеет функции, подобной returnLabelText() (но мой виджет делает это), он завершается ошибкой.
Какой лучший способ получить мой виджет?

1 Ответ

2 голосов
/ 20 сентября 2010

QWidget :: childAt (int, int) возвращает виджет child , а не родительский виджет. В вашем случае он возвращает QProgressBar. Затем вы пытаетесь привести в MyWidget, что это не так. То, что вы ищете, для родителя QProgressBar (или QLabel).

static_cast не проверяет тип объекта, который вы пытаетесь привести, и всегда будет давать ненулевой указатель, даже если приведение неверно. Здесь вы ищете dynamic_cast, который вернет NULL, если объект не того типа, который вы ищете. Поскольку вы ищете родителя (или предка) виджета, по которому вы щелкаете, вы можете использовать цикл, чтобы перебрать родословную виджета, по которому щелкнули, чтобы найти экземпляр MyWidget, который вы ищете.

void DragDrop::mousePressEvent(QMouseEvent *event) {
  QWidget *widget = childAt(event->pos());
  do {
    MyWidget *myWidget = dynamic_cast<MyWidget*>(widget);
    widget = widget->parentWidget();
  } while (myWidget == NULL && widget != NULL)
  if (myWidget == NULL)
    return;

  qDebug() << myWidget->returnLabelText();
  // ...
}
...