diff --git a/.idea/libraries/Dart_Packages.xml b/.idea/libraries/Dart_Packages.xml
index 8959fcc..d1b4b25 100644
--- a/.idea/libraries/Dart_Packages.xml
+++ b/.idea/libraries/Dart_Packages.xml
@@ -5,14 +5,14 @@
-
+
-
+
@@ -128,6 +128,27 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -254,6 +275,20 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -464,6 +499,13 @@
+
+
+
+
+
+
+
@@ -481,42 +523,49 @@
-
+
-
+
-
+
-
+
-
+
-
+
+
+
+
+
+
+
+
@@ -537,7 +586,7 @@
-
+
@@ -597,59 +646,59 @@
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
@@ -702,6 +751,20 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -730,6 +793,13 @@
+
+
+
+
+
+
+
@@ -775,56 +845,63 @@
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
+
+
+
+
+
+
+
@@ -856,13 +933,6 @@
-
-
-
-
-
-
-
@@ -894,10 +964,9 @@
-
-
-
+
+
@@ -914,6 +983,9 @@
+
+
+
@@ -931,6 +1003,8 @@
+
+
@@ -958,17 +1032,19 @@
+
-
-
-
-
-
-
+
+
+
+
+
+
+
-
+
@@ -977,38 +1053,42 @@
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
+
diff --git a/.idea/libraries/Flutter_Plugins.xml b/.idea/libraries/Flutter_Plugins.xml
index 9f76510..29ea25b 100644
--- a/.idea/libraries/Flutter_Plugins.xml
+++ b/.idea/libraries/Flutter_Plugins.xml
@@ -1,25 +1,26 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/lib/api/marianumcloud/talk/chat/richObjectStringProcessor.dart b/lib/api/marianumcloud/talk/chat/richObjectStringProcessor.dart
index 4bef792..27241a9 100644
--- a/lib/api/marianumcloud/talk/chat/richObjectStringProcessor.dart
+++ b/lib/api/marianumcloud/talk/chat/richObjectStringProcessor.dart
@@ -1,7 +1,12 @@
+import 'dart:convert';
+
+import 'package:cached_network_image/cached_network_image.dart';
+import 'package:flutter/material.dart';
import 'package:marianum_mobile/api/marianumcloud/talk/chat/getChatResponse.dart';
+import 'package:shared_preferences/shared_preferences.dart';
class RichObjectStringProcessor {
- static String parse(String message, Map? data) {
+ static String parseTextPreview(String message, Map? data) {
if(data == null) return message;
data.forEach((key, value) {
@@ -10,4 +15,31 @@ class RichObjectStringProcessor {
return message;
}
+
+ static Future parseAnyToWidget(String message, Map? data) async {
+ if(data == null) return Text(message);
+ if(!message.contains(RegExp("{file}"))) return Text(parseTextPreview(message, data));
+
+ SharedPreferences preferences = await SharedPreferences.getInstance();
+
+ Widget? back;
+ data.forEach((key, value) {
+ back = CachedNetworkImage(
+ errorWidget: (context, url, error) {
+ return Text("Datei: ${value.name}", style: const TextStyle(fontWeight: FontWeight.bold));
+ },
+ alignment: Alignment.center,
+ placeholder: (context, url) {
+ return const Padding(padding: EdgeInsets.all(10), child: CircularProgressIndicator());
+ },
+ fadeInDuration: const Duration(seconds: 1),
+ imageUrl: "https://cloud.marianum-fulda.de/core/preview?fileId=${value.id}&x=110&y=-1&a=1",
+ httpHeaders: {
+ "Authorization": "Basic ${base64.encode(utf8.encode("${preferences.getString("username")}:${preferences.getString("password")}"))}"
+ },
+ );
+ });
+
+ return back ?? Text("NOPE");
+ }
}
\ No newline at end of file
diff --git a/lib/screen/pages/talk/chatList.dart b/lib/screen/pages/talk/chatList.dart
index 65d1ad6..d5d2d71 100644
--- a/lib/screen/pages/talk/chatList.dart
+++ b/lib/screen/pages/talk/chatList.dart
@@ -56,7 +56,7 @@ class _ChatListState extends State {
chats.add(ListTile(
title: Text(chatRoom.displayName),
- subtitle: Text("${Jiffy.unixFromSecondsSinceEpoch(chatRoom.lastMessage.timestamp).fromNow()}: ${RichObjectStringProcessor.parse(chatRoom.lastMessage.message.replaceAll("\n", " "), chatRoom.lastMessage.messageParameters)}", overflow: TextOverflow.ellipsis),
+ subtitle: Text("${Jiffy.unixFromSecondsSinceEpoch(chatRoom.lastMessage.timestamp).fromNow()}: ${RichObjectStringProcessor.parseTextPreview(chatRoom.lastMessage.message.replaceAll("\n", " "), chatRoom.lastMessage.messageParameters)}", overflow: TextOverflow.ellipsis),
trailing: Visibility(
visible: chatRoom.unreadMessages > 0,
child: Container(
@@ -83,7 +83,7 @@ class _ChatListState extends State {
onTap: () async {
Navigator.of(context).push(MaterialPageRoute(builder: (context) {
return ChatView(
- user: chatRoom,
+ room: chatRoom,
selfId: username,
avatar: circleAvatar,
);
diff --git a/lib/screen/pages/talk/chatView.dart b/lib/screen/pages/talk/chatView.dart
index 575851c..1fabbf4 100644
--- a/lib/screen/pages/talk/chatView.dart
+++ b/lib/screen/pages/talk/chatView.dart
@@ -10,11 +10,11 @@ import 'package:marianum_mobile/data/chatList/chatProps.dart';
import 'package:provider/provider.dart';
class ChatView extends StatefulWidget {
- final GetRoomResponseObject user;
+ final GetRoomResponseObject room;
final String selfId;
final CircleAvatar avatar;
- const ChatView({Key? key, required this.user, required this.selfId, required this.avatar}) : super(key: key);
+ const ChatView({Key? key, required this.room, required this.selfId, required this.avatar}) : super(key: key);
@override
State createState() => _ChatViewState();
@@ -56,7 +56,7 @@ class _ChatViewState extends State {
super.initState();
WidgetsBinding.instance.addPostFrameCallback((timeStamp) {
- Provider.of(context, listen: false).setQueryToken(widget.user.token);
+ Provider.of(context, listen: false).setQueryToken(widget.room.token);
});
}
@@ -67,11 +67,13 @@ class _ChatViewState extends State {
List messages = List.empty(growable: true);
if(!data.primaryLoading()) {
- bool showMetadata = true;
+ bool showActorDisplayName = true;
+ bool showBubbleTime = true;
data.getChatResponse.sortByTimestamp().forEach((element) {
- showMetadata = element.messageType == GetRoomResponseObjectMessageType.comment;
+ showActorDisplayName = element.messageType == GetRoomResponseObjectMessageType.comment && widget.room.type != GetRoomResponseObjectConversationType.oneToOne;
+ showBubbleTime = element.messageType != GetRoomResponseObjectMessageType.system;
BubbleStyle currentStyle;
if(element.messageType == GetRoomResponseObjectMessageType.comment) {
@@ -84,38 +86,85 @@ class _ChatViewState extends State {
currentStyle = styleSystem;
}
+ var _actorTextStyle = TextStyle(color: Theme.of(context).primaryColor, fontWeight: FontWeight.bold);
messages.add(Bubble(
margin: BubbleEdges.only(bottom: element == data.getChatResponse.sortByTimestamp().last ? 20 : 0),
style: currentStyle,
- child: Stack(
- children: [
- Visibility(
- visible: showMetadata,
- child: Positioned(
- top: 0,
- left: 0,
- child: Text(element.actorDisplayName, style: TextStyle(fontWeight: FontWeight.bold, color: Theme.of(context).primaryColor)),
+ child: Container(
+ constraints: BoxConstraints(
+ maxWidth: MediaQuery.of(context).size.width * 0.9,
+ minWidth: _textSize(element.actorDisplayName, _actorTextStyle).width,
+ ),
+ child: Stack(
+ children: [
+ Padding(
+ padding: EdgeInsets.only(bottom: showBubbleTime ? 18 : 0, top: showActorDisplayName ? 18 : 0),
+ child: FutureBuilder(
+ future: RichObjectStringProcessor.parseAnyToWidget(element.message, element.messageParameters),
+ builder: (context, snapshot) {
+ if(!snapshot.hasData) return const CircularProgressIndicator();
+ return snapshot.data ?? const Icon(Icons.error);
+ },
+ )
),
- ),
- Padding(
- padding: EdgeInsets.symmetric(vertical: showMetadata ? 18 : 0),
- child: Text(RichObjectStringProcessor.parse(element.message, element.messageParameters)),
- ),
- Visibility(
- visible: showMetadata,
- child: Positioned(
- bottom: 0,
- right: 0,
- child: Text(
- "${Jiffy.unixFromSecondsSinceEpoch(element.timestamp).yMMMMd} - ${Jiffy.unixFromSecondsSinceEpoch(element.timestamp).format("HH:mm")}",
- style: TextStyle(color: Theme.of(context).disabledColor),
+ Visibility(
+ visible: showActorDisplayName,
+ child: Positioned(
+ top: 0,
+ left: 0,
+ child: Text(
+ element.actorDisplayName,
+ textAlign: TextAlign.start,
+ style: _actorTextStyle,
+ ),
),
),
- ),
- ],
+ Visibility(
+ visible: showBubbleTime,
+ child: Positioned(
+ bottom: 0,
+ right: 0,
+ child: Text(
+ Jiffy.unixFromSecondsSinceEpoch(element.timestamp).format("HH:mm"),
+ textAlign: TextAlign.end,
+ style: const TextStyle(color: Colors.grey, fontSize: 12),
+ ),
+ ),
+ ),
+ ],
+ ),
),
+
+
+ // Stack(
+ // children: [
+ // Visibility(
+ // visible: showMetadata,
+ // child: Positioned(
+ // top: 0,
+ // left: 0,
+ // child: Expanded(child: Text(element.actorDisplayName, style: TextStyle(fontWeight: FontWeight.bold, color: Theme.of(context).primaryColor))),
+ // ),
+ // ),
+ // Padding(
+ // padding: EdgeInsets.symmetric(vertical: showMetadata ? 18 : 0),
+ // child: Text(RichObjectStringProcessor.parse(element.message, element.messageParameters)),
+ // ),
+ // Visibility(
+ // visible: showMetadata,
+ // child: Positioned(
+ // bottom: 0,
+ // right: 0,
+ // child: Text(
+ // "${Jiffy.unixFromSecondsSinceEpoch(element.timestamp).yMMMMd} - ${Jiffy.unixFromSecondsSinceEpoch(element.timestamp).format("HH:mm")}",
+ // style: TextStyle(color: Theme.of(context).disabledColor),
+ // ),
+ // ),
+ // ),
+ // ],
+ // ),
));
});
}
@@ -127,7 +176,9 @@ class _ChatViewState extends State {
children: [
widget.avatar,
const SizedBox(width: 10),
- Text(widget.user.displayName, overflow: TextOverflow.ellipsis, maxLines: 1),
+ Expanded(
+ child: Text(widget.room.displayName, overflow: TextOverflow.ellipsis, maxLines: 1),
+ )
],
),
),
@@ -175,7 +226,7 @@ class _ChatViewState extends State {
setState(() {
sending = true;
});
- SendMessage(widget.user.token, SendMessageParams(_textBoxController.text)).run().then((value) => {
+ SendMessage(widget.room.token, SendMessageParams(_textBoxController.text)).run().then((value) => {
Provider.of(context, listen: false).run(),
_textBoxController.text = "",
setState(() {
@@ -196,4 +247,13 @@ class _ChatViewState extends State {
},
);
}
+
+ Size _textSize(String text, TextStyle style) {
+ final TextPainter textPainter = TextPainter(
+ text: TextSpan(text: text, style: style),
+ maxLines: 1,
+ textDirection: TextDirection.ltr)
+ ..layout(minWidth: 0, maxWidth: double.infinity);
+ return textPainter.size;
+ }
}
diff --git a/lib/screen/settings/debug/debugOverview.dart b/lib/screen/settings/debug/debugOverview.dart
index 00366be..d19e845 100644
--- a/lib/screen/settings/debug/debugOverview.dart
+++ b/lib/screen/settings/debug/debugOverview.dart
@@ -31,6 +31,7 @@ class _DebugOverviewState extends State {
leading: const Icon(Icons.delete_forever),
title: const Text("Cache löschen"),
onTap: () {
+ PaintingBinding.instance.imageCache.clear();
storage.collection("MarianumMobile").delete().then((value) => {
Navigator.pop(context)
});
diff --git a/macos/Flutter/GeneratedPluginRegistrant.swift b/macos/Flutter/GeneratedPluginRegistrant.swift
index b19945c..63ad0d1 100644
--- a/macos/Flutter/GeneratedPluginRegistrant.swift
+++ b/macos/Flutter/GeneratedPluginRegistrant.swift
@@ -7,10 +7,12 @@ import Foundation
import path_provider_foundation
import shared_preferences_foundation
+import sqflite
import url_launcher_macos
func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {
PathProviderPlugin.register(with: registry.registrar(forPlugin: "PathProviderPlugin"))
SharedPreferencesPlugin.register(with: registry.registrar(forPlugin: "SharedPreferencesPlugin"))
+ SqflitePlugin.register(with: registry.registrar(forPlugin: "SqflitePlugin"))
UrlLauncherPlugin.register(with: registry.registrar(forPlugin: "UrlLauncherPlugin"))
}
diff --git a/pubspec.yaml b/pubspec.yaml
index ad2297b..524af28 100644
--- a/pubspec.yaml
+++ b/pubspec.yaml
@@ -47,16 +47,13 @@ dependencies:
json_annotation: ^4.8.0
localstore: ^1.2.3
intl: ^0.17.0
- webdav: #^1.0.9
- git:
- url: https://github.com/timestee/dart-webdav.git
- ref: 1a70d3f7236484ed170f688980020b344d729d39
nextcloud:
git:
url: https://github.com/provokateurin/nextcloud-neon
path: packages/nextcloud
flutter_launcher_icons: ^0.11.0
pretty_json: ^2.0.0
+ cached_network_image: ^3.2.3
dependency_overrides:
xml: ^6.2.2