Improve images in the chatbar

- Don't show the hide button
- Shrink them to better fit
- Allow a little more maxh height in the chatbar for attachments
- Make sure that the button states work properly when adding and removing images
This commit is contained in:
James Graham
2026-02-08 14:25:54 +00:00
parent f02366ee48
commit 60cf12524f
7 changed files with 71 additions and 26 deletions

View File

@@ -75,7 +75,7 @@ QQC2.Control {
QQC2.ScrollView {
id: chatScrollView
Layout.fillWidth: true
Layout.maximumHeight: Kirigami.Units.gridUnit * 8
Layout.maximumHeight: Kirigami.Units.gridUnit * (root.model.hasAttachment ? 12 : 8)
contentWidth: availableWidth
clip: true

View File

@@ -58,6 +58,7 @@ RowLayout {
readonly property ChatButtonHelper chatButtonHelper: ChatButtonHelper {
textItem: root.contentModel.focusedTextItem
inQuote: root.contentModel.focusType == LibNeoChat.MessageComponentType.Quote
hasAttachment: root.contentModel.hasAttachment
}
signal clicked

View File

@@ -5,11 +5,8 @@
#include <Kirigami/Platform/PlatformTheme>
#include "chatbarcache.h"
#include "chattextitemhelper.h"
#include "enums/chatbartype.h"
#include "enums/richformat.h"
#include "neochatroom.h"
ChatButtonHelper::ChatButtonHelper(QObject *parent)
: QObject(parent)
@@ -34,12 +31,6 @@ void ChatButtonHelper::setTextItem(ChatTextItemHelper *textItem)
m_textItem = textItem;
if (m_textItem) {
connect(m_textItem, &ChatTextItemHelper::roomChanged, this, [this]() {
if (m_textItem->room() && m_textItem->type() != ChatBarType::None) {
const auto cache = m_textItem->room()->cacheForType(m_textItem->type());
connect(cache, &ChatBarCache::attachmentPathChanged, this, &ChatButtonHelper::richFormatEnabledChanged);
}
});
connect(m_textItem, &ChatTextItemHelper::textFormatChanged, this, &ChatButtonHelper::richFormatEnabledChanged);
connect(m_textItem, &ChatTextItemHelper::textFormatChanged, this, &ChatButtonHelper::styleChanged);
connect(m_textItem, &ChatTextItemHelper::charFormatChanged, this, &ChatButtonHelper::charFormatChanged);
@@ -68,6 +59,21 @@ void ChatButtonHelper::setInQuote(bool inQuote)
Q_EMIT styleChanged();
}
bool ChatButtonHelper::hasAttachment() const
{
return m_hasAttachment;
}
void ChatButtonHelper::setHasAttachment(bool hasAttachment)
{
if (hasAttachment == m_hasAttachment) {
return;
}
m_hasAttachment = hasAttachment;
Q_EMIT hasAttachmentChanged();
Q_EMIT richFormatEnabledChanged();
}
bool ChatButtonHelper::richFormatEnabled() const
{
if (!m_textItem) {
@@ -86,16 +92,9 @@ bool ChatButtonHelper::richFormatEnabled() const
bool ChatButtonHelper::styleFormatEnabled() const
{
if (!m_textItem) {
if (!m_textItem || m_hasAttachment) {
return false;
}
const auto room = m_textItem->room();
if (!room) {
return false;
}
if (const auto cache = room->cacheForType(m_textItem->type())) {
return cache->attachmentPath().isEmpty();
}
return true;
}

View File

@@ -28,6 +28,11 @@ class ChatButtonHelper : public QObject
*/
Q_PROPERTY(bool inQuote READ inQuote WRITE setInQuote NOTIFY inQuoteChanged)
/**
* @brief Whether the model has an attachment..
*/
Q_PROPERTY(bool hasAttachment READ hasAttachment WRITE setHasAttachment NOTIFY hasAttachmentChanged)
/**
* @brief Whether rich formating is enabled at the current cursor location.
*/
@@ -102,6 +107,9 @@ public:
bool inQuote() const;
void setInQuote(bool inQuote);
bool hasAttachment() const;
void setHasAttachment(bool hasAttachment);
bool richFormatEnabled() const;
bool styleFormatEnabled() const;
bool bold() const;
@@ -149,6 +157,7 @@ public:
Q_SIGNALS:
void textItemChanged();
void inQuoteChanged();
void hasAttachmentChanged();
void richFormatEnabledChanged();
void charFormatChanged();
void styleChanged();
@@ -157,6 +166,7 @@ Q_SIGNALS:
private:
QPointer<ChatTextItemHelper> m_textItem;
bool m_inQuote = false;
bool m_hasAttachment = false;
void selectLinkText(QTextCursor &cursor) const;
};

View File

@@ -58,7 +58,9 @@ DelegateChooser {
DelegateChoice {
roleValue: MessageComponentType.Image
delegate: ImageComponent {}
delegate: ImageComponent {
rightAnchorMargin: root.rightAnchorMargin
}
}
DelegateChoice {

View File

@@ -7,6 +7,7 @@ pragma ComponentBehavior: Bound
import QtCore
import QtQuick
import QtQuick.Controls as QQC2
import QtQuick.Layouts
import org.kde.kirigami as Kirigami
@@ -38,19 +39,33 @@ Item {
*/
required property var fileTransferInfo
/**
* @brief Whether the component should be editable.
*/
required property bool editable
/**
* The maximum height of the image. Can be left undefined most of the times. Passed to MediaSizeHelper::contentMaxHeight.
*/
property var contentMaxHeight: undefined
property var contentMaxHeight: editable ? Kirigami.Units.gridUnit * 8 : undefined
/**
* @brief Extra margin required when anchoring an item on the right.
*
* Normally used for scrollbars.
*/
property int rightAnchorMargin: 0
Layout.fillWidth: true
implicitWidth: mediaSizeHelper.currentSize.width
implicitHeight: mediaSizeHelper.currentSize.height
QQC2.Button {
anchors.right: parent.right
anchors.top: parent.top
anchors.margins: Kirigami.Units.smallSpacing
visible: !_private.hideImage
anchors.top: root.top
anchors.topMargin: Kirigami.Units.smallSpacing
anchors.right: root.right
anchors.rightMargin: root.rightAnchorMargin + Kirigami.Units.smallSpacing
visible: !_private.hideImage && !root.editable
icon.name: "view-hidden"
text: i18nc("@action:button", "Hide Image")
display: QQC2.Button.IconOnly
@@ -64,6 +79,21 @@ Item {
QQC2.ToolTip.visible: hovered
QQC2.ToolTip.delay: Kirigami.Units.toolTipDelay
}
QQC2.Button {
id: cancelButton
anchors.top: root.top
anchors.topMargin: Kirigami.Units.smallSpacing
anchors.right: root.right
anchors.rightMargin: root.rightAnchorMargin + Kirigami.Units.smallSpacing
visible: root.editable
display: QQC2.AbstractButton.IconOnly
text: i18nc("@action:button", "Remove attachment")
icon.name: "dialog-close"
onClicked: root.Message.contentModel?.removeAttachment()
QQC2.ToolTip.text: text
QQC2.ToolTip.visible: hovered
QQC2.ToolTip.delay: Kirigami.Units.toolTipDelay
}
Loader {
id: imageLoader
@@ -149,8 +179,10 @@ Item {
if (root.componentAttributes.animated) {
_private.imageItem.paused = true;
}
root.Message.timeline.interactive = false;
if (!root.componentAttributes.isSticker) {
if (root.Message.timeline) {
root.Message.timeline.interactive = false;
}
if (!root.componentAttributes.isSticker && !root.editable) {
RoomManager.maximizeMedia(root.eventId);
}
}

View File

@@ -498,6 +498,7 @@ void ChatBarMessageContentModel::removeAttachment()
mediaRow = 1;
}
removeComponent(mediaRow);
refocusCurrentComponent();
if (m_room) {
m_room->cacheForType(m_type)->setAttachmentPath({});
}