Add new friends system, and sharing legs support
All checks were successful
Release / meta (push) Successful in 9s
Release / linux-build (push) Successful in 6m37s
Release / web-build (push) Successful in 5m29s
Release / android-build (push) Successful in 15m58s
Release / release-master (push) Successful in 20s
Release / release-dev (push) Successful in 26s
All checks were successful
Release / meta (push) Successful in 9s
Release / linux-build (push) Successful in 6m37s
Release / web-build (push) Successful in 5m29s
Release / android-build (push) Successful in 15m58s
Release / release-master (push) Successful in 20s
Release / release-dev (push) Successful in 26s
This commit is contained in:
@@ -13,12 +13,16 @@ import 'package:mileograph_flutter/components/pages/loco_legs.dart';
|
||||
import 'package:mileograph_flutter/components/pages/loco_timeline.dart';
|
||||
import 'package:mileograph_flutter/components/pages/logbook.dart';
|
||||
import 'package:mileograph_flutter/components/pages/more.dart';
|
||||
import 'package:mileograph_flutter/components/pages/badges.dart';
|
||||
import 'package:mileograph_flutter/components/pages/new_entry.dart';
|
||||
import 'package:mileograph_flutter/components/pages/new_traction.dart';
|
||||
import 'package:mileograph_flutter/components/pages/profile.dart';
|
||||
import 'package:mileograph_flutter/components/pages/settings.dart';
|
||||
import 'package:mileograph_flutter/components/pages/stats.dart';
|
||||
import 'package:mileograph_flutter/components/pages/traction.dart';
|
||||
import 'package:mileograph_flutter/components/widgets/friend_request_notification_card.dart';
|
||||
import 'package:mileograph_flutter/components/widgets/leg_share_notification_card.dart';
|
||||
import 'package:mileograph_flutter/objects/objects.dart';
|
||||
import 'package:mileograph_flutter/services/authservice.dart';
|
||||
import 'package:mileograph_flutter/services/data_service.dart';
|
||||
import 'package:mileograph_flutter/services/navigation_guard.dart';
|
||||
@@ -206,7 +210,15 @@ class _MyAppState extends State<MyApp> {
|
||||
path: '/traction/new',
|
||||
builder: (context, state) => const NewTractionPage(),
|
||||
),
|
||||
GoRoute(path: '/add', builder: (context, state) => NewEntryPage()),
|
||||
GoRoute(
|
||||
path: '/add',
|
||||
builder: (context, state) {
|
||||
final extra = state.extra;
|
||||
return NewEntryPage(
|
||||
legShare: extra is LegShareData ? extra : null,
|
||||
);
|
||||
},
|
||||
),
|
||||
GoRoute(
|
||||
path: '/more',
|
||||
builder: (context, state) => const MorePage(),
|
||||
@@ -215,6 +227,10 @@ class _MyAppState extends State<MyApp> {
|
||||
path: '/more/profile',
|
||||
builder: (context, state) => const ProfilePage(),
|
||||
),
|
||||
GoRoute(
|
||||
path: '/more/badges',
|
||||
builder: (context, state) => const BadgesPage(),
|
||||
),
|
||||
GoRoute(
|
||||
path: '/more/stats',
|
||||
builder: (context, state) => const StatsPage(),
|
||||
@@ -350,6 +366,13 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
if (data.notifications.isEmpty) {
|
||||
data.fetchNotifications();
|
||||
}
|
||||
if (data.friendships.isEmpty && !data.isFriendshipsLoading) {
|
||||
data.fetchFriendships();
|
||||
}
|
||||
if ((data.pendingIncoming.isEmpty && data.pendingOutgoing.isEmpty) &&
|
||||
!data.isPendingFriendshipsLoading) {
|
||||
data.fetchPendingFriendships();
|
||||
}
|
||||
_startNotificationPolling();
|
||||
});
|
||||
});
|
||||
@@ -435,6 +458,11 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
),
|
||||
actions: [
|
||||
_buildNotificationAction(context, data),
|
||||
IconButton(
|
||||
tooltip: 'Profile',
|
||||
onPressed: () => context.go('/more/profile'),
|
||||
icon: const Icon(Icons.person),
|
||||
),
|
||||
IconButton(
|
||||
tooltip: 'Settings',
|
||||
onPressed: () => context.go('/more/settings'),
|
||||
@@ -645,6 +673,13 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
Widget _buildNotificationsContent(BuildContext context, bool isWide) {
|
||||
final data = context.watch<DataService>();
|
||||
final notifications = data.notifications;
|
||||
final dismissibleIds = notifications
|
||||
.where(
|
||||
(n) =>
|
||||
!_isFriendRequestNotification(n) && !_isLegShareNotification(n),
|
||||
)
|
||||
.map((e) => e.id)
|
||||
.toList();
|
||||
final loading = data.isNotificationsLoading;
|
||||
final listHeight = isWide
|
||||
? 380.0
|
||||
@@ -671,6 +706,9 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
separatorBuilder: (_, index) => const SizedBox(height: 8),
|
||||
itemBuilder: (ctx, index) {
|
||||
final item = notifications[index];
|
||||
final isFriendRequest = _isFriendRequestNotification(item);
|
||||
final isLegShare = _isLegShareNotification(item);
|
||||
final isSpecial = isFriendRequest || isLegShare;
|
||||
return Card(
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(12.0),
|
||||
@@ -693,7 +731,11 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
),
|
||||
const SizedBox(height: 4),
|
||||
Text(
|
||||
item.body,
|
||||
isFriendRequest || isLegShare
|
||||
? isFriendRequest
|
||||
? 'Accept to share entries'
|
||||
: 'Shared entry details below.'
|
||||
: item.body,
|
||||
style: Theme.of(context).textTheme.bodyMedium,
|
||||
),
|
||||
if (item.createdAt != null) ...[
|
||||
@@ -716,9 +758,10 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
),
|
||||
),
|
||||
],
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
if (!isSpecial) ...[
|
||||
const SizedBox(width: 8),
|
||||
TextButton(
|
||||
onPressed: () =>
|
||||
@@ -726,7 +769,20 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
child: const Text('Dismiss'),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
if (isFriendRequest)
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(top: 8.0),
|
||||
child: FriendRequestNotificationCard(
|
||||
notification: item,
|
||||
),
|
||||
),
|
||||
if (isLegShare)
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(top: 8.0),
|
||||
child: LegShareNotificationCard(notification: item),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
@@ -756,10 +812,7 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
TextButton(
|
||||
onPressed: notifications.isEmpty
|
||||
? null
|
||||
: () => _dismissNotifications(
|
||||
context,
|
||||
notifications.map((e) => e.id).toList(),
|
||||
),
|
||||
: () => _dismissNotifications(context, dismissibleIds),
|
||||
child: const Text('Dismiss all'),
|
||||
),
|
||||
],
|
||||
@@ -794,6 +847,29 @@ class _MyHomePageState extends State<MyHomePage> {
|
||||
return '$y-$m-$d $hh:$mm';
|
||||
}
|
||||
|
||||
bool _isFriendRequestNotification(UserNotification notification) {
|
||||
final type = notification.type.trim().toLowerCase();
|
||||
final channel = notification.channel.trim().toLowerCase();
|
||||
final title = notification.title.trim().toLowerCase();
|
||||
bool matchesChannel =
|
||||
channel == 'friend_request' || channel == 'friend-request';
|
||||
if (!matchesChannel) {
|
||||
matchesChannel = channel.contains('friend_request') ||
|
||||
channel.contains('friend-request') ||
|
||||
channel.contains('friend');
|
||||
}
|
||||
return matchesChannel ||
|
||||
type == 'friend_request' ||
|
||||
type == 'friend-request' ||
|
||||
title.contains('friend request');
|
||||
}
|
||||
|
||||
bool _isLegShareNotification(UserNotification notification) {
|
||||
final channel = notification.channel.trim().toLowerCase();
|
||||
final type = notification.type.trim().toLowerCase();
|
||||
return channel.contains('leg_share') || type.contains('leg_share');
|
||||
}
|
||||
|
||||
Widget _buildBadge(String label) {
|
||||
return Container(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 6, vertical: 2),
|
||||
|
||||
Reference in New Issue
Block a user