Skip to content
This repository was archived by the owner on Oct 2, 2024. It is now read-only.

Commit 7333eae

Browse files
committedOct 31, 2021
Migrate to Material Design 3 (Material You)
1 parent b5a5297 commit 7333eae

31 files changed

+383
-134
lines changed
 

‎README.md

+4-5
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111

1212
Or download signed binaries for **all mainstream platforms** in the [Releases](https://github.com/tsinis/colors_ai/releases) section of this repository.
1313

14-
# Colors AI 🤖
14+
# Colors AI 🎨🤖
1515

1616
## Table of content
1717

@@ -20,7 +20,6 @@ Or download signed binaries for **all mainstream platforms** in the [Releases](h
2020
* [Architecture](#Architecture)
2121
* [Directory Structure](#Directory-Structure)
2222
* [Tests](#Tests)
23-
* [Packages](#Packages)
2423
* [Accessibility](#Accessibility)
2524
* [How to run it](#How-to-run-it)
2625
* [UI/UX Design](#UI/UX-Design)
@@ -49,21 +48,22 @@ Application is **partially covered with Unit, Widget, and Integration tests**. M
4948

5049
## Accessibility
5150

52-
The app was originally designed to be accessible by **WCAG 2.1 AA standards at minimum, and AAA in particular**, although it was not intended to be used by the blind or by people with severe visual disabilities. All **texts have a contrast ratio at least of 4.5, images 3.0, touch target sizes of at least 48dp**. The application was audited physically on a first-generation iPhone SE (smallest iPhone at this moment) with maximum font size, thickness, contrast, and component magnification. The **audit was also performed on the macOS** version of the app, using the same Accessibility Inspector as on the iOS. The **report from the official Accessibility Scanner for Android** (with a tested device with screen size 640x320px and maximum UI and font scale) can be found at [resources/accessibility](./resources/accessibility/) folder. As you may see it will only complain about the small tap size of text links in the *About* app section and overall screen semantics (which is a [framework bug](https://github.com/flutter/flutter/issues/39531)). Also, the application is **translated into 4 languages and have a haptic feedback (vibration) on mobile devices**. The UI was also built to be **controllable via keyboard/input device/remote control/gamepad**, [here you will find a remote control showcase video](https://drive.google.com/file/d/15Ppuk3ELnP6MhUP6smwmrOS-LdbF0ji0/view?usp=sharing).
51+
The app was originally designed to be accessible by **WCAG 2.1 AA standards at minimum, and AAA in particular**, although it was not intended to be used by the blind or by people with severe visual disabilities. All **texts have a contrast ratio at least of 4.5, images 3.0, touch target sizes of at least 48dp**. The application was audited physically on a first-generation iPhone SE (smallest iPhone at this moment) with maximum font size, thickness, contrast, and component magnification. The **audit was also performed on the macOS** version of the app, using the same Accessibility Inspector as on the iOS. The **report from the official Accessibility Scanner for Android** (with a tested device with screen size 640x320px and maximum UI and font scale) can be found at [resources/accessibility](./resources/accessibility/) folder. As you may see it will only complain about the small tap size of text links in the *About* app section and overall screen semantics (which is a [framework bug](https://github.com/flutter/flutter/issues/39531)). Also, the application is **translated into 4 languages, have a haptic feedback (vibration) on mobile devices and sound feedback on all platforms** (expect PCs at this moment of time). The UI was also built to be **controllable via keyboard/input device/remote control/gamepad**, [here you will find a remote control showcase video](https://drive.google.com/file/d/15Ppuk3ELnP6MhUP6smwmrOS-LdbF0ji0/view?usp=sharing).
5352
However, in the future, I'm planning to improve the control via the input device.
5453

5554
## How to run it
5655

5756
Flutter version **2.6.0-12.0.pre.94** or higher is assumed to be installed. Please run this command from the project's folder, in your terminal:
5857

5958
```bash
59+
flutter pub get
6060
flutter gen-l10n
6161
flutter run
6262
```
6363

6464
## UI/UX Design
6565

66-
All animations here are made with pure Flutter. The application's UI is designed with "gesture-first" UX on mobile platforms and strictly following [Material Design Guidelines](https://material.io/design). Neutral grey color UI is used here to not disrupt user's color perception with highly contrasting light or dark themes.
66+
All animations here are made with pure Flutter. The application's UI is designed with "gesture-first" UX on mobile platforms and strictly following [Material Design 3 (Material You) Guidelines](https://m3.material.io). Neutral grey color UI is used here to not disrupt user's color perception with highly contrasting light or dark themes.
6767

6868
## To-Do Section
6969

@@ -75,7 +75,6 @@ All animations here are made with pure Flutter. The application's UI is designed
7575
* [x] L10N.
7676
* [ ] Add more keyboard shortcuts.
7777
* [ ] Add Feedback.
78-
* [ ] Map BLoC events to state via Freezed.
7978
* [ ] Provide support for Favorites backup (online?).
8079

8180
## Licenses

‎analysis_options.yaml

+7
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,13 @@ dart_code_metrics:
5757
metrics-exclude:
5858
- test/**
5959
rules:
60+
- avoid-nested-conditional-expressions:
61+
acceptable-level: 2
62+
- prefer-correct-type-name
63+
- prefer-last
64+
- refer-correct-identifier-length
65+
- prefer-first
66+
- prefer-const-border-radius
6067
- avoid-unused-parameters
6168
- binary-expression-operand-order
6269
- double-literal-format

‎ios/Podfile.lock

+1-1
Original file line numberDiff line numberDiff line change
@@ -67,4 +67,4 @@ SPEC CHECKSUMS:
6767

6868
PODFILE CHECKSUM: aafe91acc616949ddb318b77800a7f51bffa2a4c
6969

70-
COCOAPODS: 1.11.0
70+
COCOAPODS: 1.11.2

‎lib/about/ui/view/about_dialog.dart

+2-1
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import 'package:flutter_gen/gen_l10n/app_localizations.dart';
66
import '../../../core/ui/constants.dart';
77
import '../../blocs/about_dialog/about_bloc.dart';
88
import '../widgets/app_icon.dart';
9+
import '../widgets/material3_dialog.dart';
910

1011
class AboutAppDialog extends StatelessWidget {
1112
const AboutAppDialog();
@@ -15,7 +16,7 @@ class AboutAppDialog extends StatelessWidget {
1516
final TextStyle? linkStyle =
1617
Theme.of(context).textTheme.bodyText2?.copyWith(color: Theme.of(context).indicatorColor);
1718

18-
return AboutDialog(
19+
return AboutDialogM3(
1920
applicationName: appName,
2021
applicationVersion: BlocProvider.of<AboutBloc>(context).state.appVersion,
2122
applicationLegalese: '2021 © Roman Cinis',

‎lib/about/ui/widgets/app_icon.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ class AppIcon extends StatelessWidget {
1515
child: Material(
1616
elevation: 4,
1717
clipBehavior: Clip.antiAlias,
18-
borderRadius: BorderRadius.circular(16),
18+
borderRadius: const BorderRadius.all(Radius.circular(16)),
1919
child: ColoredBox(
2020
color: const Color(0xff424242),
2121
child: Transform.translate(
+69
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
import 'package:flutter/material.dart';
2+
3+
import '../../../core/extensions/string.dart';
4+
5+
class AboutDialogM3 extends StatelessWidget {
6+
const AboutDialogM3({
7+
required this.applicationName,
8+
required this.applicationVersion,
9+
required this.applicationIcon,
10+
this.applicationLegalese,
11+
this.children,
12+
Key? key,
13+
}) : super(key: key);
14+
15+
static const double _textVerticalSeparation = 18;
16+
17+
final String applicationName;
18+
final String applicationVersion;
19+
final Widget applicationIcon;
20+
final String? applicationLegalese;
21+
final List<Widget>? children;
22+
23+
@override
24+
Widget build(BuildContext context) => AlertDialog(
25+
actionsPadding: const EdgeInsets.only(bottom: 8, right: 8),
26+
shape: const RoundedRectangleBorder(borderRadius: BorderRadius.all(Radius.circular(28))),
27+
content: ListBody(
28+
children: <Widget>[
29+
Row(
30+
crossAxisAlignment: CrossAxisAlignment.start,
31+
children: <Widget>[
32+
IconTheme(data: Theme.of(context).iconTheme, child: applicationIcon),
33+
Expanded(
34+
child: Padding(
35+
padding: const EdgeInsets.symmetric(horizontal: 24),
36+
child: ListBody(
37+
children: <Widget>[
38+
Text(applicationName, style: Theme.of(context).textTheme.headline5),
39+
Text(applicationVersion, style: Theme.of(context).textTheme.bodyText2),
40+
const SizedBox(height: _textVerticalSeparation),
41+
Text(applicationLegalese ?? '', style: Theme.of(context).textTheme.caption),
42+
],
43+
),
44+
),
45+
),
46+
],
47+
),
48+
...?children,
49+
],
50+
),
51+
actions: <Widget>[
52+
TextButton(
53+
child: Text(MaterialLocalizations.of(context).viewLicensesButtonLabel.toBeginningOfSentenceCase()),
54+
onPressed: () => showLicensePage(
55+
context: context,
56+
applicationName: applicationName,
57+
applicationVersion: applicationVersion,
58+
applicationIcon: applicationIcon,
59+
applicationLegalese: applicationLegalese,
60+
),
61+
),
62+
TextButton(
63+
child: Text(MaterialLocalizations.of(context).closeButtonLabel.toBeginningOfSentenceCase()),
64+
onPressed: () => Navigator.pop(context),
65+
),
66+
],
67+
scrollable: true,
68+
);
69+
}

‎lib/app/theme/theme.dart

+33-3
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,11 @@ class AppTheme {
1212
return isDarkTheme ? _darkTheme : _lightTheme;
1313
}
1414

15+
static const _visualDensity = VisualDensity.standard;
16+
static const _material3FabSize = BoxConstraints.tightForFinite(height: 56);
17+
static const _material3FabBorder = RoundedRectangleBorder(borderRadius: BorderRadius.all(Radius.circular(16)));
18+
static const _material3ButtonShape = RoundedRectangleBorder(borderRadius: BorderRadius.all(Radius.circular(20)));
19+
1520
final ThemeData _lightTheme = ThemeData(
1621
primarySwatch: Colors.grey,
1722
primaryColor: Colors.grey[400],
@@ -26,20 +31,33 @@ class AppTheme {
2631
dialogTheme: DialogTheme(backgroundColor: Colors.grey[100]),
2732
radioTheme: RadioThemeData(fillColor: MaterialStateProperty.all<Color>(Colors.black)),
2833
textButtonTheme: TextButtonThemeData(style: TextButton.styleFrom(primary: Colors.grey[850])),
29-
elevatedButtonTheme: ElevatedButtonThemeData(style: ElevatedButton.styleFrom(primary: Colors.grey[200])),
34+
elevatedButtonTheme: ElevatedButtonThemeData(
35+
style: ElevatedButton.styleFrom(
36+
primary: Colors.grey[200],
37+
shape: _material3ButtonShape,
38+
visualDensity: _visualDensity,
39+
),
40+
),
3041
appBarTheme: AppBarTheme(
42+
elevation: 2,
43+
shadowColor: Colors.black45,
3144
iconTheme: const IconThemeData(color: _grey800),
3245
backgroundColor: Colors.grey[400],
3346
),
3447
floatingActionButtonTheme: FloatingActionButtonThemeData(
48+
extendedPadding: const EdgeInsets.symmetric(horizontal: 16),
49+
extendedSizeConstraints: _material3FabSize,
50+
shape: _material3FabBorder,
3551
backgroundColor: Colors.grey[100],
3652
foregroundColor: Colors.grey[850],
3753
focusElevation: 10,
3854
),
3955
outlinedButtonTheme: OutlinedButtonThemeData(
4056
style: OutlinedButton.styleFrom(
4157
primary: Colors.grey[850],
58+
visualDensity: _visualDensity,
4259
backgroundColor: Colors.transparent,
60+
shape: _material3ButtonShape,
4361
side: const BorderSide(color: _grey800),
4462
),
4563
),
@@ -64,10 +82,20 @@ class AppTheme {
6482
indicatorColor: Colors.teal[200],
6583
disabledColor: Colors.grey[600],
6684
primaryIconTheme: IconThemeData(color: Colors.grey[350]),
67-
radioTheme: RadioThemeData(fillColor: MaterialStateProperty.all<Color>(Colors.grey[400]!)),
85+
appBarTheme: const AppBarTheme(shadowColor: Colors.black54, elevation: 2),
86+
radioTheme: RadioThemeData(fillColor: MaterialStateProperty.all<Color?>(Colors.grey[400])),
6887
textButtonTheme: TextButtonThemeData(style: TextButton.styleFrom(primary: Colors.grey[350])),
69-
elevatedButtonTheme: ElevatedButtonThemeData(style: ElevatedButton.styleFrom(primary: Colors.grey[350])),
88+
elevatedButtonTheme: ElevatedButtonThemeData(
89+
style: ElevatedButton.styleFrom(
90+
shape: _material3ButtonShape,
91+
primary: Colors.grey[350],
92+
visualDensity: _visualDensity,
93+
),
94+
),
7095
floatingActionButtonTheme: FloatingActionButtonThemeData(
96+
extendedPadding: const EdgeInsets.symmetric(horizontal: 16),
97+
extendedSizeConstraints: _material3FabSize,
98+
shape: _material3FabBorder,
7199
backgroundColor: Colors.grey[600],
72100
foregroundColor: Colors.white,
73101
disabledElevation: 0,
@@ -81,8 +109,10 @@ class AppTheme {
81109
),
82110
outlinedButtonTheme: OutlinedButtonThemeData(
83111
style: OutlinedButton.styleFrom(
112+
visualDensity: _visualDensity,
84113
primary: Colors.grey[300],
85114
backgroundColor: Colors.transparent,
115+
shape: _material3ButtonShape,
86116
side: BorderSide(color: Colors.grey[400]!),
87117
),
88118
),

‎lib/color_generator/ui/view/gen_colors_tab.dart

+2-2
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ class ColorsGenerator extends StatelessWidget {
3535
padding: const EdgeInsets.only(top: 20),
3636
child: Text.rich(
3737
TextSpan(
38-
text: AppLocalizations.of(context).noConnectionTitle.toUpperCase(),
38+
text: AppLocalizations.of(context).noConnectionTitle,
3939
style: const TextStyle(fontSize: 24, fontWeight: FontWeight.bold),
4040
children: <TextSpan>[
4141
TextSpan(
@@ -55,7 +55,7 @@ class ColorsGenerator extends StatelessWidget {
5555
padding: const EdgeInsets.only(top: 56, bottom: 24),
5656
child: ElevatedButton.icon(
5757
icon: const Icon(Icons.refresh_outlined, size: 20),
58-
label: Text(AppLocalizations.of(context).returnButtonLabel.toUpperCase()),
58+
label: Text(AppLocalizations.of(context).returnButtonLabel),
5959
onPressed: () => BlocProvider.of<ColorsBloc>(context).add(const ColorsStarted()),
6060
),
6161
),

‎lib/color_generator/ui/widgets/animated/animated_list_tile.dart

+17-4
Original file line numberDiff line numberDiff line change
@@ -6,12 +6,14 @@ class AnimatedListItem extends StatefulWidget {
66
required this.child,
77
required this.length,
88
required this.size,
9-
required Key key,
9+
this.hoverIndex,
10+
Key? key,
1011
}) : super(key: key);
1112

1213
final Widget child;
1314
final int index;
1415
final int length;
16+
final int? hoverIndex;
1517
final BoxConstraints size;
1618

1719
@override
@@ -20,6 +22,7 @@ class AnimatedListItem extends StatefulWidget {
2022

2123
class _AnimatedListItemState extends State<AnimatedListItem> {
2224
static const Duration duration = Duration(milliseconds: 300);
25+
static const double hoverPadding = 48;
2326
bool isAnimationDone = false;
2427

2528
@override
@@ -36,18 +39,28 @@ class _AnimatedListItemState extends State<AnimatedListItem> {
3639
double get tileHeight => widget.size.maxHeight / widget.length;
3740
double get tileWeight => widget.size.maxWidth / widget.length;
3841

42+
double get additionaHoverPadding {
43+
if (widget.hoverIndex == null) {
44+
return 0;
45+
} else if (widget.index == widget.hoverIndex) {
46+
return hoverPadding;
47+
}
48+
49+
return -(hoverPadding / widget.length);
50+
}
51+
3952
@override
4053
Widget build(BuildContext context) => AnimatedContainer(
41-
curve: Curves.decelerate,
54+
curve: Curves.easeInOutCubicEmphasized,
4255
height: isPortrait
4356
? isAnimationDone
44-
? tileHeight
57+
? tileHeight + additionaHoverPadding
4558
: (widget.index + 1) * tileHeight * widget.length
4659
: widget.size.maxHeight,
4760
width: isPortrait
4861
? widget.size.maxWidth
4962
: isAnimationDone
50-
? tileWeight
63+
? tileWeight + additionaHoverPadding
5164
: (widget.index + 1) * tileWeight * widget.length,
5265
duration: duration,
5366
child: AnimatedOpacity(

‎lib/color_generator/ui/widgets/lists/colors_list.dart

+72-55
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,19 @@
11
import 'dart:async';
2-
import 'dart:io';
32

43
import 'package:async/async.dart';
54
import 'package:flutter/foundation.dart';
65
import 'package:flutter/gestures.dart';
76
import 'package:flutter/material.dart';
87
import 'package:flutter_bloc/flutter_bloc.dart';
98
import 'package:flutter_gen/gen_l10n/app_localizations.dart';
9+
import 'package:platform_info/platform_info.dart';
1010

1111
import '../../../../color_picker/ui/view/colorpicker.dart';
1212
import '../../../../core/extensions/color.dart';
1313
import '../../../../core/models/color_palette/color_palette.dart';
1414
import '../../../../core/ui/widgets/lists/default_grey_colors_list.dart';
1515
import '../../../../favorites/blocs/add_favorites/fab_bloc.dart';
16+
import '../../../../oboarding/blocs/onboarding/onboarding_bloc.dart';
1617
import '../../../../oboarding/ui/view/onboarding_overlay.dart';
1718
import '../../../../settings/blocs/settings_hydrated_bloc.dart';
1819
import '../../../../sound/blocs/sounds_vibration/sound_bloc.dart';
@@ -37,6 +38,8 @@ class _ColorsListState extends State<ColorsList> with SingleTickerProviderStateM
3738
late final Animation<double> animation;
3839
late final Animation<double> reverseAnimation;
3940

41+
int? hoverIndex;
42+
4043
List<Color> get palette => widget.palette.colors;
4144

4245
void cancelOperation() => cancelableOperation.cancel();
@@ -79,13 +82,15 @@ class _ColorsListState extends State<ColorsList> with SingleTickerProviderStateM
7982

8083
bool get isPortrait => MediaQuery.of(context).orientation == Orientation.portrait;
8184

85+
void changeHoverIndex([int? index]) => setState(() => hoverIndex = index);
86+
8287
@override
8388
Widget build(BuildContext context) => LayoutBuilder(
8489
builder: (_, size) {
8590
final int length = palette.length;
8691
final double tileHeight = size.maxHeight / length;
8792
final Size third =
88-
isPortrait ? Size(size.maxWidth / 3, tileHeight) : Size(size.maxWidth / length, size.maxHeight / 3);
93+
isPortrait ? Size.fromWidth(size.maxWidth / 3) : Size(size.maxWidth / length, size.maxHeight / 3);
8994

9095
return BlocListener<ColorsBloc, ColorsState>(
9196
listener: (_, colorsState) {
@@ -95,7 +100,7 @@ class _ColorsListState extends State<ColorsList> with SingleTickerProviderStateM
95100
},
96101
child: Stack(
97102
children: [
98-
if (!kIsWeb && Platform.isIOS)
103+
if (!kIsWeb && platform.isIOS)
99104
FadeTransition(
100105
opacity: animation,
101106
child: Align(
@@ -131,62 +136,74 @@ class _ColorsListState extends State<ColorsList> with SingleTickerProviderStateM
131136
},
132137
child: FadeTransition(
133138
opacity: animation,
134-
child: ReorderableListView(
135-
scrollDirection: isPortrait ? Axis.vertical : Axis.horizontal,
136-
buildDefaultDragHandles: false,
137-
dragStartBehavior: DragStartBehavior.down,
138-
physics: const AlwaysScrollableScrollPhysics(),
139-
onReorder: (int oldIndex, int newIndex) => BlocProvider.of<ColorsBloc>(context)
140-
.add(ColorsReordered(oldIndex: oldIndex, newIndex: newIndex)),
141-
children: List.generate(
142-
length,
143-
(int index) {
144-
final Color color = palette.elementAt(index);
145-
final Color contrastColor = color.contrastColor();
146-
147-
return AnimatedListItem(
148-
index: index,
149-
size: size,
150-
key: ValueKey<int>(index),
151-
length: length,
152-
child: ReorderableDragListener(
153-
index: index,
154-
onDragStarted: setOperation,
155-
onDragEnded: cancelOperation,
156-
child: InkWell(
157-
onDoubleTap: () {
158-
BlocProvider.of<SoundBloc>(context).add(const SoundLocked());
159-
BlocProvider.of<LockedBloc>(context).add(LockChanged(index));
160-
},
161-
child: Container(
162-
width: size.maxWidth,
163-
height: tileHeight,
164-
color: color,
165-
child: Stack(
166-
alignment: Alignment.centerLeft,
167-
children: [
168-
Colorpicker(
169-
index,
170-
color: color,
171-
isPortrait: isPortrait,
172-
textColor: contrastColor,
173-
buttonSize: isPortrait
174-
? third
175-
: Size(
176-
size.maxWidth / length,
177-
size.maxHeight,
178-
),
139+
child: BlocBuilder<OnboardingBloc, OnboardingState>(
140+
builder: (_, onboardingState) {
141+
final isHoveringAvailable = onboardingState is OnboardingDoneSuccess && !platform.isMobile;
142+
143+
return ReorderableListView.builder(
144+
itemCount: length,
145+
scrollDirection: isPortrait ? Axis.vertical : Axis.horizontal,
146+
buildDefaultDragHandles: false,
147+
dragStartBehavior: DragStartBehavior.down,
148+
physics: const AlwaysScrollableScrollPhysics(),
149+
onReorder: (int oldIndex, int newIndex) => BlocProvider.of<ColorsBloc>(context)
150+
.add(ColorsReordered(oldIndex: oldIndex, newIndex: newIndex)),
151+
itemBuilder: (_, int index) {
152+
final Color color = palette.elementAt(index);
153+
final Color contrastColor = color.contrastColor();
154+
155+
return MouseRegion(
156+
key: ValueKey<int>(index),
157+
onHover: (_) => changeHoverIndex(index),
158+
onExit: (_) => changeHoverIndex(),
159+
child: AnimatedListItem(
160+
index: index,
161+
size: size,
162+
length: length,
163+
hoverIndex: isHoveringAvailable ? hoverIndex : null,
164+
child: ReorderableDragListener(
165+
index: index,
166+
onDragStarted: setOperation,
167+
onDragEnded: cancelOperation,
168+
child: InkWell(
169+
onDoubleTap: () {
170+
BlocProvider.of<SoundBloc>(context).add(const SoundLocked());
171+
BlocProvider.of<LockedBloc>(context).add(LockChanged(index));
172+
},
173+
child: DecoratedBox(
174+
decoration: BoxDecoration(
175+
boxShadow: [
176+
BoxShadow(
177+
color: color,
178+
blurStyle: BlurStyle.solid,
179+
spreadRadius: 1,
180+
offset: const Offset(0, -1),
181+
),
182+
],
183+
),
184+
child: Stack(
185+
alignment: Alignment.centerLeft,
186+
children: [
187+
Colorpicker(
188+
index,
189+
color: color,
190+
isPortrait: isPortrait,
191+
textColor: contrastColor,
192+
buttonSize: isPortrait ? third : Size.fromHeight(size.maxHeight),
193+
),
194+
Center(
195+
child: LockColorButton(index, color: contrastColor, buttonSize: third),
196+
),
197+
],
179198
),
180-
Center(child: LockColorButton(index, color: contrastColor, buttonSize: third)),
181-
],
199+
),
182200
),
183201
),
184202
),
185-
),
186-
);
187-
},
188-
growable: false,
189-
),
203+
);
204+
},
205+
);
206+
},
190207
),
191208
),
192209
),

‎lib/color_picker/ui/widgets/colorpicker_dialog.dart

+2
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,7 @@ class _ColorpickerDialogState extends State<ColorpickerDialog> {
7878

7979
@override
8080
Widget build(BuildContext context) => SimpleDialog(
81+
// shape: const RoundedRectangleBorder(borderRadius: BorderRadius.all(Radius.circular(28))),
8182
contentPadding: EdgeInsets.zero,
8283
children: [
8384
if (hidePickerArea) const SizedBox(height: 12),
@@ -102,6 +103,7 @@ class _ColorpickerDialogState extends State<ColorpickerDialog> {
102103
enableSuggestions: false,
103104
enableIMEPersonalizedLearning: false,
104105
onTap: setColorFromHex,
106+
onFieldSubmitted: (_) => Navigator.of(context).pop(),
105107
textAlignVertical: TextAlignVertical.center,
106108
scrollPadding: const EdgeInsets.only(bottom: 20),
107109
inputFormatters: [HexFormatter()],

‎lib/core/extensions/string.dart

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
extension StringExtension on String {
2+
String toBeginningOfSentenceCase() => '${this[0].toUpperCase()}${substring(1).toLowerCase()}';
3+
}

‎lib/core/ui/view/scaffold.dart

+1-2
Original file line numberDiff line numberDiff line change
@@ -152,7 +152,7 @@ class _NavigationScreenState extends State<MainScreen> {
152152
action: isUrlCopied
153153
? SnackBarAction(
154154
textColor: Theme.of(context).scaffoldBackgroundColor,
155-
label: AppLocalizations.of(context).urlOpenButtonLabel.toUpperCase(),
155+
label: AppLocalizations.of(context).urlOpenButtonLabel,
156156
onPressed: () => BlocProvider.of<SnackbarBloc>(context).add(
157157
const UrlOpenedSuccess(),
158158
),
@@ -167,7 +167,6 @@ class _NavigationScreenState extends State<MainScreen> {
167167
crossAxisAlignment: CrossAxisAlignment.start,
168168
children: [
169169
if (!isPortrait) NavRail(navState, toShowGenFab: showGenFab),
170-
if (!isPortrait) const VerticalDivider(width: 1),
171170
Expanded(
172171
child: navTabs.elementAt(navState.tabIndex),
173172
),

‎lib/core/ui/widgets/lists/default_grey_colors_list.dart

+12-2
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,18 @@ class DefaultGreyList extends StatelessWidget {
1515
children: List.generate(
1616
length ?? defaultColors.length,
1717
(int i) => Flexible(
18-
child: Container(
19-
color: defaultColors[i],
18+
child: DecoratedBox(
19+
decoration: BoxDecoration(
20+
color: defaultColors[i],
21+
boxShadow: [
22+
BoxShadow(
23+
color: defaultColors[i],
24+
blurStyle: BlurStyle.solid,
25+
spreadRadius: 1,
26+
offset: const Offset(0, -1),
27+
),
28+
],
29+
),
2030
),
2131
),
2232
growable: false,

‎lib/favorites/ui/view/favorites_tab.dart

+2-2
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ class FavoritesTab extends StatelessWidget {
3737
padding: const EdgeInsets.only(top: 20),
3838
child: Text.rich(
3939
TextSpan(
40-
text: AppLocalizations.of(context).noFavoritesTitle.toUpperCase(),
40+
text: AppLocalizations.of(context).noFavoritesTitle,
4141
style: const TextStyle(fontSize: 24, fontWeight: FontWeight.bold),
4242
children: [
4343
TextSpan(
@@ -53,7 +53,7 @@ class FavoritesTab extends StatelessWidget {
5353
padding: const EdgeInsets.only(top: 56, bottom: 24),
5454
child: ElevatedButton.icon(
5555
icon: const Icon(Icons.add, size: 20),
56-
label: Text(AppLocalizations.of(context).addFavoritesButtonLabel.toUpperCase()),
56+
label: Text(AppLocalizations.of(context).addFavoritesButtonLabel),
5757
onPressed: () => BlocProvider.of<FavoritesBloc>(context)
5858
.add(FavoritesAdded(favorite: context.read<ColorsRepository>().toPalette())),
5959
),

‎lib/favorites/ui/widgets/buttons/remove_all_favorites_button.dart

+5-2
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import 'package:flutter_bloc/flutter_bloc.dart';
55
import 'package:flutter_gen/gen_l10n/app_localizations.dart';
66
import 'package:mdi/mdi.dart';
77

8+
import '../../../../core/extensions/string.dart';
89
import '../../../blocs/list_favorites/favorites_bloc.dart';
910
import '../../../blocs/remove_favorites/remove_favs_bloc.dart';
1011

@@ -55,6 +56,8 @@ class _RemoveAllFavoritesButtonState extends State<RemoveAllFavoritesButton> wit
5556
),
5657
// https://material.io/components/dialogs#alert-dialog
5758
builder: (_) => AlertDialog(
59+
actionsPadding: const EdgeInsets.only(bottom: 8, right: 8),
60+
shape: const RoundedRectangleBorder(borderRadius: BorderRadius.all(Radius.circular(28))),
5861
content: Text(
5962
haveSelection
6063
? '${AppLocalizations.of(context).removeSomeTitle(state.selections.length)}?'
@@ -63,12 +66,12 @@ class _RemoveAllFavoritesButtonState extends State<RemoveAllFavoritesButton> wit
6366
actions: <TextButton>[
6467
TextButton(
6568
onPressed: () => Navigator.pop(dialogContext, false),
66-
child: Text(MaterialLocalizations.of(context).cancelButtonLabel.toUpperCase()),
69+
child: Text(MaterialLocalizations.of(context).cancelButtonLabel.toBeginningOfSentenceCase()),
6770
),
6871
TextButton(
6972
onPressed: () => Navigator.pop(dialogContext, true),
7073
child: Text(
71-
AppLocalizations.of(context).removeButtonLabel.toUpperCase(),
74+
AppLocalizations.of(context).removeButtonLabel,
7275
style: TextStyle(color: Theme.of(context).errorColor),
7376
),
7477
),

‎lib/oboarding/ui/view/onboarding_overlay.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -101,7 +101,7 @@ class OnboardingOverlay extends StatelessWidget {
101101
style: ElevatedButton.styleFrom(primary: Theme.of(context).indicatorColor),
102102
onPressed: () => BlocProvider.of<OnboardingBloc>(context).add(const OnboardingFinished()),
103103
child: Text(
104-
AppLocalizations.of(context).onboardingDoneButtonLabel.toUpperCase(),
104+
AppLocalizations.of(context).onboardingDoneButtonLabel,
105105
key: TestKeys.onboardingFinish,
106106
style: const TextStyle(color: Colors.white),
107107
),

‎lib/settings/ui/view/settings_dialog.dart

+6-2
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import 'package:flutter/material.dart';
22
import 'package:flutter_bloc/flutter_bloc.dart';
33
import 'package:flutter_gen/gen_l10n/app_localizations.dart';
44

5+
import '../../../core/extensions/string.dart';
56
import '../../blocs/settings_hydrated_bloc.dart';
67

78
class SettingsDialog extends StatelessWidget {
@@ -10,6 +11,8 @@ class SettingsDialog extends StatelessWidget {
1011
@override
1112
Widget build(BuildContext context) => BlocBuilder<SettingsBloc, SettingsState>(
1213
builder: (_, state) => AlertDialog(
14+
actionsPadding: const EdgeInsets.only(bottom: 8, right: 8),
15+
shape: const RoundedRectangleBorder(borderRadius: BorderRadius.all(Radius.circular(28))),
1316
scrollable: true,
1417
contentPadding: const EdgeInsets.only(bottom: 16, top: 16),
1518
title: Text(AppLocalizations.of(context).settings),
@@ -35,6 +38,7 @@ class SettingsDialog extends StatelessWidget {
3538
}
3639
},
3740
),
41+
const SizedBox(height: 8),
3842
const Divider(height: 1),
3943
Padding(
4044
padding: const EdgeInsets.only(left: 16, bottom: 8, top: 12),
@@ -76,12 +80,12 @@ class SettingsDialog extends StatelessWidget {
7680
BlocProvider.of<SettingsBloc>(context).add(const SettingsRegularColorsSelected());
7781
},
7882
child: Text(
79-
AppLocalizations.of(context).resetButtonLabel.toUpperCase(),
83+
AppLocalizations.of(context).resetButtonLabel,
8084
),
8185
),
8286
TextButton(
8387
onPressed: () => Navigator.pop(context),
84-
child: Text(MaterialLocalizations.of(context).closeButtonLabel),
88+
child: Text(MaterialLocalizations.of(context).closeButtonLabel.toBeginningOfSentenceCase()),
8589
),
8690
],
8791
),

‎lib/share/repository/share_repository.dart

+17-1
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
11
import 'dart:io' show File;
22
import 'dart:typed_data' show Uint8List;
33

4+
import 'package:file_selector/file_selector.dart';
45
import 'package:flutter/foundation.dart';
6+
import 'package:platform_info/platform_info.dart';
57
import 'package:printing/printing.dart';
68
import 'package:share_plus/share_plus.dart';
79

@@ -24,6 +26,7 @@ class ShareRepository with FileCreator, TextBasedFileCreator, DeviceCapabilities
2426
Colordot(),
2527
Coolors(),
2628
DesignAI(),
29+
DopelyColors(),
2730
MakeTintsAndShades(),
2831
MuzliColors(),
2932
Palettable(),
@@ -139,9 +142,22 @@ class ShareRepository with FileCreator, TextBasedFileCreator, DeviceCapabilities
139142
return _shareFile(file);
140143
}
141144

145+
Future<void> _saveFile(File file) async {
146+
final String? path = await getSavePath();
147+
if (path == null) {
148+
return;
149+
}
150+
final XFile textFile = XFile(file.path, name: _fileName);
151+
await textFile.saveTo(path);
152+
}
153+
142154
Future<bool> _shareFile(File file) async {
143155
if (file.existsSync()) {
144-
await Share.shareFiles([_filePath], subject: appName);
156+
if (!kIsWeb && (platform.isWindows || platform.isLinux)) {
157+
await _saveFile(file);
158+
} else {
159+
await Share.shareFiles([_filePath], subject: appName);
160+
}
145161

146162
return true;
147163
} else {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
part of '../url_providers.dart';
2+
3+
class DopelyColors extends ColorsUrlProvider {
4+
const DopelyColors()
5+
: super(
6+
baseUrl: 'colors.dopely.top/color-wheel/custom/',
7+
formats: 'JPG, JPEG, CSS, PDF, PNG, SVG, TXT, HTML +',
8+
);
9+
// https://colors.dopely.top/color-wheel/custom/691b82-31cea7-c74f4f-59178e-aeb4a2
10+
}

‎lib/share/services/url_providers/url_providers.dart

+1
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ part 'providers/colordesigner.dart';
1010
part 'providers/colordot.dart';
1111
part 'providers/coolors.dart';
1212
part 'providers/design_ai.dart';
13+
part 'providers/dopely_colors.dart';
1314
part 'providers/make_tints_and_shades.dart';
1415
part 'providers/muzli_colors.dart';
1516
part 'providers/palettable.dart';

‎lib/share/ui/widgets/share_sections/file_share_section.dart

+11-6
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import 'package:flutter_bloc/flutter_bloc.dart';
66
import 'package:flutter_gen/gen_l10n/app_localizations.dart';
77

88
import '../../../../common/blocs/snackbars/snackbars_bloc.dart';
9+
import '../../../../core/extensions/string.dart';
910
import '../../../../core/models/color_palette/color_palette.dart';
1011
import '../../../blocs/share/share_hydrated_bloc.dart';
1112
import '../../../models/file_format_enum.dart';
@@ -49,7 +50,13 @@ class FileShareSection extends ShareSection {
4950
}
5051
}
5152

52-
bool get isNotSupportedByOS => !kIsWeb && (Platform.isWindows || Platform.isLinux);
53+
String _shareOrSaveButtonLabel(BuildContext context) {
54+
if (!kIsWeb && (Platform.isWindows || Platform.isLinux)) {
55+
return '${MaterialLocalizations.of(context).saveButtonLabel.toBeginningOfSentenceCase()} ${file.format}';
56+
} else {
57+
return AppLocalizations.of(context).shareAsFormat(file.format);
58+
}
59+
}
5360

5461
@override
5562
Widget build(BuildContext context) {
@@ -101,7 +108,7 @@ class FileShareSection extends ShareSection {
101108
padding: const EdgeInsets.only(bottom: 8),
102109
child: OutlinedButton.icon(
103110
icon: const Icon(Icons.content_copy_outlined, size: 20),
104-
label: Text(AppLocalizations.of(context).copyAsFormat(file.format).toUpperCase()),
111+
label: Text(AppLocalizations.of(context).copyAsFormat(file.format)),
105112
onPressed: cannotCopy
106113
? null
107114
: () {
@@ -114,10 +121,8 @@ class FileShareSection extends ShareSection {
114121
padding: const EdgeInsets.only(bottom: 8),
115122
child: ElevatedButton.icon(
116123
icon: const Icon(Icons.link, size: 20),
117-
label: Text(AppLocalizations.of(context).shareAsFormat(file.format).toUpperCase()),
118-
onPressed: isNotSupportedByOS
119-
? null
120-
: () => BlocProvider.of<ShareBloc>(context).add(ShareFileShared(palette)),
124+
label: Text(_shareOrSaveButtonLabel(context)),
125+
onPressed: () => BlocProvider.of<ShareBloc>(context).add(ShareFileShared(palette)),
121126
),
122127
),
123128
],

‎lib/share/ui/widgets/share_sections/url_share_section.dart

+9-3
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
1+
import 'package:flutter/foundation.dart';
12
import 'package:flutter/material.dart';
23
import 'package:flutter_bloc/flutter_bloc.dart';
34
import 'package:flutter_gen/gen_l10n/app_localizations.dart';
5+
import 'package:platform_info/platform_info.dart';
46

57
import '../../../../common/blocs/snackbars/snackbars_bloc.dart';
68
import '../../../../core/models/color_palette/color_palette.dart';
@@ -23,6 +25,8 @@ class UrlShareSection extends ShareSection {
2325
final String? exportFormats;
2426
final List<ColorsUrlProvider> providersList;
2527

28+
bool get _isNotSupportedByOS => kIsWeb || platform.isWindows || platform.isLinux;
29+
2630
@override
2731
Widget build(BuildContext context) {
2832
final bool isPortrait = MediaQuery.of(context).orientation == Orientation.portrait;
@@ -83,7 +87,7 @@ class UrlShareSection extends ShareSection {
8387
padding: const EdgeInsets.only(bottom: 8),
8488
child: OutlinedButton.icon(
8589
icon: const Icon(Icons.content_copy_outlined, size: 20),
86-
label: Text(AppLocalizations.of(context).copyUrlButtonLabel.toUpperCase()),
90+
label: Text(AppLocalizations.of(context).copyUrlButtonLabel),
8791
onPressed: () {
8892
BlocProvider.of<ShareBloc>(context).add(ShareUrlCopied(palette));
8993
BlocProvider.of<SnackbarBloc>(context).add(const UrlCopiedSuccess());
@@ -94,8 +98,10 @@ class UrlShareSection extends ShareSection {
9498
padding: const EdgeInsets.only(bottom: 8),
9599
child: ElevatedButton.icon(
96100
icon: const Icon(Icons.link, size: 20),
97-
label: Text(AppLocalizations.of(context).shareUrlButtonLabel.toUpperCase()),
98-
onPressed: () => BlocProvider.of<ShareBloc>(context).add(ShareUrlShared(palette)),
101+
label: Text(AppLocalizations.of(context).shareUrlButtonLabel),
102+
onPressed: _isNotSupportedByOS
103+
? null
104+
: () => BlocProvider.of<ShareBloc>(context).add(ShareUrlShared(palette)),
99105
),
100106
),
101107
],

‎linux/flutter/generated_plugin_registrant.cc

+4
Original file line numberDiff line numberDiff line change
@@ -6,11 +6,15 @@
66

77
#include "generated_plugin_registrant.h"
88

9+
#include <file_selector_linux/file_selector_plugin.h>
910
#include <printing/printing_plugin.h>
1011
#include <url_launcher_linux/url_launcher_plugin.h>
1112
#include <window_size/window_size_plugin.h>
1213

1314
void fl_register_plugins(FlPluginRegistry* registry) {
15+
g_autoptr(FlPluginRegistrar) file_selector_linux_registrar =
16+
fl_plugin_registry_get_registrar_for_plugin(registry, "FileSelectorPlugin");
17+
file_selector_plugin_register_with_registrar(file_selector_linux_registrar);
1418
g_autoptr(FlPluginRegistrar) printing_registrar =
1519
fl_plugin_registry_get_registrar_for_plugin(registry, "PrintingPlugin");
1620
printing_plugin_register_with_registrar(printing_registrar);

‎linux/flutter/generated_plugins.cmake

+1
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
#
44

55
list(APPEND FLUTTER_PLUGIN_LIST
6+
file_selector_linux
67
printing
78
url_launcher_linux
89
window_size

‎macos/Podfile.lock

+1-1
Original file line numberDiff line numberDiff line change
@@ -61,4 +61,4 @@ SPEC CHECKSUMS:
6161

6262
PODFILE CHECKSUM: 290b89638b803a41d96e2a2c02a9e1e635956f78
6363

64-
COCOAPODS: 1.11.0
64+
COCOAPODS: 1.11.2

‎pubspec.lock

+66-24
Original file line numberDiff line numberDiff line change
@@ -7,28 +7,28 @@ packages:
77
name: _fe_analyzer_shared
88
url: "https://pub.dartlang.org"
99
source: hosted
10-
version: "24.0.0"
10+
version: "30.0.0"
1111
analyzer:
1212
dependency: transitive
1313
description:
1414
name: analyzer
1515
url: "https://pub.dartlang.org"
1616
source: hosted
17-
version: "2.1.0"
17+
version: "2.7.0"
1818
analyzer_plugin:
1919
dependency: transitive
2020
description:
2121
name: analyzer_plugin
2222
url: "https://pub.dartlang.org"
2323
source: hosted
24-
version: "0.7.0"
24+
version: "0.8.0"
2525
animations:
2626
dependency: "direct main"
2727
description:
2828
name: animations
2929
url: "https://pub.dartlang.org"
3030
source: hosted
31-
version: "2.0.1"
31+
version: "2.0.2"
3232
ansicolor:
3333
dependency: transitive
3434
description:
@@ -42,14 +42,14 @@ packages:
4242
name: archive
4343
url: "https://pub.dartlang.org"
4444
source: hosted
45-
version: "3.1.2"
45+
version: "3.1.5"
4646
args:
4747
dependency: transitive
4848
description:
4949
name: args
5050
url: "https://pub.dartlang.org"
5151
source: hosted
52-
version: "2.0.0"
52+
version: "2.3.0"
5353
async:
5454
dependency: transitive
5555
description:
@@ -63,7 +63,7 @@ packages:
6363
name: audio_session
6464
url: "https://pub.dartlang.org"
6565
source: hosted
66-
version: "0.1.6"
66+
version: "0.1.6+1"
6767
barcode:
6868
dependency: transitive
6969
description:
@@ -119,14 +119,14 @@ packages:
119119
name: build_runner
120120
url: "https://pub.dartlang.org"
121121
source: hosted
122-
version: "2.1.2"
122+
version: "2.1.4"
123123
build_runner_core:
124124
dependency: transitive
125125
description:
126126
name: build_runner_core
127127
url: "https://pub.dartlang.org"
128128
source: hosted
129-
version: "7.1.0"
129+
version: "7.2.2"
130130
built_collection:
131131
dependency: transitive
132132
description:
@@ -204,6 +204,13 @@ packages:
204204
url: "https://pub.dartlang.org"
205205
source: hosted
206206
version: "3.0.0"
207+
cross_file:
208+
dependency: transitive
209+
description:
210+
name: cross_file
211+
url: "https://pub.dartlang.org"
212+
source: hosted
213+
version: "0.3.2"
207214
crypto:
208215
dependency: transitive
209216
description:
@@ -224,7 +231,7 @@ packages:
224231
name: dart_code_metrics
225232
url: "https://pub.dartlang.org"
226233
source: hosted
227-
version: "4.3.3"
234+
version: "4.6.0"
228235
dart_style:
229236
dependency: transitive
230237
description:
@@ -260,6 +267,41 @@ packages:
260267
url: "https://pub.dartlang.org"
261268
source: hosted
262269
version: "6.1.2"
270+
file_selector:
271+
dependency: "direct main"
272+
description:
273+
name: file_selector
274+
url: "https://pub.dartlang.org"
275+
source: hosted
276+
version: "0.8.2+1"
277+
file_selector_linux:
278+
dependency: "direct main"
279+
description:
280+
name: file_selector_linux
281+
url: "https://pub.dartlang.org"
282+
source: hosted
283+
version: "0.0.2+1"
284+
file_selector_platform_interface:
285+
dependency: transitive
286+
description:
287+
name: file_selector_platform_interface
288+
url: "https://pub.dartlang.org"
289+
source: hosted
290+
version: "2.0.2"
291+
file_selector_web:
292+
dependency: transitive
293+
description:
294+
name: file_selector_web
295+
url: "https://pub.dartlang.org"
296+
source: hosted
297+
version: "0.8.1+2"
298+
file_selector_windows:
299+
dependency: "direct main"
300+
description:
301+
name: file_selector_windows
302+
url: "https://pub.dartlang.org"
303+
source: hosted
304+
version: "0.0.2+1"
263305
fixnum:
264306
dependency: transitive
265307
description:
@@ -441,21 +483,21 @@ packages:
441483
name: json_annotation
442484
url: "https://pub.dartlang.org"
443485
source: hosted
444-
version: "4.1.0"
486+
version: "4.3.0"
445487
json_serializable:
446488
dependency: "direct dev"
447489
description:
448490
name: json_serializable
449491
url: "https://pub.dartlang.org"
450492
source: hosted
451-
version: "5.0.2"
493+
version: "6.0.1"
452494
just_audio:
453495
dependency: "direct main"
454496
description:
455497
name: just_audio
456498
url: "https://pub.dartlang.org"
457499
source: hosted
458-
version: "0.9.12"
500+
version: "0.9.14"
459501
just_audio_platform_interface:
460502
dependency: transitive
461503
description:
@@ -520,12 +562,12 @@ packages:
520562
source: hosted
521563
version: "5.0.15"
522564
msix:
523-
dependency: "direct main"
565+
dependency: "direct dev"
524566
description:
525567
name: msix
526568
url: "https://pub.dartlang.org"
527569
source: hosted
528-
version: "2.1.3"
570+
version: "2.6.2"
529571
nested:
530572
dependency: transitive
531573
description:
@@ -539,14 +581,14 @@ packages:
539581
name: package_config
540582
url: "https://pub.dartlang.org"
541583
source: hosted
542-
version: "2.0.0"
584+
version: "2.0.2"
543585
package_info_plus:
544586
dependency: "direct main"
545587
description:
546588
name: package_info_plus
547589
url: "https://pub.dartlang.org"
548590
source: hosted
549-
version: "1.0.6"
591+
version: "1.3.0"
550592
package_info_plus_linux:
551593
dependency: transitive
552594
description:
@@ -560,7 +602,7 @@ packages:
560602
name: package_info_plus_macos
561603
url: "https://pub.dartlang.org"
562604
source: hosted
563-
version: "1.1.1"
605+
version: "1.2.0"
564606
package_info_plus_platform_interface:
565607
dependency: transitive
566608
description:
@@ -581,7 +623,7 @@ packages:
581623
name: package_info_plus_windows
582624
url: "https://pub.dartlang.org"
583625
source: hosted
584-
version: "1.0.3"
626+
version: "1.0.4"
585627
path:
586628
dependency: transitive
587629
description:
@@ -602,7 +644,7 @@ packages:
602644
name: path_provider
603645
url: "https://pub.dartlang.org"
604646
source: hosted
605-
version: "2.0.5"
647+
version: "2.0.6"
606648
path_provider_linux:
607649
dependency: transitive
608650
description:
@@ -735,7 +777,7 @@ packages:
735777
name: share_plus
736778
url: "https://pub.dartlang.org"
737779
source: hosted
738-
version: "2.1.4"
780+
version: "3.0.4"
739781
share_plus_linux:
740782
dependency: transitive
741783
description:
@@ -791,7 +833,7 @@ packages:
791833
name: simple_animations
792834
url: "https://pub.dartlang.org"
793835
source: hosted
794-
version: "4.0.0"
836+
version: "4.0.1"
795837
sky_engine:
796838
dependency: transitive
797839
description: flutter
@@ -810,7 +852,7 @@ packages:
810852
name: source_helper
811853
url: "https://pub.dartlang.org"
812854
source: hosted
813-
version: "1.2.1"
855+
version: "1.3.0"
814856
source_span:
815857
dependency: transitive
816858
description:
@@ -943,7 +985,7 @@ packages:
943985
name: vector_math
944986
url: "https://pub.dartlang.org"
945987
source: hosted
946-
version: "2.1.0"
988+
version: "2.1.1"
947989
vibration:
948990
dependency: "direct main"
949991
description:

‎pubspec.yaml

+16-14
Original file line numberDiff line numberDiff line change
@@ -6,17 +6,19 @@ maintainer: Roman Cinis
66

77
publish_to: 'none'
88

9-
version: 1.4.0+7
9+
version: 1.5.0+8
1010

11-
# Flutter's master channel at this moment
1211
environment:
1312
sdk: ">=2.15.0-149.0.dev <3.0.0"
1413
flutter: ">=2.6.0-12.0.pre.94 <3.0.0"
1514

1615
dependencies:
17-
animations: ^2.0.1 # From Google
16+
animations: ^2.0.2 # From Google
1817
color_converter: ^0.2.1
1918
equatable: ^2.0.3 # From Flutter Community
19+
file_selector: ^0.8.2+1 # From Google
20+
file_selector_linux: ^0.0.2+1 # From Google
21+
file_selector_windows: ^0.0.2+1 # From Google
2022
flutter: # From Google
2123
sdk: flutter
2224
flutter_bloc: 7.0.0 # Flutter Favorite
@@ -27,16 +29,15 @@ dependencies:
2729
http: ^0.13.0-nullsafety.0 # From Google
2830
hydrated_bloc: 7.0.1
2931
intl: ^0.17.0 # From Google
30-
json_annotation: ^4.0.0-nullsafety.0 # From Google
31-
just_audio: ^0.9.12 # Flutter Favorite
32+
json_annotation: ^4.3.0 # From Google
33+
just_audio: ^0.9.14 # Flutter Favorite
3234
mdi: ^5.0.0-nullsafety.0
33-
msix: ^2.1.3 # Recommended by Google
34-
package_info_plus: ^1.0.6 # From Flutter Community (former Google)
35-
path_provider: ^2.0.5 # From Google
35+
package_info_plus: ^1.3.0 # From Flutter Community (former Google)
36+
path_provider: ^2.0.6 # From Google
3637
platform_info: ^3.1.0 # Contributor
3738
printing: ^5.6.0
38-
share_plus: ^2.1.4 # From Flutter Community (former Google)
39-
simple_animations: ^4.0.0
39+
share_plus: ^3.0.4 # From Flutter Community (former Google)
40+
simple_animations: ^4.0.1
4041
url_launcher: ^6.0.0-nullsafety.7 # From Google
4142
vibration: ^1.7.4-nullsafety.0
4243
window_size: # From Google
@@ -46,16 +47,17 @@ dependencies:
4647
ref: 03d957e8b5c99fc83cd4a781031b154ab3de8753
4748

4849
dev_dependencies:
49-
build_runner: ^2.1.2 # From Google
50-
dart_code_metrics: ^4.3.3
50+
build_runner: ^2.1.4 # From Google
51+
dart_code_metrics: ^4.6.0
5152
flutter_lints: ^1.0.4 # From Google
5253
flutter_test: # From Google
5354
sdk: flutter
5455
hive_generator: ^1.1.1
5556
integration_test: # From Google
5657
sdk: flutter
57-
json_serializable: ^5.0.2 # From Google
58+
json_serializable: ^6.0.1 # From Google
5859
mockito: ^5.0.0-nullsafety.5 # From Google
60+
msix: ^2.6.2 # Recommended by Google
5961

6062
flutter:
6163
generate: true
@@ -69,7 +71,7 @@ msix_config:
6971
publisher_display_name: Roman Cinis
7072
publisher: CN=3F745294-7EE6-4235-B7C5-8E22B9089351
7173
identity_name: 53621RomanCinis.ColorsAI
72-
msix_version: 1.4.0.0
74+
msix_version: 1.5.0.0
7375
icons_background_color: transparent
7476
vs_generated_images_folder_path: resources\windows\store_assets
7577
languages: en-us, sk-sk, ru-ru, cs-cz

‎snap/snapcraft.yaml

+3-2
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
name: colors-ai
2-
version: 1.4.0
2+
version: 1.5.0
33
summary: Colors AI
44
description: A color scheme generator that uses deep learning from Colormind.
55
confinement: strict
6+
license: MIT
67
base: core18
78
grade: stable
89
architectures:
@@ -11,7 +12,7 @@ architectures:
1112
apps:
1213
colors-ai:
1314
command: colors_ai
14-
extensions: [flutter-master]
15+
extensions: [flutter-beta]
1516
plugs:
1617
- network
1718
- home

‎windows/flutter/generated_plugin_registrant.cc

+3
Original file line numberDiff line numberDiff line change
@@ -6,11 +6,14 @@
66

77
#include "generated_plugin_registrant.h"
88

9+
#include <file_selector_windows/file_selector_plugin.h>
910
#include <printing/printing_plugin.h>
1011
#include <url_launcher_windows/url_launcher_plugin.h>
1112
#include <window_size/window_size_plugin.h>
1213

1314
void RegisterPlugins(flutter::PluginRegistry* registry) {
15+
FileSelectorPluginRegisterWithRegistrar(
16+
registry->GetRegistrarForPlugin("FileSelectorPlugin"));
1417
PrintingPluginRegisterWithRegistrar(
1518
registry->GetRegistrarForPlugin("PrintingPlugin"));
1619
UrlLauncherPluginRegisterWithRegistrar(

‎windows/flutter/generated_plugins.cmake

+1
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
#
44

55
list(APPEND FLUTTER_PLUGIN_LIST
6+
file_selector_windows
67
printing
78
url_launcher_windows
89
window_size

0 commit comments

Comments
 (0)
This repository has been archived.