ctai/src/ctaiHistoryWidget.cpp

202 lines
6.6 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#include "ctaiHistoryWidget.h"
ctaiHistoryWidget::ctaiHistoryWidget(QWidget *parent)
: QTableWidget(parent)
{
setup_table();
}
void ctaiHistoryWidget::setup_table()
{
setColumnCount(1);
setShowGrid(false);
verticalHeader()->hide();
horizontalHeader()->hide();
horizontalHeader()->setSectionResizeMode(0, QHeaderView::Stretch);
verticalHeader()->setSectionResizeMode(QHeaderView::ResizeToContents);
// 设置自动滚动属性
setVerticalScrollMode(QAbstractItemView::ScrollPerPixel);
// 滚动步长
verticalScrollBar()->setSingleStep(10);
}
ctaiHistoryWidget::~ctaiHistoryWidget()
{
for (auto &pair : message_map_)
{
delete pair.second.first; // 删除model_data
}
clear();
}
void ctaiHistoryWidget::add_message(const model_data &message)
{
QString send_id;
if (message.msg_type_mode == SYSTEM)
{
send_id = QSL(message.postback_send_id);
}
else
{
send_id = QSL(message.send_user_id);
}
auto it = message_map_.find(send_id);
if (it != message_map_.end() && it->second.first->msg_type_mode == SYSTEM)
{
// 更新现有消息
model_data *stored_data = it->second.first;
int row = it->second.second;
// 如果传入的对象属性为null或者[DONE]表示传输完毕或者其他情况
// 此时需要将tokens更新掉所有其他属性不更新传输数据
QWidget *widget = cellWidget(row, 0);
if (!QSL(message.postback_model_data).isEmpty() &&
!QSL(message.postback_model_data).contains("[DONE]"))
{
// 更新传入信息
stored_data->postback_model_data += message.postback_model_data;
if (auto message_widget = qobject_cast<ctaiHistoryTextEdit *>(widget))
{
message_widget->addSystemMessage(message);
}
}
else
{
// 更新tokens信息
update_stored_data(stored_data, message);
if (auto message_widget = qobject_cast<ctaiHistoryTextEdit *>(widget))
{
message_widget->updateTokensMessage(message);
}
}
// 立即滚动到底部
scrollToBottom();
}
else
{
// 添加新消息
model_data *new_data = new model_data(message);
ctaiHistoryTextEdit *message_widget = new ctaiHistoryTextEdit(this);
message_widget->initLayout(new_data->msg_type_mode);
message_widget->show();
if (new_data->msg_type_mode == SYSTEM)
{
message_widget->addHeaderMessage(*new_data);
message_widget->updateTokensMessage(*new_data);
message_widget->addSystemMessage(*new_data);
}
else
{
message_widget->addHeaderMessage(*new_data);
message_widget->addUserMessage(*new_data);
}
// 创建新行
int row = rowCount();
insertRow(row);
setCellWidget(row, 0, message_widget);
// 存储到map中
message_map_[send_id] = std::make_pair(new_data, row);
// 连接删除信号
connect(message_widget, SIGNAL(signalsDeleteMsg(QString)), this, SLOT(slotsRemoveMsg(QString)));
// 连接高度变化信号
connect(message_widget, SIGNAL(signalsRowHeightChanged(bool)), this, SLOT(slotsRowsHeightSync(bool)));
connect(message_widget, SIGNAL(signalsEditHisResToSend(QString,HISTORY_SEND_MODE)), this, SIGNAL(signalsWidgetHisResToSend(QString, HISTORY_SEND_MODE)));
// 滚动到新消息
scrollToItem(item(row, 0));
}
}
// 自适应信息高度
void ctaiHistoryWidget::slotsRowsHeightSync(bool fold_state)
{
if (fold_state)
{
// 全部行高自适应
for (int row = 0; row < rowCount(); ++row)
{
setRowHeight(row, 87);
resizeRowToContents(row);
}
scrollToBottom();
}
else
{
int row = rowCount() - 1;
if (row >= 0 && row < rowCount())
{
int currentHeight = rowHeight(row);
setRowHeight(row, currentHeight + 100);
resizeRowToContents(row);
}
}
}
void ctaiHistoryWidget::slotsRemoveMsg(QString send_id)
{
auto it = message_map_.find(send_id);
if (it != message_map_.end())
{
int row = it->second.second;
// 确保行号有效
if (row >= 0 && row < rowCount())
{
// 在删除行之前先删除单元格中的widget
QWidget *widget = cellWidget(row, 0);
if (widget)
{
removeCellWidget(row, 0);
delete widget;
}
// 删除行
// removeRow(row);
qDebug() << "row:" << row;
// 更新map中后续行的行号
for (auto &pair : message_map_)
{
if (pair.second.second > row)
{
pair.second.second--;
}
}
// 从map中移除该条目
delete it->second.first;
message_map_.erase(it);
}
}
}
ctaiHistoryTextEdit *ctaiHistoryWidget::current_message() const
{
int current_row = currentRow();
if (current_row >= 0)
{
return qobject_cast<ctaiHistoryTextEdit *>(cellWidget(current_row, 0));
}
return nullptr;
}
void ctaiHistoryWidget::update_stored_data(model_data *stored_data, const model_data &message)
{
stored_data->api_key = message.api_key;
stored_data->api_url = message.api_url;
stored_data->postback_completion_tokens = message.postback_completion_tokens;
stored_data->postback_finish_reason = message.postback_finish_reason;
stored_data->postback_prompt_cache_hit_tokens = message.postback_prompt_cache_hit_tokens;
stored_data->postback_prompt_cache_miss_tokens = message.postback_prompt_cache_miss_tokens;
stored_data->postback_prompt_tokens = message.postback_prompt_tokens;
stored_data->postback_send_id = message.postback_send_id;
stored_data->postback_server_model = message.postback_server_model;
stored_data->postback_stream_mode = message.postback_stream_mode;
stored_data->postback_system_fingerprint = message.postback_system_fingerprint;
stored_data->postback_time = message.postback_time;
stored_data->postback_total_tokens = message.postback_total_tokens;
stored_data->request_body = message.request_body;
stored_data->send_accept_header = message.send_accept_header;
stored_data->send_content_header = message.send_content_header;
stored_data->send_user_data = message.send_user_data;
stored_data->user_model = message.user_model;
// postback_model_data 不在这里赋值
}