Qt開發:QListWidget的介紹和使用

文章目錄

    • 一、QListWidget的簡介
    • 二、QListWidget的基本用法
    • 三、QListWidget的數據操作
      • 2.1 插入數據
      • 2.2 查找數據
      • 2.3 選項設置
    • 四、QListWidget的信號與槽

一、QListWidget的簡介

??QListWidget 是 Qt 框架中用于顯示和操作條目列表的控件,它是 QListView 的一個子類,提供了更高層級的封裝,允許你以面向 item 的方式 管理列表內容。

二、QListWidget的基本用法

#include <QListWidget>
#include <QDebug>MainWindow::MainWindow(QWidget *parent): QWidget(parent)
{this->setFixedSize(800, 600);QListWidget* listWidget = new QListWidget(this);// 添加文本項listWidget->addItem("Apple");listWidget->addItem("Banana");// 添加帶圖標的項QListWidgetItem* item = new QListWidgetItem(QIcon(":/icons/pineapple.png"), "Pineapple");listWidget->addItem(item);// 設置多選模式listWidget->setSelectionMode(QAbstractItemView::MultiSelection);// 響應點擊事件connect(listWidget, &QListWidget::itemClicked, this, [](QListWidgetItem* item){qDebug() << "你點擊了: " << item->text();});
}

三、QListWidget的數據操作

2.1 插入數據

2.1.1 void QListWidget::addItem(const QString &label)
作用:用于向列表中添加一個文本條目。
參數:label:要顯示的文本內容(QString 類型)。

效果:

  • 在列表末尾添加一個新項,內容為 label。
  • 內部自動創建一個 QListWidgetItem 并加入 QListWidget。

示例用法:

QListWidget* listWidget = new QListWidget(this);// 添加幾個條目
listWidget->addItem("蘋果");
listWidget->addItem("香蕉");
listWidget->addItem("葡萄");

2.1.2 void QListWidget::addItems(const QStringList &labels)
作用:用于批量添加多個條目到列表中,每個條目都是一個文本項。
參數:labels:一個 QStringList 類型的字符串列表,每個字符串會變成一個條目。

示例用法:

QStringList fruits;
fruits << "蘋果" << "香蕉" << "葡萄" << "橘子";QListWidget* listWidget = new QListWidget(this);
listWidget->addItems(fruits);

這將向列表中依次添加 4 個條目,文本分別是 “蘋果”、“香蕉”、“葡萄” 和 “橘子”。

2.1.3 void QListWidget::addItem(QListWidgetItem *item)
作用:用于向列表中添加一個自定義的條目對象。
參數:item:指向一個 QListWidgetItem 對象的指針,表示你要添加的條目。

效果:

  • 將該條目插入到列表末尾。
  • QListWidget 會自動接管該對象的所有權,無需手動釋放。

示例用法:添加帶圖標和自定義樣式的項

QListWidget* listWidget = new QListWidget(this);// 創建一個自定義的條目
QListWidgetItem* item = new QListWidgetItem(QIcon(":/icons/star.png"), "重要任務");// 設置附加樣式
item->setFont(QFont("Microsoft YaHei", 12, QFont::Bold));
item->setForeground(Qt::red);
item->setBackground(Qt::yellow);
item->setToolTip("這是一個高優先級任務");// 添加到列表中
listWidget->addItem(item);

使用 setData() 來綁定自定義數據:
在 Qt 中,setData() 是 QListWidgetItem 的成員函數,用于將自定義數據綁定到某個列表項上,便于后續查找、操作或傳遞附加信息。

函數原型:

void QListWidgetItem::setData(int role, const QVariant &value);

參數說明:

  • role:數據的“角色”,例如 Qt::UserRole、Qt::DisplayRole
  • value:任意類型的數據,必須能被包裝成 QVariant(如 int, QString, bool, QPointF, 自定義結構體等)

常用角色:

  • Qt::UserRole:開發者自定義使用的第一個角色。
  • Qt::UserRole + 1, +2, …:可自定義多個字段。
  • Qt::DisplayRole:值為0,控制 item 的主顯示文本。
  • Qt::ToolTipRole:值為3,控制鼠標懸停提示。

示例:綁定一個 ID 到列表項

QListWidget* listWidget = new QListWidget(this);QListWidgetItem* item = new QListWidgetItem("任務一");
item->setData(Qt::UserRole, 101); // 綁定任務 ID
listWidget->addItem(item);// 點擊時讀取 ID
connect(listWidget, &QListWidget::itemClicked, this, [](QListWidgetItem* item){int taskId = item->data(Qt::UserRole).toInt();qDebug() << "點擊任務 ID:" << taskId;
});

進階用法:綁定多個字段

QListWidgetItem* item = new QListWidgetItem("設備 A");
item->setData(Qt::UserRole, 42);              // 設備ID
item->setData(Qt::UserRole + 1, "在線");      // 狀態
item->setData(Qt::UserRole + 2, QColor("green"));  // 狀態顏色
listWidget->addItem(item);

讀取方式:

int deviceId = item->data(Qt::UserRole).toInt();
QString status = item->data(Qt::UserRole + 1).toString();
QColor color = item->data(Qt::UserRole + 2).value<QColor>();

自定義結構體綁定:
如果你有一個結構體,也可以用 QVariant 包裝它,只要注冊了類型:

struct TaskInfo {int id;QString name;
};
Q_DECLARE_METATYPE(TaskInfo)

注冊類型:

qRegisterMetaType<TaskInfo>("TaskInfo");

綁定使用:

TaskInfo info = {123, "檢查任務"};
QVariant var;
var.setValue(info);QListWidgetItem* item = new QListWidgetItem("任務123");
item->setData(Qt::UserRole, var);

如何注冊自定義結構體到 QVariant?

步驟一:定義并聲明結構體
1.定義結構體并使用 Q_DECLARE_METATYPE

struct TaskInfo {int id;QString name;
};
Q_DECLARE_METATYPE(TaskInfo)  // 必須放在 struct 定義之后

Q_DECLARE_METATYPE 告訴 Qt 怎么將 TaskInfo 包裝進 QVariant。

步驟二:注冊類型
2. 在主函數或初始化階段注冊

#include <QMetaType>// 一般在 main() 或 QApplication 初始化前注冊
int main(int argc, char *argv[]) {qRegisterMetaType<TaskInfo>("TaskInfo");QApplication app(argc, argv);...
}

如果只打算把它塞進 QVariant(不跨線程、不用信號槽傳輸),可以省略 qRegisterMetaType,只用 Q_DECLARE_METATYPE。

示例:綁定結構體到 QListWidgetItem

TaskInfo task{101, "圖像識別任務"};QVariant v;
v.setValue(task);QListWidgetItem* item = new QListWidgetItem(task.name);
item->setData(Qt::UserRole, v);
listWidget->addItem(item);

讀取時還原結構體:

QVariant v = item->data(Qt::UserRole);
TaskInfo task = v.value<TaskInfo>();
qDebug() << "ID:" << task.id << " Name:" << task.name;

2.1.4 void QListWidget::insertItem(int row, QListWidgetItem *item)
作用:用于在指定位置插入一個自定義的條目(QListWidgetItem)。

參數說明:

  • row:插入位置的行索引(從 0 開始)
  • item:要插入的條目對象指針(QListWidgetItem*)

使用示例:

QListWidget* listWidget = new QListWidget(this);// 添加幾個初始條目
listWidget->addItem("蘋果");
listWidget->addItem("香蕉");// 創建要插入的新條目
QListWidgetItem* item = new QListWidgetItem("插入的葡萄");// 插入到索引 1 的位置(即“香蕉”之前)
listWidget->insertItem(1, item);

插入后,列表將變為:
在這里插入圖片描述
示例:在當前選中項上方插入

int row = listWidget->currentRow();  // 獲取當前選中行
QListWidgetItem* newItem = new QListWidgetItem("新任務");
listWidget->insertItem(row, newItem);

2.1.5 void QListWidget::insertItem(int row, const QString &label)
作用:用于在指定位置插入一個文本條目。

參數說明:

  • row:插入位置的索引,從 0 開始計數。
  • label:要插入的條目顯示文本(QString 類型)

使用示例:

QListWidget* listWidget = new QListWidget(this);// 添加初始條目
listWidget->addItem("第一項");
listWidget->addItem("第三項");// 在第 1 行插入“第二項”
listWidget->insertItem(1, "第二項");

2.1.6 void QListWidget::insertItems(int row, const QStringList &labels)
作用:用于批量在指定位置插入多個純文本條目。

參數說明:

  • row:插入起始位置索引(從 0 開始)
  • labels:一組要插入的字符串(QStringList)

示例:在指定位置插入多個條目

QListWidget* listWidget = new QListWidget(this);// 初始添加兩個條目
listWidget->addItem("星期一");
listWidget->addItem("星期五");// 要插入的新項
QStringList midWeek = { "星期二", "星期三", "星期四" };// 插入到索引 1(即“星期五”之前)
listWidget->insertItems(1, midWeek);

輸出結果:
在這里插入圖片描述

2.2 查找數據

2.2.1 QListWidgetItem *QListWidget::currentItem() const
作用:

  • 如果當前列表中有一項被選中,它將返回指向該項的指針。
  • 如果沒有項被選中,返回 nullptr。
  • “當前項”并不一定是“多選”狀態下選中的所有項之一,而是焦點所在的那一項。

使用示例:

QListWidget *listWidget = new QListWidget(this);// 添加一些項
listWidget->addItem("蘋果");
listWidget->addItem("香蕉");
listWidget->addItem("橘子");// 獲取當前項
QListWidgetItem *item = listWidget->currentItem();
if (item) {qDebug() << "當前選中的項是:" << item->text();
} else {qDebug() << "當前沒有選中任何項";
}

可以在信號 currentItemChanged(QListWidgetItem *current, QListWidgetItem *previous) 中使用它,
例如:

connect(listWidget, &QListWidget::currentItemChanged,this, [](QListWidgetItem *current, QListWidgetItem *previous){if (current) {qDebug() << "新選中項:" << current->text();}
});

2.2.2 int QListWidget::currentRow() const
作用:
獲取當前被選中的項在列表中的行號(從 0 開始計數)。

  • 如果列表中當前有選中的項,它返回該項的索引(行號)。
  • 如果沒有任何項被選中,則返回 -1。

使用示例:

QListWidget *listWidget = new QListWidget(this);// 添加一些項
listWidget->addItem("第一行");
listWidget->addItem("第二行");
listWidget->addItem("第三行");// 設置當前選中第二項(行號 1)
listWidget->setCurrentRow(1);// 獲取當前選中的行號
int row = listWidget->currentRow();
qDebug() << "當前選中項的行號是:" << row;

結合 currentItem() 一起使用:

QListWidgetItem *item = listWidget->currentItem();
int row = listWidget->currentRow();if (item && row != -1) {qDebug() << "當前項內容:" << item->text();qDebug() << "當前項所在行號:" << row;
}

2.2.3 QListWidgetItem *QListWidget::item(int row) const
作用:

  • 數 row 是項在列表中的索引,從 0 開始。
  • 如果索引有效(0 ≤ row < count),返回對應項的指針。
  • 如果索引越界,返回 nullptr。

使用示例:

QListWidget *listWidget = new QListWidget(this);// 添加項
listWidget->addItem("A");
listWidget->addItem("B");
listWidget->addItem("C");// 獲取第 1 行(第二項)
QListWidgetItem *item = listWidget->item(1);
if (item) {qDebug() << "第1行的項是:" << item->text();  // 輸出 "B"
} else {qDebug() << "行號無效,未找到項。";
}

常見用途:
遍歷所有項:

for (int i = 0; i < listWidget->count(); ++i) {QListWidgetItem *item = listWidget->item(i);qDebug() << "第" << i << "行的內容:" << item->text();
}

設置某一行文本:

QListWidgetItem *item = listWidget->item(2);
if (item)item->setText("新內容");

2.2.4 QListWidgetItem *QListWidget::itemAt(const QPoint &p) const
作用:
返回在 QListWidget 中,指定坐標 p(窗口坐標)下的項(QListWidgetItem*)。

  • 參數 p 是一個 QPoint,表示相對于 QListWidget 視圖坐標系統中的一個點(例如鼠標點擊的位置)。
  • 如果該位置有對應的項,則返回該項的指針;
  • 如果該位置沒有任何項(空白區域),則返回 nullptr。

使用示例:

void MyWidget::mousePressEvent(QMouseEvent *event)
{QPoint pos = event->pos();  // 獲取點擊的位置QListWidgetItem *item = myListWidget->itemAt(pos);if (item) {qDebug() << "點擊了項:" << item->text();} else {qDebug() << "點擊的是空白區域";}
}

注意:如果在外部控件中處理鼠標事件,可能需要將坐標從全局或父窗口坐標轉換到 QListWidget 的局部坐標,
例如:

QPoint localPos = listWidget->mapFromGlobal(QCursor::pos());
QListWidgetItem *item = listWidget->itemAt(localPos);

2.2.5 QListWidgetItem *QListWidget::itemAt(int x, int y) const
作用:
返回位于 QListWidget 中指定坐標位置 (x, y) 的項指針(QListWidgetItem*)。

  • x 和 y 是相對于 QListWidget 視圖的坐標(通常來源于鼠標事件)。
  • 如果該位置有一項,則返回該項的指針;
  • 如果該位置是空白區域,則返回 nullptr。

使用示例:

void MyWidget::mousePressEvent(QMouseEvent *event)
{int x = event->x();int y = event->y();QListWidgetItem *item = myListWidget->itemAt(x, y);if (item) {qDebug() << "你點擊了項:" << item->text();} else {qDebug() << "你點擊了空白區域";}
}

2.2.6 QWidget *QListWidget::itemWidget(QListWidgetItem *item) const
作用:
獲取與指定 QListWidgetItem 關聯的自定義子控件(QWidget*)。

  • 如果該 item 使用了 setItemWidget() 設置了一個控件,該函數返回該控件;
  • 如果該項沒有關聯控件,則返回 nullptr;
  • 該函數主要用于實現“列表項嵌套控件”的復雜 UI,例如在列表中顯示按鈕、復選框、進度條等。

使用示例:

// 創建一個 QListWidget 和一個自定義控件
QListWidget *listWidget = new QListWidget(this);
QListWidgetItem *item = new QListWidgetItem(listWidget);QPushButton *button = new QPushButton("點擊我");
listWidget->addItem(item);
listWidget->setItemWidget(item, button);// 獲取這個控件
QWidget *w = listWidget->itemWidget(item);
if (w) {qDebug() << "找到控件類型:" << w->metaObject()->className(); // 輸出 QPushButton
}

典型用途:
實現帶復選框的列表項:

QCheckBox *check = new QCheckBox("選項A");
QListWidgetItem *item = new QListWidgetItem(listWidget);
listWidget->addItem(item);
listWidget->setItemWidget(item, check);

獲取狀態:

QCheckBox *check = qobject_cast<QCheckBox *>(listWidget->itemWidget(item));
if (check && check->isChecked()) {qDebug() << "該項被選中了!";
}

2.2.7 void QListWidget::removeItemWidget(QListWidgetItem *item)
作用:
將綁定在某個 QListWidgetItem 上的子控件(通過 setItemWidget() 設置的 QWidget)從列表項中移除,但不刪除該控件。

  • 該函數不會銷毀控件,只是將它從 QListWidget 的布局中移除。
  • 如果你需要徹底銷毀控件,應該手動調用 delete。

使用示例:

QListWidgetItem *item = new QListWidgetItem(listWidget);
QPushButton *button = new QPushButton("按鈕");
listWidget->addItem(item);
listWidget->setItemWidget(item, button);// 移除控件
listWidget->removeItemWidget(item);// 控件仍然存在,可以手動銷毀
button->deleteLater();

注意事項:

  • removeItemWidget() 不會刪除 QListWidgetItem;
  • 也不會刪除綁定的 QWidget;
  • 被移除的控件不會自動重新顯示在 UI 中,除非你手動添加到別處;
  • 控件的父對象仍是 QListWidget,因此在不需要時應調用 delete 或 deleteLater() 銷毀。

刪除項并清理控件的完整做法:

QWidget *widget = listWidget->itemWidget(item);
listWidget->removeItemWidget(item);
delete widget;  // 或 widget->deleteLater();
delete item;

2.2.8 int QListWidget::row(const QListWidgetItem *item) const
作用:
返回指定 QListWidgetItem* 在 QListWidget 中的行號(索引)。

  • 行號從 0 開始;
  • 如果 item 是當前 QListWidget 中的有效項,則返回其索引;
  • 如果該項不在列表中,返回 -1。

使用示例:

QListWidget *listWidget = new QListWidget(this);// 添加項
QListWidgetItem *item1 = new QListWidgetItem("蘋果");
QListWidgetItem *item2 = new QListWidgetItem("香蕉");
listWidget->addItem(item1);
listWidget->addItem(item2);// 獲取某項所在行號
int index = listWidget->row(item2);
qDebug() << "香蕉在第幾行:" << index;  // 輸出 1

注意事項:

  • 參數必須是 listWidget 中已經存在的項;
  • 如果是新創建的項,還未添加進列表,調用 row() 會返回 -1。

2.2.9 QList<QListWidgetItem *> QListWidget::selectedItems() const

作用:
返回當前所有被選中的 QListWidgetItem* 列表。

  • 支持單選和多選模式;
  • 單選時,返回列表最多包含一個元素;
  • 多選時,返回所有選中項;
  • 無選中項時,返回空列表。

使用示例:

QList<QListWidgetItem *> selectedItems = listWidget->selectedItems();if (selectedItems.isEmpty()) {qDebug() << "沒有選中任何項";
} else {for (QListWidgetItem *item : selectedItems) {qDebug() << "選中項文本:" << item->text();}
}

多選模式設置示例:

listWidget->setSelectionMode(QAbstractItemView::MultiSelection);

注意事項:

  • 返回的是指向項的指針,不是索引;
  • 若需刪除選中項,先使用 takeItem() 移除,再刪除指針。

刪除所有選中項示例:

auto selectedItems = listWidget->selectedItems();
for (auto item : selectedItems) {delete listWidget->takeItem(listWidget->row(item));
}

下面是一個完整的 Qt QListWidget 多選操作示例,演示如何設置多選模式,獲取所有選中項,并執行批量刪除操作。

#include <QApplication>
#include <QListWidget>
#include <QPushButton>
#include <QVBoxLayout>
#include <QWidget>
#include <QDebug>class MyWidget : public QWidget {Q_OBJECT
public:MyWidget(QWidget *parent = nullptr) : QWidget(parent) {listWidget = new QListWidget(this);deleteButton = new QPushButton("刪除選中項", this);// 設置多選模式listWidget->setSelectionMode(QAbstractItemView::MultiSelection);// 添加示例項listWidget->addItem("蘋果");listWidget->addItem("香蕉");listWidget->addItem("橘子");listWidget->addItem("葡萄");listWidget->addItem("西瓜");QVBoxLayout *layout = new QVBoxLayout(this);layout->addWidget(listWidget);layout->addWidget(deleteButton);connect(deleteButton, &QPushButton::clicked, this, &MyWidget::deleteSelectedItems);}private slots:void deleteSelectedItems() {// 獲取所有選中的項QList<QListWidgetItem *> selectedItems = listWidget->selectedItems();if (selectedItems.isEmpty()) {qDebug() << "沒有選中任何項。";return;}// 逐個刪除選中項for (QListWidgetItem *item : selectedItems) {// 先從列表中取出,再delete,避免內存泄漏delete listWidget->takeItem(listWidget->row(item));}}private:QListWidget *listWidget;QPushButton *deleteButton;
};int main(int argc, char *argv[]) {QApplication a(argc, argv);MyWidget w;w.show();return a.exec();
}

2.3 選項設置

2.3.1 void QListWidget::setCurrentItem(QListWidgetItem *item)
作用:
設置指定的 QListWidgetItem* 為當前選中項(即焦點所在項)。

  • 使該項變為當前項,列表視圖會自動滾動到該項;
  • 會觸發 currentItemChanged 信號;
  • 如果傳入 nullptr,表示取消當前項的選中。

使用示例:

QListWidget *listWidget = new QListWidget(this);
listWidget->addItem("蘋果");
listWidget->addItem("香蕉");
listWidget->addItem("橘子");QListWidgetItem *item = listWidget->item(1); // 獲取第二項“香蕉”
listWidget->setCurrentItem(item); // 設置“香蕉”為當前選中項

結合信號使用:

connect(listWidget, &QListWidget::currentItemChanged,this, [](QListWidgetItem *current, QListWidgetItem *previous) {if (current) {qDebug() << "當前選中項變更為:" << current->text();}
});

注意事項:

  • 只設置當前項,不一定改變“選中狀態”(selection)——視 selectionMode 而定;
  • 如果需要同時設置當前項并選中它,可以先調用 setCurrentItem(),然后調用 setItemSelected(item, true)。

選中當前項示例:

listWidget->setCurrentItem(item);
listWidget->setItemSelected(item, true);

2.3.2 void QListWidget::setCurrentItem(QListWidgetItem *item, QItemSelectionModel::SelectionFlags command)
作用:
將指定的 QListWidgetItem* 設置為當前項,并根據 command 參數來控制選中和焦點的行為。

  • 這個重載函數允許更精細地控制當前項的選擇和焦點狀態;
  • command 是 QItemSelectionModel::SelectionFlags 枚舉類型,常用值包括:
    • QItemSelectionModel::Clear — 清除當前選擇;
    • QItemSelectionModel::Select — 選擇項;
    • QItemSelectionModel::Deselect — 取消選擇;
    • QItemSelectionModel::Toggle — 切換選擇狀態;
    • QItemSelectionModel::Current — 設置當前項(焦點項)。

常用組合示例:
僅設置當前項(焦點項),不改變選中狀態:

listWidget->setCurrentItem(item, QItemSelectionModel::Current);

設置當前項并選中它:

listWidget->setCurrentItem(item, QItemSelectionModel::Select | QItemSelectionModel::Current);

取消當前項的選中狀態但仍保持當前焦點:

listWidget->setCurrentItem(item, QItemSelectionModel::Deselect | QItemSelectionModel::Current);

使用示例代碼:

QListWidget *listWidget = new QListWidget(this);
listWidget->addItem("蘋果");
listWidget->addItem("香蕉");
listWidget->addItem("橘子");QListWidgetItem *item = listWidget->item(1); // 第二項“香蕉”// 設置“香蕉”為當前項并選中
listWidget->setCurrentItem(item, QItemSelectionModel::Select | QItemSelectionModel::Current);

2.3.3 void QListWidget::setCurrentRow(int row)

作用:
設置 QListWidget 中指定行號(row)的項為“當前項”。

  • 會觸發 currentItemChanged() 信號;
  • 會自動滾動視圖,使該項可見;
  • 并將焦點移動到該項;
  • 如果 row 超出范圍(小于 0 或大于等于 count),不會改變當前項。

使用示例:

QListWidget *listWidget = new QListWidget(this);
listWidget->addItem("蘋果");
listWidget->addItem("香蕉");
listWidget->addItem("橘子");// 設置第二項為當前項(行號 1)
listWidget->setCurrentRow(1);

結合信號槽使用:

connect(listWidget, &QListWidget::currentItemChanged,this, [](QListWidgetItem *current, QListWidgetItem *previous) {if (current)qDebug() << "當前項變為:" << current->text();
});

注意事項:

  • setCurrentRow() 只設置當前項(有焦點的項),并不影響其他選中項;
  • 若在多選模式下使用,僅更改焦點,不會影響多選狀態;
  • 如果需要選中該項,可結合使用 setItemSelected() 或使用另一個重載版本 setCurrentRow(int, QItemSelectionModel::SelectionFlags)。

2.3.4 void QListWidget::setCurrentRow(int row, QItemSelectionModel::SelectionFlags command)

作用:
設置 QListWidget 中指定行號 row 對應的項為“當前項”,并根據 command 參數控制其選中狀態或行為。這個函數相比 setCurrentRow(int row) 更加靈活,允許通過 QItemSelectionModel::SelectionFlags 控制選擇行為,例如是否選中該行、是否取消其他選中項、是否切換狀態等。

常用的 SelectionFlags:
來自枚舉 QItemSelectionModel::SelectionFlags,常用值如下:
在這里插入圖片描述
使用示例
示例 1:設置某行為當前項并選中

listWidget->setCurrentRow(2, QItemSelectionModel::Select | QItemSelectionModel::Current);

示例 2:設置某行為當前項,但取消選中狀態

listWidget->setCurrentRow(1, QItemSelectionModel::Deselect | QItemSelectionModel::Current);

示例 3:只設置當前項(不選中)

listWidget->setCurrentRow(0, QItemSelectionModel::Current);

示例 4:清除所有選中項并設置新當前項

listWidget->setCurrentRow(3, QItemSelectionModel::Clear | QItemSelectionModel::Select | QItemSelectionModel::Current);

2.3.5 void QListWidget::setItemWidget(QListWidgetItem *item, QWidget *widget)

作用:
將一個 QWidget* 控件嵌入到指定的 QListWidgetItem 項上,使該項顯示為該控件。

  • 這使你可以在 QListWidget 的每一項中使用如按鈕、復選框、進度條等自定義控件;
  • 替代了 QListWidgetItem::setText() 的默認文本顯示方式;
  • 一個項只能綁定一個控件;若再次設置會替換原控件。

基本使用示例:

QListWidget *listWidget = new QListWidget(this);// 創建列表項
QListWidgetItem *item = new QListWidgetItem(listWidget);
listWidget->addItem(item);// 創建控件(如按鈕)并設置到該項上
QPushButton *button = new QPushButton("點擊我");
listWidget->setItemWidget(item, button);

更多控件示例:
顯示復選框

QCheckBox *checkBox = new QCheckBox("選項A");
QListWidgetItem *item = new QListWidgetItem(listWidget);
listWidget->addItem(item);
listWidget->setItemWidget(item, checkBox);

顯示進度條

QProgressBar *progress = new QProgressBar();
progress->setValue(70);
QListWidgetItem *item = new QListWidgetItem(listWidget);
listWidget->addItem(item);
listWidget->setItemWidget(item, progress);

注意事項:

  • 設置后,item->text() 不會顯示在界面中,控件會完全替代默認顯示;
  • 控件將作為 listWidget 的子控件管理,一般不需要手動銷毀;
  • 如需移除控件,請使用 removeItemWidget(),如果不再使用應手動 delete 控件。

2.3.6 QListWidgetItem *takeItem(int row)

作用:
用于從列表中移除并返回指定行的 QListWidgetItem 指針,但不刪除它。你可以隨后對這個 item 做進一步處理,比如修改、重新插入或手動刪除。

參數:row:要移除的 item 的索引(從 0 開始)

返回值:

  • 返回指向被移除的 QListWidgetItem 的指針;
  • 如果 row 無效(超出范圍),返回 nullptr。

常見用途:

  • 移除某項后,保存或修改再重新插入;
  • 手動刪除 item(注意:你拿到的是堆對象,需要 delete);
  • 移動 item(先 takeItem,再 insertItem)。

示例:移除并刪除某一項

int row = 2;
QListWidgetItem *item = listWidget->takeItem(row);
if (item) {delete item;  // 必須手動釋放內存!
}

示例:將一項從位置 A 移到位置 B

int from = 2;
int to = 0;
QListWidgetItem *item = listWidget->takeItem(from);
if (item) {listWidget->insertItem(to, item);
}

注意事項:

  • 內存釋放 takeItem() 不刪除 item,你必須手動 delete
  • 信號響應 takeItem() 不會觸發 itemChanged 之類信號
  • 重新插入 可以 insertItem() 插回

四、QListWidget的信號與槽

4.1 void currentItemChanged(QListWidgetItem *current, QListWidgetItem *previous)

作用:用于通知當前選中項發生變化時的事件。

參數說明:
- List item

觸發時機:

  • 用戶用鼠標或鍵盤改變了選中項;
  • 程序調用了 setCurrentItem() 或 setCurrentRow();
  • 初次選中項或取消選中時,previous 或 current 為 nullptr。

示例:連接信號槽
示例 1:lambda 寫法(推薦)

connect(listWidget, &QListWidget::currentItemChanged,this, [](QListWidgetItem *current, QListWidgetItem *previous) {if (current) {qDebug() << "當前項文本:" << current->text();}if (previous) {qDebug() << "前一項文本:" << previous->text();}
});

示例 2:使用自定義槽函數

// 聲明槽函數
void onCurrentItemChanged(QListWidgetItem *current, QListWidgetItem *previous);// 連接信號
connect(listWidget, &QListWidget::currentItemChanged,this, &YourClass::onCurrentItemChanged);// 實現槽函數
void YourClass::onCurrentItemChanged(QListWidgetItem *current, QListWidgetItem *previous) {if (current)qDebug() << "當前項:" << current->text();if (previous)qDebug() << "之前項:" << previous->text();
}

4.2 void currentRowChanged(int currentRow)

作用:用于在當前選中行發生變化時通知你當前選中的行號。

參數說明:
在這里插入圖片描述
觸發時機:

  • 用戶點擊不同的項;
  • 使用鍵盤上下箭頭切換項;
  • 程序調用 setCurrentRow() 或 setCurrentItem();

示例:使用 lambda 響應行號變化

connect(listWidget, &QListWidget::currentRowChanged,this, [](int row) {qDebug() << "當前選中行:" << row;
});

示例:使用槽函數

// 連接信號
connect(listWidget, &QListWidget::currentRowChanged,this, &YourClass::onCurrentRowChanged);// 槽函數定義
void YourClass::onCurrentRowChanged(int row) {qDebug() << "當前選中行號:" << row;QListWidgetItem* item = listWidget->item(row);if (item)qDebug() << "對應文本:" << item->text();
}

4.3 void itemActivated(QListWidgetItem *item)
作用:當用戶激活某個條目時發出,常用于響應用戶雙擊某項或按下回車鍵激活當前項。

觸發方式:
在這里插入圖片描述
示例:連接 itemActivated 信號
使用 lambda:

connect(listWidget, &QListWidget::itemActivated,this, [](QListWidgetItem *item) {if (item)qDebug() << "激活項文本:" << item->text();
});

使用自定義槽函數:

connect(listWidget, &QListWidget::itemActivated,this, &YourClass::onItemActivated);void YourClass::onItemActivated(QListWidgetItem *item) {if (item)qDebug() << "用戶激活了:" << item->text();
}

常見用途:

  • 打開對應的詳細界面(如文件管理器中打開文件);
  • 響應確認操作(如雙擊打開圖片);
  • 與 QStackedWidget 聯動切換內容頁面;
  • 啟動編輯、顯示彈窗、觸發某項動作等。

對比其他信號:
在這里插入圖片描述
4.4 void itemChanged(QListWidgetItem *item)

作用:用于在某個條目的數據內容發生變化時發出,尤其適用于文本修改或勾選狀態改變等情況。

觸發條件:
在這里插入圖片描述
前提條件:必須啟用可更改標志
為使條目可編輯或勾選,你必須設置適當的 Qt::ItemFlags,例如:

QListWidgetItem* item = new QListWidgetItem("默認文本");
item->setFlags(item->flags() | Qt::ItemIsEditable | Qt::ItemIsUserCheckable);
listWidget->addItem(item);

示例:響應 item 內容變更

connect(listWidget, &QListWidget::itemChanged,this, [](QListWidgetItem *item) {qDebug() << "項內容發生改變:" << item->text();
});

在這里插入圖片描述
輸出結果:
在這里插入圖片描述

示例:檢測復選框狀態改變
在這里插入圖片描述
輸出結果:
在這里插入圖片描述
注意事項:

  • 即使程序修改數據也會觸發信號;
  • 如果不希望程序內設置數據時觸發信號,可在修改前使用 blockSignals(true) 臨時關閉。
listWidget->blockSignals(true);
item->setText("程序修改的文本");
listWidget->blockSignals(false);

4.5 void itemClicked(QListWidgetItem *item)

作用:當用戶點擊列表中的某一項時發出。這是一個非常常用的信號,用于處理用戶點擊操作的邏輯響應。

參數說明:
在這里插入圖片描述

觸發條件:

  • 用戶用鼠標左鍵點擊某個列表項時觸發;
  • 程序調用 setCurrentItem() 不會觸發;
  • 只響應用戶行為,不響應程序設置。

示例:使用 lambda 響應點擊

connect(listWidget, &QListWidget::itemClicked,this, [](QListWidgetItem *item) {if (item)qDebug() << "用戶點擊了項:" << item->text();
});

示例:自定義槽函數響應

connect(listWidget, &QListWidget::itemClicked,this, &YourClass::onItemClicked);void YourClass::onItemClicked(QListWidgetItem *item) {qDebug() << "被點擊的項文本:" << item->text();
}

4.6 void itemDoubleClicked(QListWidgetItem *item)

作用:用于在用戶雙擊某個列表項時發出,常用于打開詳情、進入編輯模式、或執行確認操作等。

觸發條件:
在這里插入圖片描述
參數說明:
在這里插入圖片描述
示例:使用 lambda 處理雙擊

connect(listWidget, &QListWidget::itemDoubleClicked,this, [](QListWidgetItem *item) {if (item)qDebug() << "用戶雙擊了項:" << item->text();
});

示例:自定義槽函數處理雙擊行為

connect(listWidget, &QListWidget::itemDoubleClicked,this, &YourClass::onItemDoubleClicked);void YourClass::onItemDoubleClicked(QListWidgetItem *item) {if (item)qDebug() << "雙擊觸發操作:" << item->text();
}

4.7 void itemEntered(QListWidgetItem *item)

作用:當鼠標光標進入某一項區域時發出,可用于實現鼠標懸浮提示、預覽、動態樣式等效果。

使用前提:
要使用 itemEntered 信號,必須啟用列表控件的“鼠標追蹤模式”:

listWidget->setMouseTracking(true);

否則你將不會收到任何鼠標進入的事件。

觸發條件:
在這里插入圖片描述
示例:連接信號處理懸浮提示

listWidget->setMouseTracking(true);  // 必須啟用鼠標追蹤connect(listWidget, &QListWidget::itemEntered,this, [](QListWidgetItem *item) {if (item)qDebug() << "鼠標進入項:" << item->text();
});

示例:懸浮顯示 tooltip 提示

connect(listWidget, &QListWidget::itemEntered,this, [](QListWidgetItem *item) {if (item)QToolTip::showText(QCursor::pos(), "提示:" + item->text());
});

常見用途:

  • 鼠標懸浮項高亮顯示;
  • 動態顯示 tooltip、縮略圖、預覽信息;
  • 進入某項區域觸發臨時動作或動畫;
  • 聯動其他控件響應懸停項。

4.8 void itemPressed(QListWidgetItem *item)

作用:當用戶按下鼠標按鈕(通常是左鍵)在某個列表項上時觸發,也就是說這個信號在鼠標按下瞬間發出,而不是釋放或點擊完成

觸發條件:

  • List item
    參數說明:
    在這里插入圖片描述
    示例:使用 lambda 連接信號
connect(listWidget, &QListWidget::itemPressed,this, [](QListWidgetItem *item) {if (item)qDebug() << "鼠標按下項:" << item->text();
});

示例:使用自定義槽函數

connect(listWidget, &QListWidget::itemPressed,this, &YourClass::onItemPressed);void YourClass::onItemPressed(QListWidgetItem *item) {if (item)qDebug() << "按下了項:" << item->text();
}

常見用途:

  • 實現拖拽開始的檢測(配合 mouseMoveEvent);
  • 右鍵菜單彈出前的準備工作;
  • 點擊按下時做一些視覺反饋(比如按下陰影效果);
  • 處理復雜點擊行為(例如區分按下和釋放事件)。

4.9 void itemSelectionChanged()

作用:當列表中選中項的集合發生變化時觸發。無論是單選還是多選模式,只要選中項發生增減或變化,這個信號都會被發出。

觸發條件:

  • 用戶用鼠標或鍵盤改變選中項(單選或多選);
  • 程序調用諸如 setCurrentItem(), setItemSelected(), clearSelection() 等函數改變選中狀態;
  • 只要選中項集合變化就會觸發。

示例:響應選中項集合變化

connect(listWidget, &QListWidget::itemSelectionChanged,this, [=]() {QList<QListWidgetItem*> selectedItems = listWidget->selectedItems();qDebug() << "當前選中項數量:" << selectedItems.size();for (auto item : selectedItems) {qDebug() << "選中項文本:" << item->text();}
});

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/pingmian/87616.shtml
繁體地址,請注明出處:http://hk.pswp.cn/pingmian/87616.shtml
英文地址,請注明出處:http://en.pswp.cn/pingmian/87616.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

React Native 親切的組件們(函數式組件/class組件)和陌生的樣式

寫多了taro, 看見react native中的組件好親切啊&#xff0c;幾乎一模一樣。 一、函數式組件 — 常用 1&#xff09;無狀態&#xff0c;每次刷新都是生成一個新的狀態 2&#xff09;基于狀態變化的管理 3&#xff09;簡潔&#xff0c;代碼少&#xff0c;易于服用 import Reac…

Spring boot之身份驗證和訪問控制

本文筆記跟隨于遇見狂神說老師的視頻 一.SpringSecurity&#xff08;安全&#xff09; 1.相關概念 在web開發中&#xff0c;安全第一位&#xff0c;有簡單的方法&#xff0c;比如&#xff1a;攔截器&#xff0c;過濾器 也有安全框架&#xff0c;比如&#xff1a;SpringSecu…

C#使用開源框架NetronLight繪制流程圖

之前使用MindFusion.Diagramming繪制流程圖確認很方便&#xff0c;只能試用版&#xff0c;如果長期使用&#xff0c;需要收費。 C#使用MindFusion.Diagramming框架繪制流程圖(2):流程圖示例_c# 畫流程圖控件-CSDN博客 這里找一個簡易開源框架NetronLight&#xff0c;GIT下載地…

支持向量機(SVM)在腦部MRI分類中的深入應用與實現

?? 博主簡介:CSDN博客專家、CSDN平臺優質創作者,高級開發工程師,數學專業,10年以上C/C++, C#, Java等多種編程語言開發經驗,擁有高級工程師證書;擅長C/C++、C#等開發語言,熟悉Java常用開發技術,能熟練應用常用數據庫SQL server,Oracle,mysql,postgresql等進行開發應用…

AtCoder AT_abc413_c [ABC413C] Large Queue 題解

題目大意 有一個初始為空的序列 A A A&#xff0c; Q Q Q 次操作分為兩類&#xff1a; 第一類&#xff1a;將 c c c 個 x x x 放到 A A A 的末尾。第二類&#xff1a;將前 k k k 個數的和輸出并移除它們。 思路 這是一個求和問題&#xff0c;想到的第一個思路是前綴和…

「源力覺醒 創作者計劃」_文心大模型開源:開啟 AI 新時代的大門

在人工智能的浩瀚星空中&#xff0c;大模型技術宛如一顆璀璨的巨星&#xff0c;照亮了無數行業前行的道路。自誕生以來&#xff0c;大模型憑借其強大的語言理解與生成能力&#xff0c;引發了全球范圍內的技術變革與創新浪潮。百度宣布于 6 月 30 日開源文心大模型 4.5 系列&…

Git 怎么判斷是否沖突?

&#x1f4cc; [Q&A] Git 怎么判斷是否沖突&#xff1f; Git 使用的是三路合并算法&#xff08;Three-way Merge&#xff09;&#xff0c;它比較&#xff1a; 共同祖先提交&#xff08;base&#xff09; 當前分支的改動&#xff08;ours&#xff09; 被合并分支的改動&am…

在sf=0.1時測試fireducks、duckdb、polars的tpch

首先&#xff0c;從https://github.1git.de/fireducks-dev/polars-tpch下載源代碼包&#xff0c;將其解壓縮到/par/fire目錄。 然后進入此目錄&#xff0c;運行 SCALE_FACTOR0.1 ./run-fireducks.sh&#xff0c;腳本會首先安裝所需的包&#xff0c;編譯tpch的數據生成器&#x…

AWS多賬號管理終極指南:從安裝配置到高效使用

引言:為什么需要多賬號管理? 在云計算時代,企業使用多個AWS賬號已成為最佳實踐。根據AWS Well-Architected Framework,多賬號架構可以: 實現環境隔離(生產/測試/開發)滿足不同業務單元的安全要求簡化資源管理和成本分配符合合規性要求(如SOC2、ISO27001)本文將手把手…

UE5音頻技術

1 . 調制器 Modulator 調整參數 調制器可以使聲音每次音高都不一樣 2. 隨機 節點 3. 混音器 Mixer 混合兩個音頻 4. 串聯器 Concatenator 按循序播放 5.多普勒 Doppler 根據距離音頻變化 6.包絡線 Enveloper 武器充能發射 7.混響

創客匠人視角:創始人 IP 打造與知識變現的培訓賦能體系

在知識付費行業進入精耕期的當下&#xff0c;為何部分企業投入大量培訓卻收效甚微&#xff1f;創客匠人 CEO 老蔣通過服務 5W 知識博主的經驗指出&#xff1a;唯有將創始人 IP 思維與培訓體系深度融合&#xff0c;才能讓培訓成為知識變現的 “轉換器”。一、內訓體系重構&…

基于Java+SpringBoot的三國之家網站

源碼編號&#xff1a;S591 源碼名稱&#xff1a;基于SpringBoot的三國之家網站 用戶類型&#xff1a;雙角色&#xff0c;用戶、管理員 數據庫表數量&#xff1a;20 張表 主要技術&#xff1a;Java、Vue、ElementUl 、SpringBoot、Maven 運行環境&#xff1a;Windows/Mac、…

推薦算法系統系列五>推薦算法CF協同過濾用戶行為挖掘(itembase+userbase)

注&#xff1a;此文章內容均節選自充電了么創始人&#xff0c;CEO兼CTO陳敬雷老師的新書《GPT多模態大模型與AI Agent智能體》&#xff08;跟我一起學人工智能&#xff09;【陳敬雷編著】【清華大學出版社】 配套視頻 推薦算法系統實戰全系列精品課【陳敬雷】 文章目錄 推薦算…

pytest之fixture中yield詳解

1. fixture——yield介紹 fixture的teardown操作并不是獨立的函數&#xff0c;用yield關鍵字呼喚teardown操作。前面通過fixture實現了在每個用例之前執行初始化操作&#xff0c;那么用例執行完之后&#xff0c;如需要清除數據&#xff08;或還原&#xff09;操作&#xff0c;…

Nginx 動靜分離原理與工作機制詳解:從架構優化到性能提升

前言&#xff1a;在 Web 應用架構不斷演進的今天&#xff0c;如何高效處理日益增長的訪問量和復雜的業務邏輯&#xff0c;成為開發者必須面對的挑戰。當我們在瀏覽器中打開一個網頁&#xff0c;那些直觀可見的 HTML 頁面、精美絕倫的圖片、流暢運行的 JavaScript 腳本&#xff…

介紹electron

一、Electron 是什么&#xff1f; Electron 是一個基于 Chromium 和 Node.js 的框架&#xff0c;允許開發者使用前端技術&#xff08;HTML/CSS/JavaScript&#xff09;構建原生桌面應用。其核心優勢在于&#xff1a; 跨平臺&#xff1a;一次開發&#xff0c;生成 Windows、ma…

DeepSeek與詭秘之主

1、大模型像個腐儒 其實從大模型的訓練方式來看&#xff0c;它算不上天賦異稟。尤其在成長階段&#xff0c;大模型那種種令人驚艷的表現&#xff0c;足夠讓人誤以為這是個天才。 可人這種生物&#xff0c;注定是貪婪的。在大模型成長后期&#xff0c;伴隨著各種技巧的驗證&…

動手實踐OpenHands系列學習筆記5:代理系統架構概述

筆記5&#xff1a;代理系統架構概述 一、引言 AI代理系統是一種能夠自主執行任務的智能軟件架構&#xff0c;OpenHands作為AI驅動的軟件開發代理平臺&#xff0c;擁有完整的代理系統架構設計。本筆記將探討AI代理架構的基本原理&#xff0c;并通過分析OpenHands核心架構&…

智能電動汽車 --- 車輛網關路由緩存

我是穿拖鞋的漢子,魔都中堅持長期主義的汽車電子工程師。 老規矩,分享一段喜歡的文字,避免自己成為高知識低文化的工程師: 簡單,單純,喜歡獨處,獨來獨往,不易合同頻過著接地氣的生活,除了生存溫飽問題之外,沒有什么過多的欲望,表面看起來很高冷,內心熱情,如果你身…

Spring中實現依賴注入(DI)的三種方式

1. Autowired 字段注入&#xff08;不推薦&#xff09;? Service public class UserService {Autowired // 直接在字段上注入private UserRepository userRepository; } ??原理??&#xff1a;Spring 啟動時掃描所有 Component、Service 等注解的類&#xff0c;發現 Aut…