Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
37 commits
Select commit Hold shift + click to select a range
f66dcb1
refactor(plan_navigation): update routing and content handling for in…
dhakar66 Jun 29, 2026
763ed6c
feat(plan_details): add thumbnail and shareable image support in plan…
dhakar66 Jun 29, 2026
e8c681a
feat: add deep link support for series sharing and enhance routing
dhakar66 Jun 30, 2026
8b12cc5
image streah fix
TenzDelek Jul 1, 2026
e6171f4
p with s
TenzDelek Jul 1, 2026
47c5e57
padding on about
TenzDelek Jul 1, 2026
c88c29e
padding
TenzDelek Jul 1, 2026
6b36224
refactor: streamline recitation navigation by removing redundant para…
dhakar66 Jul 1, 2026
2223efc
refactor: remove unused user plans provider and enhance series enroll…
tentamdin Jul 1, 2026
e175aa7
feat: add sharing functionality to the reader bottom sheet and implem…
dhakar66 Jul 1, 2026
edc72a4
refactor: update locale handling and simplify home screen layout
tentamdin Jul 1, 2026
7f4d3c8
base
TenzDelek Jul 1, 2026
e0722b6
feat: add home deep link generation and enhance verse sharing functio…
dhakar66 Jul 1, 2026
8540cbb
refactor: enhance Mala screen layout with improved padding and visual…
tentamdin Jul 1, 2026
4942abf
almost done
TenzDelek Jul 1, 2026
fd29e45
feat: implement accumulator groups feature with data fetching and UI …
tentamdin Jul 1, 2026
24f7b26
last one
TenzDelek Jul 1, 2026
bb57c96
fix name cut of
TenzDelek Jul 1, 2026
56aebce
feat: add accumulator group model and UI components for group accumul…
tentamdin Jul 1, 2026
9b9a390
feat: add group accumulation sheet and localization for group accumul…
tentamdin Jul 1, 2026
2d1acf8
fix
TenzDelek Jul 1, 2026
4314c4b
feat: implement group accumulation functionality with selection and s…
tentamdin Jul 1, 2026
1006bf8
feat: enhance group accumulation management with local state handling…
tentamdin Jul 1, 2026
bc2be77
Merge pull request #463 from OpenPecha/chore/PlansBottomSheetSharable…
tentamdin Jul 1, 2026
e8e04f2
Merge pull request #473 from OpenPecha/feat/PlanShareDeepLink
tentamdin Jul 1, 2026
0240032
fix: update localisation
tentamdin Jul 1, 2026
48d492c
Merge pull request #474 from OpenPecha/bug-fixing
tentamdin Jul 1, 2026
f8f2a0d
Update lib/features/reader/presentation/widgets/reader_app_bar/reader…
tentamdin Jul 1, 2026
715ef66
Merge branch 'develop' into feat/ChantsShare
tentamdin Jul 1, 2026
75beaaf
Merge pull request #475 from OpenPecha/feat/ChantsShare
tentamdin Jul 1, 2026
6aaaf42
Merge pull request #477 from OpenPecha/accu
tentamdin Jul 1, 2026
b0814be
Merge pull request #476 from OpenPecha/refactor/series-detail-enrollm…
tentamdin Jul 1, 2026
4e5297f
Merge pull request #478 from OpenPecha/feat/VerseOfDayDeepLinkShare
tentamdin Jul 1, 2026
dcfdca5
fix: disable some action on group accumulation
tentamdin Jul 1, 2026
487571a
refactor: streamline accumulator ID handling and improve local state …
tentamdin Jul 1, 2026
5a58a27
Merge branch 'develop' into feature/mala-screen-layout
tentamdin Jul 1, 2026
71b9135
Merge pull request #480 from OpenPecha/feature/mala-screen-layout
tentamdin Jul 1, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions lib/core/config/locale/locale_notifier.dart
Original file line number Diff line number Diff line change
Expand Up @@ -99,8 +99,8 @@ final localeProvider = StateNotifierProvider<LocaleNotifier, Locale>((ref) {

/// Language code sent to backend APIs for translatable content.
///
/// UI may be hi/mn/ne, but the API only serves en/zh/bo — unsupported locales
/// fall back to English via [AppConfig.resolveContentLanguage].
/// Mirrors the user's selected app locale when supported; unknown codes fall
/// back to English via [AppConfig.resolveContentLanguage].
final contentLanguageProvider = Provider<String>((ref) {
return AppConfig.resolveContentLanguage(
ref.watch(localeProvider).languageCode,
Expand Down
6 changes: 6 additions & 0 deletions lib/core/config/protected_routes.dart
Original file line number Diff line number Diff line change
Expand Up @@ -62,10 +62,16 @@ class ProtectedRoutes {
// which are user-scoped and 403 without a token.
'/accumulators/', // Catch-all: detail, create (/user), update (/user/{id})

// Group accumulator counts (submit requires auth).
'/group-accumulators/', // Catch-all: POST count, GET detail, etc.

// Group join / follow
'/author/groups/{groupId}/join',
'/author/groups/{groupId}/follow',

// Group accumulators (group prayer accumulations)
'/group-accumulators/',
Comment on lines +65 to +73

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 The path /group-accumulators/ is listed twice — once under "Group accumulator counts" and again under "Group accumulators". The duplicate has no functional impact (the route is protected either way) but creates maintenance confusion about which comment applies and suggests copy-paste residue.

Suggested change
// Group accumulator counts (submit requires auth).
'/group-accumulators/', // Catch-all: POST count, GET detail, etc.
// Group join / follow
'/author/groups/{groupId}/join',
'/author/groups/{groupId}/follow',
// Group accumulators (group prayer accumulations)
'/group-accumulators/',
// Group accumulator counts / detail (submit requires auth).
'/group-accumulators/', // Catch-all: POST count, GET detail, join, etc.
// Group join / follow
'/author/groups/{groupId}/join',
'/author/groups/{groupId}/follow',

Note: If this suggestion doesn't match your team's coding style, reply to this and let me know. I'll remember it for next time!


// Plans (public endpoints but may need auth for user-specific data)
'/plans/{planId}',
'/plans/{planId}/days/{dayNumber}',
Expand Down
28 changes: 27 additions & 1 deletion lib/core/config/router/app_router.dart
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import 'package:flutter_pecha/features/auth/presentation/screens/login_page.dart
import 'package:flutter_pecha/features/auth/presentation/screens/splash_screen.dart';
import 'package:flutter_pecha/features/calendar/presentation/screens/tibetan_calendar_screen.dart';
import 'package:flutter_pecha/features/group_profile/domain/entities/group_profile.dart';
import 'package:flutter_pecha/features/group_profile/presentation/screens/group_accumulator_screen.dart';
import 'package:flutter_pecha/features/group_profile/presentation/screens/group_profile_screen.dart';
import 'package:flutter_pecha/features/home/domain/entities/series.dart';
import 'package:flutter_pecha/features/home/presentation/screens/main_navigation_screen.dart';
Expand Down Expand Up @@ -122,6 +123,16 @@ final appRouterProvider = Provider<GoRouter>((ref) {
redirect: (_, __) => AppRoutes.home,
),

// Compatibility fallback for series deep links delivered directly to
// go_router instead of through AppLinksDeepLinkService.
GoRoute(
path: '/open/series/:seriesId',
name: 'open-series',
redirect: (_, state) {
final seriesId = state.pathParameters['seriesId'] ?? '';
return '/home/series/$seriesId';
},
),
// Compatibility fallback in case a platform sends the first-party app
// link directly to go_router instead of through AppLinksDeepLinkService.
GoRoute(
Expand Down Expand Up @@ -241,6 +252,21 @@ final appRouterProvider = Provider<GoRouter>((ref) {
return GroupProfileScreen(groupId: groupId);
},
),
GoRoute(
path: "group-accumulator/:accumulatorId",
name: "home-group-accumulator",
parentNavigatorKey: rootNavigatorKey,
builder: (context, state) {
final accumulatorId =
state.pathParameters['accumulatorId'] ?? '';
final extra = state.extra as Map<String, dynamic>?;
final groupTitle = extra?['groupTitle'] as String?;
return GroupAccumulatorScreen(
accumulatorId: accumulatorId,
groupTitle: groupTitle,
);
},
),
GoRoute(
path: "timers",
name: "home-timers",
Expand Down Expand Up @@ -499,7 +525,7 @@ final appRouterProvider = Provider<GoRouter>((ref) {
},
),

// plan text route - inline TEXT subtasks (sibling to /reader)
// plan content route - inline TEXT/IMAGE subtasks (sibling to /reader)
GoRoute(
path: "/plan-text/:subtaskId",
name: "plan-text",
Expand Down
7 changes: 4 additions & 3 deletions lib/core/config/router/app_routes.dart
Original file line number Diff line number Diff line change
Expand Up @@ -48,9 +48,10 @@ class AppRoutes {
static const String reader = '/reader';

// ========== PLAN TEXT ROUTES ==========
/// Inline plan text screen — renders subtasks where `content_type == "TEXT"`.
/// Inline plan content screen — renders subtasks where `content_type` is
/// `TEXT` or `IMAGE`.
/// Path param is the subtask id; the actual content travels in `extra`
/// as a [NavigationContext] whose `currentItem` carries `inlineContent`.
/// as a [NavigationContext] whose `currentItem` carries inline content.
static const String planText = '/plan-text';

// ========== SEARCH ROUTES ==========
Expand Down Expand Up @@ -88,7 +89,7 @@ class AppRoutes {
practicePlanPreview, // Allow guests to browse/preview plans
reader,
notifications, // Local-only — guests can configure routine notifications
planText, // Guests can see inline TEXT subtasks
planText, // Guests can see inline TEXT/IMAGE subtasks
};

/// Base paths that require full authentication (prefix matching)
Expand Down
1 change: 1 addition & 0 deletions lib/core/constants/app_assets.dart
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,7 @@ class AppAssets {

// ========== GROUP & SERIES ICONS ==========
static const IconData usersThree = PhosphorIconsRegular.usersThree;
static const IconData usercard = PhosphorIconsRegular.users;
static const IconData bookOpenText = PhosphorIconsRegular.bookOpenText;
static const IconData calendarDots = PhosphorIconsRegular.calendarDots;
static const IconData arrowRight = PhosphorIconsRegular.arrowRight;
Expand Down
11 changes: 2 additions & 9 deletions lib/core/constants/app_config.dart
Original file line number Diff line number Diff line change
Expand Up @@ -40,18 +40,11 @@ class AppConfig {
'ne',
];

/// Languages the backend can serve translatable content in.
static const List<String> backendContentLanguages = [
englishLanguageCode,
chineseLanguageCode,
tibetanLanguageCode,
];

/// Maps a UI locale to the language code sent to content APIs.
/// Falls back to English when the backend does not support the locale.
/// Returns the locale when it is a supported app language; otherwise English.
static String resolveContentLanguage(String localeCode) {
final code = localeCode.toLowerCase();
if (backendContentLanguages.contains(code)) return code;
if (supportedLanguages.contains(code)) return code;
return englishLanguageCode;
}

Expand Down
10 changes: 10 additions & 0 deletions lib/core/deep_linking/deep_link_router.dart
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,16 @@ class DeepLinkRouter {

static _DeepLinkDestination _resolveFirstPartyAppLink(Uri uri) {
final segments = uri.pathSegments;
if (segments.length >= 3 &&
segments[0] == 'open' &&
segments[1] == 'series') {
final seriesId = segments[2];
return _DeepLinkDestination(
'/home/series/${Uri.encodeComponent(seriesId)}',
opensOnTop: true,
);
}

if (segments.length >= 3 &&
segments[0] == 'open' &&
segments[1] == 'reader') {
Expand Down
22 changes: 22 additions & 0 deletions lib/core/deep_linking/deep_link_url_builder.dart
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,28 @@ class DeepLinkUrlBuilder {

static const String _host = 'webuddhist.com';

static Uri homeLink() {
return Uri(scheme: 'https', host: _host, pathSegments: ['open']);
}

/// Returns a link that opens the reader at the very first segment —
/// i.e. no segment/lang params so the app starts from the top.
static Uri readerLink({required String textId}) {
return Uri(
scheme: 'https',
host: _host,
pathSegments: ['open', 'reader', textId],
);
}

static Uri seriesLink({required String seriesId}) {
return Uri(
scheme: 'https',
host: _host,
pathSegments: ['open', 'series', seriesId],
);
}

static Uri readerSegmentLink({
required String textId,
required String segmentId,
Expand Down
4 changes: 4 additions & 0 deletions lib/core/l10n/app_bo.arb
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,9 @@
}
}
},
"mala_group_accumulations": "Group accumulations",
"mala_groups_section": "Groups",
"mala_group_untitled": "Untitled group",
"home_timer": "སྒོམ་ཐུན།",
"preset_timers": "སྔོན་སྒྲིག་དུས་ཚོད།",
"meditation_timer": "སྒོམ་ཐུན།",
Expand All @@ -112,6 +115,7 @@
"nav_settings": "སྒྲིག་འགོད།",
"nav_connect": "མཐུད།",
"nav_me": "ང་།",
"tab_practices": "ཉམས་ལེན།",
"text_search": "འཚོལ།",
"text_toc_versions": "པར་གཞི།",
"text_commentary": "འགྲེལ་བ་ཁག",
Expand Down
19 changes: 19 additions & 0 deletions lib/core/l10n/app_en.arb
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,9 @@
}
}
},
"mala_group_accumulations": "Group accumulations",
"mala_groups_section": "Groups",
"mala_group_untitled": "Untitled group",
"home_timer": "Timer",
"preset_timers": "Preset timers",
"meditation_timer": "Meditation Timer",
Expand All @@ -112,6 +115,7 @@
"nav_settings": "Settings",
"nav_connect": "Connect",
"nav_me": "Me",
"tab_practices": "Practices",
"text_search": "Search",
"text_toc_versions": "Versions",
"text_commentary": "Commentaries",
Expand Down Expand Up @@ -785,6 +789,21 @@
"group_practice_with_us": "Practice with us",
"group_change_practice_title": "Change group practice",
"group_change_practice_message": "You are already practicing this plan with another group. Would you like to change your practice group?",
"group_join_to_contribute": "Join to contribute",
"group_accumulator_join_error": "Unable to join accumulation. Please try again.",
"group_accumulator_participants": "{count} participants",
"@group_accumulator_participants": {
"placeholders": {
"count": {
"type": "int"
}
}
},
"group_accumulator_leaderboard": "Leaderboard",
"group_accumulator_my_contributions": "My Contributions",
"group_accumulator_recited": "Recited",
"group_accumulator_total": "Total",
"group_accumulator_contributions_empty": "Join this accumulation to track your contributions.",
"@group_and_more_links": {
"placeholders": {
"count": {
Expand Down
4 changes: 4 additions & 0 deletions lib/core/l10n/app_hi.arb
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,9 @@
}
}
},
"mala_group_accumulations": "Group accumulations",
"mala_groups_section": "Groups",
"mala_group_untitled": "Untitled group",
"home_timer": "टाइमर",
"preset_timers": "पूर्व-निर्धारित टाइमर",
"meditation_timer": "ध्यान टाइमर",
Expand All @@ -112,6 +115,7 @@
"nav_settings": "सेटिंग्स",
"nav_connect": "कनेक्ट",
"nav_me": "मैं",
"tab_practices": "अभ्यास",
"text_search": "खोजें",
"text_toc_versions": "संस्करण",
"text_commentary": "टीकाएँ",
Expand Down
4 changes: 4 additions & 0 deletions lib/core/l10n/app_mn.arb
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,9 @@
}
}
},
"mala_group_accumulations": "Group accumulations",
"mala_groups_section": "Groups",
"mala_group_untitled": "Untitled group",
"home_timer": "Цаг хэмжигч",
"preset_timers": "Бэлэн тохируулсан цаг",
"meditation_timer": "Бясалгалын цаг хэмжигч",
Expand All @@ -112,6 +115,7 @@
"nav_settings": "Тохиргоо",
"nav_connect": "Холбогдох",
"nav_me": "Би",
"tab_practices": "Дадлага",
"text_search": "Хайх",
"text_toc_versions": "Хувилбарууд",
"text_commentary": "Тайлбар",
Expand Down
4 changes: 4 additions & 0 deletions lib/core/l10n/app_ne.arb
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,9 @@
}
}
},
"mala_group_accumulations": "Group accumulations",
"mala_groups_section": "Groups",
"mala_group_untitled": "Untitled group",
"home_timer": "टाइमर",
"preset_timers": "पूर्वनिर्धारित टाइमरहरू",
"meditation_timer": "ध्यान टाइमर",
Expand All @@ -112,6 +115,7 @@
"nav_settings": "सेटिङ",
"nav_connect": "जोडिनुहोस्",
"nav_me": "म",
"tab_practices": "अभ्यास",
"text_search": "खोज्नुहोस्",
"text_toc_versions": "संस्करणहरू",
"text_commentary": "टीकाहरू",
Expand Down
4 changes: 4 additions & 0 deletions lib/core/l10n/app_zh.arb
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,9 @@
}
}
},
"mala_group_accumulations": "Group accumulations",
"mala_groups_section": "Groups",
"mala_group_untitled": "Untitled group",
"home_timer": "計時",
"preset_timers": "預設計時",
"meditation_timer": "禪修計時",
Expand All @@ -112,6 +115,7 @@
"nav_settings": "設定",
"nav_connect": "社群",
"nav_me": "個人",
"tab_practices": "修持計畫",
"text_search": "搜尋",
"text_toc_versions": "版本",
"text_commentary": "注釋",
Expand Down
Loading
Loading