历史消息记录(二)
前言
在上一集我们完成了历史记录的窗口的布局、点击历史消息记录按钮的槽函数以及两个关键查询功能的切换槽函数功能。那么这一集我们就要完成这个历史消息记录的大概功能。
需求分析
我们还是来看那张效果图
整个窗口我们还差这个滚动区的每一条消息内容的内容还未完成。那我们就要着手完成。
由于这每一条消息记录都是长得雷同,所以我们就要封装一个类来完成这个历史记录元素。
由于我们的每条消息的消息内容不一定都是文本,所以我们肯定要考虑那四种不同的消息类型。
我们这里暂时先考虑文本消息类型。
那么我们就要封装成一个工厂函数来完成我们所需功能。
历史消息元素
以下内容都是我们常规的操作,就不多赘述了。
//一条历史记录的工厂函数
HistoryItem *HistoryItem::makeHistoryItem(const Message &message)
{
//创建对象
HistoryItem* item = new HistoryItem();
item->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred);
//布局管理器
QGridLayout* layout = new QGridLayout();
layout->setVerticalSpacing(0);
layout->setHorizontalSpacing(10);
layout->setContentsMargins(0,0,0,0);
item->setLayout(layout);
//头像
QPushButton* avatarBtn = new QPushButton();
avatarBtn->setFixedSize(40,40);
avatarBtn->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed);
avatarBtn->setIconSize(QSize(40,40));
avatarBtn->setIcon(message.sender.avatar);
avatarBtn->setStyleSheet("QPushButton { border: none; }");
//昵称+时间
QLabel* nameLabel = new QLabel();
nameLabel->setText(message.sender.nickname + " | " + message.time);
nameLabel->setFixedHeight(20);
nameLabel->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed);
//消息内容
QWidget* contentWidget = nullptr;
if(message.messageType == TEXT_TYPE){
//文本消息
QLabel* label = new QLabel();
label->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
label->setWordWrap(true);//文本自动换行
label->setText(QString(message.content));
label->adjustSize();//设置label自动调整大小
contentWidget = label;
}else if(message.messageType == IMAGE_TYPE){
//图片消息
}else if(message.messageType == FILE_TYPE){
//文件消息
}else if(message.messageType == SPEECH_TYPE){
//语音消息
}else{
LOG() << "错误的消息类型!messageType=" << message.messageType;
}
//添加控件到布局管理器
layout->addWidget(avatarBtn,0,0,2,1);
layout->addWidget(nameLabel,0,1,1,1);
layout->addWidget(contentWidget,1,1,5,1);
return item;
}
工具函数
当然我们还需要写两个工具函数,用于添加历史消息记录和清空历史消息记录!
HistoryItem* item = HistoryItem::makeHistoryItem(message);
container->layout()->addWidget(item);
}
void HistoryMessageWidget::clear()
{
//从后往前遍历
QVBoxLayout* layout = dynamic_cast<QVBoxLayout*>(container->layout());
for(int i = layout->count()-1; i >= 0; --i){
QWidget* w = layout->itemAt(i)->widget();
if(w == nullptr){
continue;
}
layout->removeWidget(w);
w->deleteLater();
}
}
假数据
那么我们就可以构造一些假数据了!
#if TEST_UI
for(int i = 0; i <= 30; ++i){
UserInfo sender;
sender.userId = "";
sender.nickname = "狗头程序员" + QString::number(i);
sender.avatar = QIcon(":/resource/image/defaultAvatar.png");
sender.description = "";
sender.phone = "123456789";
Message message = message.makeMessage(TEXT_TYPE, "", sender, QString("程序员" + QString::number(i) + "在认真敲代码").toUtf8(), "");
this->addHistoryMessage(message);
}
#endif
只需要点击运行就可以看到我们之前的效果图啦!那么我们的历史消息记录窗口先到这里。