QListWidget รายการปัญหาการวางตำแหน่งที่สอดคล้องกัน
ฉันยังใหม่กับกรอบงาน Qt ในแอปพลิเคชันใหม่ฉันต้องการสร้างรายการด้วยรายการที่กำหนดเอง รายการเหล่านี้ค่อนข้างเรียบง่ายและต้องมีป้ายชื่อภาพขนาดย่อและป้ายคำอธิบาย ( ภาพที่นี่ )
ตอนนี้ฉันไม่ต้องการเล่นกับการวาดแบบกำหนดเองและทุกอย่างนั้นเพราะฉันคิดว่ามันง่ายกว่าที่จะทำรายการที่ฉันต้องการด้วยวิดเจ็ต / เลย์เอาต์ที่เหมาะสมดังนั้นฉันจึงตัดสินใจใช้ QListwidget และคลาสย่อย QAbstractItemModel (KeyframeModel) และ QListWidgetItem (TileWidgetItem)
หลังจากเขียนโค้ดแล้วดูเหมือนว่าฉันต้องการ แต่สิ่งแปลก ๆ เกิดขึ้นกับ QListWidget (โหมดตาราง) เมื่อฉันเพิ่มบางรายการ ในกรณีของฉัน QListWidget สามารถปรับขนาดได้ (เนื่องจากการฝังอยู่ในเลย์เอาต์หลัก) และจำนวนคอลัมน์ควรขึ้นอยู่กับความกว้างของรายการและรายการ รายการมีขนาดคงที่ (อย่างน้อยตอนนี้) แต่เมื่อฉันปรับขนาดรายการหนึ่งในรายการที่ความกว้างของรายการบางรายการไม่ตรงแนวและฉันไม่รู้ว่าเกิดอะไรขึ้น ด้านล่างนี้เป็นภาพหน้าจอจากแอป:
Pic. 1 แสดงสถานะเริ่มต้น (ทันทีหลังจากเริ่ม)
Pic. 2 รายการหลังจากปรับขนาด # 1
Pic. 3 รายการหลังจากปรับขนาด # 2
การปรับขนาด # 2 นั้นกว้างกว่าการปรับขนาด # 1 เพียงไม่กี่พิกเซลและการปรับขนาด # 1 นั้นยากที่จะได้รับ (ตัวเรือนขอบ) - ความกว้างของพิกเซลน้อยลงไม่กี่พิกเซลและฉันมี 2 คอลัมน์ (ไม่เป็นไร) แต่มีพิกเซลมากขึ้นและฉันก็จบลงด้วยกรณี # 2. ในทุกกรณีจำนวนคอลัมน์ไม่เป็นไร
บางครั้งรายการสุดท้ายก็ไม่ตรงแนวหลังจากเริ่มโปรแกรมทันทีเช่นที่นี่ (หลังจากเริ่มเหมือนในรูปที่ 1 แต่คุณสามารถเห็นผลลัพธ์ที่แตกต่างกันแม้จะมีความกว้างของรายการเท่ากันก็ตาม) ฉันสงสัยว่าทำไมมันจึงไม่สอดคล้องกันหลังจากเริ่มต้นใช้งาน
ฉันขาดอะไรไปหรือเปล่า? ฉันต้องทำบางส่วนด้วยวิธีอื่นหรือไม่? หรือเป็นเพียงความผิดพลาดบางอย่างในโหมดดีบัก?
ด้านล่างฉันโพสต์รหัส:
ใบสมัคร:
// Source file
QtGuiApplication1::QtGuiApplication1(QWidget *parent)
: QMainWindow(parent)
{
ui.setupUi(this);
//--------------------------------------------------------------------------------
// Add elements to the list
TileWidgetItem *item = new TileWidgetItem();
item->setData(TileWidgetItem::TileRole::TitleRole, QVariant("Long title"));
item->setData(TileWidgetItem::TileRole::DescriptionRole, QVariant("My long info"));
item->setText("My super text");
qDebug() << "Widget size hint: " << item->sizeHint();
ui.listWidget_moves->addItem(item);
item->updateView();
TileWidgetItem *item1 = new TileWidgetItem();
item1->setData(TileWidgetItem::TileRole::TitleRole, QVariant("Item #2"));
item1->setText("Tile #2");
ui.listWidget_moves->addItem(item1);
item1->updateView();
TileWidgetItem *item2 = new TileWidgetItem();
ui.listWidget_moves->addItem(item2);
item2->updateView();
TileWidgetItem *item3 = new TileWidgetItem();
ui.listWidget_moves->addItem(item3);
item3->updateView();
//--------------------------------------------------------------------------------
// Adjust cell size
QSize cellSize;
for (uint i = 0; i < ui.listWidget_moves->count(); i++)
{
int dim = ui.listWidget_moves->item(i)->sizeHint().height();
if (dim > cellSize.height())
cellSize.setHeight(dim);
dim = ui.listWidget_moves->item(i)->sizeHint().width();
if (dim > cellSize.width())
cellSize.setWidth(dim);
}
ui.listWidget_moves->setGridSize(cellSize);
}
วิดเจ็ตรายการ:
// Source file
constexpr int MAX_THUMB_SIZE = 100;
TileWidgetItem::TileWidgetItem(QListWidget *listview)
: QListWidgetItem(listview, ItemType::UserType)
{
/* Prepare main widget */
QWidget *view = new QWidget();
view->setObjectName("tile");
view->setStyleSheet(
"QWidget#tile { margin: 4 8; background-color: #404040; border: 1 solid rgba(0,0,0,30%); border-radius: 4px }\n"
"QWidget#tile::hover { border: 1 solid #EEE; background-color: #484848 }\n"
"QWidget#tile[selected=true] { background-color: #00F }"
);
//-----------------------------------------------------------
/* Prepare layout */
QVBoxLayout *layout = new QVBoxLayout();
layout->setSizeConstraint(QLayout::SizeConstraint::SetFixedSize);
//-----------------------------------------------------------
/* Prepare title with icon */
QHBoxLayout *titleLayout = new QHBoxLayout();
QLabel *titleIcon = new QLabel();
titleIcon->setObjectName("titleIcon");
titleIcon->setStyleSheet("background-color: black");
titleIcon->setFixedSize(QSize(16, 16));
titleLayout->addWidget(titleIcon);
QLabel *title = new QLabel("Title");
title->setObjectName("title");
title->setMinimumWidth(60);
title->setStyleSheet("background-color: #800;");
titleLayout->addWidget(title);
QWidget *titleWidget = new QWidget();
titleWidget->setStyleSheet("background-color: #080");
titleWidget->setLayout(titleLayout);
layout->addWidget(titleWidget);
//-----------------------------------------------------------
/* Prepare thumbnail */
QLabel *thumbnail = new QLabel();
thumbnail->setObjectName("thumbnail");
thumbnail->setStyleSheet("background-color: black; border: 1 solid #F00");
thumbnail->setFixedSize(QSize(MAX_THUMB_SIZE, MAX_THUMB_SIZE * 0.7f));
thumbnail->setPixmap(QPixmap("Resources/moto.jpg").scaledToWidth(MAX_THUMB_SIZE));
layout->addWidget(thumbnail);
//-----------------------------------------------------------
/* Preparing additional info */
QLabel *description = new QLabel("Description");
description->setObjectName("description");
//description->setToolTip("Custom info tip");
description->setContentsMargins(4, 2, 4, 2);
layout->addWidget(description);
//-----------------------------------------------------------
view->setLayout(layout);
_customView = view;
_titleView = title;
_descriptionView = description;
setSizeHint(_customView->sizeHint());
updateView();
}
TileWidgetItem::~TileWidgetItem()
{
}
void TileWidgetItem::setData(int role, const QVariant &value)
{
QListWidgetItem::setData(role, value);
if (value.type() == QVariant::Type::String)
{
if (role == TileRole::TitleRole)
{
this->_titleView->setText(value.toString());
}
else if (role == TileRole::DescriptionRole)
{
this->_descriptionView->setText(value.toString());
}
setSizeHint(_customView->sizeHint());
}
}
void TileWidgetItem::updateView()
{
if (listWidget() != nullptr)
{
listWidget()->setItemWidget(this, this->_customView);
}
}
// Header file
class TileWidgetItem : public QListWidgetItem
{
public:
enum TileRole
{
TitleRole = Qt::UserRole + 1,
DescriptionRole,
ThumbnailRole
};
public:
TileWidgetItem(QListWidget *listview = nullptr);
~TileWidgetItem();
void setData(int role, const QVariant &value) override;
void updateView();
QWidget *customView() const { return _customView; };
QString getTitle() const { return _titleView->text(); };
QString getInfo() const { return _descriptionView->text(); };
private:
QWidget *_customView;
QLabel *_titleView;
QLabel *_descriptionView;
};
แพลตฟอร์ม: Windows 10
เวอร์ชัน Qt: 5.14.2
IDE: Visual Studio 2019 (พร้อมเครื่องมือ Qt VS)
คำตอบ
ในที่สุดฉันก็ใช้ผู้รับมอบสิทธิ์ที่กำหนดเองซึ่งแก้ปัญหาได้
ฉันต้องการที่จะใช้ระบบมากเกินไปและในฉันก็พ่ายแพ้ :)