Replace HInteractiveRectangle by HTiledelegate

This commit is contained in:
miruka 2019-08-21 04:39:07 -04:00
parent 4abf57c8d4
commit 46e685847f
10 changed files with 215 additions and 276 deletions

View File

@ -1,6 +1,5 @@
- Refactoring - Refactoring
- Use HInterfaceBox for EditAccount Profile and Encryption - Use HInterfaceBox for EditAccount Profile and Encryption
- Use ItemDelegate
- Make all icon SVG files white/black, since we can now use ColorOverlay - Make all icon SVG files white/black, since we can now use ColorOverlay
- Make the icon blue in EditAccount when hovering and no avatar set - Make the icon blue in EditAccount when hovering and no avatar set
@ -12,6 +11,7 @@
- Room Sidepane - Room Sidepane
- Hide when window too small - Hide when window too small
- Also save/load its size - Also save/load its size
- Is auto-sizing actually needed, or can we just set a default manual size?
- When qml syntax highlighting supports ES6 string interpolation, use them - When qml syntax highlighting supports ES6 string interpolation, use them
- Fixes - Fixes

View File

@ -4,6 +4,11 @@ import QtQuick.Layouts 1.12
Button { Button {
id: button id: button
spacing: theme.spacing
leftPadding: spacing / 1.5
rightPadding: spacing / 1.5
topPadding: spacing / 2
bottomPadding: spacing / 2
opacity: enabled ? 1 : theme.disabledElementsOpacity opacity: enabled ? 1 : theme.disabledElementsOpacity
onVisibleChanged: if (! visible) loading = false onVisibleChanged: if (! visible) loading = false

View File

@ -18,8 +18,7 @@ ListView {
highlight: HRectangle { highlight: HRectangle {
color: theme.controls.interactiveRectangle.checkedOverlay color: theme.controls.button.checkedOverlay
opacity: theme.controls.interactiveRectangle.checkedOpacity
} }
// Important: // Important:

View File

@ -0,0 +1,101 @@
import QtQuick 2.12
import QtQuick.Layouts 1.12
HButton {
id: tile
signal activated()
signal highlightMe()
property bool isCurrent: false
readonly property var delegateModel: model
default property var additionalItems: []
readonly property alias title: title
readonly property alias additionalInfo: additionalInfo
readonly property alias rightInfo: rightInfo
readonly property alias subtitle: subtitle
property Item image
property Item details: HColumnLayout {
Layout.fillWidth: true
HRowLayout {
spacing: tile.spacing
HLabel {
id: title
text: "Title"
elide: Text.ElideRight
verticalAlignment: Qt.AlignVCenter
Layout.fillWidth: true
}
HRowLayout {
id: additionalInfo
}
HLabel {
id: rightInfo
font.pixelSize: theme.fontSize.small
visible: Layout.maximumWidth > 0
Layout.maximumWidth:
text && tile.width >= 200 ? implicitWidth : 0
Behavior on Layout.maximumWidth { HNumberAnimation {} }
}
}
HRichLabel {
id: subtitle
textFormat: Text.StyledText
font.pixelSize: theme.fontSize.small
elide: Text.ElideRight
visible: Layout.maximumHeight > 0
Layout.maximumHeight: text ? implicitWidth : 0
Layout.fillWidth: true
Behavior on Layout.maximumHeight { HNumberAnimation {} }
}
}
contentItem: HRowLayout {
spacing: tile.spacing
children: [image, details].concat(additionalItems)
}
onIsCurrentChanged: if (isCurrent) highlightMe()
onHighlightMe: accountRoomList.currentIndex = model.index
onClicked: {
ListView.highlightRangeMode = ListView.NoHighlightRange
ListView.highlightMoveDuration = 0
activated()
ListView.highlightRangeMode = ListView.ApplyRange
ListView.highlightMoveDuration = theme.animationDuration
}
Timer {
interval: 100
repeat: true
running: ListView.currentIndex == -1
// Component.onCompleted won't work for this
onTriggered: if (isCurrent) highlightMe()
}
// Connections {
// target: ListView
// onHideHoverHighlight: tile.hovered = false
// }
}

View File

@ -1,38 +1,18 @@
import QtQuick 2.12 import QtQuick 2.12
import QtQuick.Layouts 1.12
import "../../Base" import "../../Base"
import "../../utils.js" as Utils
HInteractiveRectangle { HTileDelegate {
id: memberDelegate id: memberDelegate
width: memberList.width
height: rowLayout.height
HRowLayout {
id: rowLayout
x: roomSidePane.currentSpacing
width: parent.width - roomSidePane.currentSpacing * 1.5
height: avatar.height + roomSidePane.currentSpacing / 1.5
spacing: roomSidePane.currentSpacing spacing: roomSidePane.currentSpacing
rightPadding: 0
backgroundColor: theme.sidePane.member.background
HUserAvatar { image: HUserAvatar {
id: avatar
userId: model.user_id userId: model.user_id
displayName: model.display_name displayName: model.display_name
avatarUrl: model.avatar_url avatarUrl: model.avatar_url
} }
HColumnLayout { title.color: theme.sidePane.member.name
Layout.fillWidth: true title.text: model.display_name || model.user_id
HLabel {
id: memberName
text: model.display_name || model.user_id
elide: Text.ElideRight
verticalAlignment: Qt.AlignVCenter
Layout.fillWidth: true
}
}
}
} }

View File

@ -6,7 +6,6 @@ import "../../utils.js" as Utils
HColumnLayout { HColumnLayout {
HListView { HListView {
id: memberList id: memberList
bottomMargin: currentSpacing
model: HListModel { model: HListModel {
keyField: "user_id" keyField: "user_id"
@ -16,7 +15,9 @@ HColumnLayout {
) )
} }
delegate: MemberDelegate {} delegate: MemberDelegate {
width: memberList.width
}
Layout.fillWidth: true Layout.fillWidth: true
Layout.fillHeight: true Layout.fillHeight: true

View File

@ -75,7 +75,7 @@ HListView {
} }
function activate() { function activate() {
currentItem.item.activate() currentItem.item.activated()
} }
function toggleCollapseAccount() { function toggleCollapseAccount() {

View File

@ -2,21 +2,24 @@ import QtQuick 2.12
import QtQuick.Layouts 1.12 import QtQuick.Layouts 1.12
import "../Base" import "../Base"
HInteractiveRectangle { HTileDelegate {
id: accountDelegate id: accountDelegate
color: theme.sidePane.account.background spacing: 0
// checked: isCurrent topPadding: model.index > 0 ? sidePane.currentSpacing / 2 : 0
height: row.height bottomPadding: topPadding
backgroundColor: theme.sidePane.account.background
opacity: collapsed && ! forceExpand ?
theme.sidePane.account.collapsedOpacity : 1
readonly property var delegateModel: model isCurrent: window.uiState.page == "Pages/EditAccount/EditAccount.qml" &&
readonly property bool isCurrent:
window.uiState.page == "Pages/EditAccount/EditAccount.qml" &&
window.uiState.pageProperties.userId == model.data.user_id window.uiState.pageProperties.userId == model.data.user_id
readonly property bool forceExpand:
Boolean(accountRoomList.filter) Behavior on opacity { HNumberAnimation {} }
readonly property bool forceExpand: Boolean(accountRoomList.filter)
// Hide harmless error when a filter matches nothing // Hide harmless error when a filter matches nothing
readonly property bool collapsed: try { readonly property bool collapsed: try {
@ -24,109 +27,50 @@ HInteractiveRectangle {
} catch (err) {} } catch (err) {}
onIsCurrentChanged: if (isCurrent) beHighlighted() onActivated: pageLoader.showPage(
"EditAccount/EditAccount", { "userId": model.data.user_id }
)
function beHighlighted() {
accountRoomList.currentIndex = model.index
}
function toggleCollapse() { function toggleCollapse() {
window.uiState.collapseAccounts[model.data.user_id] = ! collapsed window.uiState.collapseAccounts[model.data.user_id] = ! collapsed
window.uiStateChanged() window.uiStateChanged()
} }
function activate() {
pageLoader.showPage(
"EditAccount/EditAccount", { "userId": model.data.user_id }
)
}
image: HUserAvatar {
// Component.onCompleted won't work for this
Timer {
interval: 100
repeat: true
running: accountRoomList.currentIndex == -1
onTriggered: if (isCurrent) beHighlighted()
}
Connections {
target: accountRoomList
onHideHoverHighlight: accountDelegate.hovered = false
}
TapHandler {
onTapped: {
accountRoomList.highlightRangeMode = ListView.NoHighlightRange
accountRoomList.highlightMoveDuration = 0
activate()
accountRoomList.highlightRangeMode = ListView.ApplyRange
accountRoomList.highlightMoveDuration = theme.animationDuration
}
}
HRowLayout {
id: row
width: parent.width
HUserAvatar {
id: avatar
userId: model.data.user_id userId: model.data.user_id
displayName: model.data.display_name displayName: model.data.display_name
avatarUrl: model.data.avatar_url avatarUrl: model.data.avatar_url
opacity: collapsed && ! forceExpand ?
theme.sidePane.account.collapsedOpacity : 1
Behavior on opacity { HNumberAnimation {} }
Layout.topMargin: model.index > 0 ? sidePane.currentSpacing / 2 : 0
Layout.bottomMargin: Layout.topMargin
} }
HLabel { title.color: theme.sidePane.account.name
id: accountLabel title.text: model.data.display_name || model.data.user_id
color: theme.sidePane.account.name title.font.pixelSize: theme.fontSize.big
text: model.data.display_name || model.data.user_id title.leftPadding: sidePane.currentSpacing
font.pixelSize: theme.fontSize.big
elide: HLabel.ElideRight
leftPadding: sidePane.currentSpacing
verticalAlignment: Text.AlignVCenter
opacity: collapsed && ! forceExpand ?
theme.sidePane.account.collapsedOpacity : 1
Behavior on opacity { HNumberAnimation {} }
Layout.fillWidth: true
Layout.fillHeight: true
}
HButton { HButton {
id: expandButton id: expand
iconName: "expand" iconName: "expand"
ico.dimension: 16 ico.dimension: 16
backgroundColor: "transparent" backgroundColor: "transparent"
leftPadding: sidePane.currentSpacing leftPadding: sidePane.currentSpacing / 1.5
rightPadding: leftPadding rightPadding: leftPadding
onClicked: accountDelegate.toggleCollapse() onClicked: accountDelegate.toggleCollapse()
visible: opacity > 0 visible: opacity > 0
opacity: opacity: accountDelegate.forceExpand ? 0 : 1
accountDelegate.forceExpand ? 0 :
collapsed ? theme.sidePane.account.collapsedOpacity + 0.2 :
1
Behavior on opacity { HNumberAnimation {} }
ico.transform: Rotation { ico.transform: Rotation {
origin.x: expandButton.ico.dimension / 2 origin.x: expand.ico.dimension / 2
origin.y: expandButton.ico.dimension / 2 origin.y: expand.ico.dimension / 2
angle: collapsed ? 180 : 90 angle: collapsed ? 180 : 90
Behavior on angle { HNumberAnimation {} } Behavior on angle { HNumberAnimation {} }
} }
Behavior on opacity { HNumberAnimation {} }
Layout.fillHeight: true Layout.fillHeight: true
} }
} }
}

View File

@ -3,141 +3,62 @@ import QtQuick.Layouts 1.12
import "../Base" import "../Base"
import "../utils.js" as Utils import "../utils.js" as Utils
HInteractiveRectangle { HTileDelegate {
id: roomDelegate id: roomDelegate
color: theme.sidePane.room.background spacing: sidePane.currentSpacing
visible: height > 0 backgroundColor: theme.sidePane.room.background
height: rowLayout.height
opacity: model.data.left ? theme.sidePane.room.leftRoomOpacity : 1 opacity: model.data.left ? theme.sidePane.room.leftRoomOpacity : 1
isCurrent: window.uiState.page == "Chat/Chat.qml" &&
window.uiState.pageProperties.userId == model.user_id &&
window.uiState.pageProperties.roomId == model.data.room_id
Behavior on opacity { HNumberAnimation {} } Behavior on opacity { HNumberAnimation {} }
readonly property var delegateModel: model readonly property var eventDate:
model.data.last_event ? model.data.last_event.date : null
readonly property bool forceExpand:
Boolean(accountRoomList.filter)
readonly property bool isCurrent:
window.uiState.page == "Chat/Chat.qml" &&
window.uiState.pageProperties.userId == model.user_id &&
window.uiState.pageProperties.roomId == model.data.room_id
onIsCurrentChanged: if (isCurrent) beHighlighted() onActivated: pageLoader.showRoom(model.user_id, model.data.room_id)
function beHighlighted() { image: HRoomAvatar {
accountRoomList.currentIndex = model.index
}
function activate() {
pageLoader.showRoom(model.user_id, model.data.room_id)
}
// Component.onCompleted won't work for this
Timer {
interval: 100
repeat: true
running: accountRoomList.currentIndex == -1
onTriggered: if (isCurrent) beHighlighted()
}
Connections {
target: accountRoomList
onHideHoverHighlight: roomDelegate.hovered = false
}
TapHandler {
onTapped: {
accountRoomList.highlightRangeMode = ListView.NoHighlightRange
accountRoomList.highlightMoveDuration = 0
activate()
accountRoomList.highlightRangeMode = ListView.ApplyRange
accountRoomList.highlightMoveDuration = theme.animationDuration
}
}
HRowLayout {
id: rowLayout
spacing: sidePane.currentSpacing
x: sidePane.currentSpacing
width: parent.width - sidePane.currentSpacing * 1.75
height: roomName.height + subtitle.height + sidePane.currentSpacing
HRoomAvatar {
id: roomAvatar
displayName: model.data.display_name displayName: model.data.display_name
avatarUrl: model.data.avatar_url avatarUrl: model.data.avatar_url
} }
HColumnLayout { title.color: theme.sidePane.room.name
Layout.fillWidth: true title.text: model.data.display_name || "<i>Empty room</i>"
title.textFormat: model.data.display_name? Text.PlainText : Text.StyledText
HRowLayout { additionalInfo.children: HIcon {
spacing: rowLayout.spacing
HLabel {
id: roomName
color: theme.sidePane.room.name
text: model.data.display_name || "<i>Empty room</i>"
textFormat:
model.data.display_name?
Text.PlainText : Text.StyledText
elide: Text.ElideRight
verticalAlignment: Qt.AlignVCenter
Layout.fillWidth: true
}
HIcon {
svgName: "invite-received" svgName: "invite-received"
visible: Layout.maximumWidth > 0 visible: Layout.maximumWidth > 0
Layout.maximumWidth: Layout.maximumWidth:
model.data.inviter_id && ! model.data.left ? model.data.inviter_id && ! model.data.left ?
implicitWidth : 0 implicitWidth : 0
Behavior on Layout.maximumWidth { HNumberAnimation {} } Behavior on Layout.maximumWidth { HNumberAnimation {} }
} }
HLabel { rightInfo.color: theme.sidePane.room.lastEventDate
readonly property var evDate: rightInfo.text: {
model.data.last_event ? ! eventDate ? "" :
model.data.last_event.date : null
id: lastEventDate Utils.dateIsToday(eventDate) ?
font.pixelSize: theme.fontSize.small Utils.formatTime(eventDate, false) : // no seconds
color: theme.sidePane.room.lastEventDate
text: ! evDate ? "" : eventDate.getFullYear() == new Date().getFullYear() ?
Qt.formatDate(eventDate, "d MMM") : // e.g. "5 Dec"
Utils.dateIsToday(evDate) ? eventDate.getFullYear()
Utils.formatTime(evDate, false) : // no seconds
evDate.getFullYear() == new Date().getFullYear() ?
Qt.formatDate(evDate, "d MMM") : // e.g. "5 Dec"
evDate.getFullYear()
visible: Layout.maximumWidth > 0
Layout.maximumWidth:
text && roomDelegate.width >= 200 ? implicitWidth : 0
Behavior on Layout.maximumWidth { HNumberAnimation {} }
}
} }
HRichLabel { subtitle.color: theme.sidePane.room.subtitle
id: subtitle subtitle.textFormat: Text.StyledText
color: theme.sidePane.room.subtitle subtitle.text: {
visible: Boolean(text)
textFormat: Text.StyledText
font.pixelSize: theme.fontSize.small
elide: Text.ElideRight
text: {
if (! model.data.last_event) { return "" } if (! model.data.last_event) { return "" }
let ev = model.data.last_event let ev = model.data.last_event
@ -151,9 +72,4 @@ HInteractiveRectangle {
ev.sender_name, ev.sender_id ev.sender_name, ev.sender_id
) + ": " + ev.inline_content ) + ": " + ev.inline_content
} }
Layout.fillWidth: true
}
}
}
} }

View File

@ -106,17 +106,6 @@ controls:
color text: colors.text color text: colors.text
interactiveRectangle:
color background: "transparent"
color hoveredOverlay: hsluv(0, 0, 50)
color pressedOverlay: hsluv(0, 0, 50)
color checkedOverlay: hsluv(0, 0, 50)
real hoveredOpacity: 0.3
real pressedOpacity: 0.2
real checkedOpacity: 0.2
textField: textField:
color background: colors.inputBackground color background: colors.inputBackground
color focusedBackground: background color focusedBackground: background
@ -184,6 +173,10 @@ sidePane:
color subtitle: colors.dimText color subtitle: colors.dimText
color lastEventDate: colors.halfDimText color lastEventDate: colors.halfDimText
member:
color background: "transparent"
color name: colors.text
settingsButton: settingsButton:
color background: colors.inputBackground color background: colors.inputBackground