mirror of
https://gitlab.com/famedly/fluffychat.git
synced 2024-11-27 23:09:35 +01:00
feat: Add chat permissions settings
This commit is contained in:
parent
e30772eefc
commit
bf4b439572
32
lib/components/dialogs/adaptive_flat_button.dart
Normal file
32
lib/components/dialogs/adaptive_flat_button.dart
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
import 'package:fluffychat/utils/platform_infos.dart';
|
||||||
|
import 'package:flutter/cupertino.dart';
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
|
||||||
|
class AdaptiveFlatButton extends StatelessWidget {
|
||||||
|
final Widget child;
|
||||||
|
final Color textColor;
|
||||||
|
final Function onPressed;
|
||||||
|
|
||||||
|
const AdaptiveFlatButton({
|
||||||
|
Key key,
|
||||||
|
this.child,
|
||||||
|
this.textColor,
|
||||||
|
this.onPressed,
|
||||||
|
}) : super(key: key);
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
if (PlatformInfos.isCupertinoStyle) {
|
||||||
|
return CupertinoDialogAction(
|
||||||
|
child: child,
|
||||||
|
onPressed: onPressed,
|
||||||
|
textStyle: textColor != null ? TextStyle(color: textColor) : null,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return FlatButton(
|
||||||
|
child: child,
|
||||||
|
textColor: textColor,
|
||||||
|
onPressed: onPressed,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
@ -6,6 +6,7 @@ import 'package:flutter/cupertino.dart';
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter_gen/gen_l10n/l10n.dart';
|
import 'package:flutter_gen/gen_l10n/l10n.dart';
|
||||||
import '../avatar.dart';
|
import '../avatar.dart';
|
||||||
|
import 'adaptive_flat_button.dart';
|
||||||
import 'simple_dialogs.dart';
|
import 'simple_dialogs.dart';
|
||||||
import '../../utils/string_color.dart';
|
import '../../utils/string_color.dart';
|
||||||
|
|
||||||
@ -121,14 +122,14 @@ class _KeyVerificationPageState extends State<KeyVerificationDialog> {
|
|||||||
mainAxisSize: MainAxisSize.min,
|
mainAxisSize: MainAxisSize.min,
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
buttons.add(_AdaptiveFlatButton(
|
buttons.add(AdaptiveFlatButton(
|
||||||
child: Text(L10n.of(context).submit),
|
child: Text(L10n.of(context).submit),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
input = textEditingController.text;
|
input = textEditingController.text;
|
||||||
checkInput();
|
checkInput();
|
||||||
},
|
},
|
||||||
));
|
));
|
||||||
buttons.add(_AdaptiveFlatButton(
|
buttons.add(AdaptiveFlatButton(
|
||||||
child: Text(L10n.of(context).skip),
|
child: Text(L10n.of(context).skip),
|
||||||
onPressed: () => widget.request.openSSSS(skip: true),
|
onPressed: () => widget.request.openSSSS(skip: true),
|
||||||
));
|
));
|
||||||
@ -140,11 +141,11 @@ class _KeyVerificationPageState extends State<KeyVerificationDialog> {
|
|||||||
style: TextStyle(fontSize: 20)),
|
style: TextStyle(fontSize: 20)),
|
||||||
margin: EdgeInsets.only(left: 8.0, right: 8.0),
|
margin: EdgeInsets.only(left: 8.0, right: 8.0),
|
||||||
);
|
);
|
||||||
buttons.add(_AdaptiveFlatButton(
|
buttons.add(AdaptiveFlatButton(
|
||||||
child: Text(L10n.of(context).accept),
|
child: Text(L10n.of(context).accept),
|
||||||
onPressed: () => widget.request.acceptVerification(),
|
onPressed: () => widget.request.acceptVerification(),
|
||||||
));
|
));
|
||||||
buttons.add(_AdaptiveFlatButton(
|
buttons.add(AdaptiveFlatButton(
|
||||||
child: Text(L10n.of(context).reject),
|
child: Text(L10n.of(context).reject),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
widget.request.rejectVerification().then((_) {
|
widget.request.rejectVerification().then((_) {
|
||||||
@ -204,11 +205,11 @@ class _KeyVerificationPageState extends State<KeyVerificationDialog> {
|
|||||||
],
|
],
|
||||||
mainAxisSize: MainAxisSize.min,
|
mainAxisSize: MainAxisSize.min,
|
||||||
);
|
);
|
||||||
buttons.add(_AdaptiveFlatButton(
|
buttons.add(AdaptiveFlatButton(
|
||||||
child: Text(L10n.of(context).theyMatch),
|
child: Text(L10n.of(context).theyMatch),
|
||||||
onPressed: () => widget.request.acceptSas(),
|
onPressed: () => widget.request.acceptSas(),
|
||||||
));
|
));
|
||||||
buttons.add(_AdaptiveFlatButton(
|
buttons.add(AdaptiveFlatButton(
|
||||||
textColor: Colors.red,
|
textColor: Colors.red,
|
||||||
child: Text(L10n.of(context).theyDontMatch),
|
child: Text(L10n.of(context).theyDontMatch),
|
||||||
onPressed: () => widget.request.rejectSas(),
|
onPressed: () => widget.request.rejectSas(),
|
||||||
@ -244,7 +245,7 @@ class _KeyVerificationPageState extends State<KeyVerificationDialog> {
|
|||||||
],
|
],
|
||||||
mainAxisSize: MainAxisSize.min,
|
mainAxisSize: MainAxisSize.min,
|
||||||
);
|
);
|
||||||
buttons.add(_AdaptiveFlatButton(
|
buttons.add(AdaptiveFlatButton(
|
||||||
child: Text(L10n.of(context).close),
|
child: Text(L10n.of(context).close),
|
||||||
onPressed: () => Navigator.of(context).pop(),
|
onPressed: () => Navigator.of(context).pop(),
|
||||||
));
|
));
|
||||||
@ -359,32 +360,3 @@ class _Emoji extends StatelessWidget {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class _AdaptiveFlatButton extends StatelessWidget {
|
|
||||||
final Widget child;
|
|
||||||
final Color textColor;
|
|
||||||
final Function onPressed;
|
|
||||||
|
|
||||||
const _AdaptiveFlatButton({
|
|
||||||
Key key,
|
|
||||||
this.child,
|
|
||||||
this.textColor,
|
|
||||||
this.onPressed,
|
|
||||||
}) : super(key: key);
|
|
||||||
|
|
||||||
@override
|
|
||||||
Widget build(BuildContext context) {
|
|
||||||
if (PlatformInfos.isCupertinoStyle) {
|
|
||||||
return CupertinoDialogAction(
|
|
||||||
child: child,
|
|
||||||
onPressed: onPressed,
|
|
||||||
textStyle: textColor != null ? TextStyle(color: textColor) : null,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
return FlatButton(
|
|
||||||
child: child,
|
|
||||||
textColor: textColor,
|
|
||||||
onPressed: onPressed,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
85
lib/components/dialogs/permission_slider_dialog.dart
Normal file
85
lib/components/dialogs/permission_slider_dialog.dart
Normal file
@ -0,0 +1,85 @@
|
|||||||
|
import 'package:fluffychat/components/dialogs/adaptive_flat_button.dart';
|
||||||
|
import 'package:fluffychat/utils/platform_infos.dart';
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter/cupertino.dart';
|
||||||
|
import 'package:flutter_gen/gen_l10n/l10n.dart';
|
||||||
|
|
||||||
|
class PermissionSliderDialog extends StatefulWidget {
|
||||||
|
const PermissionSliderDialog({Key key, this.initialPermission = 0})
|
||||||
|
: super(key: key);
|
||||||
|
|
||||||
|
Future<int> show(BuildContext context) => PlatformInfos.isCupertinoStyle
|
||||||
|
? showCupertinoDialog<int>(context: context, builder: (context) => this)
|
||||||
|
: showDialog<int>(context: context, builder: (context) => this);
|
||||||
|
|
||||||
|
final int initialPermission;
|
||||||
|
@override
|
||||||
|
_PermissionSliderDialogState createState() => _PermissionSliderDialogState();
|
||||||
|
}
|
||||||
|
|
||||||
|
class _PermissionSliderDialogState extends State<PermissionSliderDialog> {
|
||||||
|
int _permission;
|
||||||
|
@override
|
||||||
|
void initState() {
|
||||||
|
_permission = widget.initialPermission;
|
||||||
|
super.initState();
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
final slider = PlatformInfos.isCupertinoStyle
|
||||||
|
? CupertinoSlider(
|
||||||
|
value: _permission.toDouble(),
|
||||||
|
onChanged: (d) => setState(() => _permission = d.round()),
|
||||||
|
max: 100.0,
|
||||||
|
min: 0.0,
|
||||||
|
)
|
||||||
|
: Slider(
|
||||||
|
value: _permission.toDouble(),
|
||||||
|
onChanged: (d) => setState(() => _permission = d.round()),
|
||||||
|
max: 100.0,
|
||||||
|
min: 0.0,
|
||||||
|
);
|
||||||
|
final title = Text(
|
||||||
|
L10n.of(context).setPermissionsLevel,
|
||||||
|
textAlign: TextAlign.center,
|
||||||
|
);
|
||||||
|
final content = Column(
|
||||||
|
mainAxisSize: MainAxisSize.min,
|
||||||
|
children: [
|
||||||
|
Text('Level: ' +
|
||||||
|
(_permission == 100
|
||||||
|
? '$_permission (${L10n.of(context).admin})'
|
||||||
|
: _permission >= 50
|
||||||
|
? '$_permission (${L10n.of(context).moderator})'
|
||||||
|
: _permission.toString())),
|
||||||
|
Container(
|
||||||
|
height: 56,
|
||||||
|
child: slider,
|
||||||
|
),
|
||||||
|
],
|
||||||
|
);
|
||||||
|
final buttons = [
|
||||||
|
AdaptiveFlatButton(
|
||||||
|
child: Text(L10n.of(context).cancel),
|
||||||
|
onPressed: () => Navigator.of(context).pop<int>(null),
|
||||||
|
),
|
||||||
|
AdaptiveFlatButton(
|
||||||
|
child: Text(L10n.of(context).confirm),
|
||||||
|
onPressed: () => Navigator.of(context).pop<int>(_permission),
|
||||||
|
),
|
||||||
|
];
|
||||||
|
if (PlatformInfos.isCupertinoStyle) {
|
||||||
|
return CupertinoAlertDialog(
|
||||||
|
title: title,
|
||||||
|
content: content,
|
||||||
|
actions: buttons,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return AlertDialog(
|
||||||
|
title: title,
|
||||||
|
content: content,
|
||||||
|
actions: buttons,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
@ -3,6 +3,7 @@ import 'dart:math';
|
|||||||
import 'package:adaptive_dialog/adaptive_dialog.dart';
|
import 'package:adaptive_dialog/adaptive_dialog.dart';
|
||||||
import 'package:famedlysdk/famedlysdk.dart';
|
import 'package:famedlysdk/famedlysdk.dart';
|
||||||
import 'package:fluffychat/components/adaptive_page_layout.dart';
|
import 'package:fluffychat/components/adaptive_page_layout.dart';
|
||||||
|
import 'package:fluffychat/components/dialogs/permission_slider_dialog.dart';
|
||||||
import 'package:fluffychat/utils/app_route.dart';
|
import 'package:fluffychat/utils/app_route.dart';
|
||||||
import 'package:fluffychat/utils/fluffy_share.dart';
|
import 'package:fluffychat/utils/fluffy_share.dart';
|
||||||
import 'package:fluffychat/views/chat.dart';
|
import 'package:fluffychat/views/chat.dart';
|
||||||
@ -52,24 +53,14 @@ class UserBottomSheet extends StatelessWidget {
|
|||||||
Navigator.of(context).pop();
|
Navigator.of(context).pop();
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 'admin':
|
case 'permission':
|
||||||
if (await _askConfirmation()) {
|
final newPermission =
|
||||||
|
await PermissionSliderDialog(initialPermission: user.powerLevel)
|
||||||
|
.show(context);
|
||||||
|
if (newPermission != null) {
|
||||||
|
if (newPermission == 100 && await _askConfirmation() == false) break;
|
||||||
await SimpleDialogs(context)
|
await SimpleDialogs(context)
|
||||||
.tryRequestWithLoadingDialog(user.setPower(100));
|
.tryRequestWithLoadingDialog(user.setPower(newPermission));
|
||||||
Navigator.of(context).pop();
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 'moderator':
|
|
||||||
if (await _askConfirmation()) {
|
|
||||||
await SimpleDialogs(context)
|
|
||||||
.tryRequestWithLoadingDialog(user.setPower(50));
|
|
||||||
Navigator.of(context).pop();
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 'user':
|
|
||||||
if (await _askConfirmation()) {
|
|
||||||
await SimpleDialogs(context)
|
|
||||||
.tryRequestWithLoadingDialog(user.setPower(0));
|
|
||||||
Navigator.of(context).pop();
|
Navigator.of(context).pop();
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@ -119,38 +110,14 @@ class UserBottomSheet extends StatelessWidget {
|
|||||||
value: 'message'),
|
value: 'message'),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
if (user.canChangePowerLevel &&
|
if (user.canChangePowerLevel) {
|
||||||
user.room.ownPowerLevel == 100 &&
|
|
||||||
user.powerLevel != 100) {
|
|
||||||
items.add(
|
items.add(
|
||||||
PopupMenuItem(
|
PopupMenuItem(
|
||||||
child: _TextWithIcon(
|
child: _TextWithIcon(
|
||||||
L10n.of(context).makeAnAdmin,
|
L10n.of(context).setPermissionsLevel,
|
||||||
Icons.arrow_upward,
|
Icons.edit_attributes_outlined,
|
||||||
),
|
),
|
||||||
value: 'admin'),
|
value: 'permission'),
|
||||||
);
|
|
||||||
}
|
|
||||||
if (user.canChangePowerLevel &&
|
|
||||||
user.room.ownPowerLevel >= 50 &&
|
|
||||||
user.powerLevel != 50) {
|
|
||||||
items.add(
|
|
||||||
PopupMenuItem(
|
|
||||||
child: _TextWithIcon(
|
|
||||||
L10n.of(context).makeAModerator,
|
|
||||||
Icons.arrow_upward_outlined,
|
|
||||||
),
|
|
||||||
value: 'moderator'),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
if (user.canChangePowerLevel && user.powerLevel != 0) {
|
|
||||||
items.add(
|
|
||||||
PopupMenuItem(
|
|
||||||
child: _TextWithIcon(
|
|
||||||
L10n.of(context).revokeAllPermissions,
|
|
||||||
Icons.arrow_downward_outlined,
|
|
||||||
),
|
|
||||||
value: 'user'),
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
if (user.canKick) {
|
if (user.canKick) {
|
||||||
|
@ -1370,11 +1370,71 @@
|
|||||||
"count": {}
|
"count": {}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"editBlockedServers": "Edit blocked servers",
|
||||||
|
"@editBlockedServers": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"enableEncryption": "Enable encryption",
|
||||||
|
"@enableEncryption": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"replaceRoomWithNewerVersion": "Replace room with newer version",
|
||||||
|
"@replaceRoomWithNewerVersion": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"editRoomAvatar": "Edit room avatar",
|
||||||
|
"@editRoomAvatar": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"defaultPermissionLevel": "Default permission level",
|
||||||
|
"@defaultPermissionLevel": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"sendMessages": "Send messages",
|
||||||
|
"@sendMessages": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"configureChat": "Configure chat",
|
||||||
|
"@configureChat": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"participant": "Participant",
|
||||||
|
"@participant": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
"send": "Send",
|
"send": "Send",
|
||||||
"@send": {
|
"@send": {
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"placeholders": {}
|
"placeholders": {}
|
||||||
},
|
},
|
||||||
|
"whoCanPerformWhichAction": "Who can perform which action",
|
||||||
|
"@whoCanPerformWhichAction": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"editChatPermissions": "Edit chat permissions",
|
||||||
|
"@editChatPermissions": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"setCustomEmotes": "Set custom emotes",
|
||||||
|
"@setCustomEmotes": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
|
"setPermissionsLevel": "Set permissions level",
|
||||||
|
"@setPermissionsLevel": {
|
||||||
|
"type": "text",
|
||||||
|
"placeholders": {}
|
||||||
|
},
|
||||||
"sendAMessage": "Send a message",
|
"sendAMessage": "Send a message",
|
||||||
"@sendAMessage": {
|
"@sendAMessage": {
|
||||||
"type": "text",
|
"type": "text",
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import 'package:adaptive_dialog/adaptive_dialog.dart';
|
import 'package:adaptive_dialog/adaptive_dialog.dart';
|
||||||
import 'package:fluffychat/config/app_config.dart';
|
import 'package:fluffychat/config/app_config.dart';
|
||||||
import 'package:fluffychat/utils/fluffy_share.dart';
|
import 'package:fluffychat/utils/fluffy_share.dart';
|
||||||
|
import 'package:fluffychat/views/chat_permissions_settings.dart';
|
||||||
import 'package:flushbar/flushbar_helper.dart';
|
import 'package:flushbar/flushbar_helper.dart';
|
||||||
import 'package:famedlysdk/famedlysdk.dart';
|
import 'package:famedlysdk/famedlysdk.dart';
|
||||||
import 'package:famedlysdk/matrix_api.dart';
|
import 'package:famedlysdk/matrix_api.dart';
|
||||||
@ -316,6 +317,7 @@ class _ChatDetailsState extends State<ChatDetails> {
|
|||||||
child: Icon(Icons.insert_emoticon),
|
child: Icon(Icons.insert_emoticon),
|
||||||
),
|
),
|
||||||
title: Text(L10n.of(context).emoteSettings),
|
title: Text(L10n.of(context).emoteSettings),
|
||||||
|
subtitle: Text(L10n.of(context).setCustomEmotes),
|
||||||
onTap: () async {
|
onTap: () async {
|
||||||
// okay, we need to test if there are any emote state events other than the default one
|
// okay, we need to test if there are any emote state events other than the default one
|
||||||
// if so, we need to be directed to a selection screen for which pack we want to look at
|
// if so, we need to be directed to a selection screen for which pack we want to look at
|
||||||
@ -476,6 +478,24 @@ class _ChatDetailsState extends State<ChatDetails> {
|
|||||||
),
|
),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
|
ListTile(
|
||||||
|
title: Text(L10n.of(context).editChatPermissions),
|
||||||
|
subtitle: Text(
|
||||||
|
L10n.of(context).whoCanPerformWhichAction),
|
||||||
|
leading: CircleAvatar(
|
||||||
|
backgroundColor:
|
||||||
|
Theme.of(context).scaffoldBackgroundColor,
|
||||||
|
foregroundColor: Colors.grey,
|
||||||
|
child: Icon(Icons.edit_attributes_outlined),
|
||||||
|
),
|
||||||
|
onTap: () => Navigator.of(context).push(
|
||||||
|
AppRoute.defaultRoute(
|
||||||
|
context,
|
||||||
|
ChatPermissionsSettingsView(
|
||||||
|
roomId: widget.room.id),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
Divider(thickness: 1),
|
Divider(thickness: 1),
|
||||||
ListTile(
|
ListTile(
|
||||||
title: Text(
|
title: Text(
|
||||||
|
249
lib/views/chat_permissions_settings.dart
Normal file
249
lib/views/chat_permissions_settings.dart
Normal file
@ -0,0 +1,249 @@
|
|||||||
|
import 'dart:developer';
|
||||||
|
|
||||||
|
import 'package:fluffychat/components/adaptive_page_layout.dart';
|
||||||
|
import 'package:fluffychat/components/dialogs/permission_slider_dialog.dart';
|
||||||
|
import 'package:fluffychat/components/dialogs/simple_dialogs.dart';
|
||||||
|
import 'package:fluffychat/components/matrix.dart';
|
||||||
|
import 'package:flushbar/flushbar_helper.dart';
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter_gen/gen_l10n/l10n.dart';
|
||||||
|
import 'package:famedlysdk/famedlysdk.dart';
|
||||||
|
|
||||||
|
import 'chat_list.dart';
|
||||||
|
|
||||||
|
class ChatPermissionsSettingsView extends StatelessWidget {
|
||||||
|
final String roomId;
|
||||||
|
|
||||||
|
const ChatPermissionsSettingsView({Key key, this.roomId}) : super(key: key);
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return AdaptivePageLayout(
|
||||||
|
firstScaffold: ChatList(
|
||||||
|
activeChat: roomId,
|
||||||
|
),
|
||||||
|
secondScaffold: ChatPermissionsSettings(roomId: roomId),
|
||||||
|
primaryPage: FocusPage.SECOND,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class ChatPermissionsSettings extends StatelessWidget {
|
||||||
|
final String roomId;
|
||||||
|
|
||||||
|
const ChatPermissionsSettings({Key key, @required this.roomId})
|
||||||
|
: super(key: key);
|
||||||
|
|
||||||
|
void _editPowerLevel(BuildContext context, String key, int currentLevel,
|
||||||
|
{String category}) async {
|
||||||
|
final room = Matrix.of(context).client.getRoomById(roomId);
|
||||||
|
if (!room.canSendEvent(EventTypes.RoomPowerLevels)) {
|
||||||
|
return FlushbarHelper.createError(message: L10n.of(context).noPermission)
|
||||||
|
.show(context);
|
||||||
|
}
|
||||||
|
final newLevel =
|
||||||
|
await PermissionSliderDialog(initialPermission: currentLevel)
|
||||||
|
.show(context);
|
||||||
|
if (newLevel == null) return;
|
||||||
|
final content = Map<String, dynamic>.from(
|
||||||
|
room.getState(EventTypes.RoomPowerLevels).content);
|
||||||
|
if (category != null) {
|
||||||
|
if (!content.containsKey(category)) {
|
||||||
|
content[category] = <String, dynamic>{};
|
||||||
|
}
|
||||||
|
content[category][key] = newLevel;
|
||||||
|
} else {
|
||||||
|
content[key] = newLevel;
|
||||||
|
}
|
||||||
|
inspect(content);
|
||||||
|
await SimpleDialogs(context).tryRequestWithLoadingDialog(
|
||||||
|
room.client.sendState(room.id, EventTypes.RoomPowerLevels, content),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Scaffold(
|
||||||
|
appBar: AppBar(title: Text(L10n.of(context).editChatPermissions)),
|
||||||
|
body: StreamBuilder(
|
||||||
|
stream: Matrix.of(context).client.onSync.stream.where(
|
||||||
|
(e) =>
|
||||||
|
(e?.rooms?.join?.containsKey(roomId) ?? false) &&
|
||||||
|
(e.rooms.join[roomId]?.timeline?.events
|
||||||
|
?.any((s) => s.type == EventTypes.RoomPowerLevels) ??
|
||||||
|
false),
|
||||||
|
),
|
||||||
|
builder: (context, _) {
|
||||||
|
final room = Matrix.of(context).client.getRoomById(roomId);
|
||||||
|
final powerLevelsContent = Map<String, dynamic>.from(
|
||||||
|
room.getState(EventTypes.RoomPowerLevels).content);
|
||||||
|
final powerLevels = Map<String, dynamic>.from(powerLevelsContent)
|
||||||
|
..removeWhere((k, v) => !(v is int));
|
||||||
|
final eventsPowerLevels =
|
||||||
|
Map<String, dynamic>.from(powerLevelsContent['events'])
|
||||||
|
..removeWhere((k, v) => !(v is int));
|
||||||
|
|
||||||
|
return ListView(
|
||||||
|
children: [
|
||||||
|
Column(
|
||||||
|
mainAxisSize: MainAxisSize.min,
|
||||||
|
children: [
|
||||||
|
for (var entry in powerLevels.entries)
|
||||||
|
PermissionsListTile(
|
||||||
|
permissionKey: entry.key,
|
||||||
|
permission: entry.value,
|
||||||
|
onTap: () =>
|
||||||
|
_editPowerLevel(context, entry.key, entry.value),
|
||||||
|
),
|
||||||
|
Divider(thickness: 1),
|
||||||
|
ListTile(
|
||||||
|
title: Text(
|
||||||
|
L10n.of(context).notifications,
|
||||||
|
style: TextStyle(
|
||||||
|
color: Theme.of(context).primaryColor,
|
||||||
|
fontWeight: FontWeight.bold,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
Builder(builder: (context) {
|
||||||
|
final key = 'rooms';
|
||||||
|
final int value =
|
||||||
|
powerLevelsContent.containsKey('notifications')
|
||||||
|
? powerLevelsContent['notifications']['rooms'] ?? 0
|
||||||
|
: 0;
|
||||||
|
return PermissionsListTile(
|
||||||
|
permissionKey: key,
|
||||||
|
permission: value,
|
||||||
|
category: 'notifications',
|
||||||
|
onTap: () => _editPowerLevel(context, key, value,
|
||||||
|
category: 'notifications'),
|
||||||
|
);
|
||||||
|
}),
|
||||||
|
Divider(thickness: 1),
|
||||||
|
ListTile(
|
||||||
|
title: Text(
|
||||||
|
L10n.of(context).configureChat,
|
||||||
|
style: TextStyle(
|
||||||
|
color: Theme.of(context).primaryColor,
|
||||||
|
fontWeight: FontWeight.bold,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
if (eventsPowerLevels != null)
|
||||||
|
for (var entry in eventsPowerLevels.entries)
|
||||||
|
PermissionsListTile(
|
||||||
|
permissionKey: entry.key,
|
||||||
|
category: 'events',
|
||||||
|
permission: entry.value,
|
||||||
|
onTap: () => _editPowerLevel(
|
||||||
|
context, entry.key, entry.value,
|
||||||
|
category: 'events'),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
],
|
||||||
|
);
|
||||||
|
},
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class PermissionsListTile extends StatelessWidget {
|
||||||
|
final String permissionKey;
|
||||||
|
final int permission;
|
||||||
|
final String category;
|
||||||
|
final void Function() onTap;
|
||||||
|
|
||||||
|
const PermissionsListTile({
|
||||||
|
Key key,
|
||||||
|
@required this.permissionKey,
|
||||||
|
@required this.permission,
|
||||||
|
this.category,
|
||||||
|
this.onTap,
|
||||||
|
}) : super(key: key);
|
||||||
|
|
||||||
|
String getLocalizedPowerLevelString(BuildContext context) {
|
||||||
|
if (category == null) {
|
||||||
|
switch (permissionKey) {
|
||||||
|
case 'users_default':
|
||||||
|
return L10n.of(context).defaultPermissionLevel;
|
||||||
|
case 'events_default':
|
||||||
|
return L10n.of(context).sendMessages;
|
||||||
|
case 'state_default':
|
||||||
|
return L10n.of(context).configureChat;
|
||||||
|
case 'ban':
|
||||||
|
return L10n.of(context).banFromChat;
|
||||||
|
case 'kick':
|
||||||
|
return L10n.of(context).kickFromChat;
|
||||||
|
case 'redact':
|
||||||
|
return L10n.of(context).deleteMessage;
|
||||||
|
case 'invite':
|
||||||
|
return L10n.of(context).inviteContact;
|
||||||
|
}
|
||||||
|
} else if (category == 'notifications') {
|
||||||
|
switch (permissionKey) {
|
||||||
|
case 'rooms':
|
||||||
|
return L10n.of(context).notifications;
|
||||||
|
}
|
||||||
|
} else if (category == 'events') {
|
||||||
|
switch (permissionKey) {
|
||||||
|
case EventTypes.RoomName:
|
||||||
|
return L10n.of(context).changeTheNameOfTheGroup;
|
||||||
|
case EventTypes.RoomPowerLevels:
|
||||||
|
return L10n.of(context).editChatPermissions;
|
||||||
|
case EventTypes.HistoryVisibility:
|
||||||
|
return L10n.of(context).visibilityOfTheChatHistory;
|
||||||
|
case EventTypes.RoomCanonicalAlias:
|
||||||
|
return L10n.of(context).setInvitationLink;
|
||||||
|
case EventTypes.RoomAvatar:
|
||||||
|
return L10n.of(context).editRoomAvatar;
|
||||||
|
case EventTypes.RoomTombstone:
|
||||||
|
return L10n.of(context).replaceRoomWithNewerVersion;
|
||||||
|
case EventTypes.Encryption:
|
||||||
|
return L10n.of(context).enableEncryption;
|
||||||
|
case 'm.room.server_acl':
|
||||||
|
return L10n.of(context).editBlockedServers;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return permissionKey;
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return ListTile(
|
||||||
|
onTap: onTap,
|
||||||
|
leading: CircleAvatar(
|
||||||
|
backgroundColor: Theme.of(context).scaffoldBackgroundColor,
|
||||||
|
foregroundColor: Colors.grey,
|
||||||
|
child: Icon(Icons.edit_attributes_outlined),
|
||||||
|
),
|
||||||
|
title: Text(getLocalizedPowerLevelString(context)),
|
||||||
|
subtitle: Row(
|
||||||
|
children: [
|
||||||
|
Container(
|
||||||
|
padding: EdgeInsets.all(4),
|
||||||
|
decoration: BoxDecoration(
|
||||||
|
color: Theme.of(context).secondaryHeaderColor,
|
||||||
|
borderRadius: BorderRadius.circular(8),
|
||||||
|
),
|
||||||
|
child: Center(
|
||||||
|
child: Text(permission.toString()),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
SizedBox(width: 8),
|
||||||
|
Text(permission.toLocalizedPowerLevelString(context)),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
extension on int {
|
||||||
|
String toLocalizedPowerLevelString(BuildContext context) {
|
||||||
|
return this == 100
|
||||||
|
? L10n.of(context).admin
|
||||||
|
: this >= 50
|
||||||
|
? L10n.of(context).moderator
|
||||||
|
: L10n.of(context).participant;
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user