mirror of
https://github.com/status-im/status-desktop.git
synced 2025-01-22 20:40:18 +00:00
feat: style mention suggestions and make it work with keyboard
This commit is contained in:
parent
676549cccd
commit
4371501efc
@ -183,42 +183,6 @@ StackLayout {
|
||||
height: chatInput.height
|
||||
Layout.preferredHeight: height
|
||||
color: "transparent"
|
||||
|
||||
SuggestionBox {
|
||||
id: suggestionsBox
|
||||
model: suggestions
|
||||
width: chatContainer.width
|
||||
anchors.bottom: inputArea.top
|
||||
anchors.left: inputArea.left
|
||||
filter: chatInput.textInput.text
|
||||
cursorPosition: chatInput.textInput.cursorPosition
|
||||
property: "ensName, alias"
|
||||
onItemSelected: function (item, lastAtPosition, lastCursorPosition) {
|
||||
let hasEmoji = Emoji.hasEmoji(chatInput.textInput.text)
|
||||
let currentText = hasEmoji ?
|
||||
chatsModel.plainText(Emoji.deparse(chatInput.textInput.text)) :
|
||||
chatsModel.plainText(chatInput.textInput.text);
|
||||
|
||||
let aliasName = item[suggestionsBox.property.split(",").map(p => p.trim()).find(p => !!item[p])]
|
||||
aliasName = aliasName.replace(".stateofus.eth", "")
|
||||
let nameLen = aliasName.length + 2 // We're doing a +2 here because of the `@` and the trailing whitespace
|
||||
let position = 0;
|
||||
let text = ""
|
||||
|
||||
if (currentText === "@") {
|
||||
position = nameLen
|
||||
text = "@" + aliasName + " "
|
||||
} else {
|
||||
let left = currentText.substring(0, lastAtPosition)
|
||||
let right = currentText.substring(hasEmoji ? lastCursorPosition + 2 : lastCursorPosition)
|
||||
text = `${left} @${aliasName} ${right}`
|
||||
}
|
||||
|
||||
chatInput.textInput.text = hasEmoji ? Emoji.parse(text, "26x26") : text
|
||||
chatInput.textInput.cursorPosition = lastAtPosition + aliasName.length + 2
|
||||
suggestionsBox.suggestionsModel.clear()
|
||||
}
|
||||
}
|
||||
|
||||
Loader {
|
||||
active: chatsModel.loadingMessages
|
||||
|
@ -34,19 +34,24 @@ Rectangle {
|
||||
property alias property: filterItem.property
|
||||
property int cursorPosition
|
||||
signal itemSelected(var item, int lastAtPosition, int lastCursorPosition)
|
||||
property alias listView: listView
|
||||
|
||||
function selectCurrentItem() {
|
||||
container.itemSelected(listView.model.get(listView.currentIndex), filterItem.lastAtPosition, filterItem.cursorPosition)
|
||||
}
|
||||
|
||||
z: parent.z + 100
|
||||
visible: filter.length > 0 && suggestionsModel.count > 0
|
||||
height: visible ? popup.height + (Style.current.padding * 2) : 0
|
||||
height: Math.min(400, listView.contentHeight + Style.current.smallPadding)
|
||||
|
||||
opacity: visible ? 1.0 : 0
|
||||
Behavior on opacity {
|
||||
NumberAnimation { }
|
||||
}
|
||||
|
||||
// --- defaults
|
||||
color: Style.current.white2
|
||||
radius: 16
|
||||
color:Style.current.background
|
||||
radius: Style.current.radius
|
||||
border.width: 0
|
||||
layer.enabled: true
|
||||
layer.effect: DropShadow{
|
||||
width: container.width
|
||||
@ -69,69 +74,55 @@ Rectangle {
|
||||
}
|
||||
|
||||
|
||||
ScrollView {
|
||||
id: popup
|
||||
height: items.height >= 400 ? 400 : items.height
|
||||
width: parent.width
|
||||
anchors.centerIn: parent
|
||||
ListView {
|
||||
id: listView
|
||||
model: container.suggestionsModel
|
||||
keyNavigationEnabled: true
|
||||
anchors.fill: parent
|
||||
anchors.topMargin: Style.current.halfPadding
|
||||
anchors.leftMargin: Style.current.halfPadding
|
||||
anchors.rightMargin: Style.current.halfPadding
|
||||
anchors.bottomMargin: Style.current.halfPadding
|
||||
clip: true
|
||||
|
||||
property int selectedIndex
|
||||
property var selectedItem: selectedIndex == -1 ? null : model[selectedIndex]
|
||||
signal suggestionClicked(var item)
|
||||
ScrollBar.vertical.policy: items.contentHeight > items.height ? ScrollBar.AlwaysOn : ScrollBar.AlwaysOff
|
||||
ScrollBar.horizontal.policy: ScrollBar.AlwaysOff
|
||||
|
||||
Column {
|
||||
id: items
|
||||
clip: true
|
||||
height: childrenRect.height
|
||||
delegate: Rectangle {
|
||||
id: rectangle
|
||||
color: listView.currentIndex === index ? Style.current.backgroundHover : Style.current.transparent
|
||||
border.width: 0
|
||||
width: parent.width
|
||||
Repeater {
|
||||
id: repeater
|
||||
model: container.suggestionsModel
|
||||
delegate: Rectangle {
|
||||
id: delegateItem
|
||||
property var suggestion: model
|
||||
property bool hovered
|
||||
height: 42
|
||||
radius: Style.current.radius
|
||||
|
||||
height: 50
|
||||
width: container.width
|
||||
color: hovered ? Style.current.blue : "white"
|
||||
StatusImageIdenticon {
|
||||
id: accountImage
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
anchors.left: parent.left
|
||||
anchors.leftMargin: Style.current.smallPadding
|
||||
source: model.identicon
|
||||
}
|
||||
|
||||
StatusImageIdenticon {
|
||||
id: accountImage
|
||||
anchors.left: parent.left
|
||||
anchors.leftMargin: Style.current.smallPadding
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
source: suggestion.identicon
|
||||
}
|
||||
StyledText {
|
||||
text: model[container.property.split(",").map(p => p.trim()).find(p => !!model[p])]
|
||||
color: Style.current.textColor
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
anchors.left: accountImage.right
|
||||
anchors.leftMargin: Style.current.smallPadding
|
||||
font.pixelSize: 15
|
||||
}
|
||||
|
||||
Text {
|
||||
id: textComponent
|
||||
color: delegateItem.hovered ? Style.current.white : Style.current.black
|
||||
text: suggestion[container.property.split(",").map(p => p.trim()).find(p => !!suggestion[p])]
|
||||
width: parent.width
|
||||
height: parent.height
|
||||
anchors.left: accountImage.right
|
||||
anchors.leftMargin: Style.current.padding
|
||||
verticalAlignment: Text.AlignVCenter
|
||||
font.pixelSize: 15
|
||||
}
|
||||
MouseArea {
|
||||
cursorShape: Qt.PointingHandCursor
|
||||
anchors.fill: parent
|
||||
hoverEnabled: true
|
||||
onEntered: {
|
||||
delegateItem.hovered = true
|
||||
}
|
||||
onExited: {
|
||||
delegateItem.hovered = false
|
||||
}
|
||||
onClicked: {
|
||||
container.itemSelected(delegateItem.suggestion, filterItem.lastAtPosition, filterItem.cursorPosition)
|
||||
}
|
||||
}
|
||||
MouseArea {
|
||||
cursorShape: Qt.PointingHandCursor
|
||||
anchors.fill: parent
|
||||
hoverEnabled: true
|
||||
onEntered: {
|
||||
listView.currentIndex = index
|
||||
}
|
||||
onClicked: {
|
||||
container.itemSelected(model, filterItem.lastAtPosition, filterItem.cursorPosition)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -7,6 +7,7 @@ import QtQuick.Dialogs 1.3
|
||||
import "../../imports"
|
||||
import "../../shared"
|
||||
import "../../app/AppLayouts/Chat/ChatColumn/samples"
|
||||
import "../../app/AppLayouts/Chat/ChatColumn"
|
||||
|
||||
import "./emojiList.js" as EmojiJSON
|
||||
|
||||
@ -85,6 +86,11 @@ Rectangle {
|
||||
event.accepted = true;
|
||||
return
|
||||
}
|
||||
if (suggestionsBox.visible) {
|
||||
suggestionsBox.selectCurrentItem();
|
||||
event.accepted = true;
|
||||
return
|
||||
}
|
||||
if (messageInputField.length < messageLimit) {
|
||||
sendMsg(event);
|
||||
return;
|
||||
@ -98,9 +104,11 @@ Rectangle {
|
||||
}
|
||||
|
||||
if (event.key === Qt.Key_Down) {
|
||||
suggestionsBox.listView.incrementCurrentIndex()
|
||||
return emojiSuggestions.listView.incrementCurrentIndex()
|
||||
}
|
||||
if (event.key === Qt.Key_Up) {
|
||||
suggestionsBox.listView.decrementCurrentIndex()
|
||||
return emojiSuggestions.listView.decrementCurrentIndex()
|
||||
}
|
||||
|
||||
@ -342,6 +350,42 @@ Rectangle {
|
||||
id: emojiSuggestions
|
||||
}
|
||||
|
||||
SuggestionBox {
|
||||
id: suggestionsBox
|
||||
model: suggestions
|
||||
x : messageInput.x
|
||||
y: -height - Style.current.smallPadding
|
||||
width: messageInput.width
|
||||
filter: messageInputField.text
|
||||
cursorPosition: messageInputField.cursorPosition
|
||||
property: "ensName, alias"
|
||||
onItemSelected: function (item, lastAtPosition, lastCursorPosition) {
|
||||
let hasEmoji = Emoji.hasEmoji(messageInputField.text)
|
||||
let currentText = hasEmoji ?
|
||||
chatsModel.plainText(Emoji.deparse(messageInputField.text)) :
|
||||
chatsModel.plainText(messageInputField.text);
|
||||
|
||||
let aliasName = item[suggestionsBox.property.split(",").map(p => p.trim()).find(p => !!item[p])]
|
||||
aliasName = aliasName.replace(".stateofus.eth", "")
|
||||
let nameLen = aliasName.length + 2 // We're doing a +2 here because of the `@` and the trailing whitespace
|
||||
let position = 0;
|
||||
let text = ""
|
||||
|
||||
if (currentText === "@") {
|
||||
position = nameLen
|
||||
text = "@" + aliasName + " "
|
||||
} else {
|
||||
let left = currentText.substring(0, lastAtPosition)
|
||||
let right = currentText.substring(hasEmoji ? lastCursorPosition + 2 : lastCursorPosition)
|
||||
text = `${left} @${aliasName} ${right}`
|
||||
}
|
||||
|
||||
messageInputField.text = hasEmoji ? Emoji.parse(text, "26x26") : text
|
||||
messageInputField.cursorPosition = lastAtPosition + aliasName.length + 2
|
||||
suggestionsBox.suggestionsModel.clear()
|
||||
}
|
||||
}
|
||||
|
||||
StatusChatCommandsPopup {
|
||||
id: chatCommandsPopup
|
||||
x: 8
|
||||
|
Loading…
x
Reference in New Issue
Block a user