Pages Implementation
Implemented Profile and Recent Conversation skeleton pages
This commit is contained in:
@@ -1,7 +1,7 @@
|
|||||||
# messaging_app
|
## Messaging App - messaging_app
|
||||||
|
|
||||||
A chat app built using Flutter for Both iOS and Android.
|
# A chat app built using Flutter for Both iOS and Android.
|
||||||
|
|
||||||
Backend is being covered by Appwrite. It is opensource and can be selfhosted, which is the main reason for using is a backend.
|
Backend is being covered by Appwrite. It is opensource and can be selfhosted, which is the main reason for it being used a backend.
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
description: This file stores settings for Dart & Flutter DevTools.
|
description: This file stores settings for Dart & Flutter DevTools.
|
||||||
documentation: https://docs.flutter.dev/tools/devtools/extensions#configure-extension-enablement-states
|
documentation: https://docs.flutter.dev/tools/devtools/extensions#configure-extension-enablement-states
|
||||||
extensions:
|
extensions:
|
||||||
|
- provider: true
|
||||||
@@ -1,10 +1,11 @@
|
|||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
|
|
||||||
import 'package:appwrite/appwrite.dart';
|
import 'package:appwrite/appwrite.dart';
|
||||||
import 'package:appwrite/models.dart' as models;
|
import 'package:appwrite/models.dart' as model;
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:image_picker/image_picker.dart';
|
import 'package:image_picker/image_picker.dart';
|
||||||
import 'package:messaging_app/components/constants.dart';
|
import 'package:messaging_app/components/constants.dart';
|
||||||
|
import 'package:messaging_app/models/conversations.dart';
|
||||||
|
import 'package:messaging_app/models/users.dart';
|
||||||
import 'package:messaging_app/service/navigation_service.dart';
|
import 'package:messaging_app/service/navigation_service.dart';
|
||||||
import 'package:messaging_app/service/snackbar_service.dart';
|
import 'package:messaging_app/service/snackbar_service.dart';
|
||||||
|
|
||||||
@@ -24,29 +25,31 @@ class MessagingProviders extends ChangeNotifier {
|
|||||||
late final Storage storage;
|
late final Storage storage;
|
||||||
|
|
||||||
// Auth Status
|
// Auth Status
|
||||||
AuthStatus? status;
|
late AuthStatus status;
|
||||||
|
late model.User? user;
|
||||||
models.User? user;
|
late model.Session session;
|
||||||
models.Session? session;
|
|
||||||
|
|
||||||
static MessagingProviders instance = MessagingProviders();
|
static MessagingProviders instance = MessagingProviders();
|
||||||
|
|
||||||
MessagingProviders() {
|
MessagingProviders() {
|
||||||
init();
|
_init();
|
||||||
loadUser();
|
_loadUser();
|
||||||
}
|
}
|
||||||
|
|
||||||
init() {
|
_init() {
|
||||||
client.setEndpoint(endPoint).setProject(projectId).setSelfSigned();
|
client.setEndpoint(endPoint).setProject(projectId).setSelfSigned();
|
||||||
account = Account(client);
|
account = Account(client);
|
||||||
database = Databases(client);
|
database = Databases(client);
|
||||||
storage = Storage(client);
|
storage = Storage(client);
|
||||||
}
|
}
|
||||||
|
|
||||||
loadUser() async {
|
_loadUser() async {
|
||||||
try {
|
try {
|
||||||
user = await account.get();
|
user = await account.get();
|
||||||
|
if (user != null) {
|
||||||
status = AuthStatus.authenticated;
|
status = AuthStatus.authenticated;
|
||||||
|
_autoLogin();
|
||||||
|
}
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
status = AuthStatus.notAuthenticated;
|
status = AuthStatus.notAuthenticated;
|
||||||
} finally {
|
} finally {
|
||||||
@@ -54,7 +57,11 @@ class MessagingProviders extends ChangeNotifier {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void loginWithEmailAndPassword(String _email, String _password) async {
|
void _autoLogin() {
|
||||||
|
NavigationService.instance.navigateToReplacement("home");
|
||||||
|
}
|
||||||
|
|
||||||
|
void login(String _email, String _password) async {
|
||||||
//
|
//
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
try {
|
try {
|
||||||
@@ -65,17 +72,11 @@ class MessagingProviders extends ChangeNotifier {
|
|||||||
session = await account.createEmailPasswordSession(
|
session = await account.createEmailPasswordSession(
|
||||||
email: _email, password: _password);
|
email: _email, password: _password);
|
||||||
|
|
||||||
|
user = await account.get();
|
||||||
status = AuthStatus.authenticated;
|
status = AuthStatus.authenticated;
|
||||||
var value = await database.getDocument(
|
|
||||||
databaseId: databaseId,
|
|
||||||
collectionId: userCollectionId,
|
|
||||||
documentId: session!.userId,
|
|
||||||
);
|
|
||||||
|
|
||||||
SnackBarService.instance
|
SnackBarService.instance.showSnackBarSuccess("Welcome! ${user!.name}");
|
||||||
.showSnackBarSuccess("Welcome! ${value.data['name']}");
|
|
||||||
NavigationService.instance.navigateToReplacement("home");
|
NavigationService.instance.navigateToReplacement("home");
|
||||||
account.deleteSession(sessionId: 'current');
|
|
||||||
} on AppwriteException catch (e) {
|
} on AppwriteException catch (e) {
|
||||||
SnackBarService.instance.showSnackBarError(e.message!);
|
SnackBarService.instance.showSnackBarError(e.message!);
|
||||||
status = AuthStatus.error;
|
status = AuthStatus.error;
|
||||||
@@ -91,6 +92,22 @@ class MessagingProviders extends ChangeNotifier {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void logout() async {
|
||||||
|
try {
|
||||||
|
await account.deleteSession(sessionId: 'current');
|
||||||
|
user = null;
|
||||||
|
status = AuthStatus.notAuthenticated;
|
||||||
|
// await onSuccess();
|
||||||
|
await NavigationService.instance.navigateToReplacement("login");
|
||||||
|
SnackBarService.instance.showSnackBarError("Logged out Successfully");
|
||||||
|
} on AppwriteException catch (e) {
|
||||||
|
SnackBarService.instance.showSnackBarError(e.message!);
|
||||||
|
} on Exception catch (e) {
|
||||||
|
SnackBarService.instance.showSnackBarError(e.toString());
|
||||||
|
}
|
||||||
|
notifyListeners();
|
||||||
|
}
|
||||||
|
|
||||||
Future<void> createUser(String _email, String _password, String _name,
|
Future<void> createUser(String _email, String _password, String _name,
|
||||||
Future<void> onSuccess(String _uid)) async {
|
Future<void> onSuccess(String _uid)) async {
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
@@ -149,6 +166,43 @@ class MessagingProviders extends ChangeNotifier {
|
|||||||
notifyListeners();
|
notifyListeners();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Stream<Users> getUser(String userId) {
|
||||||
|
var _userData = database.getDocument(
|
||||||
|
databaseId: databaseId,
|
||||||
|
collectionId: userCollectionId,
|
||||||
|
documentId: userId,
|
||||||
|
);
|
||||||
|
|
||||||
|
return _userData.asStream().map((_snapshot) {
|
||||||
|
return Users.fromData(_snapshot);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
Stream<List<Conversations>> getUserConversation(String userId) {
|
||||||
|
//
|
||||||
|
List<dynamic> _chatId = [];
|
||||||
|
List<dynamic> _details = [];
|
||||||
|
List<Conversations> _returnValue = [];
|
||||||
|
|
||||||
|
var _conversationData = database.getDocument(
|
||||||
|
databaseId: databaseId,
|
||||||
|
collectionId: convCollectionId,
|
||||||
|
documentId: userId.trim(),
|
||||||
|
);
|
||||||
|
|
||||||
|
return _conversationData.asStream().map(
|
||||||
|
(_snapshot) {
|
||||||
|
_chatId = _snapshot.data['chatId'];
|
||||||
|
_details = _snapshot.data['details'];
|
||||||
|
|
||||||
|
for (int i = 0; i < _chatId.length; i++) {
|
||||||
|
_returnValue.add(Conversations.fromData(_chatId[i], _details[i]));
|
||||||
|
}
|
||||||
|
return _returnValue;
|
||||||
|
},
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
uploadUserImage(XFile? file, String _uid) async {
|
uploadUserImage(XFile? file, String _uid) async {
|
||||||
notifyListeners();
|
notifyListeners();
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -0,0 +1,18 @@
|
|||||||
|
import 'package:messaging_app/models/details.dart';
|
||||||
|
|
||||||
|
class Conversations {
|
||||||
|
String chatId;
|
||||||
|
Details details;
|
||||||
|
|
||||||
|
Conversations({
|
||||||
|
required this.chatId,
|
||||||
|
required this.details,
|
||||||
|
});
|
||||||
|
|
||||||
|
factory Conversations.fromData(String _chatId, String details) {
|
||||||
|
return Conversations(
|
||||||
|
chatId: _chatId,
|
||||||
|
details: Details.fromData(details),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,28 @@
|
|||||||
|
import 'dart:convert';
|
||||||
|
|
||||||
|
class Details {
|
||||||
|
String name;
|
||||||
|
String image;
|
||||||
|
int? unseenCount;
|
||||||
|
String lastMessage;
|
||||||
|
DateTime? timeStamp;
|
||||||
|
|
||||||
|
Details({
|
||||||
|
required this.name,
|
||||||
|
required this.image,
|
||||||
|
required this.lastMessage,
|
||||||
|
required this.timeStamp,
|
||||||
|
required this.unseenCount,
|
||||||
|
});
|
||||||
|
|
||||||
|
factory Details.fromData(String _data) {
|
||||||
|
Map _decodedData = json.decode(_data);
|
||||||
|
return Details(
|
||||||
|
name: _decodedData['name'],
|
||||||
|
image: _decodedData['image'],
|
||||||
|
lastMessage: _decodedData['lastMessage'],
|
||||||
|
timeStamp: DateTime.parse(_decodedData['timeStamp'] ?? ""),
|
||||||
|
unseenCount: _decodedData['unseenCount'],
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,25 @@
|
|||||||
|
import 'package:appwrite/models.dart';
|
||||||
|
|
||||||
|
class Users {
|
||||||
|
String name;
|
||||||
|
String email;
|
||||||
|
String image;
|
||||||
|
DateTime lastSeen;
|
||||||
|
|
||||||
|
Users({
|
||||||
|
required this.name,
|
||||||
|
required this.email,
|
||||||
|
required this.image,
|
||||||
|
required this.lastSeen,
|
||||||
|
});
|
||||||
|
|
||||||
|
factory Users.fromData(Document _snapshot) {
|
||||||
|
return Users(
|
||||||
|
name: _snapshot.data["name"],
|
||||||
|
email: _snapshot.data["email"],
|
||||||
|
image: _snapshot.data["image"],
|
||||||
|
lastSeen: DateTime.parse(_snapshot.data["lastSeen"]),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -1,4 +1,6 @@
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:messaging_app/pages/profile_page.dart';
|
||||||
|
import 'package:messaging_app/pages/recent_converstations.dart';
|
||||||
|
|
||||||
class HomePage extends StatefulWidget {
|
class HomePage extends StatefulWidget {
|
||||||
const HomePage({super.key});
|
const HomePage({super.key});
|
||||||
@@ -10,17 +12,80 @@ class HomePage extends StatefulWidget {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class _HomePageState extends State<HomePage> {
|
class _HomePageState extends State<HomePage>
|
||||||
|
with SingleTickerProviderStateMixin {
|
||||||
|
// //
|
||||||
|
late double _deviceHeight;
|
||||||
|
late double _deviceWidth;
|
||||||
|
late TabController _tabController;
|
||||||
|
|
||||||
|
@override
|
||||||
|
void initState() {
|
||||||
|
super.initState();
|
||||||
|
_tabController = TabController(
|
||||||
|
length: 3,
|
||||||
|
vsync: this,
|
||||||
|
initialIndex: 1,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
void dispose() {
|
||||||
|
_tabController.dispose();
|
||||||
|
super.dispose();
|
||||||
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
//
|
//
|
||||||
|
_deviceHeight = MediaQuery.of(context).size.height;
|
||||||
|
_deviceWidth = MediaQuery.of(context).size.width;
|
||||||
|
|
||||||
return Scaffold(
|
return Scaffold(
|
||||||
backgroundColor: Theme.of(context).scaffoldBackgroundColor,
|
backgroundColor: Theme.of(context).scaffoldBackgroundColor,
|
||||||
appBar: AppBar(
|
appBar: AppBar(
|
||||||
backgroundColor: Theme.of(context).scaffoldBackgroundColor,
|
backgroundColor: Theme.of(context).scaffoldBackgroundColor,
|
||||||
title: Text("Messaging App"),
|
title: Text("Slick Messenger"),
|
||||||
titleTextStyle: TextStyle(fontSize: 15),
|
titleTextStyle: TextStyle(fontSize: 16),
|
||||||
|
bottom: TabBar(
|
||||||
|
unselectedLabelColor: Colors.grey,
|
||||||
|
indicatorColor: Colors.blue,
|
||||||
|
labelColor: Colors.blue,
|
||||||
|
controller: _tabController,
|
||||||
|
tabs: [
|
||||||
|
Tab(
|
||||||
|
icon: Icon(
|
||||||
|
Icons.people_outline,
|
||||||
|
size: 25,
|
||||||
),
|
),
|
||||||
|
),
|
||||||
|
Tab(
|
||||||
|
icon: Icon(
|
||||||
|
Icons.chat_bubble_outline,
|
||||||
|
size: 25,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
Tab(
|
||||||
|
icon: Icon(
|
||||||
|
Icons.person_outline,
|
||||||
|
size: 25,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
body: _tabBarPages(),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _tabBarPages() {
|
||||||
|
return TabBarView(
|
||||||
|
controller: _tabController,
|
||||||
|
children: [
|
||||||
|
Placeholder(),
|
||||||
|
RecentConverstationsPage(_deviceHeight, _deviceWidth),
|
||||||
|
ProfilePage(_deviceHeight, _deviceWidth),
|
||||||
|
],
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import 'package:messaging_app/service/snackbar_service.dart';
|
|||||||
import 'package:provider/provider.dart';
|
import 'package:provider/provider.dart';
|
||||||
|
|
||||||
class LoginPage extends StatefulWidget {
|
class LoginPage extends StatefulWidget {
|
||||||
const LoginPage({super.key});
|
const LoginPage({super.key,});
|
||||||
|
|
||||||
@override
|
@override
|
||||||
State<StatefulWidget> createState() {
|
State<StatefulWidget> createState() {
|
||||||
@@ -41,7 +41,6 @@ class _LoginPageState extends State<LoginPage> {
|
|||||||
value: MessagingProviders.instance,
|
value: MessagingProviders.instance,
|
||||||
child: _loginPageUI(),
|
child: _loginPageUI(),
|
||||||
),
|
),
|
||||||
//_loginPageUI(),
|
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@@ -172,12 +171,12 @@ class _LoginPageState extends State<LoginPage> {
|
|||||||
onPressed: () {
|
onPressed: () {
|
||||||
if (_formKey.currentState!.validate()) {
|
if (_formKey.currentState!.validate()) {
|
||||||
//Login User
|
//Login User
|
||||||
_auth.loginWithEmailAndPassword(_email!, _password!);
|
_auth.login(_email!, _password!);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
color: Colors.blue,
|
color: Colors.blue,
|
||||||
child: Text(
|
child: Text(
|
||||||
'Login',
|
'Login'.toUpperCase(),
|
||||||
style: TextStyle(
|
style: TextStyle(
|
||||||
fontSize: 18,
|
fontSize: 18,
|
||||||
fontWeight: FontWeight.w700,
|
fontWeight: FontWeight.w700,
|
||||||
|
|||||||
@@ -0,0 +1,124 @@
|
|||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter_spinkit/flutter_spinkit.dart';
|
||||||
|
import 'package:messaging_app/components/messaging_provider.dart';
|
||||||
|
import 'package:messaging_app/models/users.dart';
|
||||||
|
import 'package:provider/provider.dart';
|
||||||
|
|
||||||
|
class ProfilePage extends StatelessWidget {
|
||||||
|
//
|
||||||
|
|
||||||
|
final double _deviceHeight;
|
||||||
|
final double _deviceWidth;
|
||||||
|
late MessagingProviders _auth;
|
||||||
|
|
||||||
|
ProfilePage(this._deviceHeight, this._deviceWidth, {super.key});
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Container(
|
||||||
|
height: _deviceHeight,
|
||||||
|
width: _deviceWidth,
|
||||||
|
child: ChangeNotifierProvider<MessagingProviders>.value(
|
||||||
|
value: MessagingProviders.instance,
|
||||||
|
child: _profilePageUI(),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _profilePageUI() {
|
||||||
|
return Builder(builder: (BuildContext _context) {
|
||||||
|
_auth = Provider.of<MessagingProviders>(_context);
|
||||||
|
return StreamBuilder<Users>(
|
||||||
|
stream: MessagingProviders.instance.getUser(_auth.user!.$id),
|
||||||
|
builder: (_, _snapshot) {
|
||||||
|
var _userData = _snapshot.data;
|
||||||
|
return _snapshot.hasData
|
||||||
|
? Align(
|
||||||
|
child: SizedBox(
|
||||||
|
height: _deviceHeight * 0.50,
|
||||||
|
child: Column(
|
||||||
|
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
||||||
|
mainAxisSize: MainAxisSize.max,
|
||||||
|
crossAxisAlignment: CrossAxisAlignment.center,
|
||||||
|
children: [
|
||||||
|
_userImageWidget(_userData!.image),
|
||||||
|
_userNameWidget(_userData.name),
|
||||||
|
_userEmailWidget(_userData.email),
|
||||||
|
_logoutButton(),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
)
|
||||||
|
: SpinKitWanderingCubes(
|
||||||
|
color: Colors.blue,
|
||||||
|
size: 50.0,
|
||||||
|
);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _userImageWidget(String _image) {
|
||||||
|
double _imageRadius = _deviceHeight * 0.20;
|
||||||
|
return Container(
|
||||||
|
height: _imageRadius,
|
||||||
|
width: _imageRadius,
|
||||||
|
decoration: BoxDecoration(
|
||||||
|
borderRadius: BorderRadius.circular(_imageRadius),
|
||||||
|
image: DecorationImage(
|
||||||
|
fit: BoxFit.fill,
|
||||||
|
image: NetworkImage(_image),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _userNameWidget(String _name) {
|
||||||
|
return Container(
|
||||||
|
height: _deviceHeight * 0.05,
|
||||||
|
width: _deviceWidth,
|
||||||
|
child: Text(
|
||||||
|
_name,
|
||||||
|
textAlign: TextAlign.center,
|
||||||
|
style: TextStyle(
|
||||||
|
color: Colors.white,
|
||||||
|
fontSize: 30,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _userEmailWidget(String _email) {
|
||||||
|
return Container(
|
||||||
|
height: _deviceHeight * 0.03,
|
||||||
|
width: _deviceWidth,
|
||||||
|
child: Text(
|
||||||
|
_email,
|
||||||
|
textAlign: TextAlign.center,
|
||||||
|
style: TextStyle(
|
||||||
|
color: Colors.white24,
|
||||||
|
fontSize: 15,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _logoutButton() {
|
||||||
|
return Container(
|
||||||
|
height: _deviceHeight * 0.06,
|
||||||
|
width: _deviceWidth * 0.80,
|
||||||
|
child: MaterialButton(
|
||||||
|
onPressed: () {
|
||||||
|
_auth.logout();
|
||||||
|
},
|
||||||
|
color: Colors.red,
|
||||||
|
child: Text(
|
||||||
|
"Logout".toUpperCase(),
|
||||||
|
style: TextStyle(
|
||||||
|
fontSize: 18,
|
||||||
|
fontWeight: FontWeight.w700,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,95 @@
|
|||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter_spinkit/flutter_spinkit.dart';
|
||||||
|
import 'package:messaging_app/components/messaging_provider.dart';
|
||||||
|
import 'package:messaging_app/models/conversations.dart';
|
||||||
|
import 'package:provider/provider.dart';
|
||||||
|
import 'package:timeago/timeago.dart' as timeago;
|
||||||
|
|
||||||
|
class RecentConverstationsPage extends StatelessWidget {
|
||||||
|
//
|
||||||
|
|
||||||
|
final double _deviceHeight;
|
||||||
|
final double _deviceWidth;
|
||||||
|
late MessagingProviders _auth;
|
||||||
|
|
||||||
|
RecentConverstationsPage(this._deviceHeight, this._deviceWidth);
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Container(
|
||||||
|
height: _deviceHeight,
|
||||||
|
width: _deviceWidth,
|
||||||
|
child: ChangeNotifierProvider<MessagingProviders>.value(
|
||||||
|
value: MessagingProviders.instance,
|
||||||
|
child: _conversationView(),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _conversationView() {
|
||||||
|
return Builder(builder: (_context) {
|
||||||
|
_auth = Provider.of<MessagingProviders>(_context);
|
||||||
|
return Container(
|
||||||
|
height: _deviceHeight,
|
||||||
|
width: _deviceWidth,
|
||||||
|
child: StreamBuilder<List<Conversations>>(
|
||||||
|
stream: MessagingProviders.instance
|
||||||
|
.getUserConversation(_auth.user!.$id),
|
||||||
|
builder: (_, _snapshot) {
|
||||||
|
return _snapshot.hasData
|
||||||
|
? ListView.builder(
|
||||||
|
itemCount: _snapshot.data!.length,
|
||||||
|
itemBuilder: (_context, _index) {
|
||||||
|
var _details = _snapshot.data![_index].details;
|
||||||
|
return ListTile(
|
||||||
|
onTap: () {
|
||||||
|
//
|
||||||
|
},
|
||||||
|
title: Text(_details.name),
|
||||||
|
subtitle: Text(_details.lastMessage),
|
||||||
|
leading: Container(
|
||||||
|
width: 50,
|
||||||
|
height: 50,
|
||||||
|
decoration: BoxDecoration(
|
||||||
|
borderRadius: BorderRadius.circular(100),
|
||||||
|
image: DecorationImage(
|
||||||
|
fit: BoxFit.cover,
|
||||||
|
image: NetworkImage(_details.image),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
trailing: _listTrailingWidget(_details.timeStamp),
|
||||||
|
);
|
||||||
|
},
|
||||||
|
)
|
||||||
|
: SpinKitWanderingCubes(
|
||||||
|
color: Colors.blue,
|
||||||
|
size: 50.0,
|
||||||
|
);
|
||||||
|
}),
|
||||||
|
);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget _listTrailingWidget(DateTime? _date) {
|
||||||
|
return Column(
|
||||||
|
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
||||||
|
mainAxisSize: MainAxisSize.max,
|
||||||
|
crossAxisAlignment: CrossAxisAlignment.end,
|
||||||
|
children: [
|
||||||
|
Text(
|
||||||
|
timeago.format(_date!),
|
||||||
|
style: TextStyle(fontSize: 15),
|
||||||
|
),
|
||||||
|
Container(
|
||||||
|
height: 12,
|
||||||
|
width: 12,
|
||||||
|
decoration: BoxDecoration(
|
||||||
|
color: Colors.blue,
|
||||||
|
borderRadius: BorderRadius.circular(100),
|
||||||
|
),
|
||||||
|
)
|
||||||
|
],
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -224,7 +224,6 @@ class _RegisterationPageState extends State<RegisterationPage> {
|
|||||||
width: _deviceWidth,
|
width: _deviceWidth,
|
||||||
child: MaterialButton(
|
child: MaterialButton(
|
||||||
onPressed: () {
|
onPressed: () {
|
||||||
String name = _name!;
|
|
||||||
if (_image == null) {
|
if (_image == null) {
|
||||||
SnackBarService.instance
|
SnackBarService.instance
|
||||||
.showSnackBarError("Please Select Image");
|
.showSnackBarError("Please Select Image");
|
||||||
@@ -234,12 +233,12 @@ class _RegisterationPageState extends State<RegisterationPage> {
|
|||||||
_auth.createUser(
|
_auth.createUser(
|
||||||
_email!,
|
_email!,
|
||||||
_password!,
|
_password!,
|
||||||
name,
|
_name!,
|
||||||
(String _uid) async {
|
(String _uid) async {
|
||||||
var _url = await _auth.uploadUserImage(_image, _uid);
|
var _url = await _auth.uploadUserImage(_image, _uid);
|
||||||
_auth.createUserInDB(_uid, _email!, name, _url);
|
_auth.createUserInDB(_uid, _email!, _name!, _url);
|
||||||
if (_auth.status == AuthStatus.authenticated) {
|
if (_auth.status == AuthStatus.authenticated) {
|
||||||
_auth.loginWithEmailAndPassword(_email!, _password!);
|
_auth.login(_email!, _password!);
|
||||||
}
|
}
|
||||||
//
|
//
|
||||||
},
|
},
|
||||||
@@ -248,7 +247,7 @@ class _RegisterationPageState extends State<RegisterationPage> {
|
|||||||
},
|
},
|
||||||
color: Colors.blue,
|
color: Colors.blue,
|
||||||
child: Text(
|
child: Text(
|
||||||
'Register',
|
'Register'.toUpperCase(),
|
||||||
style: TextStyle(
|
style: TextStyle(
|
||||||
fontSize: 18,
|
fontSize: 18,
|
||||||
fontWeight: FontWeight.w700,
|
fontWeight: FontWeight.w700,
|
||||||
|
|||||||
@@ -23,7 +23,7 @@ class NavigationService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Manually Call Function
|
// Manually Call Function
|
||||||
goBack() {
|
void goBack() {
|
||||||
return navigatorKey!.currentState!.pop();
|
return navigatorKey!.currentState!.pop();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+3
-26
@@ -1,54 +1,31 @@
|
|||||||
name: messaging_app
|
name: messaging_app
|
||||||
description: "A new Flutter project."
|
description: "A new Flutter project."
|
||||||
# The following line prevents the package from being accidentally published to
|
|
||||||
# pub.dev using `flutter pub publish`. This is preferred for private packages.
|
|
||||||
publish_to: 'none' # Remove this line if you wish to publish to pub.dev
|
|
||||||
|
|
||||||
# The following defines the version and build number for your application.
|
publish_to: 'none'
|
||||||
# A version number is three numbers separated by dots, like 1.2.43
|
|
||||||
# followed by an optional build number separated by a +.
|
|
||||||
# Both the version and the builder number may be overridden in flutter
|
|
||||||
# build by specifying --build-name and --build-number, respectively.
|
|
||||||
# In Android, build-name is used as versionName while build-number used as versionCode.
|
|
||||||
# Read more about Android versioning at https://developer.android.com/studio/publish/versioning
|
|
||||||
# In iOS, build-name is used as CFBundleShortVersionString while build-number is used as CFBundleVersion.
|
|
||||||
# Read more about iOS versioning at
|
|
||||||
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
|
|
||||||
# In Windows, build-name is used as the major, minor, and patch parts
|
|
||||||
# of the product and file versions while build-number is used as the build suffix.
|
|
||||||
version: 1.0.0+1
|
version: 1.0.0+1
|
||||||
|
|
||||||
environment:
|
environment:
|
||||||
sdk: ^3.6.0
|
sdk: ^3.6.0
|
||||||
|
|
||||||
# Dependencies specify other packages that your package needs in order to work.
|
|
||||||
# To automatically upgrade your package dependencies to the latest versions
|
|
||||||
# consider running `flutter pub upgrade --major-versions`. Alternatively,
|
|
||||||
# dependencies can be manually updated by changing the version numbers below to
|
|
||||||
# the latest version available on pub.dev. To see which dependencies have newer
|
|
||||||
# versions available, run `flutter pub outdated`.
|
|
||||||
dependencies:
|
dependencies:
|
||||||
flutter:
|
flutter:
|
||||||
sdk: flutter
|
sdk: flutter
|
||||||
|
|
||||||
# The following adds the Cupertino Icons font to your application.
|
|
||||||
# Use with the CupertinoIcons class for iOS style icons.
|
|
||||||
cupertino_icons: ^1.0.8
|
cupertino_icons: ^1.0.8
|
||||||
appwrite: 13.1.1
|
appwrite: 13.1.1
|
||||||
timeago: ^3.7.0
|
|
||||||
flutter_spinkit: ^5.2.1
|
flutter_spinkit: ^5.2.1
|
||||||
provider: ^6.1.2
|
provider: ^6.1.2
|
||||||
image_picker: ^1.1.2
|
image_picker: ^1.1.2
|
||||||
|
timeago: ^3.7.0
|
||||||
|
|
||||||
dev_dependencies:
|
dev_dependencies:
|
||||||
flutter_test:
|
flutter_test:
|
||||||
sdk: flutter
|
sdk: flutter
|
||||||
|
|
||||||
|
|
||||||
flutter_lints: ^5.0.0
|
flutter_lints: ^5.0.0
|
||||||
|
|
||||||
flutter:
|
flutter:
|
||||||
|
|
||||||
uses-material-design: true
|
uses-material-design: true
|
||||||
|
|
||||||
# To add assets to your application, add an assets section, like this:
|
# To add assets to your application, add an assets section, like this:
|
||||||
|
|||||||
Reference in New Issue
Block a user