removed deprecated uses, fmt
This commit is contained in:
@@ -6,7 +6,8 @@ class ImagePickerImpl extends ImagePickerRepository {
|
|||||||
@override
|
@override
|
||||||
Future<File> pickImage() async {
|
Future<File> pickImage() async {
|
||||||
final picker = ImagePicker();
|
final picker = ImagePicker();
|
||||||
final pickedFile = await picker.getImage(source: ImageSource.gallery, maxWidth: 400);
|
final pickedFile =
|
||||||
|
await picker.getImage(source: ImageSource.gallery, maxWidth: 400);
|
||||||
return File(pickedFile.path);
|
return File(pickedFile.path);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -46,7 +46,9 @@ class StreamApiLocalImpl extends StreamApiRepository {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Future<Channel> createGroupChat(String channelId, String name, List<String> members, {String image}) async {
|
Future<Channel> createGroupChat(
|
||||||
|
String channelId, String name, List<String> members,
|
||||||
|
{String image}) async {
|
||||||
final channel = _client.channel('messaging', id: channelId, extraData: {
|
final channel = _client.channel('messaging', id: channelId, extraData: {
|
||||||
'name': name,
|
'name': name,
|
||||||
'image': image,
|
'image': image,
|
||||||
@@ -58,13 +60,14 @@ class StreamApiLocalImpl extends StreamApiRepository {
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
Future<Channel> createSimpleChat(String friendId) async {
|
Future<Channel> createSimpleChat(String friendId) async {
|
||||||
final channel =
|
final channel = _client.channel('messaging',
|
||||||
_client.channel('messaging', id: '${_client.state.user.id.hashCode}${friendId.hashCode}', extraData: {
|
id: '${_client.state.user.id.hashCode}${friendId.hashCode}',
|
||||||
'members': [
|
extraData: {
|
||||||
friendId,
|
'members': [
|
||||||
_client.state.user.id,
|
friendId,
|
||||||
],
|
_client.state.user.id,
|
||||||
});
|
],
|
||||||
|
});
|
||||||
await channel.watch();
|
await channel.watch();
|
||||||
return channel;
|
return channel;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -20,8 +20,10 @@ class AuthImpl extends AuthRepository {
|
|||||||
try {
|
try {
|
||||||
UserCredential userCredential;
|
UserCredential userCredential;
|
||||||
final GoogleSignInAccount googleUser = await GoogleSignIn().signIn();
|
final GoogleSignInAccount googleUser = await GoogleSignIn().signIn();
|
||||||
final GoogleSignInAuthentication googleAuth = await googleUser.authentication;
|
final GoogleSignInAuthentication googleAuth =
|
||||||
final GoogleAuthCredential googleAuthCredential = GoogleAuthProvider.credential(
|
await googleUser.authentication;
|
||||||
|
final GoogleAuthCredential googleAuthCredential =
|
||||||
|
GoogleAuthProvider.credential(
|
||||||
accessToken: googleAuth.accessToken,
|
accessToken: googleAuth.accessToken,
|
||||||
idToken: googleAuth.idToken,
|
idToken: googleAuth.idToken,
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -62,7 +62,8 @@ class StreamApiImpl extends StreamApiRepository {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Future<Channel> createGroupChat(String id, String name, List<String> members, {String image}) async {
|
Future<Channel> createGroupChat(String id, String name, List<String> members,
|
||||||
|
{String image}) async {
|
||||||
final channel = _client.channel('messaging', id: id, extraData: {
|
final channel = _client.channel('messaging', id: id, extraData: {
|
||||||
'name': name,
|
'name': name,
|
||||||
'image': image,
|
'image': image,
|
||||||
@@ -74,13 +75,14 @@ class StreamApiImpl extends StreamApiRepository {
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
Future<Channel> createSimpleChat(String friendId) async {
|
Future<Channel> createSimpleChat(String friendId) async {
|
||||||
final channel =
|
final channel = _client.channel('messaging',
|
||||||
_client.channel('messaging', id: '${_client.state.user.id.hashCode}${friendId.hashCode}', extraData: {
|
id: '${_client.state.user.id.hashCode}${friendId.hashCode}',
|
||||||
'members': [
|
extraData: {
|
||||||
friendId,
|
'members': [
|
||||||
_client.state.user.id,
|
friendId,
|
||||||
],
|
_client.state.user.id,
|
||||||
});
|
],
|
||||||
|
});
|
||||||
await channel.watch();
|
await channel.watch();
|
||||||
return channel;
|
return channel;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,7 +6,9 @@ abstract class StreamApiRepository {
|
|||||||
Future<String> getToken(String userId);
|
Future<String> getToken(String userId);
|
||||||
Future<bool> connectIfExist(String userId);
|
Future<bool> connectIfExist(String userId);
|
||||||
Future<ChatUser> connectUser(ChatUser user, String token);
|
Future<ChatUser> connectUser(ChatUser user, String token);
|
||||||
Future<Channel> createGroupChat(String channelId, String name, List<String> members, {String image});
|
Future<Channel> createGroupChat(
|
||||||
|
String channelId, String name, List<String> members,
|
||||||
|
{String image});
|
||||||
Future<Channel> createSimpleChat(String friendId);
|
Future<Channel> createSimpleChat(String friendId);
|
||||||
Future<void> logout();
|
Future<void> logout();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -18,10 +18,13 @@ import 'package:stream_chat_flutter/stream_chat_flutter.dart';
|
|||||||
List<RepositoryProvider> buildRepositories(StreamChatClient client) {
|
List<RepositoryProvider> buildRepositories(StreamChatClient client) {
|
||||||
//TODO: Here you can use your local implementations of your repositories
|
//TODO: Here you can use your local implementations of your repositories
|
||||||
return [
|
return [
|
||||||
RepositoryProvider<StreamApiRepository>(create: (_) => StreamApiImpl(client)),
|
RepositoryProvider<StreamApiRepository>(
|
||||||
RepositoryProvider<PersistentStorageRepository>(create: (_) => PersistentStorageImpl()),
|
create: (_) => StreamApiImpl(client)),
|
||||||
|
RepositoryProvider<PersistentStorageRepository>(
|
||||||
|
create: (_) => PersistentStorageImpl()),
|
||||||
RepositoryProvider<AuthRepository>(create: (_) => AuthImpl()),
|
RepositoryProvider<AuthRepository>(create: (_) => AuthImpl()),
|
||||||
RepositoryProvider<UploadStorageRepository>(create: (_) => UploadStorageImpl()),
|
RepositoryProvider<UploadStorageRepository>(
|
||||||
|
create: (_) => UploadStorageImpl()),
|
||||||
RepositoryProvider<ImagePickerRepository>(create: (_) => ImagePickerImpl()),
|
RepositoryProvider<ImagePickerRepository>(create: (_) => ImagePickerImpl()),
|
||||||
RepositoryProvider<ProfileSignInUseCase>(
|
RepositoryProvider<ProfileSignInUseCase>(
|
||||||
create: (context) => ProfileSignInUseCase(
|
create: (context) => ProfileSignInUseCase(
|
||||||
|
|||||||
@@ -25,7 +25,8 @@ class CreateGroupUseCase {
|
|||||||
final channelId = Uuid().v4();
|
final channelId = Uuid().v4();
|
||||||
String image;
|
String image;
|
||||||
if (input.imageFile != null) {
|
if (input.imageFile != null) {
|
||||||
image = await _uploadStorageRepository.uploadPhoto(input.imageFile, 'channels/$channelId');
|
image = await _uploadStorageRepository.uploadPhoto(
|
||||||
|
input.imageFile, 'channels/$channelId');
|
||||||
}
|
}
|
||||||
final channel = await _streamApiRepository.createGroupChat(
|
final channel = await _streamApiRepository.createGroupChat(
|
||||||
channelId,
|
channelId,
|
||||||
|
|||||||
@@ -27,8 +27,10 @@ class ProfileSignInUseCase {
|
|||||||
final token = await _streamApiRepository.getToken(auth.id);
|
final token = await _streamApiRepository.getToken(auth.id);
|
||||||
String image;
|
String image;
|
||||||
if (input.imageFile != null) {
|
if (input.imageFile != null) {
|
||||||
image = await _uploadStorageRepository.uploadPhoto(input.imageFile, 'users/${auth.id}');
|
image = await _uploadStorageRepository.uploadPhoto(
|
||||||
|
input.imageFile, 'users/${auth.id}');
|
||||||
}
|
}
|
||||||
await _streamApiRepository.connectUser(ChatUser(name: input.name, id: auth.id, image: image), token);
|
await _streamApiRepository.connectUser(
|
||||||
|
ChatUser(name: input.name, id: auth.id, image: image), token);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -34,7 +34,8 @@ class MyApp extends StatelessWidget {
|
|||||||
return StreamChat(
|
return StreamChat(
|
||||||
child: child,
|
child: child,
|
||||||
client: _streamChatClient,
|
client: _streamChatClient,
|
||||||
streamChatThemeData: StreamChatThemeData.fromTheme(Theme.of(context)).copyWith(
|
streamChatThemeData:
|
||||||
|
StreamChatThemeData.fromTheme(Theme.of(context)).copyWith(
|
||||||
ownMessageTheme: MessageTheme(
|
ownMessageTheme: MessageTheme(
|
||||||
messageBackgroundColor: Theme.of(context).accentColor,
|
messageBackgroundColor: Theme.of(context).accentColor,
|
||||||
messageText: TextStyle(color: Colors.white),
|
messageText: TextStyle(color: Colors.white),
|
||||||
|
|||||||
@@ -18,5 +18,7 @@ Future pushAndReplaceToPage(BuildContext context, Widget widget) async {
|
|||||||
|
|
||||||
Future popAllAndPush(BuildContext context, Widget widget) async {
|
Future popAllAndPush(BuildContext context, Widget widget) async {
|
||||||
await Navigator.pushAndRemoveUntil(
|
await Navigator.pushAndRemoveUntil(
|
||||||
context, MaterialPageRoute(builder: (BuildContext context) => widget), ModalRoute.withName('/'));
|
context,
|
||||||
|
MaterialPageRoute(builder: (BuildContext context) => widget),
|
||||||
|
ModalRoute.withName('/'));
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -90,7 +90,8 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
children: <Widget>[
|
children: <Widget>[
|
||||||
Flexible(
|
Flexible(
|
||||||
child: ChannelName(
|
child: ChannelName(
|
||||||
textStyle: StreamChatTheme.of(context).channelPreviewTheme.title,
|
textStyle:
|
||||||
|
StreamChatTheme.of(context).channelPreviewTheme.title,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
StreamBuilder<List<Member>>(
|
StreamBuilder<List<Member>>(
|
||||||
@@ -99,7 +100,8 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
builder: (context, snapshot) {
|
builder: (context, snapshot) {
|
||||||
if (!snapshot.hasData ||
|
if (!snapshot.hasData ||
|
||||||
snapshot.data.isEmpty ||
|
snapshot.data.isEmpty ||
|
||||||
!snapshot.data.any((Member e) => e.user.id == channel.client.state.user.id)) {
|
!snapshot.data.any((Member e) =>
|
||||||
|
e.user.id == channel.client.state.user.id)) {
|
||||||
return SizedBox();
|
return SizedBox();
|
||||||
}
|
}
|
||||||
return ChannelUnreadIndicator(
|
return ChannelUnreadIndicator(
|
||||||
@@ -118,15 +120,21 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
(m) => !m.isDeleted && m.shadowed != true,
|
(m) => !m.isDeleted && m.shadowed != true,
|
||||||
orElse: () => null,
|
orElse: () => null,
|
||||||
);
|
);
|
||||||
if (lastMessage?.user?.id == StreamChat.of(context).user.id) {
|
if (lastMessage?.user?.id ==
|
||||||
|
StreamChat.of(context).user.id) {
|
||||||
return Padding(
|
return Padding(
|
||||||
padding: const EdgeInsets.only(right: 4.0),
|
padding: const EdgeInsets.only(right: 4.0),
|
||||||
child: SendingIndicator(
|
child: SendingIndicator(
|
||||||
message: lastMessage,
|
message: lastMessage,
|
||||||
size: StreamChatTheme.of(context).channelPreviewTheme.indicatorIconSize,
|
size: StreamChatTheme.of(context)
|
||||||
|
.channelPreviewTheme
|
||||||
|
.indicatorIconSize,
|
||||||
isMessageRead: channel.state.read
|
isMessageRead: channel.state.read
|
||||||
?.where((element) => element.user.id != channel.client.state.user.id)
|
?.where((element) =>
|
||||||
?.where((element) => element.lastRead.isAfter(lastMessage.createdAt))
|
element.user.id !=
|
||||||
|
channel.client.state.user.id)
|
||||||
|
?.where((element) => element.lastRead
|
||||||
|
.isAfter(lastMessage.createdAt))
|
||||||
?.isNotEmpty ==
|
?.isNotEmpty ==
|
||||||
true,
|
true,
|
||||||
),
|
),
|
||||||
@@ -158,7 +166,8 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
|
|
||||||
var startOfDay = DateTime(now.year, now.month, now.day);
|
var startOfDay = DateTime(now.year, now.month, now.day);
|
||||||
|
|
||||||
if (lastMessageAt.millisecondsSinceEpoch >= startOfDay.millisecondsSinceEpoch) {
|
if (lastMessageAt.millisecondsSinceEpoch >=
|
||||||
|
startOfDay.millisecondsSinceEpoch) {
|
||||||
stringDate = Jiffy(lastMessageAt.toLocal()).format('HH:mm');
|
stringDate = Jiffy(lastMessageAt.toLocal()).format('HH:mm');
|
||||||
} else if (lastMessageAt.millisecondsSinceEpoch >=
|
} else if (lastMessageAt.millisecondsSinceEpoch >=
|
||||||
startOfDay.subtract(Duration(days: 1)).millisecondsSinceEpoch) {
|
startOfDay.subtract(Duration(days: 1)).millisecondsSinceEpoch) {
|
||||||
@@ -187,8 +196,14 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
),
|
),
|
||||||
Text(
|
Text(
|
||||||
' Channel is muted',
|
' Channel is muted',
|
||||||
style: StreamChatTheme.of(context).channelPreviewTheme.subtitle.copyWith(
|
style: StreamChatTheme.of(context)
|
||||||
color: StreamChatTheme.of(context).channelPreviewTheme.subtitle.color,
|
.channelPreviewTheme
|
||||||
|
.subtitle
|
||||||
|
.copyWith(
|
||||||
|
color: StreamChatTheme.of(context)
|
||||||
|
.channelPreviewTheme
|
||||||
|
.subtitle
|
||||||
|
.color,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
@@ -198,7 +213,8 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
channel: channel,
|
channel: channel,
|
||||||
alternativeWidget: _buildLastMessage(context),
|
alternativeWidget: _buildLastMessage(context),
|
||||||
style: StreamChatTheme.of(context).channelPreviewTheme.subtitle.copyWith(
|
style: StreamChatTheme.of(context).channelPreviewTheme.subtitle.copyWith(
|
||||||
color: StreamChatTheme.of(context).channelPreviewTheme.subtitle.color,
|
color:
|
||||||
|
StreamChatTheme.of(context).channelPreviewTheme.subtitle.color,
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@@ -208,7 +224,9 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
stream: channel.state.messagesStream,
|
stream: channel.state.messagesStream,
|
||||||
initialData: channel.state.messages,
|
initialData: channel.state.messages,
|
||||||
builder: (context, snapshot) {
|
builder: (context, snapshot) {
|
||||||
final lastMessage = snapshot.data?.lastWhere((m) => m.shadowed != true && !m.isDeleted, orElse: () => null);
|
final lastMessage = snapshot.data?.lastWhere(
|
||||||
|
(m) => m.shadowed != true && !m.isDeleted,
|
||||||
|
orElse: () => null);
|
||||||
if (lastMessage == null) {
|
if (lastMessage == null) {
|
||||||
return SizedBox();
|
return SizedBox();
|
||||||
}
|
}
|
||||||
@@ -224,7 +242,9 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
} else if (e.type == 'giphy') {
|
} else if (e.type == 'giphy') {
|
||||||
return '[GIF]';
|
return '[GIF]';
|
||||||
}
|
}
|
||||||
return e == lastMessage.attachments.last ? (e.title ?? 'File') : '${e.title ?? 'File'} , ';
|
return e == lastMessage.attachments.last
|
||||||
|
? (e.title ?? 'File')
|
||||||
|
: '${e.title ?? 'File'} , ';
|
||||||
}).where((e) => e != null),
|
}).where((e) => e != null),
|
||||||
lastMessage.text ?? '',
|
lastMessage.text ?? '',
|
||||||
];
|
];
|
||||||
@@ -238,11 +258,21 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
lastMessage.mentionedUsers,
|
lastMessage.mentionedUsers,
|
||||||
lastMessage.attachments,
|
lastMessage.attachments,
|
||||||
StreamChatTheme.of(context).channelPreviewTheme.subtitle.copyWith(
|
StreamChatTheme.of(context).channelPreviewTheme.subtitle.copyWith(
|
||||||
color: StreamChatTheme.of(context).channelPreviewTheme.subtitle.color,
|
color: StreamChatTheme.of(context)
|
||||||
fontStyle: (lastMessage.isSystem || lastMessage.isDeleted) ? FontStyle.italic : FontStyle.normal),
|
.channelPreviewTheme
|
||||||
|
.subtitle
|
||||||
|
.color,
|
||||||
|
fontStyle: (lastMessage.isSystem || lastMessage.isDeleted)
|
||||||
|
? FontStyle.italic
|
||||||
|
: FontStyle.normal),
|
||||||
StreamChatTheme.of(context).channelPreviewTheme.subtitle.copyWith(
|
StreamChatTheme.of(context).channelPreviewTheme.subtitle.copyWith(
|
||||||
color: StreamChatTheme.of(context).channelPreviewTheme.subtitle.color,
|
color: StreamChatTheme.of(context)
|
||||||
fontStyle: (lastMessage.isSystem || lastMessage.isDeleted) ? FontStyle.italic : FontStyle.normal,
|
.channelPreviewTheme
|
||||||
|
.subtitle
|
||||||
|
.color,
|
||||||
|
fontStyle: (lastMessage.isSystem || lastMessage.isDeleted)
|
||||||
|
? FontStyle.italic
|
||||||
|
: FontStyle.normal,
|
||||||
fontWeight: FontWeight.bold),
|
fontWeight: FontWeight.bold),
|
||||||
),
|
),
|
||||||
maxLines: 1,
|
maxLines: 1,
|
||||||
@@ -252,19 +282,27 @@ class MyChannelPreview extends StatelessWidget {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
TextSpan _getDisplayText(String text, List<User> mentions, List<Attachment> attachments, TextStyle normalTextStyle,
|
TextSpan _getDisplayText(
|
||||||
|
String text,
|
||||||
|
List<User> mentions,
|
||||||
|
List<Attachment> attachments,
|
||||||
|
TextStyle normalTextStyle,
|
||||||
TextStyle mentionsTextStyle) {
|
TextStyle mentionsTextStyle) {
|
||||||
var textList = text.split(' ');
|
var textList = text.split(' ');
|
||||||
var resList = <TextSpan>[];
|
var resList = <TextSpan>[];
|
||||||
for (var e in textList) {
|
for (var e in textList) {
|
||||||
if (mentions != null && mentions.isNotEmpty && mentions.any((element) => '@${element.name}' == e)) {
|
if (mentions != null &&
|
||||||
|
mentions.isNotEmpty &&
|
||||||
|
mentions.any((element) => '@${element.name}' == e)) {
|
||||||
resList.add(TextSpan(
|
resList.add(TextSpan(
|
||||||
text: '$e ',
|
text: '$e ',
|
||||||
style: mentionsTextStyle,
|
style: mentionsTextStyle,
|
||||||
));
|
));
|
||||||
} else if (attachments != null &&
|
} else if (attachments != null &&
|
||||||
attachments.isNotEmpty &&
|
attachments.isNotEmpty &&
|
||||||
attachments.where((e) => e.title != null).any((element) => element.title == e)) {
|
attachments
|
||||||
|
.where((e) => e.title != null)
|
||||||
|
.any((element) => element.title == e)) {
|
||||||
resList.add(TextSpan(
|
resList.add(TextSpan(
|
||||||
text: '$e ',
|
text: '$e ',
|
||||||
style: normalTextStyle.copyWith(fontStyle: FontStyle.italic),
|
style: normalTextStyle.copyWith(fontStyle: FontStyle.italic),
|
||||||
@@ -301,7 +339,9 @@ class ChannelUnreadIndicator extends StatelessWidget {
|
|||||||
|
|
||||||
return Material(
|
return Material(
|
||||||
borderRadius: BorderRadius.circular(8),
|
borderRadius: BorderRadius.circular(8),
|
||||||
color: StreamChatTheme.of(context).channelPreviewTheme.unreadCounterColor,
|
color: StreamChatTheme.of(context)
|
||||||
|
.channelPreviewTheme
|
||||||
|
.unreadCounterColor,
|
||||||
child: Padding(
|
child: Padding(
|
||||||
padding: const EdgeInsets.only(
|
padding: const EdgeInsets.only(
|
||||||
left: 5.0,
|
left: 5.0,
|
||||||
|
|||||||
@@ -43,8 +43,10 @@ class ChatView extends StatelessWidget {
|
|||||||
name = channel.extraData['name'];
|
name = channel.extraData['name'];
|
||||||
image = channel.extraData['image'];
|
image = channel.extraData['image'];
|
||||||
} else {
|
} else {
|
||||||
final friend =
|
final friend = channel.state.members
|
||||||
channel.state.members.where((element) => element.userId != currentUser.id).first.user;
|
.where((element) => element.userId != currentUser.id)
|
||||||
|
.first
|
||||||
|
.user;
|
||||||
name = friend.name;
|
name = friend.name;
|
||||||
image = friend.extraData['image'];
|
image = friend.extraData['image'];
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -13,21 +13,27 @@ class FriendsSelectionCubit extends Cubit<List<ChatUserState>> {
|
|||||||
FriendsSelectionCubit(this._streamApiRepository) : super([]);
|
FriendsSelectionCubit(this._streamApiRepository) : super([]);
|
||||||
final StreamApiRepository _streamApiRepository;
|
final StreamApiRepository _streamApiRepository;
|
||||||
|
|
||||||
List<ChatUserState> get selectedUsers => state.where((element) => element.selected).toList();
|
List<ChatUserState> get selectedUsers =>
|
||||||
|
state.where((element) => element.selected).toList();
|
||||||
|
|
||||||
Future<void> init() async {
|
Future<void> init() async {
|
||||||
final chatUsers = (await _streamApiRepository.getChatUsers()).map((e) => ChatUserState(e)).toList();
|
final chatUsers = (await _streamApiRepository.getChatUsers())
|
||||||
|
.map((e) => ChatUserState(e))
|
||||||
|
.toList();
|
||||||
emit(chatUsers);
|
emit(chatUsers);
|
||||||
}
|
}
|
||||||
|
|
||||||
void selectUser(ChatUserState chatUser) {
|
void selectUser(ChatUserState chatUser) {
|
||||||
final index = state.indexWhere((element) => element.chatUser.id == chatUser.chatUser.id);
|
final index = state
|
||||||
state[index] = ChatUserState(state[index].chatUser, selected: !chatUser.selected);
|
.indexWhere((element) => element.chatUser.id == chatUser.chatUser.id);
|
||||||
|
state[index] =
|
||||||
|
ChatUserState(state[index].chatUser, selected: !chatUser.selected);
|
||||||
emit(List<ChatUserState>.from(state));
|
emit(List<ChatUserState>.from(state));
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<Channel> createFriendChannel(ChatUserState chatUserState) async {
|
Future<Channel> createFriendChannel(ChatUserState chatUserState) async {
|
||||||
return await _streamApiRepository.createSimpleChat(chatUserState.chatUser.id);
|
return await _streamApiRepository
|
||||||
|
.createSimpleChat(chatUserState.chatUser.id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -7,8 +7,11 @@ import 'package:flutter_bloc/flutter_bloc.dart';
|
|||||||
import 'package:stream_chat_flutter/stream_chat_flutter.dart';
|
import 'package:stream_chat_flutter/stream_chat_flutter.dart';
|
||||||
|
|
||||||
class FriendsSelectionView extends StatelessWidget {
|
class FriendsSelectionView extends StatelessWidget {
|
||||||
void _createFriendChannel(BuildContext context, ChatUserState chatUserState) async {
|
void _createFriendChannel(
|
||||||
final channel = await context.read<FriendsSelectionCubit>().createFriendChannel(chatUserState);
|
BuildContext context, ChatUserState chatUserState) async {
|
||||||
|
final channel = await context
|
||||||
|
.read<FriendsSelectionCubit>()
|
||||||
|
.createFriendChannel(chatUserState);
|
||||||
pushAndReplaceToPage(
|
pushAndReplaceToPage(
|
||||||
context,
|
context,
|
||||||
Scaffold(
|
Scaffold(
|
||||||
@@ -26,19 +29,23 @@ class FriendsSelectionView extends StatelessWidget {
|
|||||||
final accentColor = Theme.of(context).accentColor;
|
final accentColor = Theme.of(context).accentColor;
|
||||||
return MultiBlocProvider(
|
return MultiBlocProvider(
|
||||||
providers: [
|
providers: [
|
||||||
BlocProvider(create: (context) => FriendsSelectionCubit(context.read())..init()),
|
BlocProvider(
|
||||||
|
create: (context) => FriendsSelectionCubit(context.read())..init()),
|
||||||
BlocProvider(create: (_) => FriendsGroupCubit()),
|
BlocProvider(create: (_) => FriendsGroupCubit()),
|
||||||
],
|
],
|
||||||
child: BlocBuilder<FriendsGroupCubit, bool>(builder: (context, isGroup) {
|
child: BlocBuilder<FriendsGroupCubit, bool>(builder: (context, isGroup) {
|
||||||
return BlocBuilder<FriendsSelectionCubit, List<ChatUserState>>(builder: (context, snapshot) {
|
return BlocBuilder<FriendsSelectionCubit, List<ChatUserState>>(
|
||||||
final selectedUsers = context.read<FriendsSelectionCubit>().selectedUsers;
|
builder: (context, snapshot) {
|
||||||
|
final selectedUsers =
|
||||||
|
context.read<FriendsSelectionCubit>().selectedUsers;
|
||||||
|
|
||||||
return Scaffold(
|
return Scaffold(
|
||||||
floatingActionButton: isGroup && selectedUsers.isNotEmpty
|
floatingActionButton: isGroup && selectedUsers.isNotEmpty
|
||||||
? FloatingActionButton(
|
? FloatingActionButton(
|
||||||
child: Icon(Icons.arrow_right_alt_rounded),
|
child: Icon(Icons.arrow_right_alt_rounded),
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
pushAndReplaceToPage(context, GroupSelectionView(selectedUsers));
|
pushAndReplaceToPage(
|
||||||
|
context, GroupSelectionView(selectedUsers));
|
||||||
})
|
})
|
||||||
: null,
|
: null,
|
||||||
backgroundColor: Theme.of(context).canvasColor,
|
backgroundColor: Theme.of(context).canvasColor,
|
||||||
@@ -91,12 +98,14 @@ class FriendsSelectionView extends StatelessWidget {
|
|||||||
backgroundColor: accentColor,
|
backgroundColor: accentColor,
|
||||||
child: Icon(Icons.group_outlined),
|
child: Icon(Icons.group_outlined),
|
||||||
),
|
),
|
||||||
title: Text('Create group', style: TextStyle(fontWeight: FontWeight.w700)),
|
title: Text('Create group',
|
||||||
|
style: TextStyle(fontWeight: FontWeight.w700)),
|
||||||
subtitle: Text('Talk with 2 or more contacts'),
|
subtitle: Text('Talk with 2 or more contacts'),
|
||||||
)
|
)
|
||||||
else if (isGroup && selectedUsers.isEmpty)
|
else if (isGroup && selectedUsers.isEmpty)
|
||||||
Padding(
|
Padding(
|
||||||
padding: const EdgeInsets.only(top: 15.0, left: 20.0, bottom: 20),
|
padding: const EdgeInsets.only(
|
||||||
|
top: 15.0, left: 20.0, bottom: 20),
|
||||||
child: Column(
|
child: Column(
|
||||||
mainAxisSize: MainAxisSize.min,
|
mainAxisSize: MainAxisSize.min,
|
||||||
crossAxisAlignment: CrossAxisAlignment.start,
|
crossAxisAlignment: CrossAxisAlignment.start,
|
||||||
@@ -123,7 +132,8 @@ class FriendsSelectionView extends StatelessWidget {
|
|||||||
itemBuilder: (context, index) {
|
itemBuilder: (context, index) {
|
||||||
final chatUserState = selectedUsers[index];
|
final chatUserState = selectedUsers[index];
|
||||||
return Padding(
|
return Padding(
|
||||||
padding: const EdgeInsets.symmetric(horizontal: 13.0),
|
padding: const EdgeInsets.symmetric(
|
||||||
|
horizontal: 13.0),
|
||||||
child: Stack(
|
child: Stack(
|
||||||
clipBehavior: Clip.none,
|
clipBehavior: Clip.none,
|
||||||
children: [
|
children: [
|
||||||
@@ -132,7 +142,8 @@ class FriendsSelectionView extends StatelessWidget {
|
|||||||
children: [
|
children: [
|
||||||
CircleAvatar(
|
CircleAvatar(
|
||||||
radius: 30,
|
radius: 30,
|
||||||
backgroundImage: NetworkImage(chatUserState.chatUser.image),
|
backgroundImage: NetworkImage(
|
||||||
|
chatUserState.chatUser.image),
|
||||||
),
|
),
|
||||||
Text(chatUserState.chatUser.name),
|
Text(chatUserState.chatUser.name),
|
||||||
],
|
],
|
||||||
@@ -141,11 +152,14 @@ class FriendsSelectionView extends StatelessWidget {
|
|||||||
bottom: 40,
|
bottom: 40,
|
||||||
right: -4,
|
right: -4,
|
||||||
child: InkWell(
|
child: InkWell(
|
||||||
onTap: () => context.read<FriendsSelectionCubit>().selectUser(chatUserState),
|
onTap: () => context
|
||||||
|
.read<FriendsSelectionCubit>()
|
||||||
|
.selectUser(chatUserState),
|
||||||
child: CircleAvatar(
|
child: CircleAvatar(
|
||||||
radius: 9,
|
radius: 9,
|
||||||
backgroundColor: accentColor,
|
backgroundColor: accentColor,
|
||||||
child: Icon(Icons.close_rounded, size: 12),
|
child: Icon(Icons.close_rounded,
|
||||||
|
size: 12),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
@@ -163,7 +177,8 @@ class FriendsSelectionView extends StatelessWidget {
|
|||||||
_createFriendChannel(context, chatUserState);
|
_createFriendChannel(context, chatUserState);
|
||||||
},
|
},
|
||||||
leading: CircleAvatar(
|
leading: CircleAvatar(
|
||||||
backgroundImage: NetworkImage(chatUserState.chatUser.image),
|
backgroundImage:
|
||||||
|
NetworkImage(chatUserState.chatUser.image),
|
||||||
),
|
),
|
||||||
title: Text(chatUserState.chatUser.name),
|
title: Text(chatUserState.chatUser.name),
|
||||||
trailing: isGroup
|
trailing: isGroup
|
||||||
@@ -171,7 +186,9 @@ class FriendsSelectionView extends StatelessWidget {
|
|||||||
value: chatUserState.selected,
|
value: chatUserState.selected,
|
||||||
onChanged: (val) {
|
onChanged: (val) {
|
||||||
print('select user for group');
|
print('select user for group');
|
||||||
context.read<FriendsSelectionCubit>().selectUser(chatUserState);
|
context
|
||||||
|
.read<FriendsSelectionCubit>()
|
||||||
|
.selectUser(chatUserState);
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
: null,
|
: null,
|
||||||
|
|||||||
@@ -21,7 +21,8 @@ class GroupSelectionView extends StatelessWidget {
|
|||||||
context.read(),
|
context.read(),
|
||||||
context.read(),
|
context.read(),
|
||||||
),
|
),
|
||||||
child: BlocConsumer<GroupSelectionCubit, GroupSelectionState>(listener: (context, snapshot) {
|
child: BlocConsumer<GroupSelectionCubit, GroupSelectionState>(
|
||||||
|
listener: (context, snapshot) {
|
||||||
if (snapshot.channel != null) {
|
if (snapshot.channel != null) {
|
||||||
pushAndReplaceToPage(
|
pushAndReplaceToPage(
|
||||||
context,
|
context,
|
||||||
@@ -76,9 +77,12 @@ class GroupSelectionView extends StatelessWidget {
|
|||||||
vertical: 20,
|
vertical: 20,
|
||||||
),
|
),
|
||||||
child: TextField(
|
child: TextField(
|
||||||
controller: context.read<GroupSelectionCubit>().nameTextController,
|
controller:
|
||||||
|
context.read<GroupSelectionCubit>().nameTextController,
|
||||||
decoration: InputDecoration(
|
decoration: InputDecoration(
|
||||||
fillColor: Theme.of(context).bottomNavigationBarTheme.backgroundColor,
|
fillColor: Theme.of(context)
|
||||||
|
.bottomNavigationBarTheme
|
||||||
|
.backgroundColor,
|
||||||
hintText: 'Name of the group',
|
hintText: 'Name of the group',
|
||||||
hintStyle: TextStyle(
|
hintStyle: TextStyle(
|
||||||
fontSize: 13,
|
fontSize: 13,
|
||||||
@@ -99,7 +103,8 @@ class GroupSelectionView extends StatelessWidget {
|
|||||||
children: [
|
children: [
|
||||||
CircleAvatar(
|
CircleAvatar(
|
||||||
radius: 30,
|
radius: 30,
|
||||||
backgroundImage: NetworkImage(chatUserState.chatUser.image),
|
backgroundImage:
|
||||||
|
NetworkImage(chatUserState.chatUser.image),
|
||||||
),
|
),
|
||||||
Text(chatUserState.chatUser.name),
|
Text(chatUserState.chatUser.name),
|
||||||
],
|
],
|
||||||
|
|||||||
@@ -61,7 +61,9 @@ class HomeNavigationBar extends StatelessWidget {
|
|||||||
child: Container(
|
child: Container(
|
||||||
decoration: BoxDecoration(
|
decoration: BoxDecoration(
|
||||||
borderRadius: BorderRadius.circular(25),
|
borderRadius: BorderRadius.circular(25),
|
||||||
color: Theme.of(context).bottomNavigationBarTheme.backgroundColor,
|
color: Theme.of(context)
|
||||||
|
.bottomNavigationBarTheme
|
||||||
|
.backgroundColor,
|
||||||
),
|
),
|
||||||
child: Row(
|
child: Row(
|
||||||
mainAxisAlignment: MainAxisAlignment.spaceAround,
|
mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||||
@@ -122,8 +124,10 @@ class _HomeNavItem extends StatelessWidget {
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
final selectedColor = Theme.of(context).bottomNavigationBarTheme.selectedItemColor;
|
final selectedColor =
|
||||||
final unselectedColor = Theme.of(context).bottomNavigationBarTheme.unselectedItemColor;
|
Theme.of(context).bottomNavigationBarTheme.selectedItemColor;
|
||||||
|
final unselectedColor =
|
||||||
|
Theme.of(context).bottomNavigationBarTheme.unselectedItemColor;
|
||||||
final color = selected ? selectedColor : unselectedColor;
|
final color = selected ? selectedColor : unselectedColor;
|
||||||
return GestureDetector(
|
return GestureDetector(
|
||||||
onTap: onTap,
|
onTap: onTap,
|
||||||
|
|||||||
@@ -16,7 +16,8 @@ class SettingsView extends StatelessWidget {
|
|||||||
return MultiBlocProvider(
|
return MultiBlocProvider(
|
||||||
providers: [
|
providers: [
|
||||||
BlocProvider(
|
BlocProvider(
|
||||||
create: (_) => SettingsSwitchCubit(context.read<AppThemeCubit>().isDark),
|
create: (_) =>
|
||||||
|
SettingsSwitchCubit(context.read<AppThemeCubit>().isDark),
|
||||||
),
|
),
|
||||||
BlocProvider(
|
BlocProvider(
|
||||||
create: (_) => SettingsLogoutCubit(context.read()),
|
create: (_) => SettingsLogoutCubit(context.read()),
|
||||||
@@ -75,11 +76,14 @@ class SettingsView extends StatelessWidget {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
Spacer(),
|
Spacer(),
|
||||||
BlocBuilder<SettingsSwitchCubit, bool>(builder: (context, snapshot) {
|
BlocBuilder<SettingsSwitchCubit, bool>(
|
||||||
|
builder: (context, snapshot) {
|
||||||
return Switch(
|
return Switch(
|
||||||
value: snapshot,
|
value: snapshot,
|
||||||
onChanged: (val) {
|
onChanged: (val) {
|
||||||
context.read<SettingsSwitchCubit>().onChangeDarkMode(val);
|
context
|
||||||
|
.read<SettingsSwitchCubit>()
|
||||||
|
.onChangeDarkMode(val);
|
||||||
context.read<AppThemeCubit>().updateTheme(val);
|
context.read<AppThemeCubit>().updateTheme(val);
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -13,7 +13,8 @@ class ProfileVerifyView extends StatelessWidget {
|
|||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
return BlocProvider(
|
return BlocProvider(
|
||||||
create: (context) => ProfileVerifyCubit(context.read(), context.read()),
|
create: (context) => ProfileVerifyCubit(context.read(), context.read()),
|
||||||
child: BlocConsumer<ProfileVerifyCubit, ProfileState>(listener: (context, snapshot) {
|
child: BlocConsumer<ProfileVerifyCubit, ProfileState>(
|
||||||
|
listener: (context, snapshot) {
|
||||||
if (snapshot.success) {
|
if (snapshot.success) {
|
||||||
pushAndReplaceToPage(context, HomeView());
|
pushAndReplaceToPage(context, HomeView());
|
||||||
}
|
}
|
||||||
@@ -59,9 +60,12 @@ class ProfileVerifyView extends StatelessWidget {
|
|||||||
vertical: 20,
|
vertical: 20,
|
||||||
),
|
),
|
||||||
child: TextField(
|
child: TextField(
|
||||||
controller: context.read<ProfileVerifyCubit>().nameController,
|
controller:
|
||||||
|
context.read<ProfileVerifyCubit>().nameController,
|
||||||
decoration: InputDecoration(
|
decoration: InputDecoration(
|
||||||
fillColor: Theme.of(context).bottomNavigationBarTheme.backgroundColor,
|
fillColor: Theme.of(context)
|
||||||
|
.bottomNavigationBarTheme
|
||||||
|
.backgroundColor,
|
||||||
hintText: 'Or just how people now you',
|
hintText: 'Or just how people now you',
|
||||||
hintStyle: TextStyle(
|
hintStyle: TextStyle(
|
||||||
fontSize: 13,
|
fontSize: 13,
|
||||||
|
|||||||
@@ -11,7 +11,8 @@ class SignInView extends StatelessWidget {
|
|||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
return BlocProvider(
|
return BlocProvider(
|
||||||
create: (context) => SignInCubit(context.read()),
|
create: (context) => SignInCubit(context.read()),
|
||||||
child: BlocConsumer<SignInCubit, SignInState>(listener: (context, snapshot) {
|
child:
|
||||||
|
BlocConsumer<SignInCubit, SignInState>(listener: (context, snapshot) {
|
||||||
if (snapshot == SignInState.none) {
|
if (snapshot == SignInState.none) {
|
||||||
pushAndReplaceToPage(context, ProfileVerifyView());
|
pushAndReplaceToPage(context, ProfileVerifyView());
|
||||||
} else {
|
} else {
|
||||||
@@ -59,7 +60,9 @@ class SignInView extends StatelessWidget {
|
|||||||
shape: RoundedRectangleBorder(
|
shape: RoundedRectangleBorder(
|
||||||
borderRadius: BorderRadius.circular(10),
|
borderRadius: BorderRadius.circular(10),
|
||||||
),
|
),
|
||||||
color: Theme.of(context).bottomNavigationBarTheme.backgroundColor,
|
color: Theme.of(context)
|
||||||
|
.bottomNavigationBarTheme
|
||||||
|
.backgroundColor,
|
||||||
child: InkWell(
|
child: InkWell(
|
||||||
onTap: () {
|
onTap: () {
|
||||||
context.read<SignInCubit>().signIn();
|
context.read<SignInCubit>().signIn();
|
||||||
|
|||||||
@@ -49,7 +49,6 @@ class CupertinoCircleAvatar extends StatelessWidget {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
class Divider extends StatelessWidget {
|
class Divider extends StatelessWidget {
|
||||||
const Divider({
|
const Divider({
|
||||||
Key key,
|
Key key,
|
||||||
|
|||||||
@@ -221,14 +221,22 @@ class _AdvancedOptionsPageState extends State<AdvancedOptionsPage> {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
Spacer(),
|
Spacer(),
|
||||||
RaisedButton(
|
ElevatedButton(
|
||||||
color: Theme.of(context).brightness == Brightness.light
|
style: ButtonStyle(
|
||||||
? StreamChatTheme.of(context).colorTheme.accentBlue
|
backgroundColor: MaterialStateProperty.all<Color>(
|
||||||
: Colors.white,
|
Theme.of(context).brightness == Brightness.light
|
||||||
elevation: 0,
|
? StreamChatTheme.of(context)
|
||||||
padding: const EdgeInsets.symmetric(vertical: 16),
|
.colorTheme
|
||||||
shape: RoundedRectangleBorder(
|
.accentBlue
|
||||||
borderRadius: BorderRadius.circular(26),
|
: Colors.white),
|
||||||
|
elevation: MaterialStateProperty.all<double>(0),
|
||||||
|
padding: MaterialStateProperty.all<EdgeInsets>(
|
||||||
|
const EdgeInsets.symmetric(vertical: 16)),
|
||||||
|
shape: MaterialStateProperty.all(
|
||||||
|
RoundedRectangleBorder(
|
||||||
|
borderRadius: BorderRadius.circular(26),
|
||||||
|
),
|
||||||
|
),
|
||||||
),
|
),
|
||||||
child: Text(
|
child: Text(
|
||||||
'Login',
|
'Login',
|
||||||
|
|||||||
@@ -56,7 +56,8 @@ class _ChatInfoScreenState extends State<ChatInfoScreen> {
|
|||||||
'admin',
|
'admin',
|
||||||
'owner',
|
'owner',
|
||||||
].contains(channel.state!.members
|
].contains(channel.state!.members
|
||||||
.firstWhereOrNull((m) => m.userId == channel.client.state.user!.id)
|
.firstWhereOrNull(
|
||||||
|
(m) => m.userId == channel.client.state.user!.id)
|
||||||
?.role))
|
?.role))
|
||||||
_buildDeleteListTile(),
|
_buildDeleteListTile(),
|
||||||
],
|
],
|
||||||
|
|||||||
@@ -306,7 +306,7 @@ class _GroupChatDetailsScreenState extends State<GroupChatDetailsScreen> {
|
|||||||
Row(
|
Row(
|
||||||
mainAxisAlignment: MainAxisAlignment.center,
|
mainAxisAlignment: MainAxisAlignment.center,
|
||||||
children: [
|
children: [
|
||||||
FlatButton(
|
TextButton(
|
||||||
child: Text(
|
child: Text(
|
||||||
'OK',
|
'OK',
|
||||||
style: StreamChatTheme.of(context)
|
style: StreamChatTheme.of(context)
|
||||||
|
|||||||
@@ -26,7 +26,7 @@ class StreamVersion extends StatelessWidget {
|
|||||||
yaml['packages']['stream_chat_flutter']['version'];
|
yaml['packages']['stream_chat_flutter']['version'];
|
||||||
|
|
||||||
return Text(
|
return Text(
|
||||||
'Stream SDK v ${streamChatDep}',
|
'Stream SDK v $streamChatDep',
|
||||||
style: TextStyle(
|
style: TextStyle(
|
||||||
fontSize: 14,
|
fontSize: 14,
|
||||||
color: StreamChatTheme.of(context).colorTheme.greyGainsboro,
|
color: StreamChatTheme.of(context).colorTheme.greyGainsboro,
|
||||||
|
|||||||
Reference in New Issue
Block a user