Skip to content

Commit b7ff403

Browse files
authored
Merge pull request #516 from theperu/feature/settings-redesign
Feature/settings redesign
2 parents e0529d8 + aa45e4f commit b7ff403

12 files changed

Lines changed: 286 additions & 237 deletions

File tree

lib/constants/constants.dart

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -297,6 +297,12 @@ const darkAccountColorList = [
297297
List<Color> categoryColorListTheme = categoryColorList;
298298
List<Color> accountColorListTheme = accountColorList;
299299

300+
// external URLs
301+
const String githubUrl = 'https://github.com/RIP-Comm/sossoldi';
302+
const String linkedinUrl = 'https://www.linkedin.com/company/sossoldi';
303+
const String youtubeUrl = 'https://www.youtube.com/@Sossoldi-app';
304+
const String discordUrl = 'https://discord.sossoldi.com';
305+
300306
void updateColorsBasedOnTheme(bool isDarkModeEnabled) {
301307
if (isDarkModeEnabled) {
302308
categoryColorListTheme = darkCategoryColorList;

lib/pages/accounts/account_list_page.dart

Lines changed: 2 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ class _AccountListPage extends ConsumerState<AccountListPage> {
2626
icon: const Icon(Icons.arrow_back_ios_new),
2727
onPressed: () => Navigator.pop(context),
2828
),
29+
title: const Text('Accounts'),
2930
actions: [
3031
IconButton(
3132
onPressed: () {
@@ -38,38 +39,10 @@ class _AccountListPage extends ConsumerState<AccountListPage> {
3839
],
3940
),
4041
body: SingleChildScrollView(
42+
padding: const EdgeInsets.only(top: Sizes.xl),
4143
physics: const BouncingScrollPhysics(),
4244
child: Column(
4345
children: [
44-
Padding(
45-
padding: const EdgeInsets.symmetric(
46-
vertical: Sizes.xl,
47-
horizontal: Sizes.lg,
48-
),
49-
child: Row(
50-
children: [
51-
Container(
52-
decoration: BoxDecoration(
53-
shape: BoxShape.circle,
54-
color: Theme.of(context).colorScheme.primary,
55-
),
56-
padding: const EdgeInsets.all(Sizes.sm),
57-
child: Icon(
58-
Icons.account_balance_wallet,
59-
size: 24.0,
60-
color: Theme.of(context).colorScheme.onPrimary,
61-
),
62-
),
63-
const SizedBox(width: Sizes.md),
64-
Text(
65-
"Your accounts",
66-
style: Theme.of(context).textTheme.headlineLarge!.copyWith(
67-
color: Theme.of(context).colorScheme.primary,
68-
),
69-
),
70-
],
71-
),
72-
),
7346
accountsList.when(
7447
data: (accounts) => ReorderableListView.builder(
7548
shrinkWrap: true,

lib/pages/categories/category_list_page.dart

Lines changed: 2 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ class CategoryList extends ConsumerWidget {
2121
icon: const Icon(Icons.arrow_back_ios_new),
2222
onPressed: () => Navigator.pop(context),
2323
),
24+
title: const Text('Categories'),
2425
actions: [
2526
IconButton(
2627
onPressed: () {
@@ -33,38 +34,10 @@ class CategoryList extends ConsumerWidget {
3334
],
3435
),
3536
body: SingleChildScrollView(
37+
padding: const EdgeInsets.only(top: Sizes.xl),
3638
physics: const BouncingScrollPhysics(),
3739
child: Column(
3840
children: [
39-
Padding(
40-
padding: const EdgeInsets.symmetric(
41-
vertical: Sizes.xl,
42-
horizontal: Sizes.lg,
43-
),
44-
child: Row(
45-
children: [
46-
Container(
47-
decoration: BoxDecoration(
48-
shape: BoxShape.circle,
49-
color: Theme.of(context).colorScheme.primary,
50-
),
51-
padding: const EdgeInsets.all(Sizes.sm),
52-
child: Icon(
53-
Icons.list_alt,
54-
size: 24.0,
55-
color: Theme.of(context).colorScheme.onPrimary,
56-
),
57-
),
58-
const SizedBox(width: Sizes.md),
59-
Text(
60-
"Your categories",
61-
style: Theme.of(context).textTheme.headlineLarge!.copyWith(
62-
color: Theme.of(context).colorScheme.primary,
63-
),
64-
),
65-
],
66-
),
67-
),
6841
categorysList.when(
6942
data: (categorys) => ReorderableListView.builder(
7043
shrinkWrap: true,

lib/pages/settings/backup/backup_page.dart

Lines changed: 3 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -122,22 +122,15 @@ class _BackupPageState extends ConsumerState<BackupPage> {
122122
Widget build(BuildContext context) {
123123
return Scaffold(
124124
appBar: AppBar(
125-
backgroundColor: Theme.of(context).colorScheme.onPrimary,
126-
elevation: 0,
127-
centerTitle: true,
128125
leading: IconButton(
129126
icon: const Icon(Icons.arrow_back_ios_new),
130127
onPressed: () => Navigator.pop(context),
131128
),
132-
title: Text(
133-
'Manage your data',
134-
style: Theme.of(context).textTheme.headlineLarge!.copyWith(
135-
color: Theme.of(context).colorScheme.primary,
136-
),
137-
),
129+
title: const Text('Import/Export'),
138130
),
139131
body: ListView.separated(
140-
padding: const EdgeInsets.symmetric(vertical: Sizes.lg),
132+
padding: const EdgeInsets.only(top: Sizes.xl),
133+
physics: const BouncingScrollPhysics(),
141134
itemCount: options.length,
142135
separatorBuilder: (context, index) => const SizedBox(height: Sizes.lg),
143136
itemBuilder: (context, index) {

lib/pages/settings/infos/collaborators_page.dart

Lines changed: 144 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,14 @@
1-
// Settings page.
2-
31
import 'package:flutter/material.dart';
42
import 'package:flutter_riverpod/flutter_riverpod.dart';
3+
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
54
import 'package:url_launcher/url_launcher.dart';
65

6+
import '../../../constants/constants.dart';
7+
import '../../../constants/style.dart';
78
import '../../../ui/device.dart';
9+
import '../../../ui/widgets/default_card.dart';
810

9-
class CollaboratorsPage extends ConsumerStatefulWidget {
10-
const CollaboratorsPage({super.key});
11-
12-
@override
13-
// ignore: library_private_types_in_public_api
14-
ConsumerState<CollaboratorsPage> createState() => _CollaboratorsPageState();
15-
}
16-
11+
// [name, role, url (without scheme)]
1712
var collaborators = const [
1813
["Marco Perugini", "Project Manager", "github.com/theperu"],
1914
["Michele Vulcano", "Maintainer, Backend Dev", "github.com/mikev-cw"],
@@ -29,21 +24,30 @@ var collaborators = const [
2924
["Alessandro Bongiovanni", "Flutter Dev", "github.com/bongio94"],
3025
[
3126
"Emanuel Passaro",
32-
"Social Media Manager e Strategist",
27+
"Social Media Manager",
3328
"linkedin.com/in/emanuelpassaro/",
3429
],
3530
[
3631
"Carolina Verdiani",
37-
"(digital) Marketing Project Manager",
32+
"Marketing Project Manager",
3833
"linkedin.com/in/carolina-verdiani/",
3934
],
4035
["Alessia Schina", "UX/UI Designer", "linkedin.com/in/alessiaschina"],
4136
["Federico Bruzzone", "Former Maintainer", "github.com/FedericoBruzzone"],
4237
];
4338

44-
class _CollaboratorsPageState extends ConsumerState<CollaboratorsPage> {
39+
// Cycles through the category colour palette for visual variety.
40+
IconData _platformIcon(String url) {
41+
if (url.contains('github.com')) return FontAwesomeIcons.github;
42+
if (url.contains('linkedin.com')) return FontAwesomeIcons.linkedin;
43+
return FontAwesomeIcons.globe;
44+
}
45+
46+
class CollaboratorsPage extends ConsumerWidget {
47+
const CollaboratorsPage({super.key});
48+
4549
@override
46-
Widget build(BuildContext context) {
50+
Widget build(BuildContext context, WidgetRef ref) {
4751
return Scaffold(
4852
appBar: AppBar(
4953
leading: IconButton(
@@ -52,50 +56,148 @@ class _CollaboratorsPageState extends ConsumerState<CollaboratorsPage> {
5256
),
5357
title: const Text('Collaborators'),
5458
),
55-
body: ListView.separated(
56-
physics: const BouncingScrollPhysics(),
57-
itemCount: collaborators.length,
58-
separatorBuilder: (context, index) => const Divider(height: 1),
59-
itemBuilder: (context, i) {
60-
List option = collaborators[i];
61-
return InkWell(
62-
onTap: () {
63-
Uri url = Uri.parse("https://${option[2]}");
64-
launchUrl(url);
65-
},
66-
child: Padding(
67-
padding: const EdgeInsets.all(Sizes.lg),
59+
body: SingleChildScrollView(
60+
padding: const EdgeInsets.only(top: Sizes.xl, bottom: Sizes.xxl),
61+
child: Column(
62+
crossAxisAlignment: CrossAxisAlignment.start,
63+
children: [
64+
// ── Header ─────────────────────────────────────
65+
Padding(
66+
padding: const EdgeInsets.symmetric(horizontal: Sizes.lg),
6867
child: Column(
6968
crossAxisAlignment: CrossAxisAlignment.start,
7069
children: [
7170
Text(
72-
option[0].toString(),
73-
style: Theme.of(context).textTheme.titleLarge!.copyWith(
71+
'Meet the team',
72+
style: Theme.of(context).textTheme.headlineMedium!.copyWith(
7473
color: Theme.of(context).colorScheme.primary,
7574
),
76-
textAlign: TextAlign.left,
7775
),
78-
const SizedBox(height: Sizes.xs),
76+
const SizedBox(height: Sizes.sm),
7977
Text(
80-
option[1].toString(),
78+
'sossoldi is built and maintained by a passionate open source community. Every feature, fix and idea comes from people like you.',
8179
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
82-
color: Theme.of(context).colorScheme.primary,
80+
color: Theme.of(context).colorScheme.outline,
8381
),
84-
textAlign: TextAlign.left,
8582
),
86-
const SizedBox(height: Sizes.xs),
87-
Text(
88-
option[2].toString(),
89-
style: Theme.of(context).textTheme.bodySmall!.copyWith(
90-
color: Theme.of(context).colorScheme.primary,
83+
],
84+
),
85+
),
86+
const SizedBox(height: Sizes.xl),
87+
88+
// ── Contributors list ───────────────────────────────────
89+
Column(
90+
spacing: Sizes.sm,
91+
children: List.generate(collaborators.length, (i) {
92+
final c = collaborators[i];
93+
return _ContributorCard(name: c[0], role: c[1], url: c[2]);
94+
}),
95+
),
96+
97+
const SizedBox(height: Sizes.xxl),
98+
99+
// ── CTA ────────────────────────────────────────────────
100+
DefaultCard(
101+
onTap: () => launchUrl(Uri.parse(githubUrl)),
102+
child: Row(
103+
spacing: Sizes.md,
104+
children: [
105+
Container(
106+
decoration: const BoxDecoration(
107+
color: blue5,
108+
shape: BoxShape.circle,
109+
),
110+
padding: const EdgeInsets.all(Sizes.md),
111+
child: const FaIcon(
112+
FontAwesomeIcons.github,
113+
color: white,
114+
size: 22,
115+
),
116+
),
117+
Expanded(
118+
child: Column(
119+
crossAxisAlignment: CrossAxisAlignment.start,
120+
children: [
121+
Text(
122+
'Want to contribute?',
123+
style: Theme.of(context).textTheme.titleLarge!
124+
.copyWith(
125+
color: Theme.of(context).colorScheme.primary,
126+
),
127+
),
128+
Text(
129+
'Open an issue, submit a PR or just say hi on GitHub',
130+
style: Theme.of(context).textTheme.bodySmall!
131+
.copyWith(
132+
color: Theme.of(context).colorScheme.outline,
133+
),
134+
),
135+
],
91136
),
92-
textAlign: TextAlign.left,
137+
),
138+
Icon(
139+
Icons.arrow_forward_ios,
140+
size: 16,
141+
color: Theme.of(context).colorScheme.outline,
93142
),
94143
],
95144
),
96145
),
97-
);
98-
},
146+
],
147+
),
148+
),
149+
);
150+
}
151+
}
152+
153+
class _ContributorCard extends StatelessWidget {
154+
const _ContributorCard({
155+
required this.name,
156+
required this.role,
157+
required this.url,
158+
});
159+
160+
final String name;
161+
final String role;
162+
final String url;
163+
164+
@override
165+
Widget build(BuildContext context) {
166+
return DefaultCard(
167+
onTap: () => launchUrl(Uri.parse('https://$url')),
168+
child: Row(
169+
spacing: Sizes.md,
170+
children: [
171+
Expanded(
172+
child: Column(
173+
crossAxisAlignment: CrossAxisAlignment.start,
174+
children: [
175+
Text(
176+
name,
177+
style: Theme.of(context).textTheme.titleSmall!.copyWith(
178+
color: Theme.of(context).colorScheme.primary,
179+
fontWeight: FontWeight.bold,
180+
),
181+
maxLines: 1,
182+
overflow: TextOverflow.ellipsis,
183+
),
184+
Text(
185+
role,
186+
style: Theme.of(context).textTheme.bodySmall!.copyWith(
187+
color: Theme.of(context).colorScheme.outline,
188+
),
189+
maxLines: 1,
190+
overflow: TextOverflow.ellipsis,
191+
),
192+
],
193+
),
194+
),
195+
FaIcon(
196+
_platformIcon(url),
197+
size: 14,
198+
color: Theme.of(context).colorScheme.outline,
199+
),
200+
],
99201
),
100202
);
101203
}

lib/pages/settings/infos/more_info_page.dart

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,8 @@ class MoreInfoPage extends ConsumerWidget {
2727
title: const Text('App Info'),
2828
),
2929
body: ListView.separated(
30-
padding: const EdgeInsets.symmetric(vertical: Sizes.lg),
30+
padding: const EdgeInsets.only(top: Sizes.xl),
31+
physics: const BouncingScrollPhysics(),
3132
itemCount: moreInfoOptions.length,
3233
separatorBuilder: (context, index) => const SizedBox(height: Sizes.lg),
3334
itemBuilder: (context, index) {

0 commit comments

Comments
 (0)