BubbleMessageManager.h 7.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260
  1. #ifndef BUBBLEMESSAGEMANAGER_H
  2. #define BUBBLEMESSAGEMANAGER_H
  3. #include <QApplication>
  4. #include <QClipboard>
  5. #include <QDateTime>
  6. #include <QGraphicsItem>
  7. #include <QGraphicsPixmapItem>
  8. #include <QGraphicsProxyWidget>
  9. #include <QGraphicsScene>
  10. #include <QGraphicsSceneContextMenuEvent>
  11. #include <QGraphicsSceneMouseEvent>
  12. #include <QGraphicsTextItem>
  13. #include <QGraphicsView>
  14. #include <QLabel>
  15. #include <QMenu>
  16. #include <QMimeData>
  17. #include <QPainter>
  18. #include <QPropertyAnimation>
  19. #include <QScrollBar>
  20. #include <QStyleOptionGraphicsItem>
  21. #include <QTextCursor>
  22. #include <QTextDocument>
  23. #include <QTimer>
  24. #include <QVBoxLayout>
  25. // 基础气泡消息类
  26. class BubbleMessage : public QGraphicsItem
  27. {
  28. public: // 消息类型枚举
  29. enum MessageType {
  30. TimeMessage,
  31. TextMessage,
  32. SuccessMessage,
  33. FailureMessage,
  34. FileMessage,
  35. RecallMessage,
  36. ImageMessage,
  37. TextImageMessage
  38. };
  39. // 消息方向枚举
  40. enum MessageDirection {
  41. Sent, // 发送的消息(右侧)
  42. Received // 接收的消息(左侧)
  43. };
  44. BubbleMessage(const QString &content,
  45. MessageType type,
  46. MessageDirection direction,
  47. QGraphicsItem *parent = nullptr);
  48. virtual ~BubbleMessage();
  49. QRectF boundingRect() const override;
  50. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
  51. MessageType messageType() const { return m_type; }
  52. MessageDirection messageDirection() const { return m_direction; }
  53. QString content() const { return m_content; }
  54. QDateTime timestamp() const { return m_timestamp; }
  55. virtual void updateSize();
  56. virtual bool isSelectable() const { return true; }
  57. void setAvatar(const QPixmap &avatar)
  58. {
  59. m_avatar = avatar;
  60. updateSize();
  61. }
  62. QPixmap avatar() const { return m_avatar; }
  63. protected:
  64. void contextMenuEvent(QGraphicsSceneContextMenuEvent *event) override;
  65. void mousePressEvent(QGraphicsSceneMouseEvent *event) override;
  66. void mouseReleaseEvent(QGraphicsSceneMouseEvent *event) override;
  67. void hoverEnterEvent(QGraphicsSceneHoverEvent *event) override;
  68. void hoverLeaveEvent(QGraphicsSceneHoverEvent *event) override;
  69. MessageType m_type;
  70. MessageDirection m_direction;
  71. QString m_content;
  72. QDateTime m_timestamp;
  73. QRectF m_boundingRect;
  74. bool m_isHovered;
  75. QColor m_bubbleColor;
  76. QColor m_textColor;
  77. int m_padding;
  78. int m_borderRadius;
  79. QFont m_font;
  80. QPixmap m_avatar;
  81. int m_avatarSize;
  82. bool m_isSelecting;
  83. QPointF m_selectionStart;
  84. QPointF m_selectionEnd;
  85. };
  86. // 时间消息类
  87. class TimeMessage : public BubbleMessage
  88. {
  89. public:
  90. TimeMessage(const QDateTime &time, QGraphicsItem *parent = nullptr);
  91. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
  92. bool isSelectable() const override { return false; }
  93. };
  94. // 文本消息类
  95. class TextMessage : public BubbleMessage
  96. {
  97. public:
  98. TextMessage(const QString &text, MessageDirection direction, QGraphicsItem *parent = nullptr);
  99. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
  100. void updateSize() override;
  101. virtual void mousePressEvent(QGraphicsSceneMouseEvent *event) override;
  102. virtual void mouseMoveEvent(QGraphicsSceneMouseEvent *event) override;
  103. virtual void mouseReleaseEvent(QGraphicsSceneMouseEvent *event) override;
  104. int m_selectionStart;
  105. int m_selectionEnd;
  106. bool m_hasSelection;
  107. QString selectedText();
  108. protected:
  109. QTextDocument m_textDocument;
  110. protected:
  111. int positionAt(const QPointF &pos) const;
  112. QRectF selectionRect() const;
  113. };
  114. // 成功消息类
  115. class SuccessMessage : public TextMessage
  116. {
  117. public:
  118. SuccessMessage(const QString &text, MessageDirection direction, QGraphicsItem *parent = nullptr);
  119. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
  120. };
  121. // 失败消息类
  122. class FailureMessage : public TextMessage
  123. {
  124. public:
  125. FailureMessage(const QString &text, MessageDirection direction, QGraphicsItem *parent = nullptr);
  126. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
  127. };
  128. // 文件消息类
  129. class FileMessage : public BubbleMessage
  130. {
  131. public:
  132. FileMessage(const QString &fileName,
  133. const QString &filePath,
  134. qint64 fileSize,
  135. MessageDirection direction,
  136. QGraphicsItem *parent = nullptr);
  137. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
  138. void updateSize() override;
  139. protected:
  140. QString m_fileName;
  141. QString m_filePath;
  142. qint64 m_fileSize;
  143. QPixmap m_fileIcon;
  144. };
  145. // 撤回消息类
  146. class RecallMessage : public BubbleMessage
  147. {
  148. public:
  149. RecallMessage(const QString &recalledBy,
  150. MessageDirection direction,
  151. QGraphicsItem *parent = nullptr);
  152. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
  153. bool isSelectable() const override { return false; }
  154. };
  155. // 图片消息类
  156. class ImageMessage : public BubbleMessage
  157. {
  158. public:
  159. ImageMessage(const QPixmap &image, MessageDirection direction, QGraphicsItem *parent = nullptr);
  160. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
  161. void updateSize() override;
  162. protected:
  163. QPixmap m_image;
  164. QPixmap m_scaledImage;
  165. };
  166. // 文本图片混合消息类
  167. class TextImageMessage : public BubbleMessage
  168. {
  169. public:
  170. TextImageMessage(const QString &text,
  171. const QPixmap &image,
  172. MessageDirection direction,
  173. QGraphicsItem *parent = nullptr);
  174. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
  175. void updateSize() override;
  176. protected:
  177. QTextDocument m_textDocument;
  178. QPixmap m_image;
  179. QPixmap m_scaledImage;
  180. };
  181. // 消息场景类
  182. class MessageScene : public QGraphicsScene
  183. {
  184. public:
  185. MessageScene(QObject *parent = nullptr);
  186. void addMessage(BubbleMessage *message);
  187. void clear();
  188. void setDefaultAvatars(const QPixmap &sentAvatar, const QPixmap &receivedAvatar);
  189. void arrangeMessages();
  190. private:
  191. void placeNewMessage(BubbleMessage *message);
  192. int m_verticalSpacing;
  193. int m_horizontalMargin;
  194. QPixmap m_defaultSentAvatar;
  195. QPixmap m_defaultReceivedAvatar;
  196. };
  197. // 消息视图类
  198. class BubbleMessageView : public QGraphicsView
  199. {
  200. public:
  201. BubbleMessageView(QWidget *parent = nullptr);
  202. void addTimeMessage(const QDateTime &time);
  203. void addTextMessage(const QString &text, BubbleMessage::MessageDirection direction);
  204. void addSuccessMessage(const QString &text, BubbleMessage::MessageDirection direction);
  205. void addFailureMessage(const QString &text, BubbleMessage::MessageDirection direction);
  206. void addFileMessage(const QString &fileName,
  207. const QString &filePath,
  208. qint64 fileSize,
  209. BubbleMessage::MessageDirection direction);
  210. void addRecallMessage(const QString &recalledBy, BubbleMessage::MessageDirection direction);
  211. void addImageMessage(const QPixmap &image, BubbleMessage::MessageDirection direction);
  212. void addTextImageMessage(const QString &text,
  213. const QPixmap &image,
  214. BubbleMessage::MessageDirection direction);
  215. void clearMessages();
  216. protected:
  217. void resizeEvent(QResizeEvent *event) override;
  218. void wheelEvent(QWheelEvent *event) override;
  219. private:
  220. MessageScene *m_scene;
  221. bool m_autoScroll;
  222. };
  223. #endif // BUBBLEMESSAGEMANAGER_H