Created
September 2, 2021 23:59
-
-
Save Nash0x7E2/b47f8479afe9572e5c16fb414a31481e to your computer and use it in GitHub Desktop.
Send a message using a keyboard shortcut in Flutter.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import 'package:collection/collection.dart' show IterableExtension; | |
import 'package:flutter/material.dart'; | |
import 'package:flutter/services.dart'; | |
import 'package:stream_chat_flutter/stream_chat_flutter.dart'; | |
Future<void> main() async { | |
final client = StreamChatClient( | |
's2dxdhpxd94g', | |
logLevel: Level.INFO, | |
); | |
await client.connectUser( | |
User(id: 'super-band-9'), | |
'''eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyX2lkIjoic3VwZXItYmFuZC05In0.0L6lGoeLwkz0aZRUcpZKsvaXtNEDHBcezVTZ0oPq40A''', | |
); | |
runApp( | |
MyApp( | |
client: client, | |
), | |
); | |
} | |
class MyApp extends StatelessWidget { | |
const MyApp({ | |
Key? key, | |
required this.client, | |
}) : super(key: key); | |
final StreamChatClient client; | |
@override | |
// ignore: prefer_expression_function_bodies | |
Widget build(BuildContext context) { | |
return MaterialApp( | |
builder: (context, child) => StreamChat( | |
client: client, | |
child: child, | |
), | |
home: const ChannelListPage(), | |
); | |
} | |
} | |
class ChannelListPage extends StatelessWidget { | |
const ChannelListPage({ | |
Key? key, | |
}) : super(key: key); | |
@override | |
// ignore: prefer_expression_function_bodies | |
Widget build(BuildContext context) { | |
return Scaffold( | |
body: ChannelsBloc( | |
child: ChannelListView( | |
filter: Filter.in_( | |
'members', | |
[StreamChat.of(context).currentUser!.id], | |
), | |
channelPreviewBuilder: _channelPreviewBuilder, | |
// sort: [SortOption('last_message_at')], | |
pagination: const PaginationParams( | |
limit: 20, | |
), | |
channelWidget: const ChannelPage(), | |
), | |
), | |
); | |
} | |
Widget _channelPreviewBuilder(BuildContext context, Channel channel) { | |
final lastMessage = channel.state?.messages.reversed.firstWhereOrNull( | |
(message) => !message.isDeleted, | |
); | |
final subtitle = lastMessage == null ? 'nothing yet' : lastMessage.text!; | |
final opacity = (channel.state?.unreadCount ?? 0) > 0 ? 1.0 : 0.5; | |
return ListTile( | |
onTap: () { | |
Navigator.push( | |
context, | |
MaterialPageRoute( | |
builder: (_) => StreamChannel( | |
channel: channel, | |
child: const ChannelPage(), | |
), | |
), | |
); | |
}, | |
leading: ChannelAvatar( | |
channel: channel, | |
), | |
title: ChannelName( | |
textStyle: ChannelPreviewTheme.of(context).titleStyle!.copyWith( | |
color: StreamChatTheme.of(context) | |
.colorTheme | |
.textHighEmphasis | |
.withOpacity(opacity), | |
), | |
), | |
subtitle: Text(subtitle), | |
trailing: channel.state!.unreadCount > 0 | |
? CircleAvatar( | |
radius: 10, | |
child: Text(channel.state!.unreadCount.toString()), | |
) | |
: const SizedBox(), | |
); | |
} | |
} | |
class EnterIntent extends Intent { | |
const EnterIntent(); | |
} | |
class ChannelPage extends StatefulWidget { | |
const ChannelPage({ | |
Key? key, | |
}) : super(key: key); | |
@override | |
State<ChannelPage> createState() => _ChannelPageState(); | |
} | |
class _ChannelPageState extends State<ChannelPage> { | |
late TextEditingController textEditingController; | |
@override | |
void initState() { | |
super.initState(); | |
textEditingController = TextEditingController(); | |
} | |
@override | |
void dispose() { | |
textEditingController.dispose(); | |
super.dispose(); | |
} | |
void _sendMessageOnEnter() { | |
if (textEditingController.value.text.isNotEmpty) { | |
StreamChannel.of(context).channel.sendMessage( | |
Message( | |
text: textEditingController.value.text, | |
), | |
); | |
textEditingController.clear(); | |
} | |
} | |
@override | |
Widget build(BuildContext context) { | |
return Scaffold( | |
appBar: const ChannelHeader(), | |
body: Shortcuts( | |
shortcuts: <ShortcutActivator, Intent>{ | |
LogicalKeySet(LogicalKeyboardKey.enter): const EnterIntent(), | |
}, | |
child: Actions( | |
actions: { | |
EnterIntent: CallbackAction<EnterIntent>( | |
onInvoke: (EnterIntent intent) => _sendMessageOnEnter(), | |
), | |
}, | |
child: Column( | |
children: <Widget>[ | |
const Expanded( | |
child: MessageListView(), | |
), | |
MessageInput( | |
textEditingController: textEditingController, | |
), | |
], | |
), | |
), | |
), | |
); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment