Compare commits
84 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
da30e66127 | ||
|
|
4516e1e0f4 | ||
|
|
bd80f65163 | ||
|
|
f828ecf282 | ||
|
|
a0483167c5 | ||
|
|
87288f508c | ||
|
|
dc184ed2fd | ||
|
|
49e1bf9ab1 | ||
|
|
74acf3f9dc | ||
|
|
38205d2791 | ||
|
|
81da926d4f | ||
|
|
1018fe5d3f | ||
|
|
58b32dd50f | ||
|
|
82184b895a | ||
|
|
da0f6f78a4 | ||
|
|
cfd06d064c | ||
|
|
a90e9ae92a | ||
|
|
8ab0002057 | ||
|
|
e1840be234 | ||
|
|
d6ecaaa344 | ||
|
|
0c08c2ab89 | ||
|
|
39ff11e059 | ||
|
|
93254431c5 | ||
|
|
fc14a8eac8 | ||
|
|
50759bb3ca | ||
|
|
23134d8e72 | ||
|
|
7cd095f76a | ||
|
|
d5c3054da4 | ||
|
|
ae12c838bd | ||
|
|
51727dd345 | ||
|
|
5611b000fb | ||
|
|
461896e228 | ||
|
|
e388536a03 | ||
|
|
61f22edd86 | ||
|
|
9e368691d6 | ||
|
|
dad2b3ec8f | ||
|
|
8821c37ff8 | ||
|
|
c105170eca | ||
|
|
b07c04eddc | ||
|
|
7aa0f68b10 | ||
|
|
cbdae4c312 | ||
|
|
9210940556 | ||
|
|
d8489527b4 | ||
|
|
64c9cd97de | ||
|
|
119a9890b1 | ||
|
|
69be6b5939 | ||
|
|
112152f2df | ||
|
|
2ef634a6cb | ||
|
|
fd31b4fb74 | ||
|
|
3b12520fa2 | ||
|
|
24718a5f72 | ||
|
|
db62bacc7e | ||
|
|
6500669b67 | ||
|
|
557d151ed4 | ||
|
|
95ffd485b4 | ||
|
|
ebd38fb435 | ||
|
|
a5b999e682 | ||
|
|
41d34fc0e4 | ||
|
|
b51194f90f | ||
|
|
80ac9e1ba7 | ||
|
|
e3874c824a | ||
|
|
6599c6b609 | ||
|
|
13d522221c | ||
|
|
dd8f926f32 | ||
|
|
258312e798 | ||
|
|
43d40c7e75 | ||
|
|
cbcc9a6514 | ||
|
|
625048610b | ||
|
|
fa47b67e3d | ||
|
|
9347a66acf | ||
|
|
317df56ffa | ||
|
|
fed9197716 | ||
|
|
1e892599e9 | ||
|
|
b7229ca0cf | ||
|
|
953b711823 | ||
|
|
01d903efd3 | ||
|
|
241dd81932 | ||
|
|
f6dfe0cbcf | ||
|
|
f10b97139c | ||
|
|
385c5b3405 | ||
|
|
7bc6f906f8 | ||
|
|
b8b1434a95 | ||
|
|
85c7a4bcb3 | ||
|
|
84b698a7e8 |
@@ -9,7 +9,7 @@ cmake_minimum_required(VERSION 3.16)
|
|||||||
# KDE Applications version, managed by release script.
|
# KDE Applications version, managed by release script.
|
||||||
set(RELEASE_SERVICE_VERSION_MAJOR "24")
|
set(RELEASE_SERVICE_VERSION_MAJOR "24")
|
||||||
set(RELEASE_SERVICE_VERSION_MINOR "11")
|
set(RELEASE_SERVICE_VERSION_MINOR "11")
|
||||||
set(RELEASE_SERVICE_VERSION_MICRO "70")
|
set(RELEASE_SERVICE_VERSION_MICRO "90")
|
||||||
set(RELEASE_SERVICE_VERSION "${RELEASE_SERVICE_VERSION_MAJOR}.${RELEASE_SERVICE_VERSION_MINOR}.${RELEASE_SERVICE_VERSION_MICRO}")
|
set(RELEASE_SERVICE_VERSION "${RELEASE_SERVICE_VERSION_MAJOR}.${RELEASE_SERVICE_VERSION_MINOR}.${RELEASE_SERVICE_VERSION_MICRO}")
|
||||||
|
|
||||||
project(NeoChat VERSION ${RELEASE_SERVICE_VERSION})
|
project(NeoChat VERSION ${RELEASE_SERVICE_VERSION})
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ A Qt/QML based Matrix client.
|
|||||||
|
|
||||||
<a href='https://matrix.org'><img src='https://matrix.org/docs/legacy/made-for-matrix.png' alt='Made for Matrix' height=64 target=_blank /></a>
|
<a href='https://matrix.org'><img src='https://matrix.org/docs/legacy/made-for-matrix.png' alt='Made for Matrix' height=64 target=_blank /></a>
|
||||||
<a href='https://flathub.org/apps/details/org.kde.neochat'><img width='190px' alt='Download on Flathub' src='https://flathub.org/assets/badges/flathub-badge-i-en.png'/></a>
|
<a href='https://flathub.org/apps/details/org.kde.neochat'><img width='190px' alt='Download on Flathub' src='https://flathub.org/assets/badges/flathub-badge-i-en.png'/></a>
|
||||||
<a href='https://snapcraft.io/neochat'><img width='190px' alt='Download on the Snap Store' src='https://snapcraft.io/static/images/badges/en/snap-store-black.svg'/></a>
|
<a href='https://snapcraft.io/neochat'><img width='190px' alt='Download on the Snap Store' src='https://apps.kde.org/store_badges/snapstore/en.svg'/></a>
|
||||||
|
|
||||||
## Introduction
|
## Introduction
|
||||||
|
|
||||||
|
|||||||
@@ -5,6 +5,26 @@
|
|||||||
"!room_id_1234:localhost:1234": {
|
"!room_id_1234:localhost:1234": {
|
||||||
"state": {
|
"state": {
|
||||||
"events": [
|
"events": [
|
||||||
|
{
|
||||||
|
"content": {
|
||||||
|
"m.federate": true,
|
||||||
|
"predecessor": {
|
||||||
|
"event_id": "$something:example.org",
|
||||||
|
"room_id": "!oldroom:example.org"
|
||||||
|
},
|
||||||
|
"room_version": "11"
|
||||||
|
},
|
||||||
|
"event_id": "$143273582443PhrSn:example.org",
|
||||||
|
"origin_server_ts": 1432735824653,
|
||||||
|
"room_id": "!jEsUZKDJdhlrceRyVU:example.org",
|
||||||
|
"sender": "@example:example.org",
|
||||||
|
"state_key": "",
|
||||||
|
"type": "m.room.create",
|
||||||
|
"unsigned": {
|
||||||
|
"age": 1234,
|
||||||
|
"membership": "join"
|
||||||
|
}
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"type": "m.room.member",
|
"type": "m.room.member",
|
||||||
"state_key": "@user:localhost:1234",
|
"state_key": "@user:localhost:1234",
|
||||||
@@ -26,6 +46,26 @@
|
|||||||
},
|
},
|
||||||
"timeline": {
|
"timeline": {
|
||||||
"events": [
|
"events": [
|
||||||
|
{
|
||||||
|
"content": {
|
||||||
|
"m.federate": true,
|
||||||
|
"predecessor": {
|
||||||
|
"event_id": "$something:example.org",
|
||||||
|
"room_id": "!oldroom:example.org"
|
||||||
|
},
|
||||||
|
"room_version": "11"
|
||||||
|
},
|
||||||
|
"event_id": "$143273582443PhrSn:example.org",
|
||||||
|
"origin_server_ts": 1432735824653,
|
||||||
|
"room_id": "!jEsUZKDJdhlrceRyVU:example.org",
|
||||||
|
"sender": "@example:example.org",
|
||||||
|
"state_key": "",
|
||||||
|
"type": "m.room.create",
|
||||||
|
"unsigned": {
|
||||||
|
"age": 1234,
|
||||||
|
"membership": "join"
|
||||||
|
}
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"type": "m.room.message",
|
"type": "m.room.message",
|
||||||
"sender": "@user:localhost:1234",
|
"sender": "@user:localhost:1234",
|
||||||
|
|||||||
@@ -535,7 +535,7 @@ void TextHandlerTest::componentOutput_data()
|
|||||||
QVariantMap{{QStringLiteral("class"), QStringLiteral("html")}}}};
|
QVariantMap{{QStringLiteral("class"), QStringLiteral("html")}}}};
|
||||||
QTest::newRow("quote") << QStringLiteral("<p>Text</p>\n<blockquote>\n<p>blockquote</p>\n</blockquote>")
|
QTest::newRow("quote") << QStringLiteral("<p>Text</p>\n<blockquote>\n<p>blockquote</p>\n</blockquote>")
|
||||||
<< QList<MessageComponent>{MessageComponent{MessageComponentType::Text, QStringLiteral("Text"), {}},
|
<< QList<MessageComponent>{MessageComponent{MessageComponentType::Text, QStringLiteral("Text"), {}},
|
||||||
MessageComponent{MessageComponentType::Quote, QStringLiteral("\"blockquote\""), {}}};
|
MessageComponent{MessageComponentType::Quote, QStringLiteral("“blockquote”"), {}}};
|
||||||
QTest::newRow("no tag first paragraph") << QStringLiteral("Text\n<p>Text</p>")
|
QTest::newRow("no tag first paragraph") << QStringLiteral("Text\n<p>Text</p>")
|
||||||
<< QList<MessageComponent>{MessageComponent{MessageComponentType::Text, QStringLiteral("Text"), {}},
|
<< QList<MessageComponent>{MessageComponent{MessageComponentType::Text, QStringLiteral("Text"), {}},
|
||||||
MessageComponent{MessageComponentType::Text, QStringLiteral("Text"), {}}};
|
MessageComponent{MessageComponentType::Text, QStringLiteral("Text"), {}}};
|
||||||
|
|||||||
@@ -54,10 +54,13 @@
|
|||||||
<summary xml:lang="ar">دردش على ماتركس</summary>
|
<summary xml:lang="ar">دردش على ماتركس</summary>
|
||||||
<summary xml:lang="ca">Xat a Matrix</summary>
|
<summary xml:lang="ca">Xat a Matrix</summary>
|
||||||
<summary xml:lang="ca-valencia">Xat a Matrix</summary>
|
<summary xml:lang="ca-valencia">Xat a Matrix</summary>
|
||||||
|
<summary xml:lang="de">Über Matrix unterhalten</summary>
|
||||||
<summary xml:lang="en-GB">Chat on Matrix</summary>
|
<summary xml:lang="en-GB">Chat on Matrix</summary>
|
||||||
<summary xml:lang="es">Charle en Matrix</summary>
|
<summary xml:lang="es">Charle en Matrix</summary>
|
||||||
<summary xml:lang="eu">Berriketa Matrix-en</summary>
|
<summary xml:lang="eu">Berriketa Matrix-en</summary>
|
||||||
<summary xml:lang="fr">Discuter sur Matrix</summary>
|
<summary xml:lang="fr">Discuter sur Matrix</summary>
|
||||||
|
<summary xml:lang="gl">Charlar en Matrix</summary>
|
||||||
|
<summary xml:lang="hu">Csevegés Matrixon</summary>
|
||||||
<summary xml:lang="ia">Conversation en ditecto sur Matrix</summary>
|
<summary xml:lang="ia">Conversation en ditecto sur Matrix</summary>
|
||||||
<summary xml:lang="it">Chat su Matrix</summary>
|
<summary xml:lang="it">Chat su Matrix</summary>
|
||||||
<summary xml:lang="ka">ისაუბრეთ Matrix-ზე</summary>
|
<summary xml:lang="ka">ისაუბრეთ Matrix-ზე</summary>
|
||||||
@@ -65,6 +68,7 @@
|
|||||||
<summary xml:lang="nn">Prat med via Matrix</summary>
|
<summary xml:lang="nn">Prat med via Matrix</summary>
|
||||||
<summary xml:lang="pl">Rozmawiaj na Matriksie</summary>
|
<summary xml:lang="pl">Rozmawiaj na Matriksie</summary>
|
||||||
<summary xml:lang="sl">Klepet na Matrixu</summary>
|
<summary xml:lang="sl">Klepet na Matrixu</summary>
|
||||||
|
<summary xml:lang="sv">Chatta på Matrix</summary>
|
||||||
<summary xml:lang="ta">மேட்ரிக்ஸுக்கான உரையாடல் செயலி</summary>
|
<summary xml:lang="ta">மேட்ரிக்ஸுக்கான உரையாடல் செயலி</summary>
|
||||||
<summary xml:lang="tr">Matrix Üzerinde Sohbet</summary>
|
<summary xml:lang="tr">Matrix Üzerinde Sohbet</summary>
|
||||||
<summary xml:lang="uk">Спілкування у Matrix</summary>
|
<summary xml:lang="uk">Спілкування у Matrix</summary>
|
||||||
|
|||||||
@@ -87,47 +87,26 @@ GenericName[uk]=Клієнт Matrix
|
|||||||
GenericName[x-test]=xxMatrix Clientxx
|
GenericName[x-test]=xxMatrix Clientxx
|
||||||
GenericName[zh_CN]=Matrix 客户端
|
GenericName[zh_CN]=Matrix 客户端
|
||||||
GenericName[zh_TW]=Matrix 用戶端
|
GenericName[zh_TW]=Matrix 用戶端
|
||||||
Comment=Client for the Matrix protocol
|
Comment=Chat on Matrix
|
||||||
Comment[ar]=عميل لميفاق ماتركس
|
Comment[ca]=Xat a Matrix
|
||||||
Comment[az]=Matrix protokolu üçün müştəri
|
Comment[ca@valencia]=Xat a Matrix
|
||||||
Comment[ca]=Client per al protocol Matrix
|
Comment[de]=Über Matrix unterhalten
|
||||||
Comment[ca@valencia]=Client per al protocol Matrix
|
Comment[en_GB]=Chat on Matrix
|
||||||
Comment[de]=Programm für das Matrix-Protokoll
|
Comment[es]=Chat en Matrix
|
||||||
Comment[el]=Πελάτης για το πρωτόκολλο Matrix
|
Comment[eu]=Berriketa Matrix-en
|
||||||
Comment[en_GB]=Client for the Matrix protocol
|
Comment[fr]=Clavarder sur Matrix
|
||||||
Comment[eo]=Kliento por la Matrix-protokolo
|
Comment[gl]=Charle en Matrix
|
||||||
Comment[es]=Cliente para el protocolo Matrix
|
Comment[hu]=Csevegés Matrixon
|
||||||
Comment[eu]=Matrix protokolorako bezeroa
|
Comment[ia]=Conversation en ditecto sur Matrix
|
||||||
Comment[fi]=Asiakas Matrix-yhteyskäytännölle
|
Comment[it]= su Matrix
|
||||||
Comment[fr]=Client pour le protocole « Matrix »
|
Comment[ka]=საუბარი Matrix-ზე
|
||||||
Comment[gl]=Cliente para o protocolo Matrix.
|
Comment[pl]=Rozmawiaj na Matriksie
|
||||||
Comment[he]=לקוח לפרוטוקול Matrix
|
Comment[sl]=Klepet na Matrixu
|
||||||
Comment[hu]=Kliens a Matrix protokollhoz
|
Comment[sv]=Chatta på Matrix
|
||||||
Comment[ia]=Cliente per le protocollo de Matrix
|
Comment[ta]=மேட்ரிக்ஸில் உரையாட உதவும்
|
||||||
Comment[id]=Klien untuk protokol Matrix
|
Comment[tr]=Matrix Üzerinde Sohbet Et
|
||||||
Comment[ie]=Un cliente del protocol Matrix
|
Comment[uk]=Спілкування у Matrix
|
||||||
Comment[it]=Client per il protocollo Matrix
|
Comment[zh_TW]=在 Matrix 上聊天
|
||||||
Comment[ka]=კლიენტი Matrix-ის პროტოკოლისთვის
|
|
||||||
Comment[ko]=Matrix 프로토콜용 클라이언트
|
|
||||||
Comment[lt]=Matrix protokolo kliento programa
|
|
||||||
Comment[lv]=Klients „Matrix“ protokolam
|
|
||||||
Comment[nl]=Client voor het Matrix-protocol
|
|
||||||
Comment[nn]=Klient for Matrix-protokollen
|
|
||||||
Comment[pa]=ਮੈਟਰਿਕਸ ਪਰੋਟੋਕਾਲ ਲਈ ਕਲਾਈਂਟ ਹੈ
|
|
||||||
Comment[pl]=Program obsługi protokołu Matriksa
|
|
||||||
Comment[pt]=Cliente para o protocolo Matrix
|
|
||||||
Comment[pt_BR]=Cliente para o protocolo Matrix
|
|
||||||
Comment[ro]=Client pentru protocolul Matrix
|
|
||||||
Comment[ru]=Клиент для протокола Matrix
|
|
||||||
Comment[sk]=Klient protokolu Matrix
|
|
||||||
Comment[sl]=Odjemalec za protokol Matrix
|
|
||||||
Comment[sv]=Klient för protokollet Matrix
|
|
||||||
Comment[ta]=Matrix நெறிமுறைக்கான வாங்கி
|
|
||||||
Comment[tr]=Matrix protokolü için istemci
|
|
||||||
Comment[uk]=Клієнт протоколу Matrix
|
|
||||||
Comment[x-test]=xxClient for the Matrix protocolxx
|
|
||||||
Comment[zh_CN]=为 Matrix 协议打造的客户端
|
|
||||||
Comment[zh_TW]=Matrix 通訊協定的用戶端
|
|
||||||
MimeType=x-scheme-handler/matrix;
|
MimeType=x-scheme-handler/matrix;
|
||||||
Exec=neochat %u
|
Exec=neochat %u
|
||||||
Terminal=false
|
Terminal=false
|
||||||
|
|||||||
384
po/ar/neochat.po
384
po/ar/neochat.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
384
po/az/neochat.po
384
po/az/neochat.po
File diff suppressed because it is too large
Load Diff
677
po/ca/neochat.po
677
po/ca/neochat.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
384
po/cs/neochat.po
384
po/cs/neochat.po
File diff suppressed because it is too large
Load Diff
381
po/da/neochat.po
381
po/da/neochat.po
File diff suppressed because it is too large
Load Diff
704
po/de/neochat.po
704
po/de/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/el/neochat.po
384
po/el/neochat.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
384
po/eo/neochat.po
384
po/eo/neochat.po
File diff suppressed because it is too large
Load Diff
383
po/es/neochat.po
383
po/es/neochat.po
File diff suppressed because it is too large
Load Diff
461
po/eu/neochat.po
461
po/eu/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/fi/neochat.po
384
po/fi/neochat.po
File diff suppressed because it is too large
Load Diff
393
po/fr/neochat.po
393
po/fr/neochat.po
File diff suppressed because it is too large
Load Diff
448
po/gl/neochat.po
448
po/gl/neochat.po
File diff suppressed because it is too large
Load Diff
451
po/hu/neochat.po
451
po/hu/neochat.po
File diff suppressed because it is too large
Load Diff
390
po/ia/neochat.po
390
po/ia/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/id/neochat.po
384
po/id/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/ie/neochat.po
384
po/ie/neochat.po
File diff suppressed because it is too large
Load Diff
392
po/it/neochat.po
392
po/it/neochat.po
File diff suppressed because it is too large
Load Diff
376
po/ja/neochat.po
376
po/ja/neochat.po
File diff suppressed because it is too large
Load Diff
383
po/ka/neochat.po
383
po/ka/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/ko/neochat.po
384
po/ko/neochat.po
File diff suppressed because it is too large
Load Diff
376
po/lt/neochat.po
376
po/lt/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/lv/neochat.po
384
po/lv/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/nl/neochat.po
384
po/nl/neochat.po
File diff suppressed because it is too large
Load Diff
381
po/nn/neochat.po
381
po/nn/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/pa/neochat.po
384
po/pa/neochat.po
File diff suppressed because it is too large
Load Diff
401
po/pl/neochat.po
401
po/pl/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/pt/neochat.po
384
po/pt/neochat.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
384
po/ru/neochat.po
384
po/ru/neochat.po
File diff suppressed because it is too large
Load Diff
384
po/sk/neochat.po
384
po/sk/neochat.po
File diff suppressed because it is too large
Load Diff
383
po/sl/neochat.po
383
po/sl/neochat.po
File diff suppressed because it is too large
Load Diff
400
po/sv/neochat.po
400
po/sv/neochat.po
File diff suppressed because it is too large
Load Diff
401
po/ta/neochat.po
401
po/ta/neochat.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
396
po/tr/neochat.po
396
po/tr/neochat.po
File diff suppressed because it is too large
Load Diff
383
po/uk/neochat.po
383
po/uk/neochat.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -200,6 +200,12 @@ set_source_files_properties(qml/OsmLocationPlugin.qml PROPERTIES
|
|||||||
QT_QML_SINGLETON_TYPE TRUE
|
QT_QML_SINGLETON_TYPE TRUE
|
||||||
)
|
)
|
||||||
|
|
||||||
|
if(ANDROID OR WIN32)
|
||||||
|
set_source_files_properties(qml/ShareActionStub.qml PROPERTIES
|
||||||
|
QT_QML_SOURCE_TYPENAME ShareAction
|
||||||
|
)
|
||||||
|
endif()
|
||||||
|
|
||||||
ecm_add_qml_module(neochat URI org.kde.neochat GENERATE_PLUGIN_SOURCE
|
ecm_add_qml_module(neochat URI org.kde.neochat GENERATE_PLUGIN_SOURCE
|
||||||
OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/src/org/kde/neochat
|
OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/src/org/kde/neochat
|
||||||
QML_FILES
|
QML_FILES
|
||||||
@@ -311,13 +317,9 @@ if(NOT ANDROID AND NOT WIN32)
|
|||||||
qml/EditMenu.qml
|
qml/EditMenu.qml
|
||||||
)
|
)
|
||||||
else()
|
else()
|
||||||
set_source_files_properties(qml/ShareActionStub.qml PROPERTIES
|
|
||||||
QT_RESOURCE_ALIAS qml/ShareAction.qml
|
|
||||||
)
|
|
||||||
qt_target_qml_sources(neochat QML_FILES qml/ShareActionStub.qml)
|
qt_target_qml_sources(neochat QML_FILES qml/ShareActionStub.qml)
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
|
|
||||||
configure_file(config-neochat.h.in ${CMAKE_CURRENT_BINARY_DIR}/config-neochat.h)
|
configure_file(config-neochat.h.in ${CMAKE_CURRENT_BINARY_DIR}/config-neochat.h)
|
||||||
|
|
||||||
if(WIN32)
|
if(WIN32)
|
||||||
|
|||||||
@@ -176,13 +176,14 @@ QQC2.Control {
|
|||||||
RowLayout {
|
RowLayout {
|
||||||
QQC2.ScrollView {
|
QQC2.ScrollView {
|
||||||
id: chatBarScrollView
|
id: chatBarScrollView
|
||||||
|
Layout.topMargin: Kirigami.Units.smallSpacing
|
||||||
|
Layout.bottomMargin: Kirigami.Units.smallSpacing
|
||||||
|
Layout.leftMargin: Kirigami.Units.largeSpacing
|
||||||
|
Layout.rightMargin: Kirigami.Units.largeSpacing
|
||||||
|
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
Layout.maximumHeight: Kirigami.Units.gridUnit * 8
|
Layout.maximumHeight: Kirigami.Units.gridUnit * 8
|
||||||
|
Layout.minimumHeight: Kirigami.Units.gridUnit * 3
|
||||||
Layout.topMargin: Kirigami.Units.smallSpacing
|
|
||||||
Layout.bottomMargin: Kirigami.Units.smallSpacing
|
|
||||||
Layout.minimumHeight: Kirigami.Units.gridUnit * 2
|
|
||||||
|
|
||||||
// HACK: This is to stop the ScrollBar flickering on and off as the height is increased
|
// HACK: This is to stop the ScrollBar flickering on and off as the height is increased
|
||||||
QQC2.ScrollBar.vertical.policy: chatBarHeightAnimation.running && implicitHeight <= height ? QQC2.ScrollBar.AlwaysOff : QQC2.ScrollBar.AsNeeded
|
QQC2.ScrollBar.vertical.policy: chatBarHeightAnimation.running && implicitHeight <= height ? QQC2.ScrollBar.AlwaysOff : QQC2.ScrollBar.AsNeeded
|
||||||
@@ -320,12 +321,11 @@ QQC2.Control {
|
|||||||
id: actionsRow
|
id: actionsRow
|
||||||
spacing: 0
|
spacing: 0
|
||||||
Layout.alignment: Qt.AlignBottom
|
Layout.alignment: Qt.AlignBottom
|
||||||
Layout.bottomMargin: Kirigami.Units.smallSpacing * 1.5
|
Layout.bottomMargin: Kirigami.Units.smallSpacing * 4
|
||||||
|
|
||||||
Repeater {
|
Repeater {
|
||||||
model: root.actions
|
model: root.actions
|
||||||
delegate: QQC2.ToolButton {
|
delegate: QQC2.ToolButton {
|
||||||
Layout.alignment: Qt.AlignVCenter
|
|
||||||
icon.name: modelData.isBusy ? "" : (modelData.icon.name.length > 0 ? modelData.icon.name : modelData.icon.source)
|
icon.name: modelData.isBusy ? "" : (modelData.icon.name.length > 0 ? modelData.icon.name : modelData.icon.source)
|
||||||
onClicked: modelData.trigger()
|
onClicked: modelData.trigger()
|
||||||
|
|
||||||
@@ -342,7 +342,6 @@ QQC2.Control {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
DelegateSizeHelper {
|
DelegateSizeHelper {
|
||||||
id: chatBarSizeHelper
|
id: chatBarSizeHelper
|
||||||
startBreakpoint: Kirigami.Units.gridUnit * 46
|
startBreakpoint: Kirigami.Units.gridUnit * 46
|
||||||
|
|||||||
@@ -43,6 +43,9 @@ QQC2.ItemDelegate {
|
|||||||
anchors.fill: parent
|
anchors.fill: parent
|
||||||
visible: root.emoji.startsWith("mxc") || root.isImage
|
visible: root.emoji.startsWith("mxc") || root.isImage
|
||||||
source: visible ? root.emoji : ""
|
source: visible ? root.emoji : ""
|
||||||
|
fillMode: Image.PreserveAspectFit
|
||||||
|
sourceSize.width: width
|
||||||
|
sourceSize.height: height
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -84,6 +84,7 @@ QQC2.ScrollView {
|
|||||||
|
|
||||||
Kirigami.PlaceholderMessage {
|
Kirigami.PlaceholderMessage {
|
||||||
anchors.centerIn: parent
|
anchors.centerIn: parent
|
||||||
|
icon.name: root.stickers ? "stickers" : "preferences-desktop-emoticons"
|
||||||
text: root.stickers ? i18n("No stickers") : i18n("No emojis")
|
text: root.stickers ? i18n("No stickers") : i18n("No emojis")
|
||||||
visible: emojis.count === 0
|
visible: emojis.count === 0
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -66,6 +66,7 @@ ColumnLayout {
|
|||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
Layout.preferredHeight: root.categoryIconSize + QQC2.ScrollBar.horizontal.height
|
Layout.preferredHeight: root.categoryIconSize + QQC2.ScrollBar.horizontal.height
|
||||||
QQC2.ScrollBar.horizontal.height: QQC2.ScrollBar.horizontal.visible ? QQC2.ScrollBar.horizontal.implicitHeight : 0
|
QQC2.ScrollBar.horizontal.height: QQC2.ScrollBar.horizontal.visible ? QQC2.ScrollBar.horizontal.implicitHeight : 0
|
||||||
|
visible: categories.count !== 0
|
||||||
|
|
||||||
ListView {
|
ListView {
|
||||||
id: categories
|
id: categories
|
||||||
@@ -201,8 +202,13 @@ ColumnLayout {
|
|||||||
width: root.categoryIconSize
|
width: root.categoryIconSize
|
||||||
height: width
|
height: width
|
||||||
checked: stickerModel.packIndex === model.index
|
checked: stickerModel.packIndex === model.index
|
||||||
|
padding: Kirigami.Units.largeSpacing
|
||||||
|
|
||||||
contentItem: Image {
|
contentItem: Image {
|
||||||
source: model.avatarUrl
|
source: model.avatarUrl
|
||||||
|
fillMode: Image.PreserveAspectFit
|
||||||
|
sourceSize.width: width
|
||||||
|
sourceSize.height: height
|
||||||
}
|
}
|
||||||
QQC2.ToolTip.text: model.name
|
QQC2.ToolTip.text: model.name
|
||||||
QQC2.ToolTip.delay: Kirigami.Units.toolTipDelay
|
QQC2.ToolTip.delay: Kirigami.Units.toolTipDelay
|
||||||
|
|||||||
@@ -4,6 +4,7 @@
|
|||||||
import QtQuick
|
import QtQuick
|
||||||
import QtQuick.Controls as QQC2
|
import QtQuick.Controls as QQC2
|
||||||
import QtQuick.Layouts
|
import QtQuick.Layouts
|
||||||
|
import QtQuick.Window
|
||||||
|
|
||||||
import org.kde.kirigami as Kirigami
|
import org.kde.kirigami as Kirigami
|
||||||
import org.kde.kirigamiaddons.formcard as FormCard
|
import org.kde.kirigamiaddons.formcard as FormCard
|
||||||
@@ -23,7 +24,7 @@ ColumnLayout {
|
|||||||
model: root.connection.accountDataEventTypes
|
model: root.connection.accountDataEventTypes
|
||||||
delegate: FormCard.FormButtonDelegate {
|
delegate: FormCard.FormButtonDelegate {
|
||||||
text: modelData
|
text: modelData
|
||||||
onClicked: applicationWindow().pageStack.pushDialogLayer(Qt.createComponent('org.kde.neochat', 'MessageSourceSheet'), {
|
onClicked: root.Window.window.pageStack.pushDialogLayer(Qt.createComponent('org.kde.neochat', 'MessageSourceSheet'), {
|
||||||
sourceText: root.connection.accountDataJsonString(modelData)
|
sourceText: root.connection.accountDataJsonString(modelData)
|
||||||
}, {
|
}, {
|
||||||
title: i18nc("@title:window", "Event Source"),
|
title: i18nc("@title:window", "Event Source"),
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
|
|
||||||
import QtQuick
|
import QtQuick
|
||||||
import QtQuick.Layouts
|
import QtQuick.Layouts
|
||||||
|
import QtQuick.Window
|
||||||
|
|
||||||
import org.kde.kirigami as Kirigami
|
import org.kde.kirigami as Kirigami
|
||||||
import org.kde.kirigamiaddons.formcard as FormCard
|
import org.kde.kirigamiaddons.formcard as FormCard
|
||||||
@@ -47,7 +48,7 @@ ColumnLayout {
|
|||||||
model: root.room.accountDataEventTypes
|
model: root.room.accountDataEventTypes
|
||||||
delegate: FormCard.FormButtonDelegate {
|
delegate: FormCard.FormButtonDelegate {
|
||||||
text: modelData
|
text: modelData
|
||||||
onClicked: applicationWindow().pageStack.pushDialogLayer(Qt.createComponent('org.kde.neochat', 'MessageSourceSheet'), {
|
onClicked: root.Window.window.pageStack.pushDialogLayer(Qt.createComponent('org.kde.neochat', 'MessageSourceSheet'), {
|
||||||
sourceText: root.room.roomAcountDataJson(text)
|
sourceText: root.room.roomAcountDataJson(text)
|
||||||
}, {
|
}, {
|
||||||
title: i18n("Event Source"),
|
title: i18n("Event Source"),
|
||||||
@@ -77,7 +78,7 @@ ColumnLayout {
|
|||||||
if (model.eventCount === 1) {
|
if (model.eventCount === 1) {
|
||||||
openEventSource(model.type, model.stateKey);
|
openEventSource(model.type, model.stateKey);
|
||||||
} else {
|
} else {
|
||||||
pageStack.pushDialogLayer(Qt.createComponent('org.kde.neochat.devtools', 'StateKeys'), {
|
root.Window.window.pageStack.pushDialogLayer(Qt.createComponent('org.kde.neochat.devtools', 'StateKeys'), {
|
||||||
room: root.room,
|
room: root.room,
|
||||||
eventType: model.type
|
eventType: model.type
|
||||||
}, {
|
}, {
|
||||||
@@ -89,7 +90,7 @@ ColumnLayout {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
function openEventSource(type: string, stateKey: string): void {
|
function openEventSource(type: string, stateKey: string): void {
|
||||||
onClicked: applicationWindow().pageStack.pushDialogLayer(Qt.createComponent('org.kde.neochat', 'MessageSourceSheet'), {
|
onClicked: root.Window.window.pageStack.pushDialogLayer(Qt.createComponent('org.kde.neochat', 'MessageSourceSheet'), {
|
||||||
model: stateModel,
|
model: stateModel,
|
||||||
allowEdit: true,
|
allowEdit: true,
|
||||||
room: root.room,
|
room: root.room,
|
||||||
|
|||||||
@@ -13,6 +13,7 @@ LoginStep {
|
|||||||
id: root
|
id: root
|
||||||
|
|
||||||
FormCard.FormTextDelegate {
|
FormCard.FormTextDelegate {
|
||||||
|
textItem.wrapMode: Text.Wrap
|
||||||
text: i18n("Please wait while your messages are loaded from the server. This might take a little while.")
|
text: i18n("Please wait while your messages are loaded from the server. This might take a little while.")
|
||||||
}
|
}
|
||||||
FormCard.AbstractFormDelegate {
|
FormCard.AbstractFormDelegate {
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ import QtQuick.Layouts
|
|||||||
|
|
||||||
import org.kde.kirigami as Kirigami
|
import org.kde.kirigami as Kirigami
|
||||||
import org.kde.kirigamiaddons.formcard as FormCard
|
import org.kde.kirigamiaddons.formcard as FormCard
|
||||||
|
import org.kde.kirigamiaddons.labs.components as KirigamiComponents
|
||||||
|
|
||||||
import org.kde.neochat
|
import org.kde.neochat
|
||||||
import org.kde.neochat.settings
|
import org.kde.neochat.settings
|
||||||
@@ -90,11 +91,27 @@ Kirigami.Page {
|
|||||||
id: loadedAccounts
|
id: loadedAccounts
|
||||||
model: AccountRegistry
|
model: AccountRegistry
|
||||||
delegate: FormCard.FormButtonDelegate {
|
delegate: FormCard.FormButtonDelegate {
|
||||||
text: model.userId
|
id: delegate
|
||||||
|
|
||||||
|
required property string userId
|
||||||
|
required property NeoChatConnection connection
|
||||||
|
|
||||||
|
text: QmlUtils.escapeString(connection.localUser.displayName)
|
||||||
|
description: connection.localUser.id
|
||||||
|
leadingPadding: Kirigami.Units.largeSpacing
|
||||||
|
|
||||||
onClicked: {
|
onClicked: {
|
||||||
Controller.activeConnection = model.connection;
|
Controller.activeConnection = delegate.connection;
|
||||||
root.connectionChosen();
|
root.connectionChosen();
|
||||||
}
|
}
|
||||||
|
leading: KirigamiComponents.Avatar {
|
||||||
|
id: avatar
|
||||||
|
name: delegate.text
|
||||||
|
// Note: User::avatarUrl does not set user_id, and thus cannot be used directly here. Hence the makeMediaUrl.
|
||||||
|
source: delegate.connection.localUser.avatarUrl.toString().length > 0 ? delegate.connection.makeMediaUrl(delegate.connection.localUser.avatarUrl) : ""
|
||||||
|
implicitWidth: Kirigami.Units.iconSizes.medium
|
||||||
|
implicitHeight: Kirigami.Units.iconSizes.medium
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Repeater {
|
Repeater {
|
||||||
|
|||||||
@@ -140,7 +140,7 @@ int main(int argc, char *argv[])
|
|||||||
KAboutData about(QStringLiteral("neochat"),
|
KAboutData about(QStringLiteral("neochat"),
|
||||||
i18n("NeoChat"),
|
i18n("NeoChat"),
|
||||||
QStringLiteral(NEOCHAT_VERSION_STRING),
|
QStringLiteral(NEOCHAT_VERSION_STRING),
|
||||||
i18n("Matrix client"),
|
i18n("Chat on Matrix"),
|
||||||
KAboutLicense::GPL_V3,
|
KAboutLicense::GPL_V3,
|
||||||
i18n("© 2018-2020 Black Hat, 2020-2024 KDE Community"));
|
i18n("© 2018-2020 Black Hat, 2020-2024 KDE Community"));
|
||||||
about.addAuthor(i18n("Carl Schwan"),
|
about.addAuthor(i18n("Carl Schwan"),
|
||||||
|
|||||||
@@ -600,14 +600,19 @@ bool ActionsModel::handleQuickEditAction(NeoChatRoom *room, const QString &messa
|
|||||||
} else {
|
} else {
|
||||||
originalString = event->plainBody();
|
originalString = event->plainBody();
|
||||||
}
|
}
|
||||||
|
QString replaceId = event->id();
|
||||||
|
const auto eventRelation = event->relatesTo();
|
||||||
|
if (eventRelation && eventRelation->type == "m.replace"_L1) {
|
||||||
|
replaceId = eventRelation->eventId;
|
||||||
|
}
|
||||||
if (flags == "/g"_L1) {
|
if (flags == "/g"_L1) {
|
||||||
room->postHtmlMessage(messageText, originalString.replace(regex, replacement), event->msgtype(), {}, event->id());
|
room->postHtmlMessage(messageText, originalString.replace(regex, replacement), event->msgtype(), {}, replaceId);
|
||||||
} else {
|
} else {
|
||||||
room->postHtmlMessage(messageText,
|
room->postHtmlMessage(messageText,
|
||||||
originalString.replace(originalString.indexOf(regex), regex.size(), replacement),
|
originalString.replace(originalString.indexOf(regex), regex.size(), replacement),
|
||||||
event->msgtype(),
|
event->msgtype(),
|
||||||
{},
|
{},
|
||||||
event->id());
|
replaceId);
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -85,13 +85,7 @@ QVariant CompletionModel::data(const QModelIndex &index, int role) const
|
|||||||
return m_filterModel->data(filterIndex, RoomListModel::CanonicalAliasRole);
|
return m_filterModel->data(filterIndex, RoomListModel::CanonicalAliasRole);
|
||||||
}
|
}
|
||||||
if (role == IconNameRole) {
|
if (role == IconNameRole) {
|
||||||
auto mediaId = m_filterModel->data(filterIndex, RoomListModel::AvatarRole).toString();
|
return m_filterModel->data(filterIndex, RoomListModel::AvatarRole).toString();
|
||||||
if (mediaId.isEmpty()) {
|
|
||||||
return QVariant();
|
|
||||||
}
|
|
||||||
if (m_room) {
|
|
||||||
return m_room->connection()->makeMediaUrl(QUrl(QStringLiteral("mxc://%1").arg(mediaId)));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (m_autoCompletionType == Emoji) {
|
if (m_autoCompletionType == Emoji) {
|
||||||
|
|||||||
@@ -569,15 +569,22 @@ QList<MessageComponent> MessageContentModel::componentsForType(MessageComponentT
|
|||||||
case MessageComponentType::Video: {
|
case MessageComponentType::Video: {
|
||||||
if (!event->is<StickerEvent>()) {
|
if (!event->is<StickerEvent>()) {
|
||||||
const auto roomMessageEvent = eventCast<const Quotient::RoomMessageEvent>(event);
|
const auto roomMessageEvent = eventCast<const Quotient::RoomMessageEvent>(event);
|
||||||
QList<MessageComponent> components;
|
const auto fileContent = roomMessageEvent->get<EventContent::FileContentBase>();
|
||||||
components += MessageComponent{type, QString(), {}};
|
if (fileContent != nullptr) {
|
||||||
auto body = EventHandler::rawMessageBody(*roomMessageEvent);
|
const auto fileInfo = fileContent->commonInfo();
|
||||||
components += TextHandler().textComponents(body,
|
const auto body = EventHandler::rawMessageBody(*roomMessageEvent);
|
||||||
EventHandler::messageBodyInputFormat(*roomMessageEvent),
|
// Do not attach the description to the image, if it's the same as the original filename.
|
||||||
m_room,
|
if (fileInfo.originalName != body) {
|
||||||
roomMessageEvent,
|
QList<MessageComponent> components;
|
||||||
roomMessageEvent->isReplaced());
|
components += MessageComponent{type, QString(), {}};
|
||||||
return components;
|
components += TextHandler().textComponents(body,
|
||||||
|
EventHandler::messageBodyInputFormat(*roomMessageEvent),
|
||||||
|
m_room,
|
||||||
|
roomMessageEvent,
|
||||||
|
roomMessageEvent->isReplaced());
|
||||||
|
return components;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
@@ -635,7 +642,7 @@ QList<MessageComponent> MessageContentModel::addLinkPreviews(QList<MessageCompon
|
|||||||
|
|
||||||
void MessageContentModel::closeLinkPreview(int row)
|
void MessageContentModel::closeLinkPreview(int row)
|
||||||
{
|
{
|
||||||
if (row < 0 || row > m_components.size()) {
|
if (row < 0 || row >= m_components.size()) {
|
||||||
qWarning() << "closeLinkPreview() called with row" << row << "which does not exist. m_components.size() =" << m_components.size();
|
qWarning() << "closeLinkPreview() called with row" << row << "which does not exist. m_components.size() =" << m_components.size();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -645,6 +652,7 @@ void MessageContentModel::closeLinkPreview(int row)
|
|||||||
m_removedLinkPreviews += m_components[row].attributes["link"_ls].toUrl();
|
m_removedLinkPreviews += m_components[row].attributes["link"_ls].toUrl();
|
||||||
m_components.remove(row);
|
m_components.remove(row);
|
||||||
m_components.squeeze();
|
m_components.squeeze();
|
||||||
|
endResetModel();
|
||||||
resetContent();
|
resetContent();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -212,7 +212,7 @@ QVariant RoomListModel::data(const QModelIndex &index, int role) const
|
|||||||
return room->displayName().toHtmlEscaped();
|
return room->displayName().toHtmlEscaped();
|
||||||
}
|
}
|
||||||
if (role == AvatarRole) {
|
if (role == AvatarRole) {
|
||||||
return room->avatarMediaId();
|
return room->avatarMediaUrl();
|
||||||
}
|
}
|
||||||
if (role == CanonicalAliasRole) {
|
if (role == CanonicalAliasRole) {
|
||||||
return room->canonicalAlias();
|
return room->canonicalAlias();
|
||||||
|
|||||||
@@ -286,6 +286,7 @@ QHash<int, QByteArray> RoomTreeModel::roleNames() const
|
|||||||
roles[IconRole] = "icon";
|
roles[IconRole] = "icon";
|
||||||
roles[AttentionRole] = "attention";
|
roles[AttentionRole] = "attention";
|
||||||
roles[FavouriteRole] = "favourite";
|
roles[FavouriteRole] = "favourite";
|
||||||
|
roles[RoomTypeRole] = "roomType";
|
||||||
return roles;
|
return roles;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -323,7 +324,7 @@ QVariant RoomTreeModel::data(const QModelIndex &index, int role) const
|
|||||||
return room->displayName();
|
return room->displayName();
|
||||||
}
|
}
|
||||||
if (role == AvatarRole) {
|
if (role == AvatarRole) {
|
||||||
return room->avatarMediaId();
|
return room->avatarMediaUrl();
|
||||||
}
|
}
|
||||||
if (role == CanonicalAliasRole) {
|
if (role == CanonicalAliasRole) {
|
||||||
return room->canonicalAlias();
|
return room->canonicalAlias();
|
||||||
@@ -385,6 +386,11 @@ QVariant RoomTreeModel::data(const QModelIndex &index, int role) const
|
|||||||
if (role == FavouriteRole) {
|
if (role == FavouriteRole) {
|
||||||
return room->isFavourite();
|
return room->isFavourite();
|
||||||
}
|
}
|
||||||
|
if (role == RoomTypeRole) {
|
||||||
|
if (room->creation()) {
|
||||||
|
return room->creation()->contentPart<QString>("type"_L1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -50,6 +50,7 @@ public:
|
|||||||
IconRole,
|
IconRole,
|
||||||
AttentionRole, /**< Whether there are any notifications. */
|
AttentionRole, /**< Whether there are any notifications. */
|
||||||
FavouriteRole, /**< Whether the room is favourited. */
|
FavouriteRole, /**< Whether the room is favourited. */
|
||||||
|
RoomTypeRole, /**< The room's type. */
|
||||||
};
|
};
|
||||||
Q_ENUM(EventRoles)
|
Q_ENUM(EventRoles)
|
||||||
explicit RoomTreeModel(QObject *parent = nullptr);
|
explicit RoomTreeModel(QObject *parent = nullptr);
|
||||||
|
|||||||
@@ -157,6 +157,11 @@ bool SortFilterRoomTreeModel::filterAcceptsRow(int source_row, const QModelIndex
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Hide rooms with defined types, assuming that data-holding rooms have a defined type
|
||||||
|
if (!sourceModel()->data(index, RoomTreeModel::RoomTypeRole).toString().isEmpty()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
static auto config = NeoChatConfig::self();
|
static auto config = NeoChatConfig::self();
|
||||||
if (config->allRoomsInHome() && RoomManager::instance().currentSpace().isEmpty()) {
|
if (config->allRoomsInHome() && RoomManager::instance().currentSpace().isEmpty()) {
|
||||||
return acceptRoom;
|
return acceptRoom;
|
||||||
|
|||||||
@@ -261,7 +261,7 @@ Action=Popup
|
|||||||
Name=Share
|
Name=Share
|
||||||
Name[ar]=شارك
|
Name[ar]=شارك
|
||||||
Name[ca]=Compartició
|
Name[ca]=Compartició
|
||||||
Name[ca@valencia]=Compartició
|
Name[ca@valencia]=Compartiu
|
||||||
Name[cs]=Sdílet
|
Name[cs]=Sdílet
|
||||||
Name[de]=Teilen
|
Name[de]=Teilen
|
||||||
Name[el]=Κοινοποίηση
|
Name[el]=Κοινοποίηση
|
||||||
|
|||||||
@@ -431,9 +431,9 @@ QDateTime NeoChatRoom::lastActiveTime()
|
|||||||
return messageEvents().rbegin()->get()->originTimestamp();
|
return messageEvents().rbegin()->get()->originTimestamp();
|
||||||
}
|
}
|
||||||
|
|
||||||
QString NeoChatRoom::avatarMediaId() const
|
QUrl NeoChatRoom::avatarMediaUrl() const
|
||||||
{
|
{
|
||||||
if (const auto avatar = Room::avatarMediaId(); !avatar.isEmpty()) {
|
if (const auto avatar = Room::avatarUrl(); !avatar.isEmpty()) {
|
||||||
return avatar;
|
return avatar;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -441,7 +441,7 @@ QString NeoChatRoom::avatarMediaId() const
|
|||||||
const auto directChatMembers = this->directChatMembers();
|
const auto directChatMembers = this->directChatMembers();
|
||||||
for (const auto member : directChatMembers) {
|
for (const auto member : directChatMembers) {
|
||||||
if (member != localMember()) {
|
if (member != localMember()) {
|
||||||
return member.avatarMediaId();
|
return member.avatarUrl();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -69,9 +69,9 @@ class NeoChatRoom : public Quotient::Room
|
|||||||
Q_PROPERTY(bool readMarkerLoaded READ readMarkerLoaded NOTIFY readMarkerLoadedChanged)
|
Q_PROPERTY(bool readMarkerLoaded READ readMarkerLoaded NOTIFY readMarkerLoadedChanged)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief The avatar image to be used for the room.
|
* @brief The avatar image to be used for the room, as a mxc:// URL.
|
||||||
*/
|
*/
|
||||||
Q_PROPERTY(QString avatarMediaId READ avatarMediaId NOTIFY avatarChanged STORED false)
|
Q_PROPERTY(QUrl avatarMediaUrl READ avatarMediaUrl NOTIFY avatarChanged STORED false)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Get a RoomMember object for the other person in a direct chat.
|
* @brief Get a RoomMember object for the other person in a direct chat.
|
||||||
@@ -320,7 +320,7 @@ public:
|
|||||||
|
|
||||||
[[nodiscard]] bool readMarkerLoaded() const;
|
[[nodiscard]] bool readMarkerLoaded() const;
|
||||||
|
|
||||||
[[nodiscard]] QString avatarMediaId() const;
|
[[nodiscard]] QUrl avatarMediaUrl() const;
|
||||||
|
|
||||||
NeochatRoomMember *directChatRemoteMember();
|
NeochatRoomMember *directChatRemoteMember();
|
||||||
|
|
||||||
|
|||||||
@@ -153,15 +153,6 @@ QColor NeochatRoomMember::color() const
|
|||||||
return m_room->member(m_memberId).color();
|
return m_room->member(m_memberId).color();
|
||||||
}
|
}
|
||||||
|
|
||||||
QString NeochatRoomMember::avatarMediaId() const
|
|
||||||
{
|
|
||||||
if (m_room == nullptr || m_memberId.isEmpty()) {
|
|
||||||
return {};
|
|
||||||
}
|
|
||||||
|
|
||||||
return m_room->member(m_memberId).avatarMediaId();
|
|
||||||
}
|
|
||||||
|
|
||||||
QUrl NeochatRoomMember::avatarUrl() const
|
QUrl NeochatRoomMember::avatarUrl() const
|
||||||
{
|
{
|
||||||
if (m_room == nullptr || m_memberId.isEmpty()) {
|
if (m_room == nullptr || m_memberId.isEmpty()) {
|
||||||
|
|||||||
@@ -70,7 +70,6 @@ public:
|
|||||||
int hue() const;
|
int hue() const;
|
||||||
qreal hueF() const;
|
qreal hueF() const;
|
||||||
QColor color() const;
|
QColor color() const;
|
||||||
QString avatarMediaId() const;
|
|
||||||
QUrl avatarUrl() const;
|
QUrl avatarUrl() const;
|
||||||
|
|
||||||
Q_SIGNALS:
|
Q_SIGNALS:
|
||||||
|
|||||||
@@ -30,6 +30,7 @@ class PollHandler : public QObject
|
|||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
QML_ELEMENT
|
QML_ELEMENT
|
||||||
|
QML_UNCREATABLE("Use NeoChatRoom::poll")
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief The question for the poll.
|
* @brief The question for the poll.
|
||||||
@@ -91,7 +92,7 @@ Q_SIGNALS:
|
|||||||
void hasEndedChanged();
|
void hasEndedChanged();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
const Quotient::PollStartEvent *m_pollStartEvent;
|
const Quotient::PollStartEvent *m_pollStartEvent = nullptr;
|
||||||
|
|
||||||
void updatePoll(Quotient::RoomEventsRange events);
|
void updatePoll(Quotient::RoomEventsRange events);
|
||||||
|
|
||||||
|
|||||||
@@ -26,6 +26,7 @@
|
|||||||
"Name[nn]": "Tobias Fella",
|
"Name[nn]": "Tobias Fella",
|
||||||
"Name[pl]": "Tobias Fella",
|
"Name[pl]": "Tobias Fella",
|
||||||
"Name[ru]": "Tobias Fella",
|
"Name[ru]": "Tobias Fella",
|
||||||
|
"Name[sk]": "Tobias Fella",
|
||||||
"Name[sl]": "Tobias Fella",
|
"Name[sl]": "Tobias Fella",
|
||||||
"Name[sv]": "Tobias Fella",
|
"Name[sv]": "Tobias Fella",
|
||||||
"Name[ta]": "டோபியாஸ் ஃபெல்லா",
|
"Name[ta]": "டோபியாஸ் ஃபெல்லா",
|
||||||
@@ -93,6 +94,7 @@
|
|||||||
"Name[nn]": "NeoChat",
|
"Name[nn]": "NeoChat",
|
||||||
"Name[pl]": "NeoChat",
|
"Name[pl]": "NeoChat",
|
||||||
"Name[ru]": "NeoChat",
|
"Name[ru]": "NeoChat",
|
||||||
|
"Name[sk]": "NeoChat",
|
||||||
"Name[sl]": "NeoChat",
|
"Name[sl]": "NeoChat",
|
||||||
"Name[sv]": "NeoChat",
|
"Name[sv]": "NeoChat",
|
||||||
"Name[ta]": "நியோச்சாட்",
|
"Name[ta]": "நியோச்சாட்",
|
||||||
|
|||||||
@@ -27,7 +27,8 @@ QQC2.Menu {
|
|||||||
text: "https://matrix.to/#/" + root.connection.localUser.id,
|
text: "https://matrix.to/#/" + root.connection.localUser.id,
|
||||||
title: root.connection.localUser.displayName,
|
title: root.connection.localUser.displayName,
|
||||||
subtitle: root.connection.localUser.id,
|
subtitle: root.connection.localUser.id,
|
||||||
avatarSource: root.connection.makeMediaUrl(root.connection.localUser.avatarUrl)
|
// Note: User::avatarUrl does not set user_id, and thus cannot be used directly here. Hence the makeMediaUrl.
|
||||||
|
avatarSource: root.connection.localUser.avatarUrl.toString().length > 0 ? root.connection.makeMediaUrl(root.connection.localUser.avatarUrl) : ""
|
||||||
});
|
});
|
||||||
if (typeof root.closeDialog === "function") {
|
if (typeof root.closeDialog === "function") {
|
||||||
root.closeDialog();
|
root.closeDialog();
|
||||||
|
|||||||
@@ -125,7 +125,7 @@ Kirigami.Dialog {
|
|||||||
width: Kirigami.Units.gridUnit + Kirigami.Units.largeSpacing
|
width: Kirigami.Units.gridUnit + Kirigami.Units.largeSpacing
|
||||||
height: Kirigami.Units.gridUnit + Kirigami.Units.largeSpacing
|
height: Kirigami.Units.gridUnit + Kirigami.Units.largeSpacing
|
||||||
}
|
}
|
||||||
source: userDelegate.connection.localUser.avatarMediaId ? userDelegate.connection.makeMediaUrl("mxc://" + userDelegate.connection.localUser.avatarMediaId) : ""
|
source: userDelegate.connection.localUser.avatarUrl.toString().length > 0 ? userDelegate.connection.makeMediaUrl(userDelegate.connection.localUser.avatarUrl) : ""
|
||||||
name: userDelegate.connection.localUser.displayName ?? userDelegate.connection.localUser.id
|
name: userDelegate.connection.localUser.displayName ?? userDelegate.connection.localUser.id
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -18,7 +18,7 @@ QQC2.ItemDelegate {
|
|||||||
required property NeoChatRoom currentRoom
|
required property NeoChatRoom currentRoom
|
||||||
required property bool categoryVisible
|
required property bool categoryVisible
|
||||||
required property string filterText
|
required property string filterText
|
||||||
required property string avatar
|
required property url avatar
|
||||||
required property string displayName
|
required property string displayName
|
||||||
|
|
||||||
topPadding: Kirigami.Units.largeSpacing
|
topPadding: Kirigami.Units.largeSpacing
|
||||||
@@ -32,7 +32,7 @@ QQC2.ItemDelegate {
|
|||||||
visible: root.categoryVisible || filterText.length > 0
|
visible: root.categoryVisible || filterText.length > 0
|
||||||
|
|
||||||
contentItem: KirigamiComponents.Avatar {
|
contentItem: KirigamiComponents.Avatar {
|
||||||
source: root.avatar ? root.currentRoom.connection.makeMediaUrl("mxc://" + root.avatar) : ""
|
source: root.avatar
|
||||||
name: root.displayName
|
name: root.displayName
|
||||||
|
|
||||||
sourceSize {
|
sourceSize {
|
||||||
|
|||||||
@@ -163,7 +163,7 @@ Loader {
|
|||||||
spacing: Kirigami.Units.largeSpacing
|
spacing: Kirigami.Units.largeSpacing
|
||||||
KirigamiComponents.Avatar {
|
KirigamiComponents.Avatar {
|
||||||
id: avatar
|
id: avatar
|
||||||
source: room.avatarMediaId ? root.connection.makeMediaUrl("mxc://" + room.avatarMediaId) : ""
|
source: room.avatarMediaUrl
|
||||||
name: room.displayName
|
name: room.displayName
|
||||||
Layout.preferredWidth: Kirigami.Units.gridUnit * 3
|
Layout.preferredWidth: Kirigami.Units.gridUnit * 3
|
||||||
Layout.preferredHeight: Kirigami.Units.gridUnit * 3
|
Layout.preferredHeight: Kirigami.Units.gridUnit * 3
|
||||||
|
|||||||
@@ -5,6 +5,7 @@
|
|||||||
import QtQuick
|
import QtQuick
|
||||||
import QtQuick.Controls as QQC2
|
import QtQuick.Controls as QQC2
|
||||||
import QtQuick.Layouts
|
import QtQuick.Layouts
|
||||||
|
import Qt.labs.qmlmodels
|
||||||
import org.kde.kirigami as Kirigami
|
import org.kde.kirigami as Kirigami
|
||||||
import org.kde.kirigamiaddons.components as KirigamiComponents
|
import org.kde.kirigamiaddons.components as KirigamiComponents
|
||||||
import org.kde.kirigamiaddons.formcard as FormCard
|
import org.kde.kirigamiaddons.formcard as FormCard
|
||||||
@@ -177,10 +178,25 @@ Loader {
|
|||||||
|
|
||||||
Repeater {
|
Repeater {
|
||||||
model: root.actions
|
model: root.actions
|
||||||
QQC2.MenuItem {
|
DelegateChooser {
|
||||||
visible: modelData.visible
|
role: "separator"
|
||||||
action: modelData
|
DelegateChoice {
|
||||||
onClicked: root.item.close()
|
roleValue: true
|
||||||
|
|
||||||
|
QQC2.MenuSeparator {
|
||||||
|
visible: modelData.visible
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
DelegateChoice {
|
||||||
|
roleValue: false
|
||||||
|
|
||||||
|
QQC2.MenuItem {
|
||||||
|
visible: modelData.visible
|
||||||
|
action: modelData
|
||||||
|
onClicked: root.item.close()
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
QQC2.Menu {
|
QQC2.Menu {
|
||||||
@@ -341,15 +357,30 @@ Loader {
|
|||||||
id: listViewAction
|
id: listViewAction
|
||||||
model: root.actions
|
model: root.actions
|
||||||
|
|
||||||
FormCard.FormButtonDelegate {
|
DelegateChooser {
|
||||||
icon.name: modelData.icon.name
|
role: "separator"
|
||||||
icon.color: modelData.icon.color ?? undefined
|
DelegateChoice {
|
||||||
enabled: modelData.enabled
|
roleValue: true
|
||||||
visible: modelData.visible
|
|
||||||
text: modelData.text
|
FormCard.FormDelegateSeparator {
|
||||||
onClicked: {
|
visible: modelData.visible
|
||||||
modelData.triggered();
|
}
|
||||||
root.item.close();
|
}
|
||||||
|
|
||||||
|
DelegateChoice {
|
||||||
|
roleValue: false
|
||||||
|
|
||||||
|
FormCard.FormButtonDelegate {
|
||||||
|
icon.name: modelData.icon.name
|
||||||
|
icon.color: modelData.icon.color ?? undefined
|
||||||
|
enabled: modelData.enabled
|
||||||
|
visible: modelData.visible
|
||||||
|
text: modelData.text
|
||||||
|
onClicked: {
|
||||||
|
modelData.triggered();
|
||||||
|
root.item.close();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -38,7 +38,7 @@ ColumnLayout {
|
|||||||
|
|
||||||
contentItem: KirigamiComponents.Avatar {
|
contentItem: KirigamiComponents.Avatar {
|
||||||
name: root.room ? root.room.displayName : ""
|
name: root.room ? root.room.displayName : ""
|
||||||
source: root.room ? root.room.connection.makeMediaUrl("mxc://" + root.room.avatarMediaId) : ""
|
source: root.room ? root.room.avatarMediaUrl : ""
|
||||||
|
|
||||||
Rectangle {
|
Rectangle {
|
||||||
visible: root.room.usesEncryption
|
visible: root.room.usesEncryption
|
||||||
|
|||||||
@@ -54,8 +54,8 @@ DelegateContextMenu {
|
|||||||
icon.name: "document-save"
|
icon.name: "document-save"
|
||||||
onTriggered: {
|
onTriggered: {
|
||||||
var dialog = saveAsDialog.createObject(QQC2.Overlay.overlay);
|
var dialog = saveAsDialog.createObject(QQC2.Overlay.overlay);
|
||||||
|
dialog.selectedFile = currentRoom.fileNameToDownload(eventId);
|
||||||
dialog.open();
|
dialog.open();
|
||||||
dialog.currentFile = dialog.folder + "/" + currentRoom.fileNameToDownload(eventId);
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
DelegateContextMenu.ReplyMessageAction {},
|
DelegateContextMenu.ReplyMessageAction {},
|
||||||
|
|||||||
@@ -102,7 +102,7 @@ Labs.MenuBar {
|
|||||||
}
|
}
|
||||||
Labs.MenuItem {
|
Labs.MenuItem {
|
||||||
text: i18nc("menu", "About KDE")
|
text: i18nc("menu", "About KDE")
|
||||||
onTriggered: pageStack.pushDialogLayer(Qt.createComponent("org.kde.kirigamiaddons.formcard", "AboutKDE"))
|
onTriggered: pageStack.pushDialogLayer(Qt.createComponent("org.kde.kirigamiaddons.formcard", "AboutKDEPage"))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -34,7 +34,7 @@ ColumnLayout {
|
|||||||
Layout.preferredHeight: Kirigami.Units.iconSizes.large
|
Layout.preferredHeight: Kirigami.Units.iconSizes.large
|
||||||
|
|
||||||
name: root.room ? root.room.displayName : ""
|
name: root.room ? root.room.displayName : ""
|
||||||
source: root.room ? root.room.connection.makeMediaUrl("mxc://" + root.room.avatarMediaId) : ""
|
source: root.room ? root.room.avatarMediaUrl : ""
|
||||||
|
|
||||||
Rectangle {
|
Rectangle {
|
||||||
visible: room.usesEncryption
|
visible: room.usesEncryption
|
||||||
@@ -75,6 +75,7 @@ ColumnLayout {
|
|||||||
textFormat: TextEdit.PlainText
|
textFormat: TextEdit.PlainText
|
||||||
visible: root.room && root.room.canonicalAlias
|
visible: root.room && root.room.canonicalAlias
|
||||||
text: root.room && root.room.canonicalAlias ? root.room.canonicalAlias : ""
|
text: root.room && root.room.canonicalAlias ? root.room.canonicalAlias : ""
|
||||||
|
color: Kirigami.Theme.disabledTextColor
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
QQC2.AbstractButton {
|
QQC2.AbstractButton {
|
||||||
@@ -92,7 +93,7 @@ ColumnLayout {
|
|||||||
text: barcode.content,
|
text: barcode.content,
|
||||||
title: root.room ? root.room.displayName : "",
|
title: root.room ? root.room.displayName : "",
|
||||||
subtitle: root.room ? root.room.id : "",
|
subtitle: root.room ? root.room.id : "",
|
||||||
avatarSource: root.room && root.room.avatarMediaId ? root.room.connection.makeMediaUrl("mxc://" + root.room.avatarMediaId) : ""
|
avatarSource: root.room ? root.room.avatarMediaUrl : ""
|
||||||
});
|
});
|
||||||
map.open();
|
map.open();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,7 +7,6 @@ import QtQuick.Layouts
|
|||||||
import QtCore as Core
|
import QtCore as Core
|
||||||
|
|
||||||
import org.kde.kirigami as Kirigami
|
import org.kde.kirigami as Kirigami
|
||||||
import org.kde.kirigamiaddons.labs.components as KirigamiComponents
|
|
||||||
import org.kde.kquickimageeditor as KQuickImageEditor
|
import org.kde.kquickimageeditor as KQuickImageEditor
|
||||||
|
|
||||||
Kirigami.Page {
|
Kirigami.Page {
|
||||||
@@ -168,10 +167,11 @@ Kirigami.Page {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
footer: KirigamiComponents.Banner {
|
footer: Kirigami.InlineMessage {
|
||||||
id: msg
|
id: msg
|
||||||
type: Kirigami.MessageType.Error
|
type: Kirigami.MessageType.Error
|
||||||
showCloseButton: true
|
showCloseButton: true
|
||||||
visible: false
|
visible: false
|
||||||
|
position: Kirigami.InlineMessage.Position.Header
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -104,12 +104,14 @@ Components.AlbumMaximizeComponent {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
onOpened: forceActiveFocus()
|
||||||
|
|
||||||
onItemRightClicked: RoomManager.viewEventMenu(root.currentEventId, root.currentRoom)
|
onItemRightClicked: RoomManager.viewEventMenu(root.currentEventId, root.currentRoom)
|
||||||
|
|
||||||
onSaveItem: {
|
onSaveItem: {
|
||||||
var dialog = saveAsDialog.createObject(QQC2.Overlay.overlay);
|
var dialog = saveAsDialog.createObject(QQC2.Overlay.overlay);
|
||||||
|
dialog.selectedFile = currentRoom.fileNameToDownload(root.currentEventId);
|
||||||
dialog.open();
|
dialog.open();
|
||||||
dialog.currentFile = dialog.folder + "/" + currentRoom.fileNameToDownload(root.currentEventId);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Connections {
|
Connections {
|
||||||
|
|||||||
@@ -12,7 +12,9 @@ Components.AbstractMaximizeComponent {
|
|||||||
|
|
||||||
required property string text
|
required property string text
|
||||||
property color avatarColor
|
property color avatarColor
|
||||||
required property string avatarSource
|
required property url avatarSource
|
||||||
|
|
||||||
|
onOpened: forceActiveFocus()
|
||||||
|
|
||||||
Shortcut {
|
Shortcut {
|
||||||
sequences: [StandardKey.Cancel]
|
sequences: [StandardKey.Cancel]
|
||||||
|
|||||||
@@ -30,9 +30,9 @@ Kirigami.Dialog {
|
|||||||
FormCard.AbstractFormDelegate {
|
FormCard.AbstractFormDelegate {
|
||||||
background: null
|
background: null
|
||||||
contentItem: RowLayout {
|
contentItem: RowLayout {
|
||||||
spacing: Kirigami.Units.largeSpacing * 4
|
spacing: Kirigami.Units.largeSpacing
|
||||||
Avatar {
|
Avatar {
|
||||||
source: root.connection.makeMediaUrl(SpaceHierarchyCache.recommendedSpaceAvatar)
|
source: SpaceHierarchyCache.recommendedSpaceAvatar.toString().length > 0 ? root.connection.makeMediaUrl(SpaceHierarchyCache.recommendedSpaceAvatar) : 0
|
||||||
name: SpaceHierarchyCache.recommendedSpaceDisplayName
|
name: SpaceHierarchyCache.recommendedSpaceDisplayName
|
||||||
}
|
}
|
||||||
ColumnLayout {
|
ColumnLayout {
|
||||||
@@ -51,6 +51,7 @@ Kirigami.Dialog {
|
|||||||
FormCard.FormDelegateSeparator {}
|
FormCard.FormDelegateSeparator {}
|
||||||
FormCard.FormButtonDelegate {
|
FormCard.FormButtonDelegate {
|
||||||
text: i18nc("@action:button", "Join")
|
text: i18nc("@action:button", "Join")
|
||||||
|
icon.name: "list-add-symbolic"
|
||||||
onClicked: {
|
onClicked: {
|
||||||
SpaceHierarchyCache.recommendedSpaceHidden = true;
|
SpaceHierarchyCache.recommendedSpaceHidden = true;
|
||||||
RoomManager.resolveResource(SpaceHierarchyCache.recommendedSpaceId, "join");
|
RoomManager.resolveResource(SpaceHierarchyCache.recommendedSpaceId, "join");
|
||||||
@@ -58,6 +59,7 @@ Kirigami.Dialog {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
FormCard.FormButtonDelegate {
|
FormCard.FormButtonDelegate {
|
||||||
|
icon.name: "mail-thread-ignored-symbolic"
|
||||||
text: i18nc("@action:button", "Ignore")
|
text: i18nc("@action:button", "Ignore")
|
||||||
onClicked: {
|
onClicked: {
|
||||||
SpaceHierarchyCache.recommendedSpaceHidden = true;
|
SpaceHierarchyCache.recommendedSpaceHidden = true;
|
||||||
|
|||||||
@@ -21,7 +21,7 @@ Delegates.RoundedItemDelegate {
|
|||||||
required property bool hasHighlightNotifications
|
required property bool hasHighlightNotifications
|
||||||
required property NeoChatRoom currentRoom
|
required property NeoChatRoom currentRoom
|
||||||
required property NeoChatConnection connection
|
required property NeoChatConnection connection
|
||||||
required property string avatar
|
required property url avatar
|
||||||
required property string subtitleText
|
required property string subtitleText
|
||||||
required property string displayName
|
required property string displayName
|
||||||
|
|
||||||
@@ -55,7 +55,7 @@ Delegates.RoundedItemDelegate {
|
|||||||
spacing: Kirigami.Units.largeSpacing
|
spacing: Kirigami.Units.largeSpacing
|
||||||
|
|
||||||
AvatarNotification {
|
AvatarNotification {
|
||||||
source: root.avatar ? root.connection.makeMediaUrl("mxc://" + root.avatar) : ""
|
source: root.avatar
|
||||||
name: root.displayName
|
name: root.displayName
|
||||||
visible: NeoChatConfig.showAvatarInRoomDrawer
|
visible: NeoChatConfig.showAvatarInRoomDrawer
|
||||||
implicitHeight: Kirigami.Units.gridUnit + (NeoChatConfig.compactRoomList ? 0 : Kirigami.Units.largeSpacing * 2)
|
implicitHeight: Kirigami.Units.gridUnit + (NeoChatConfig.compactRoomList ? 0 : Kirigami.Units.largeSpacing * 2)
|
||||||
|
|||||||
@@ -99,8 +99,11 @@ Kirigami.OverlayDrawer {
|
|||||||
Layout.preferredHeight: pageStack.globalToolBar.preferredHeight
|
Layout.preferredHeight: pageStack.globalToolBar.preferredHeight
|
||||||
|
|
||||||
contentItem: RowLayout {
|
contentItem: RowLayout {
|
||||||
|
spacing: 0
|
||||||
|
|
||||||
Kirigami.Heading {
|
Kirigami.Heading {
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
|
Layout.leftMargin: Kirigami.Units.largeSpacing
|
||||||
text: drawerItemLoader.item ? drawerItemLoader.item.title : ""
|
text: drawerItemLoader.item ? drawerItemLoader.item.title : ""
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -219,7 +219,7 @@ QQC2.ScrollView {
|
|||||||
required property int index
|
required property int index
|
||||||
required property string name
|
required property string name
|
||||||
required property string userId
|
required property string userId
|
||||||
required property string avatar
|
required property url avatar
|
||||||
required property int powerLevel
|
required property int powerLevel
|
||||||
required property string powerLevelString
|
required property string powerLevelString
|
||||||
|
|
||||||
|
|||||||
@@ -7,7 +7,6 @@ import QtQuick.Controls as QQC2
|
|||||||
import QtQuick.Layouts
|
import QtQuick.Layouts
|
||||||
import QtQuick.Window
|
import QtQuick.Window
|
||||||
|
|
||||||
import org.kde.kirigamiaddons.labs.components as KirigamiComponents
|
|
||||||
import org.kde.kirigami as Kirigami
|
import org.kde.kirigami as Kirigami
|
||||||
import org.kde.kitemmodels
|
import org.kde.kitemmodels
|
||||||
|
|
||||||
@@ -99,11 +98,12 @@ Kirigami.Page {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
header: KirigamiComponents.Banner {
|
header: Kirigami.InlineMessage {
|
||||||
id: banner
|
id: banner
|
||||||
|
|
||||||
showCloseButton: true
|
showCloseButton: true
|
||||||
visible: false
|
visible: false
|
||||||
|
position: Kirigami.InlineMessage.Position.Header
|
||||||
}
|
}
|
||||||
|
|
||||||
Loader {
|
Loader {
|
||||||
@@ -253,7 +253,6 @@ Kirigami.Page {
|
|||||||
messageComponentType: messageComponentType,
|
messageComponentType: messageComponentType,
|
||||||
plainText: plainText,
|
plainText: plainText,
|
||||||
htmlText: htmlText,
|
htmlText: htmlText,
|
||||||
isThread: isThread
|
|
||||||
});
|
});
|
||||||
contextMenu.open();
|
contextMenu.open();
|
||||||
}
|
}
|
||||||
@@ -265,7 +264,6 @@ Kirigami.Page {
|
|||||||
plainText: plainText,
|
plainText: plainText,
|
||||||
mimeType: mimeType,
|
mimeType: mimeType,
|
||||||
progressInfo: progressInfo,
|
progressInfo: progressInfo,
|
||||||
isThread: isThread
|
|
||||||
});
|
});
|
||||||
contextMenu.open();
|
contextMenu.open();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -182,7 +182,7 @@ QQC2.Control {
|
|||||||
id: spaceDelegate
|
id: spaceDelegate
|
||||||
|
|
||||||
required property string displayName
|
required property string displayName
|
||||||
required property string avatar
|
required property url avatar
|
||||||
required property string roomId
|
required property string roomId
|
||||||
required property var currentRoom
|
required property var currentRoom
|
||||||
|
|
||||||
@@ -191,7 +191,7 @@ QQC2.Control {
|
|||||||
Layout.maximumHeight: width - Kirigami.Units.smallSpacing
|
Layout.maximumHeight: width - Kirigami.Units.smallSpacing
|
||||||
|
|
||||||
text: displayName
|
text: displayName
|
||||||
source: avatar ? root.connection.makeMediaUrl("mxc://" + avatar) : ""
|
source: avatar
|
||||||
|
|
||||||
notificationCount: spaceDelegate.currentRoom.childrenNotificationCount
|
notificationCount: spaceDelegate.currentRoom.childrenNotificationCount
|
||||||
notificationHighlight: spaceDelegate.currentRoom.childrenHaveHighlightNotifications
|
notificationHighlight: spaceDelegate.currentRoom.childrenHaveHighlightNotifications
|
||||||
@@ -219,7 +219,7 @@ QQC2.Control {
|
|||||||
visible: SpaceHierarchyCache.recommendedSpaceId.length > 0 && !root.connection.room(SpaceHierarchyCache.recommendedSpaceId) && !SpaceHierarchyCache.recommendedSpaceHidden
|
visible: SpaceHierarchyCache.recommendedSpaceId.length > 0 && !root.connection.room(SpaceHierarchyCache.recommendedSpaceId) && !SpaceHierarchyCache.recommendedSpaceHidden
|
||||||
|
|
||||||
text: i18nc("Join <name of a space>", "Join %1", SpaceHierarchyCache.recommendedSpaceDisplayName)
|
text: i18nc("Join <name of a space>", "Join %1", SpaceHierarchyCache.recommendedSpaceDisplayName)
|
||||||
source: SpaceHierarchyCache.recommendedSpaceAvatar.length > 0 ? root.connection.makeMediaUrl(SpaceHierarchyCache.recommendedSpaceAvatar) : ""
|
source: SpaceHierarchyCache.recommendedSpaceAvatar.toString().length > 0 ? root.connection.makeMediaUrl(SpaceHierarchyCache.recommendedSpaceAvatar) : ""
|
||||||
onSelected: {
|
onSelected: {
|
||||||
recommendedSpaceDialogComponent.createObject(QQC2.Overlay.overlay, {
|
recommendedSpaceDialogComponent.createObject(QQC2.Overlay.overlay, {
|
||||||
connection: root.connection
|
connection: root.connection
|
||||||
|
|||||||
@@ -96,7 +96,7 @@ Loader {
|
|||||||
|
|
||||||
KirigamiComponents.Avatar {
|
KirigamiComponents.Avatar {
|
||||||
id: avatar
|
id: avatar
|
||||||
source: room.avatarMediaId ? root.room.connection.makeMediaUrl("mxc://" + room.avatarMediaId) : ""
|
source: room.avatarMediaUrl
|
||||||
Layout.preferredWidth: Kirigami.Units.gridUnit * 3
|
Layout.preferredWidth: Kirigami.Units.gridUnit * 3
|
||||||
Layout.preferredHeight: Kirigami.Units.gridUnit * 3
|
Layout.preferredHeight: Kirigami.Units.gridUnit * 3
|
||||||
Layout.alignment: Qt.AlignTop
|
Layout.alignment: Qt.AlignTop
|
||||||
|
|||||||
@@ -7,7 +7,6 @@ import QtQuick.Layouts
|
|||||||
|
|
||||||
import org.kde.kirigami as Kirigami
|
import org.kde.kirigami as Kirigami
|
||||||
import org.kde.kirigamiaddons.formcard as FormCard
|
import org.kde.kirigamiaddons.formcard as FormCard
|
||||||
import org.kde.kirigamiaddons.labs.components as KirigamiComponents
|
|
||||||
|
|
||||||
import org.kde.neochat
|
import org.kde.neochat
|
||||||
|
|
||||||
@@ -20,11 +19,12 @@ FormCard.FormCardPage {
|
|||||||
leftPadding: 0
|
leftPadding: 0
|
||||||
rightPadding: 0
|
rightPadding: 0
|
||||||
|
|
||||||
header: KirigamiComponents.Banner {
|
header: Kirigami.InlineMessage {
|
||||||
id: banner
|
id: banner
|
||||||
showCloseButton: true
|
showCloseButton: true
|
||||||
visible: false
|
visible: false
|
||||||
type: Kirigami.MessageType.Error
|
type: Kirigami.MessageType.Error
|
||||||
|
position: Kirigami.InlineMessage.Position.Header
|
||||||
}
|
}
|
||||||
|
|
||||||
property SSSSHandler ssssHandler: SSSSHandler {
|
property SSSSHandler ssssHandler: SSSSHandler {
|
||||||
|
|||||||
@@ -75,6 +75,8 @@ Kirigami.Dialog {
|
|||||||
QQC2.AbstractButton {
|
QQC2.AbstractButton {
|
||||||
Layout.minimumHeight: avatar.height * 0.75
|
Layout.minimumHeight: avatar.height * 0.75
|
||||||
Layout.maximumHeight: avatar.height * 1.5
|
Layout.maximumHeight: avatar.height * 1.5
|
||||||
|
Layout.maximumWidth: avatar.height * 1.5
|
||||||
|
|
||||||
contentItem: Barcode {
|
contentItem: Barcode {
|
||||||
id: barcode
|
id: barcode
|
||||||
barcodeType: Barcode.QRCode
|
barcodeType: Barcode.QRCode
|
||||||
|
|||||||
@@ -27,7 +27,7 @@ RowLayout {
|
|||||||
Layout.topMargin: Kirigami.Units.smallSpacing
|
Layout.topMargin: Kirigami.Units.smallSpacing
|
||||||
Layout.bottomMargin: Kirigami.Units.smallSpacing
|
Layout.bottomMargin: Kirigami.Units.smallSpacing
|
||||||
Layout.rightMargin: Kirigami.Units.largeSpacing
|
Layout.rightMargin: Kirigami.Units.largeSpacing
|
||||||
Layout.minimumHeight: bottomEdge ? Kirigami.Units.gridUnit * 2 : -1
|
Layout.minimumHeight: bottomEdge ? Kirigami.Units.gridUnit * 3 : -1
|
||||||
|
|
||||||
onVisibleChanged: {
|
onVisibleChanged: {
|
||||||
if (!visible) {
|
if (!visible) {
|
||||||
@@ -37,14 +37,15 @@ RowLayout {
|
|||||||
}
|
}
|
||||||
KirigamiComponents.AvatarButton {
|
KirigamiComponents.AvatarButton {
|
||||||
id: accountButton
|
id: accountButton
|
||||||
readonly property string mediaId: root.connection.localUser.avatarMediaId
|
readonly property url avatarUrl: root.connection.localUser.avatarUrl
|
||||||
|
|
||||||
Layout.preferredWidth: Kirigami.Units.iconSizes.medium
|
Layout.preferredWidth: Kirigami.Units.iconSizes.medium
|
||||||
Layout.preferredHeight: Kirigami.Units.iconSizes.medium
|
Layout.preferredHeight: Kirigami.Units.iconSizes.medium
|
||||||
Layout.leftMargin: Kirigami.Units.largeSpacing
|
Layout.leftMargin: Kirigami.Units.largeSpacing
|
||||||
|
|
||||||
text: i18n("Edit this account")
|
text: i18n("Edit this account")
|
||||||
source: mediaId ? root.connection.makeMediaUrl("mxc://" + mediaId) : ""
|
// Note: User::avatarUrl does not set user_id, and thus cannot be used directly here. Hence the makeMediaUrl.
|
||||||
|
source: avatarUrl.toString().length > 0 ? root.connection.makeMediaUrl(avatarUrl) : ""
|
||||||
name: root.connection.localUser.displayName
|
name: root.connection.localUser.displayName
|
||||||
|
|
||||||
activeFocusOnTab: true
|
activeFocusOnTab: true
|
||||||
|
|||||||
@@ -134,16 +134,15 @@ void RoomManager::activateUserModel()
|
|||||||
m_userListModel->activate();
|
m_userListModel->activate();
|
||||||
}
|
}
|
||||||
|
|
||||||
UriResolveResult RoomManager::resolveResource(const Uri &uri)
|
|
||||||
{
|
|
||||||
return UriResolverBase::visitResource(m_connection, uri);
|
|
||||||
}
|
|
||||||
|
|
||||||
void RoomManager::resolveResource(const QString &idOrUri, const QString &action)
|
void RoomManager::resolveResource(const QString &idOrUri, const QString &action)
|
||||||
{
|
{
|
||||||
Uri uri{idOrUri};
|
resolveResource(Uri{idOrUri}, action);
|
||||||
|
}
|
||||||
|
|
||||||
|
void RoomManager::resolveResource(Uri uri, const QString &action)
|
||||||
|
{
|
||||||
if (!uri.isValid()) {
|
if (!uri.isValid()) {
|
||||||
Q_EMIT showMessage(MessageType::Warning, i18n("Malformed or empty Matrix id<br />%1 is not a correct Matrix identifier", idOrUri));
|
Q_EMIT showMessage(MessageType::Warning, i18n("Malformed or empty Matrix id<br />%1 is not a correct Matrix identifier", uri.toDisplayString()));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -237,7 +236,6 @@ void RoomManager::loadInitialRoom()
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (m_isMobile) {
|
if (m_isMobile) {
|
||||||
// We still need to remember the last space on mobile
|
|
||||||
setCurrentSpace(m_lastSpaceConfig.readEntry(m_connection->userId(), QString()), false);
|
setCurrentSpace(m_lastSpaceConfig.readEntry(m_connection->userId(), QString()), false);
|
||||||
// We don't want to open a room on startup on mobile
|
// We don't want to open a room on startup on mobile
|
||||||
return;
|
return;
|
||||||
@@ -260,6 +258,7 @@ void RoomManager::openRoomForActiveConnection()
|
|||||||
setCurrentSpace({}, false);
|
setCurrentSpace({}, false);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
setCurrentSpace(m_lastSpaceConfig.readEntry(m_connection->userId(), QString()), false);
|
||||||
const auto &lastRoom = m_lastRoomConfig.readEntry(m_connection->userId(), QString());
|
const auto &lastRoom = m_lastRoomConfig.readEntry(m_connection->userId(), QString());
|
||||||
if (lastRoom.isEmpty() || !m_connection->room(lastRoom)) {
|
if (lastRoom.isEmpty() || !m_connection->room(lastRoom)) {
|
||||||
setCurrentRoom({});
|
setCurrentRoom({});
|
||||||
@@ -267,7 +266,6 @@ void RoomManager::openRoomForActiveConnection()
|
|||||||
m_currentRoom = nullptr;
|
m_currentRoom = nullptr;
|
||||||
resolveResource(lastRoom);
|
resolveResource(lastRoom);
|
||||||
}
|
}
|
||||||
setCurrentSpace(m_lastSpaceConfig.readEntry(m_connection->userId(), QString()), false);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
UriResolveResult RoomManager::visitUser(User *user, const QString &action)
|
UriResolveResult RoomManager::visitUser(User *user, const QString &action)
|
||||||
@@ -315,7 +313,9 @@ void RoomManager::visitRoom(Room *r, const QString &eventId)
|
|||||||
|
|
||||||
// It's important that we compare room *objects* here, not just room *ids*, since we need to deal with the object changing when going invite -> joined
|
// It's important that we compare room *objects* here, not just room *ids*, since we need to deal with the object changing when going invite -> joined
|
||||||
if (m_currentRoom && m_currentRoom == room) {
|
if (m_currentRoom && m_currentRoom == room) {
|
||||||
Q_EMIT goToEvent(eventId);
|
if (!eventId.isEmpty()) {
|
||||||
|
Q_EMIT goToEvent(eventId);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
setCurrentRoom(room->id());
|
setCurrentRoom(room->id());
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -168,16 +168,6 @@ public:
|
|||||||
UserListModel *userListModel() const;
|
UserListModel *userListModel() const;
|
||||||
Q_INVOKABLE void activateUserModel();
|
Q_INVOKABLE void activateUserModel();
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Resolve the given URI resource.
|
|
||||||
*
|
|
||||||
* @note It's actually Quotient::UriResolverBase::visitResource() but with Q_INVOKABLE
|
|
||||||
* and the connection grabbed from RoomManager.
|
|
||||||
*
|
|
||||||
* @sa Quotient::UriResolverBase::visitResource()
|
|
||||||
*/
|
|
||||||
Q_INVOKABLE UriResolveResult resolveResource(const Uri &uri);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Resolve the given resource.
|
* @brief Resolve the given resource.
|
||||||
*
|
*
|
||||||
@@ -188,6 +178,16 @@ public:
|
|||||||
*/
|
*/
|
||||||
Q_INVOKABLE void resolveResource(const QString &idOrUri, const QString &action = {});
|
Q_INVOKABLE void resolveResource(const QString &idOrUri, const QString &action = {});
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Resolve the given resource URI.
|
||||||
|
*
|
||||||
|
* @note It's actually Quotient::UriResolverBase::visitResource() but with Q_INVOKABLE
|
||||||
|
* and the connection grabbed from RoomManager.
|
||||||
|
*
|
||||||
|
* @sa Quotient::UriResolverBase::visitResource()
|
||||||
|
*/
|
||||||
|
Q_INVOKABLE void resolveResource(Uri uri, const QString &action = {});
|
||||||
|
|
||||||
bool hasOpenRoom() const;
|
bool hasOpenRoom() const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -34,7 +34,8 @@ FormCard.FormCardPage {
|
|||||||
|
|
||||||
padding: 0
|
padding: 0
|
||||||
|
|
||||||
source: root.connection && root.connection.localUser.avatarMediaId ? root.connection.makeMediaUrl("mxc://" + root.connection.localUser.avatarMediaId) : ""
|
// Note: User::avatarUrl does not set user_id, and thus cannot be used directly here. Hence the makeMediaUrl.
|
||||||
|
source: root.connection && (root.connection.localUser.avatarUrl.toString().length > 0 ? root.connection.makeMediaUrl(root.connection.localUser.avatarUrl) : "")
|
||||||
name: root.connection.localUser.displayName
|
name: root.connection.localUser.displayName
|
||||||
|
|
||||||
onClicked: {
|
onClicked: {
|
||||||
@@ -122,7 +123,8 @@ FormCard.FormCardPage {
|
|||||||
text: "https://matrix.to/#/" + root.connection.localUser.id,
|
text: "https://matrix.to/#/" + root.connection.localUser.id,
|
||||||
title: root.connection.localUser.displayName,
|
title: root.connection.localUser.displayName,
|
||||||
subtitle: root.connection.localUser.id,
|
subtitle: root.connection.localUser.id,
|
||||||
avatarSource: root.connection.makeMediaUrl(root.connection.localUser.avatarUrl)
|
// Note: User::avatarUrl does not set user_id, and thus cannot be used directly here. Hence the makeMediaUrl.
|
||||||
|
avatarSource: root.connection && (root.connection.localUser.avatarUrl.toString().length > 0 ? root.connection.makeMediaUrl(root.connection.localUser.avatarUrl) : "")
|
||||||
});
|
});
|
||||||
if (typeof root.closeDialog === "function") {
|
if (typeof root.closeDialog === "function") {
|
||||||
root.closeDialog();
|
root.closeDialog();
|
||||||
|
|||||||
@@ -53,7 +53,8 @@ FormCard.FormCardPage {
|
|||||||
contentItem: RowLayout {
|
contentItem: RowLayout {
|
||||||
KirigamiComponents.Avatar {
|
KirigamiComponents.Avatar {
|
||||||
name: accountDelegate.connection.localUser.displayName
|
name: accountDelegate.connection.localUser.displayName
|
||||||
source: accountDelegate.connection.localUser.avatarMediaId ? accountDelegate.connection.makeMediaUrl("mxc://" + accountDelegate.connection.localUser.avatarMediaId) : ""
|
// Note: User::avatarUrl does not set user_id, and thus cannot be used directly here. Hence the makeMediaUrl.
|
||||||
|
source: accountDelegate.connection.localUser.avatarUrl.toString().length > 0 ? accountDelegate.connection.makeMediaUrl(accountDelegate.connection.localUser.avatarUrl) : ""
|
||||||
|
|
||||||
Layout.rightMargin: Kirigami.Units.largeSpacing
|
Layout.rightMargin: Kirigami.Units.largeSpacing
|
||||||
implicitWidth: Kirigami.Units.iconSizes.medium
|
implicitWidth: Kirigami.Units.iconSizes.medium
|
||||||
|
|||||||
@@ -8,7 +8,6 @@ import QtQuick.Dialogs
|
|||||||
|
|
||||||
import org.kde.kirigami as Kirigami
|
import org.kde.kirigami as Kirigami
|
||||||
import org.kde.kirigamiaddons.formcard as FormCard
|
import org.kde.kirigamiaddons.formcard as FormCard
|
||||||
import org.kde.kirigamiaddons.labs.components as KirigamiComponents
|
|
||||||
|
|
||||||
import org.kde.neochat
|
import org.kde.neochat
|
||||||
|
|
||||||
@@ -19,11 +18,12 @@ FormCard.FormCardPage {
|
|||||||
|
|
||||||
required property NeoChatConnection connection
|
required property NeoChatConnection connection
|
||||||
|
|
||||||
header: KirigamiComponents.Banner {
|
header: Kirigami.InlineMessage {
|
||||||
id: banner
|
id: banner
|
||||||
showCloseButton: true
|
showCloseButton: true
|
||||||
visible: false
|
visible: false
|
||||||
type: Kirigami.MessageType.Error
|
type: Kirigami.MessageType.Error
|
||||||
|
position: Kirigami.InlineMessage.Position.Header
|
||||||
}
|
}
|
||||||
|
|
||||||
FormCard.FormCard {
|
FormCard.FormCard {
|
||||||
|
|||||||
@@ -23,7 +23,7 @@ FormCard.FormCardPage {
|
|||||||
}
|
}
|
||||||
|
|
||||||
FormCard.FormCard {
|
FormCard.FormCard {
|
||||||
Layout.topMargin: Kirigami.Units.largeSpacing
|
Layout.topMargin: Kirigami.Units.largeSpacing * 4
|
||||||
FormCard.FormCheckDelegate {
|
FormCard.FormCheckDelegate {
|
||||||
text: i18n("Enable notifications for this account")
|
text: i18n("Enable notifications for this account")
|
||||||
description: i18n("Whether push notifications are generated by your Matrix server")
|
description: i18n("Whether push notifications are generated by your Matrix server")
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user