Compare commits

..

5 Commits

48 changed files with 328 additions and 204 deletions

View File

@ -2,7 +2,7 @@
<application
android:label="rtime"
android:name="${applicationName}"
android:icon="@mipmap/ic_launcher">
android:icon="@mipmap/launcher_icon">
<activity
android:name="com.yalantis.ucrop.UCropActivity"
android:screenOrientation="portrait"

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

7
assets/images/drone.svg Normal file
View File

@ -0,0 +1,7 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Svg Vector Icons : http://www.onlinewebfonts.com/icon -->
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 256 256" enable-background="new 0 0 256 256" xml:space="preserve">
<metadata> Svg Vector Icons : http://www.onlinewebfonts.com/icon </metadata>
<g><g><g><path fill="#000000" d="M46.4,10.5c-9.4,1.8-16.9,5.8-23.7,12.7c-6,6-9.8,12.8-11.9,21.1c-1.1,4.4-1.1,15.4,0,19.8c2.2,8.6,5.9,15.2,12.3,21.5c4.7,4.6,9.2,7.6,14.8,9.9c5.7,2.2,8.9,2.8,16.1,2.8c8.4,0,10.3-0.4,20.6-4.7c0.6-0.2,8.7,10.7,10,13.7c1,2,1,2.8,1,20.8c0,18,0,18.8-1,20.8c-1.3,3-9.4,13.9-10,13.7c-10.3-4.2-12.2-4.7-20.6-4.7c-9.4,0-15.9,1.8-23.6,6.6c-4.4,2.7-11.2,9.5-13.9,13.9c-4.8,7.7-6.6,14.1-6.6,23.6c0,7.4,0.6,10.5,3,16.6c4.3,10.9,13.9,20.4,24.9,24.7c5.7,2.2,8.9,2.8,16.1,2.8c9.4,0,15.9-1.8,23.6-6.6c4.4-2.7,11.2-9.5,13.9-13.9c4.8-7.7,6.6-14.1,6.6-23.6c0-8.4-0.4-10.3-4.7-20.6c-0.2-0.6,10.6-8.6,13.4-9.9c2.8-1.2,6.8-1.8,10.9-1.3c4.4,0.5,15.9,0.5,20.3,0c4.1-0.4,8.1,0.1,10.9,1.3c1.1,0.5,4.7,2.8,7.8,5.1c4.5,3.3,5.7,4.4,5.4,5c-3.7,8.5-5,15-4.7,22.4c0.6,11.7,4.9,21.2,13.4,29.6c6,5.9,12.7,9.6,20.9,11.6c4.4,1.1,15.4,1.1,19.8,0c8.4-2.1,15.1-5.9,21.3-12.1c6.1-6.2,9.9-12.9,12.1-21.3c1.1-4.4,1.1-15.4,0-19.8c-2.1-8.2-5.8-14.9-11.6-20.9c-8.4-8.5-17.8-12.8-29.6-13.4c-7.5-0.4-14,1-22.4,4.7c-0.6,0.3-1.7-1-5-5.4c-2.3-3.1-4.6-6.7-5.1-7.8c-1.2-2.8-1.7-6.8-1.3-11.2c0.5-4.8,0.5-15.1,0-19.9c-0.4-4.4,0.1-8.4,1.3-11.2c1.2-2.8,9.2-13.6,9.9-13.4c10.3,4.2,12.2,4.7,20.6,4.7c9.4,0,15.9-1.8,23.6-6.6c4.4-2.7,11.2-9.5,13.9-13.9c4.8-7.7,6.6-14.1,6.6-23.6c0-9.3-1.5-14.8-6.1-22.9c-2.7-4.7-9.6-11.7-14.4-14.6c-7.7-4.8-14.1-6.6-23.6-6.6s-15.9,1.8-23.6,6.6c-4.4,2.7-11.2,9.5-13.9,13.9c-4.8,7.7-6.6,14.1-6.6,23.6c0,8.4,0.4,10.3,4.7,20.6c0.2,0.6-10.7,8.7-13.7,10c-2,0.9-2.9,1-20.8,1s-18.8,0-20.8-1c-3-1.3-13.9-9.4-13.7-10c4.2-10.3,4.7-12.2,4.7-20.6c0-7.2-0.6-10.4-2.8-16.1c-2.2-5.5-5.3-10.2-9.7-14.6c-6.2-6.3-12.6-10.1-21-12.2C60.2,9.9,51,9.6,46.4,10.5z M62.9,18.3c4.6,1.3,7.8,2.6,11.2,4.9C88.7,32.8,94.6,50.5,88.7,67c-0.9,2.5-1.6,3.7-1.9,3.5c-0.3-0.2-5.3-3.7-11-7.9c-9.2-6.7-10.5-7.8-10.5-8.8c0-0.7-0.2-1.9-0.5-2.7c-0.5-1.4-0.4-1.5,2.9-5c4.1-4.4,7.2-8.5,8.4-11.1c0.8-1.8,0.8-2.1,0.2-2.7c-0.6-0.6-0.9-0.6-2.7,0.2c-2.7,1.2-6.7,4.2-11.1,8.4c-3.5,3.3-3.6,3.4-5,2.9c-3.7-1.3-7.6-0.2-10.8,3c-3.2,3.2-4.2,7.1-3,10.8c0.5,1.4,0.4,1.5-2.9,5c-4.1,4.4-7.2,8.5-8.4,11.1c-0.8,1.8-0.8,2.1-0.2,2.7c0.6,0.6,0.9,0.6,2.7-0.2c2.7-1.2,6.7-4.2,11.1-8.4c3.5-3.3,3.6-3.4,5-2.9c0.8,0.3,2,0.5,2.7,0.5c1.1,0,2.2,1.3,8.8,10.5c4.2,5.8,7.8,10.8,7.9,11.1c0.2,0.3-1,1-3.5,1.9c-16.5,6-34.2,0.1-43.8-14.6c-8.8-13.4-7.6-31.4,2.8-43.7c5.5-6.5,12.6-10.7,21.2-12.5C50.9,17.1,59.3,17.3,62.9,18.3z M210.7,18.3c7,1.9,12.5,5,17.3,9.8c14.4,14.4,14.4,37.6,0,52.1c-8.6,8.6-21,12.5-32.6,10.3c-4.5-0.9-10.2-3-9.7-3.7c0.1-0.3,3.7-5.2,7.9-11c6.7-9.1,7.8-10.5,8.8-10.5c0.7,0,1.9-0.2,2.7-0.5c1.4-0.5,1.5-0.4,5,2.9c4.4,4.1,8.5,7.2,11.1,8.4c1.8,0.8,2.1,0.8,2.7,0.2s0.6-0.9-0.2-2.7c-1.2-2.7-4.2-6.7-8.4-11.1c-3.3-3.5-3.4-3.6-2.9-5c1.3-3.7,0.2-7.6-3-10.8c-3.2-3.2-7.1-4.2-10.8-3c-1.4,0.5-1.5,0.4-5-2.9c-4.4-4.1-8.5-7.2-11.1-8.4c-1.8-0.8-2.1-0.8-2.7-0.2s-0.6,0.9,0.2,2.7c1.2,2.7,4.2,6.7,8.4,11.1c3.3,3.5,3.4,3.6,2.9,5c-0.3,0.8-0.5,2-0.5,2.7c0,1.1-1.3,2.2-10.4,8.8c-5.8,4.2-10.7,7.7-11,7.9c-0.7,0.5-2.8-4.9-3.7-9.7c-2-10.6,1-21.9,8.1-30.3c5.5-6.5,12.6-10.7,21.2-12.5C198.7,17.1,207.1,17.3,210.7,18.3z M60.7,165.6c4.8,0.9,10.2,3,9.7,3.7c-0.2,0.3-3.7,5.3-7.9,11c-6.7,9.1-7.8,10.4-8.8,10.4c-0.7,0-1.9,0.2-2.7,0.5c-1.4,0.5-1.5,0.4-5-2.9c-4.4-4.1-8.5-7.2-11.1-8.4c-1.8-0.8-2.1-0.8-2.7-0.2s-0.6,0.9,0.2,2.7c1.2,2.7,4.2,6.7,8.4,11.1c3.3,3.5,3.4,3.6,2.9,5c-2.8,7.9,5.9,16.5,13.8,13.8c1.4-0.5,1.5-0.4,5,2.9c4.4,4.1,8.5,7.2,11.1,8.4c1.8,0.8,2.1,0.8,2.7,0.2c0.6-0.6,0.6-0.9-0.2-2.7c-1.2-2.7-4.2-6.7-8.4-11.1c-3.3-3.5-3.4-3.6-2.9-5c0.3-0.8,0.5-2,0.5-2.7c0-1.1,1.3-2.2,10.5-8.8c5.8-4.2,10.7-7.8,11-7.9c0.7-0.4,2.8,5.2,3.7,9.7c2.2,11.6-1.7,24-10.3,32.6c-12.3,12.3-31.6,14.4-46,4.9c-14.5-9.6-20.5-27.2-14.7-43.6C25.4,172.6,43.3,162.3,60.7,165.6z M210.7,166.1c7,1.9,12.5,5,17.3,9.8c12.1,12.1,14.3,30.8,5.4,45.3c-10.8,17.6-34.2,23-51.4,11.8c-14.7-9.6-20.6-27.3-14.6-43.8c0.9-2.5,1.6-3.7,1.9-3.5c0.3,0.2,5.3,3.7,11.1,7.9c9.2,6.7,10.5,7.8,10.5,8.8c0,0.7,0.2,1.9,0.5,2.7c0.5,1.4,0.4,1.5-3,5.2c-4,4.2-7.3,8.7-8.4,11.3c-0.6,1.5-0.6,1.8,0,2.4c0.6,0.6,0.9,0.6,2.7-0.2c2.7-1.2,6.7-4.2,11.1-8.4c3.5-3.3,3.6-3.4,5-2.9c3.7,1.3,7.6,0.2,10.8-3c3.2-3.2,4.2-7.1,3-10.8c-0.5-1.4-0.4-1.5,2.9-5c4.1-4.4,7.2-8.5,8.4-11.1c0.8-1.8,0.8-2.1,0.2-2.7c-0.6-0.6-0.9-0.6-2.4,0c-2.5,1.1-7,4.4-11.3,8.4c-3.6,3.4-3.8,3.5-5.2,3c-0.8-0.3-2-0.5-2.7-0.5c-1.1,0-2.2-1.3-8.8-10.5c-4.2-5.8-7.8-10.7-7.9-11c-0.4-0.6,5-2.7,9.4-3.7C198.7,164.9,207.1,165.1,210.7,166.1z"/></g></g></g>
</svg>

After

Width:  |  Height:  |  Size: 4.7 KiB

BIN
assets/images/rtimelogo.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 42 KiB

View File

@ -10,6 +10,9 @@
xml:space="preserve"
sodipodi:docname="rtimelogo.svg"
inkscape:version="1.4.2 (ebf0e940d0, 2025-05-08)"
inkscape:export-filename="rtimelogo.png"
inkscape:export-xdpi="96"
inkscape:export-ydpi="96"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:xlink="http://www.w3.org/1999/xlink"
@ -24,15 +27,16 @@
inkscape:pagecheckerboard="0"
inkscape:deskcolor="#d1d1d1"
inkscape:document-units="mm"
inkscape:zoom="1.060245"
inkscape:cx="200.42536"
inkscape:cy="275.40803"
inkscape:window-width="1916"
inkscape:window-height="1025"
inkscape:zoom="1.0080514"
inkscape:cx="95.233236"
inkscape:cy="370.51681"
inkscape:window-width="1920"
inkscape:window-height="1080"
inkscape:window-x="1920"
inkscape:window-y="26"
inkscape:window-y="0"
inkscape:window-maximized="1"
inkscape:current-layer="layer1" /><defs
inkscape:current-layer="g1"
inkscape:export-bgcolor="#28343cff" /><defs
id="defs1"><linearGradient
id="swatch23"><stop
style="stop-color:#000000;stop-opacity:1;"
@ -44,15 +48,7 @@
id="stop22" /></linearGradient></defs><g
id="g1"
transform="matrix(1.5687373,0,0,1.5687373,-98.160636,-174.17106)"><g
id="layer1"><path
style="fill:none;fill-opacity:1;stroke:#7d7d7d;stroke-width:5.543;stroke-linecap:round;stroke-dasharray:none;stroke-opacity:1"
d="m 105.75,125.90625 v 6.1875"
id="path4" /><circle
style="fill:none;fill-opacity:0.997107;stroke:#000000;stroke-width:4.909;stroke-dasharray:none;stroke-opacity:1"
id="path1"
cx="105.75"
cy="159"
r="25.6875" /><image
id="layer1"><image
width="52.916668"
height="52.916668"
preserveAspectRatio="none"
@ -60,24 +56,34 @@
id="image1"
x="5.1867809"
y="239.81689"
style="display:none" /><path
style="fill:#fad300;fill-opacity:1;stroke:#000000;stroke-width:5.023;stroke-linecap:round;stroke-miterlimit:5;stroke-dasharray:1.25575, 1.25575;stroke-dashoffset:0;stroke-opacity:1"
d="m 123.96466,139.67569 2.51906,-2.58536"
style="display:none" /></g><g
id="g2"
transform="translate(-1.4625932,0.3181559)"><path
style="fill:none;fill-opacity:1;stroke:#7d7d7d;stroke-width:6.4264;stroke-linecap:round;stroke-dasharray:none;stroke-opacity:1"
d="m 107.21261,121.07834 v 7.17361"
id="path4" /><circle
style="fill:none;fill-opacity:0.997107;stroke:#000000;stroke-width:5.69136;stroke-dasharray:none;stroke-opacity:1"
id="path1"
cx="107.21259"
cy="159.4463"
r="29.781376" /><path
style="fill:#fad300;fill-opacity:1;stroke:#000000;stroke-width:5.82353;stroke-linecap:round;stroke-miterlimit:5;stroke-dasharray:1.45588, 1.45588;stroke-dashoffset:0;stroke-opacity:1"
d="m 128.33018,137.04224 2.92053,-2.99739"
id="path18" /><circle
style="fill:none;fill-opacity:0.997107;stroke:#7d7d7d;stroke-width:4.023;stroke-dasharray:1.00575, 2.0115;stroke-dashoffset:0;stroke-opacity:1"
style="fill:none;fill-opacity:0.997107;stroke:#7d7d7d;stroke-width:4.66415;stroke-dasharray:1.16604, 2.33208;stroke-dashoffset:0;stroke-opacity:1"
id="circle6"
cx="105.74992"
cy="159.00005"
r="20.527113" /><rect
style="fill:#fad300;stroke:#000000;stroke-width:5.19697;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:0.2;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:normal"
cx="107.21252"
cy="159.44637"
r="23.798567" /><rect
style="fill:#fad300;stroke:#000000;stroke-width:6.02522;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:0.2;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:normal"
id="rect1"
width="9.8775606"
height="1.4293942"
x="100.81123"
y="123.86299" /></g><g
id="g191"><g
width="11.451771"
height="1.6572001"
x="101.48674"
y="118.70944" /><g
id="layer4"
style="display:inline"><path
style="display:inline"
transform="matrix(1.1593723,0,0,1.1593723,-15.391021,-24.893883)"><path
style="fill:#fad300;fill-opacity:1;stroke:none;stroke-width:4.43596;stroke-dasharray:none;stroke-opacity:1"
d="m 107.07629,157.6057 c 0,0 -0.9363,0.34423 3.10345,-0.74145 4.14209,-1.11318 15.49588,-0.13884 17.35688,0.21637 1.86099,0.35524 0.30569,2.51083 0.30569,2.51083 0,0 -13.04413,2.86324 -15.43783,1.84211 -2.71253,-1.15717 -3.98506,-1.11315 -5.50091,-1.0838 -0.17832,-1.71281 0.17272,-2.74405 0.17272,-2.74405 z"
id="prop" /><path

Before

Width:  |  Height:  |  Size: 10 KiB

After

Width:  |  Height:  |  Size: 11 KiB

View File

@ -427,7 +427,7 @@
isa = XCBuildConfiguration;
buildSettings = {
ALWAYS_SEARCH_USER_PATHS = NO;
ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = YES;
ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = AppIcon;
CLANG_ANALYZER_NONNULL = YES;
CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
CLANG_CXX_LIBRARY = "libc++";
@ -484,7 +484,7 @@
isa = XCBuildConfiguration;
buildSettings = {
ALWAYS_SEARCH_USER_PATHS = NO;
ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = YES;
ASSETCATALOG_COMPILER_GENERATE_SWIFT_ASSET_SYMBOL_EXTENSIONS = AppIcon;
CLANG_ANALYZER_NONNULL = YES;
CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
CLANG_CXX_LIBRARY = "libc++";

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

After

Width:  |  Height:  |  Size: 112 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 295 B

After

Width:  |  Height:  |  Size: 828 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 406 B

After

Width:  |  Height:  |  Size: 2.0 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 450 B

After

Width:  |  Height:  |  Size: 3.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 282 B

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 462 B

After

Width:  |  Height:  |  Size: 3.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 704 B

After

Width:  |  Height:  |  Size: 5.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 406 B

After

Width:  |  Height:  |  Size: 2.0 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 586 B

After

Width:  |  Height:  |  Size: 4.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 862 B

After

Width:  |  Height:  |  Size: 7.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 862 B

After

Width:  |  Height:  |  Size: 7.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

After

Width:  |  Height:  |  Size: 13 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 762 B

After

Width:  |  Height:  |  Size: 4.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

After

Width:  |  Height:  |  Size: 10 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.4 KiB

After

Width:  |  Height:  |  Size: 12 KiB

View File

@ -210,5 +210,6 @@
"customColorSetting": "Button Color",
"selectButtonColor": "Select Button Primary Color",
"pickColor": "Pick a color",
"select": "Select"
"select": "Select",
"resetColor": "Reset Color"
}

View File

@ -210,5 +210,6 @@
"customColorSetting": "Couleur des Boutons",
"selectButtonColor": "Sélectionner la couleur principale des boutons",
"pickColor": "Choisir une couleur",
"select": "Sélectionner"
"select": "Sélectionner",
"resetColor": "Réinitialiser la couleur"
}

View File

@ -736,6 +736,12 @@ abstract class AppLocalizations {
/// In en, this message translates to:
/// **'Select'**
String get select;
/// No description provided for @resetColor.
///
/// In en, this message translates to:
/// **'Reset Color'**
String get resetColor;
}
class _AppLocalizationsDelegate extends LocalizationsDelegate<AppLocalizations> {

View File

@ -354,4 +354,7 @@ class AppLocalizationsEn extends AppLocalizations {
@override
String get select => 'Select';
@override
String get resetColor => 'Reset Color';
}

View File

@ -354,4 +354,7 @@ class AppLocalizationsFr extends AppLocalizations {
@override
String get select => 'Sélectionner';
@override
String get resetColor => 'Réinitialiser la couleur';
}

View File

@ -38,7 +38,6 @@ class _MyAppState extends State<MyApp> {
Widget build(BuildContext context) {
return Consumer3<LocaleProvider, ThemeProvider, ColorProvider>(
builder: (context, localeProvider, themeProvider, colorProvider, child) {
// customAccentColor est toujours là si tu veux l'utiliser pour d'autres éléments
final customAccentColor = colorProvider.accentColor;
return MaterialApp(
@ -55,32 +54,32 @@ class _MyAppState extends State<MyApp> {
Locale('fr', ''),
],
theme: ThemeData(
primaryColor: Colors.white,
primaryColor: Colors.yellow[700],
colorScheme: ColorScheme.light(
primary: Colors.blue, // Couleur primaire fixe pour le mode clair
primary: Colors.yellow[700]!,
secondary: Colors.teal.shade400,
surface: Colors.white,
background: Colors.white,
error: Colors.red.shade700,
onPrimary: Colors.white,
onPrimary: Colors.black87,
onSecondary: Colors.white,
onSurface: Colors.black87,
onBackground: Colors.black87,
),
scaffoldBackgroundColor: Colors.white,
appBarTheme: const AppBarTheme(
backgroundColor: Color(0xFFF5F5F5),
appBarTheme: AppBarTheme(
backgroundColor: Colors.yellow[700],
foregroundColor: Colors.black87,
elevation: 0.5,
iconTheme: IconThemeData(color: Colors.black87),
titleTextStyle: TextStyle(
iconTheme: const IconThemeData(color: Colors.black87),
titleTextStyle: const TextStyle(
color: Colors.black,
fontSize: 20,
fontWeight: FontWeight.bold,
),
),
floatingActionButtonTheme: FloatingActionButtonThemeData(
backgroundColor: customAccentColor,
backgroundColor: customAccentColor,
foregroundColor: Colors.white,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(30.0),

View File

@ -224,8 +224,10 @@ class _BatteryDetailPageState extends State<BatteryDetailPage> {
),
if (_isEditing) ...[
const SizedBox(height: 15),
Row(
mainAxisAlignment: MainAxisAlignment.center,
Wrap(
alignment: WrapAlignment.center,
spacing: 10.0,
runSpacing: 10.0,
children: [
ElevatedButton.icon(
onPressed: () => _pickImage(ImageSource.camera),
@ -233,17 +235,16 @@ class _BatteryDetailPageState extends State<BatteryDetailPage> {
label: Text(l10n.takePhoto),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.blueGrey[700],
foregroundColor: Colors.white, // Texte en blanc
foregroundColor: Colors.white,
),
),
const SizedBox(width: 10),
ElevatedButton.icon(
onPressed: () => _pickImage(ImageSource.gallery),
icon: const Icon(Icons.photo_library),
label: Text(l10n.chooseFromGallery),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.blueGrey[700],
foregroundColor: Colors.white, // Texte en blanc
foregroundColor: Colors.white,
),
),
],
@ -325,13 +326,13 @@ class _BatteryDetailPageState extends State<BatteryDetailPage> {
child: ElevatedButton(
onPressed: _saveBattery,
style: Theme.of(context).elevatedButtonTheme.style?.copyWith(
padding: MaterialStateProperty.all(
const EdgeInsets.symmetric(horizontal: 40, vertical: 15)),
shape: MaterialStateProperty.all(RoundedRectangleBorder(
borderRadius: BorderRadius.circular(10),
)),
foregroundColor: MaterialStateProperty.all(Colors.white), // Texte en blanc pour le bouton Save Changes
),
padding: MaterialStateProperty.all(
const EdgeInsets.symmetric(horizontal: 40, vertical: 15)),
shape: MaterialStateProperty.all(RoundedRectangleBorder(
borderRadius: BorderRadius.circular(10),
)),
foregroundColor: MaterialStateProperty.all(Colors.white),
),
child: Text(
l10n.saveChanges,
style: const TextStyle(fontSize: 18, fontWeight: FontWeight.bold),
@ -366,7 +367,7 @@ class _BatteryDetailPageState extends State<BatteryDetailPage> {
child: ListTile(
contentPadding: const EdgeInsets.symmetric(
horizontal: 20, vertical: 12),
leading: Icon(Icons.flight_takeoff,
leading: const Icon(Icons.flight_takeoff,
color: Colors.orangeAccent, size: 32),
title: Text(
'${flight.name} - ${flightDate.toLocal().toString().split(' ')[0]}',

View File

@ -222,8 +222,10 @@ class _DroneDetailPageState extends State<DroneDetailPage> {
),
if (_isEditing) ...[
const SizedBox(height: 15),
Row(
mainAxisAlignment: MainAxisAlignment.center,
Wrap(
alignment: WrapAlignment.center,
spacing: 10.0,
runSpacing: 10.0,
children: [
ElevatedButton.icon(
onPressed: () => _pickImage(ImageSource.camera),
@ -231,17 +233,16 @@ class _DroneDetailPageState extends State<DroneDetailPage> {
label: Text(l10n.takePhoto),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.blueGrey[700],
foregroundColor: Colors.white, // Texte en blanc
foregroundColor: Colors.white,
),
),
const SizedBox(width: 10),
ElevatedButton.icon(
onPressed: () => _pickImage(ImageSource.gallery),
icon: const Icon(Icons.photo_library),
label: Text(l10n.chooseFromGallery),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.blueGrey[700],
foregroundColor: Colors.white, // Texte en blanc
foregroundColor: Colors.white,
),
),
],
@ -279,13 +280,13 @@ class _DroneDetailPageState extends State<DroneDetailPage> {
child: ElevatedButton(
onPressed: _saveDrone,
style: Theme.of(context).elevatedButtonTheme.style?.copyWith(
padding: MaterialStateProperty.all(
const EdgeInsets.symmetric(horizontal: 40, vertical: 15)),
shape: MaterialStateProperty.all(RoundedRectangleBorder(
borderRadius: BorderRadius.circular(10),
)),
foregroundColor: MaterialStateProperty.all(Colors.white), // Texte en blanc pour le bouton Save Changes
),
padding: MaterialStateProperty.all(
const EdgeInsets.symmetric(horizontal: 40, vertical: 15)),
shape: MaterialStateProperty.all(RoundedRectangleBorder(
borderRadius: BorderRadius.circular(10),
)),
foregroundColor: MaterialStateProperty.all(Colors.white),
),
child: Text(
l10n.saveChanges,
style: const TextStyle(fontSize: 18, fontWeight: FontWeight.bold),

View File

@ -15,9 +15,8 @@ import 'package:rtime/db/db_helper.dart';
import 'package:rtime/pages/flight_detail_page.dart';
import 'package:provider/provider.dart';
import 'package:rtime/providers/color_provider.dart';
import 'package:rtime/widgets/page_transition_animations.dart';
import 'package:flutter_svg/flutter_svg.dart';
class HomePage extends StatefulWidget {
const HomePage({super.key});
@ -50,7 +49,6 @@ class _HomePageState extends State<HomePage> {
final l10n = AppLocalizations.of(context)!;
final customAccentColor = Provider.of<ColorProvider>(context).accentColor;
return Scaffold(
backgroundColor: Theme.of(context).primaryColor,
body: RefreshIndicator(
@ -67,6 +65,13 @@ class _HomePageState extends State<HomePage> {
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
SvgPicture.asset(
'assets/images/rtimelogo.svg',
height: 48,
width: 48,
colorFilter: ColorFilter.mode(customAccentColor, BlendMode.srcIn),
),
const SizedBox(width: 8),
Text(
l10n.appTitle,
style: TextStyle(
@ -76,6 +81,7 @@ class _HomePageState extends State<HomePage> {
fontFamily: 'Montserrat',
),
),
const Spacer(),
IconButton(
icon:
const Icon(Icons.settings, size: 30, color: Colors.white70),
@ -91,7 +97,6 @@ class _HomePageState extends State<HomePage> {
),
const SizedBox(height: 30),
Text(
l10n.yourDrones,
style: Theme.of(context).textTheme.headlineSmall,
@ -130,7 +135,7 @@ class _HomePageState extends State<HomePage> {
const SizedBox(height: 10),
Text(l10n.addDrone,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.titleSmall!.copyWith(color: Colors.white)), // Texte blanc
style: Theme.of(context).textTheme.titleSmall!.copyWith(color: Colors.white)),
],
),
),
@ -164,7 +169,7 @@ class _HomePageState extends State<HomePage> {
const SizedBox(height: 10),
Text(l10n.addDrone,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.titleSmall!.copyWith(color: Colors.white)), // Texte blanc
style: Theme.of(context).textTheme.titleSmall!.copyWith(color: Colors.white)),
],
),
),
@ -194,7 +199,6 @@ class _HomePageState extends State<HomePage> {
const Divider(
height: 50, thickness: 2, indent: 0, endIndent: 0, color: Colors.white10),
Text(
l10n.yourBatteries,
style: Theme.of(context).textTheme.headlineSmall,
@ -233,7 +237,7 @@ class _HomePageState extends State<HomePage> {
const SizedBox(height: 10),
Text(l10n.addBattery,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.titleSmall!.copyWith(color: Colors.white)), // Texte blanc
style: Theme.of(context).textTheme.titleSmall!.copyWith(color: Colors.white)),
],
),
),
@ -267,7 +271,7 @@ class _HomePageState extends State<HomePage> {
const SizedBox(height: 10),
Text(l10n.addBattery,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.titleSmall!.copyWith(color: Colors.white)), // Texte blanc
style: Theme.of(context).textTheme.titleSmall!.copyWith(color: Colors.white)),
],
),
),
@ -297,7 +301,6 @@ class _HomePageState extends State<HomePage> {
const Divider(
height: 50, thickness: 2, indent: 0, endIndent: 0, color: Colors.white10),
Text(
l10n.latestFlights,
style: Theme.of(context).textTheme.headlineSmall,
@ -336,7 +339,8 @@ class _HomePageState extends State<HomePage> {
contentPadding: const EdgeInsets.symmetric(
horizontal: 20, vertical: 12),
leading: Icon(Icons.flight_takeoff,
color: Colors.orangeAccent, size: 32),
color: customAccentColor, // Use the user's accent color here
size: 32),
title: Text(
'${flight.name} - ${DateTime.fromMillisecondsSinceEpoch(flight.startTimestamp * 1000).toLocal().toString().split(' ')[0]}',
style: Theme.of(context).textTheme.titleMedium,
@ -371,9 +375,9 @@ class _HomePageState extends State<HomePage> {
},
label: Text(
l10n.newFlight,
style: const TextStyle(fontSize: 18, fontWeight: FontWeight.bold, color: Colors.white), // Texte blanc
style: const TextStyle(fontSize: 18, fontWeight: FontWeight.bold, color: Colors.white),
),
icon: const Icon(Icons.add_to_photos, size: 28, color: Colors.white), // Icône blanche
icon: const Icon(Icons.add_to_photos, size: 28, color: Colors.white),
),
floatingActionButtonLocation: FloatingActionButtonLocation.centerFloat,
);

View File

@ -107,8 +107,10 @@ class _NewBatteryPageState extends State<NewBatteryPage> {
Text(l10n.batteryImage,
style: Theme.of(context).textTheme.titleSmall),
const SizedBox(height: 15),
Row(
mainAxisAlignment: MainAxisAlignment.center,
Wrap(
alignment: WrapAlignment.center,
spacing: 10.0,
runSpacing: 10.0,
children: [
ElevatedButton.icon(
onPressed: () => _pickImage(ImageSource.camera),
@ -116,17 +118,16 @@ class _NewBatteryPageState extends State<NewBatteryPage> {
label: Text(l10n.takePhoto),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.blueGrey[700],
foregroundColor: Colors.white, // Set text color to white
foregroundColor: Colors.white,
),
),
const SizedBox(width: 10),
ElevatedButton.icon(
onPressed: () => _pickImage(ImageSource.gallery),
icon: const Icon(Icons.photo_library),
label: Text(l10n.chooseFromGallery),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.blueGrey[700],
foregroundColor: Colors.white, // Set text color to white
foregroundColor: Colors.white,
),
),
],
@ -211,7 +212,7 @@ class _NewBatteryPageState extends State<NewBatteryPage> {
shape: MaterialStateProperty.all(RoundedRectangleBorder(
borderRadius: BorderRadius.circular(10),
)),
foregroundColor: MaterialStateProperty.all(Colors.white), // Set text color to white
foregroundColor: MaterialStateProperty.all(Colors.white),
),
child: Text(
l10n.saveBattery,

View File

@ -101,8 +101,10 @@ class _NewDronePageState extends State<NewDronePage> {
Text(l10n.droneImage,
style: Theme.of(context).textTheme.titleSmall),
const SizedBox(height: 15),
Row(
mainAxisAlignment: MainAxisAlignment.center,
Wrap(
alignment: WrapAlignment.center,
spacing: 10.0,
runSpacing: 10.0,
children: [
ElevatedButton.icon(
onPressed: () => _pickImage(ImageSource.camera),
@ -110,17 +112,16 @@ class _NewDronePageState extends State<NewDronePage> {
label: Text(l10n.takePhoto),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.blueGrey[700],
foregroundColor: Colors.white, // Set text color to white
foregroundColor: Colors.white,
),
),
const SizedBox(width: 10),
ElevatedButton.icon(
onPressed: () => _pickImage(ImageSource.gallery),
icon: const Icon(Icons.photo_library),
label: Text(l10n.chooseFromGallery),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.blueGrey[700],
foregroundColor: Colors.white, // Set text color to white
foregroundColor: Colors.white,
),
),
],
@ -159,7 +160,7 @@ class _NewDronePageState extends State<NewDronePage> {
shape: MaterialStateProperty.all(RoundedRectangleBorder(
borderRadius: BorderRadius.circular(10),
)),
foregroundColor: MaterialStateProperty.all(Colors.white), // Set text color to white
foregroundColor: MaterialStateProperty.all(Colors.white),
),
child: Text(
l10n.saveDrone,

View File

@ -27,7 +27,7 @@ class _NewFlightPageState extends State<NewFlightPage> {
bool isFlightActive = false;
Stopwatch stopwatch = Stopwatch();
Timer? timer;
String formattedTime = '00:00:00';
String formattedTime = '00:00';
int? flightStartTime;
bool useGpsLocation = false;
@ -226,7 +226,7 @@ class _NewFlightPageState extends State<NewFlightPage> {
setState(() {
isFlightActive = false;
stopwatch.reset();
formattedTime = '00:00:00';
formattedTime = '00:00';
selectedDrone = null;
selectedBattery = null;
currentPosition = null;
@ -243,10 +243,16 @@ class _NewFlightPageState extends State<NewFlightPage> {
String _formatDuration(Duration duration) {
String twoDigits(int n) => n.toString().padLeft(2, '0');
String hours = twoDigits(duration.inHours);
String minutes = twoDigits(duration.inMinutes.remainder(60));
String seconds = twoDigits(duration.inSeconds.remainder(60));
return '$hours:$minutes:$seconds';
if (duration.inHours > 0) {
String hours = twoDigits(duration.inHours);
String minutes = twoDigits(duration.inMinutes.remainder(60));
String seconds = twoDigits(duration.inSeconds.remainder(60));
return '$hours:$minutes:$seconds';
} else {
String minutes = twoDigits(duration.inMinutes.remainder(60));
String seconds = twoDigits(duration.inSeconds.remainder(60));
return '$minutes:$seconds';
}
}
@override
@ -312,7 +318,7 @@ class _NewFlightPageState extends State<NewFlightPage> {
items: drones.map<DropdownMenuItem<Drone>>((Drone drone) {
return DropdownMenuItem<Drone>(
value: drone,
child: Text(drone.name, style: Theme.of(context).textTheme.titleMedium!.copyWith(color: Colors.white)), // Texte blanc
child: Text(drone.name, style: Theme.of(context).textTheme.titleMedium!.copyWith(color: Colors.white)),
);
}).toList(),
),
@ -368,7 +374,7 @@ class _NewFlightPageState extends State<NewFlightPage> {
items: batteries.map<DropdownMenuItem<Battery>>((Battery battery) {
return DropdownMenuItem<Battery>(
value: battery,
child: Text('${battery.name} (${battery.voltage}V)', style: Theme.of(context).textTheme.titleMedium!.copyWith(color: Colors.white)), // Texte blanc
child: Text('${battery.name} (${battery.voltage}V)', style: Theme.of(context).textTheme.titleMedium!.copyWith(color: Colors.white)),
);
}).toList(),
),
@ -482,10 +488,10 @@ class _NewFlightPageState extends State<NewFlightPage> {
child: isFlightActive
? ElevatedButton.icon(
onPressed: _stopFlight,
icon: const Icon(Icons.stop, size: 30, color: Colors.white), // Icône blanche
icon: const Icon(Icons.stop, size: 30, color: Colors.white),
label: Text(
l10n.stopFlight,
style: const TextStyle(fontSize: 22, fontWeight: FontWeight.bold, color: Colors.white), // Texte blanc
style: const TextStyle(fontSize: 22, fontWeight: FontWeight.bold, color: Colors.white),
),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.redAccent,
@ -508,10 +514,10 @@ class _NewFlightPageState extends State<NewFlightPage> {
)
: ElevatedButton.icon(
onPressed: _startFlight,
icon: const Icon(Icons.flight_takeoff, size: 30, color: Colors.white), // Icône blanche
icon: const Icon(Icons.flight_takeoff, size: 30, color: Colors.white),
label: Text(
l10n.startFlight,
style: const TextStyle(fontSize: 22, fontWeight: FontWeight.bold, color: Colors.white), // Texte blanc
style: const TextStyle(fontSize: 22, fontWeight: FontWeight.bold, color: Colors.white),
),
style: ElevatedButton.styleFrom(
backgroundColor: colorProvider.accentColor,

View File

@ -1,4 +1,3 @@
// pages/settings_page.dart
import 'package:flutter/material.dart';
import 'package:rtime/l10n/app_localizations.dart';
import 'package:provider/provider.dart';
@ -15,13 +14,11 @@ class SettingsPage extends StatefulWidget {
}
class _SettingsPageState extends State<SettingsPage> {
// Initialize with a default color or the current accent color
late Color _pickerColor; // Use late to initialize in initState
late Color _pickerColor;
@override
void initState() {
super.initState();
// Initialize _pickerColor with the current accent color from the ColorProvider
_pickerColor = Provider.of<ColorProvider>(context, listen: false).accentColor;
}
@ -36,9 +33,6 @@ class _SettingsPageState extends State<SettingsPage> {
final themeProvider = Provider.of<ThemeProvider>(context);
final colorProvider = Provider.of<ColorProvider>(context);
// REMOVE THIS LINE:
// _pickerColor = colorProvider.accentColor;
return Scaffold(
backgroundColor: Theme.of(context).colorScheme.background,
appBar: AppBar(
@ -63,9 +57,9 @@ class _SettingsPageState extends State<SettingsPage> {
child: Column(
children: [
ListTile(
title: Text(l10n.english, style: Theme.of(context).textTheme.titleMedium),
title: Text('English', style: Theme.of(context).textTheme.titleMedium),
trailing: currentLocale.languageCode == 'en'
? Icon(Icons.check_circle, color: Theme.of(context).colorScheme.secondary)
? Icon(Icons.check_circle, color: colorProvider.accentColor)
: null,
onTap: () {
final localeProvider = Provider.of<LocaleProvider>(context, listen: false);
@ -73,9 +67,9 @@ class _SettingsPageState extends State<SettingsPage> {
},
),
ListTile(
title: Text(l10n.french, style: Theme.of(context).textTheme.titleMedium),
title: Text('Français', style: Theme.of(context).textTheme.titleMedium),
trailing: currentLocale.languageCode == 'fr'
? Icon(Icons.check_circle, color: Theme.of(context).colorScheme.secondary)
? Icon(Icons.check_circle, color: colorProvider.accentColor)
: null,
onTap: () {
final localeProvider = Provider.of<LocaleProvider>(context, listen: false);
@ -98,7 +92,7 @@ class _SettingsPageState extends State<SettingsPage> {
ListTile(
title: Text(l10n.themeSystem, style: Theme.of(context).textTheme.titleMedium),
trailing: themeProvider.themeMode == ThemeMode.system
? Icon(Icons.check_circle, color: Theme.of(context).colorScheme.secondary)
? Icon(Icons.check_circle, color: colorProvider.accentColor)
: null,
onTap: () {
themeProvider.setThemeMode(ThemeMode.system);
@ -107,7 +101,7 @@ class _SettingsPageState extends State<SettingsPage> {
ListTile(
title: Text(l10n.themeLight, style: Theme.of(context).textTheme.titleMedium),
trailing: themeProvider.themeMode == ThemeMode.light
? Icon(Icons.check_circle, color: Theme.of(context).colorScheme.secondary)
? Icon(Icons.check_circle, color: colorProvider.accentColor)
: null,
onTap: () {
themeProvider.setThemeMode(ThemeMode.light);
@ -116,7 +110,7 @@ class _SettingsPageState extends State<SettingsPage> {
ListTile(
title: Text(l10n.themeDark, style: Theme.of(context).textTheme.titleMedium),
trailing: themeProvider.themeMode == ThemeMode.dark
? Icon(Icons.check_circle, color: Theme.of(context).colorScheme.secondary)
? Icon(Icons.check_circle, color: colorProvider.accentColor)
: null,
onTap: () {
themeProvider.setThemeMode(ThemeMode.dark);
@ -133,61 +127,72 @@ class _SettingsPageState extends State<SettingsPage> {
const SizedBox(height: 10),
Card(
color: Theme.of(context).cardTheme.color,
child: ListTile(
title: Text(
l10n.selectButtonColor,
style: Theme.of(context).textTheme.titleMedium,
),
trailing: Container(
width: 30,
height: 30,
decoration: BoxDecoration(
// This should always reflect the current accent color from the provider
color: colorProvider.accentColor,
shape: BoxShape.circle,
border: Border.all(color: Theme.of(context).dividerColor),
),
),
onTap: () {
// When the dialog is opened, ensure _pickerColor reflects the *current* accent color
// so that the color picker starts with the color currently in use.
setState(() {
_pickerColor = colorProvider.accentColor;
});
showDialog(
context: context,
builder: (BuildContext context) {
return AlertDialog(
title: Text(l10n.pickColor),
content: SingleChildScrollView(
child: ColorPicker(
pickerColor: _pickerColor,
onColorChanged: _onColorChanged,
pickerAreaHeightPercent: 0.8,
enableAlpha: false,
displayThumbColor: true,
paletteType: PaletteType.hsv,
),
),
actions: <Widget>[
TextButton(
child: Text(l10n.cancel),
onPressed: () {
Navigator.of(context).pop();
},
),
TextButton(
child: Text(l10n.select),
onPressed: () {
colorProvider.setAccentColor(_pickerColor);
Navigator.of(context).pop();
},
),
],
child: Column(
children: [
ListTile(
title: Text(
l10n.selectButtonColor,
style: Theme.of(context).textTheme.titleMedium,
),
trailing: Container(
width: 30,
height: 30,
decoration: BoxDecoration(
color: colorProvider.accentColor,
shape: BoxShape.circle,
border: Border.all(color: Theme.of(context).dividerColor),
),
),
onTap: () {
setState(() {
_pickerColor = colorProvider.accentColor;
});
showDialog(
context: context,
builder: (BuildContext context) {
return AlertDialog(
title: Text(l10n.pickColor),
content: SingleChildScrollView(
child: ColorPicker(
pickerColor: _pickerColor,
onColorChanged: _onColorChanged,
pickerAreaHeightPercent: 0.8,
enableAlpha: false,
displayThumbColor: true,
paletteType: PaletteType.hsv,
),
),
actions: <Widget>[
TextButton(
child: Text(l10n.cancel),
onPressed: () {
Navigator.of(context).pop();
},
),
TextButton(
child: Text(l10n.select),
onPressed: () {
colorProvider.setAccentColor(_pickerColor);
Navigator.of(context).pop();
},
),
],
);
},
);
},
);
},
),
ListTile(
title: Text(l10n.resetColor, style: Theme.of(context).textTheme.titleMedium),
trailing: const Icon(Icons.restore),
onTap: () {
colorProvider.setAccentColor(Colors.yellow[700]!);
setState(() {
_pickerColor = Colors.yellow[700]!;
});
},
),
],
),
),
],

View File

@ -1,6 +1,9 @@
import 'package:flutter/material.dart';
import 'package:rtime/models/battery.dart';
import 'package:rtime/images_manager.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:provider/provider.dart';
import 'package:rtime/providers/color_provider.dart';
class BatteryCard extends StatelessWidget {
final Battery battery;
@ -14,10 +17,13 @@ class BatteryCard extends StatelessWidget {
@override
Widget build(BuildContext context) {
final BorderRadius cardBorderRadius =
Theme.of(context).cardTheme.shape is RoundedRectangleBorder
? (Theme.of(context).cardTheme.shape as RoundedRectangleBorder).borderRadius as BorderRadius
: BorderRadius.circular(12);
final colorProvider = Provider.of<ColorProvider>(context);
final accentColor = colorProvider.accentColor;
final ShapeBorder? cardShape = Theme.of(context).cardTheme.shape;
final BorderRadius cardBorderRadius = (cardShape is RoundedRectangleBorder)
? (cardShape).borderRadius as BorderRadius
: BorderRadius.circular(12);
return Card(
margin: const EdgeInsets.only(right: 16),
@ -34,23 +40,21 @@ class BatteryCard extends StatelessWidget {
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Container(
SizedBox(
width: 80,
height: 80,
decoration: BoxDecoration(
color: Theme.of(context).brightness == Brightness.dark
? Colors.blueGrey[700]
: Colors.grey[200],
borderRadius: BorderRadius.circular(12),
),
child: battery.imageUuid != null && battery.imageUuid!.isNotEmpty
? FutureBuilder<Image?>(
future: ImagesManager.instance.loadImage(battery.imageUuid!),
builder: (context, snapshot) {
if (snapshot.connectionState == ConnectionState.waiting) {
return const Center(child: CircularProgressIndicator(color: Colors.tealAccent));
return Center(child: CircularProgressIndicator(color: accentColor));
} else if (snapshot.hasError || !snapshot.hasData || snapshot.data == null) {
return Icon(Icons.broken_image, size: 50, color: Colors.blueGrey[400]);
return Icon(
Icons.battery_charging_full,
size: 80,
color: accentColor,
);
} else {
return ClipRRect(
borderRadius: BorderRadius.circular(12),
@ -59,7 +63,11 @@ class BatteryCard extends StatelessWidget {
}
},
)
: Icon(Icons.battery_charging_full, size: 50, color: Theme.of(context).brightness == Brightness.dark ? Colors.tealAccent : Colors.green.shade400),
: Icon(
Icons.battery_charging_full,
size: 80,
color: accentColor,
),
),
const SizedBox(height: 10),
Text(

View File

@ -1,6 +1,9 @@
import 'package:flutter/material.dart';
import 'package:rtime/models/drone.dart';
import 'package:rtime/images_manager.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:provider/provider.dart';
import 'package:rtime/providers/color_provider.dart';
class DroneCard extends StatelessWidget {
final Drone drone;
@ -14,6 +17,8 @@ class DroneCard extends StatelessWidget {
@override
Widget build(BuildContext context) {
final colorProvider = Provider.of<ColorProvider>(context);
final accentColor = colorProvider.accentColor;
final BorderRadius cardBorderRadius =
Theme.of(context).cardTheme.shape is RoundedRectangleBorder
@ -22,10 +27,8 @@ class DroneCard extends StatelessWidget {
return Card(
margin: const EdgeInsets.only(right: 16),
child: InkWell(
onTap: onTap,
borderRadius: cardBorderRadius,
child: ClipRRect(
borderRadius: cardBorderRadius,
@ -36,23 +39,22 @@ class DroneCard extends StatelessWidget {
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Container(
SizedBox(
width: 80,
height: 80,
decoration: BoxDecoration(
color: Theme.of(context).brightness == Brightness.dark
? Colors.blueGrey[700]
: Colors.grey[200],
borderRadius: BorderRadius.circular(12),
),
child: drone.imageUuid != null && drone.imageUuid!.isNotEmpty
? FutureBuilder<Image?>(
future: ImagesManager.instance.loadImage(drone.imageUuid!),
builder: (context, snapshot) {
if (snapshot.connectionState == ConnectionState.waiting) {
return const Center(child: CircularProgressIndicator(color: Colors.lightBlueAccent));
return Center(child: CircularProgressIndicator(color: accentColor));
} else if (snapshot.hasError || !snapshot.hasData || snapshot.data == null) {
return Icon(Icons.broken_image, size: 50, color: Colors.blueGrey[400]);
return SvgPicture.asset(
'assets/images/drone.svg',
width: 50,
height: 50,
colorFilter: ColorFilter.mode(accentColor, BlendMode.srcIn),
);
} else {
return ClipRRect(
borderRadius: BorderRadius.circular(12),
@ -61,7 +63,12 @@ class DroneCard extends StatelessWidget {
}
},
)
: Icon(Icons.airplanemode_active, size: 50, color: Theme.of(context).brightness == Brightness.dark ? Colors.lightBlueAccent : Colors.blue.shade400),
: SvgPicture.asset(
'assets/images/drone.svg',
width: 50,
height: 50,
colorFilter: ColorFilter.mode(accentColor, BlendMode.srcIn),
),
),
const SizedBox(height: 10),
Text(

View File

@ -129,6 +129,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "2.0.4"
cli_util:
dependency: transitive
description:
name: cli_util
sha256: ff6785f7e9e3c38ac98b2fb035701789de90154024a75b6cb926445e83197d1c
url: "https://pub.dev"
source: hosted
version: "0.4.2"
clock:
dependency: transitive
description:
@ -278,6 +286,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.1.0"
flutter_launcher_icons:
dependency: "direct main"
description:
name: flutter_launcher_icons
sha256: "526faf84284b86a4cb36d20a5e45147747b7563d921373d4ee0559c54fcdbcea"
url: "https://pub.dev"
source: hosted
version: "0.13.1"
flutter_lints:
dependency: "direct dev"
description:
@ -307,6 +323,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "2.0.28"
flutter_svg:
dependency: "direct main"
description:
name: flutter_svg
sha256: cd57f7969b4679317c17af6fd16ee233c1e60a82ed209d8a475c54fd6fd6f845
url: "https://pub.dev"
source: hosted
version: "2.2.0"
flutter_test:
dependency: "direct dev"
description: flutter
@ -677,6 +701,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "1.9.1"
path_parsing:
dependency: transitive
description:
name: path_parsing
sha256: "883402936929eac138ee0a45da5b0f2c80f89913e6dc3bf77eb65b84b409c6ca"
url: "https://pub.dev"
source: hosted
version: "1.1.0"
path_provider:
dependency: "direct main"
description:
@ -1066,6 +1098,30 @@ packages:
url: "https://pub.dev"
source: hosted
version: "4.5.1"
vector_graphics:
dependency: transitive
description:
name: vector_graphics
sha256: a4f059dc26fc8295b5921376600a194c4ec7d55e72f2fe4c7d2831e103d461e6
url: "https://pub.dev"
source: hosted
version: "1.1.19"
vector_graphics_codec:
dependency: transitive
description:
name: vector_graphics_codec
sha256: "99fd9fbd34d9f9a32efd7b6a6aae14125d8237b10403b422a6a6dfeac2806146"
url: "https://pub.dev"
source: hosted
version: "1.1.13"
vector_graphics_compiler:
dependency: transitive
description:
name: vector_graphics_compiler
sha256: "557a315b7d2a6dbb0aaaff84d857967ce6bdc96a63dc6ee2a57ce5a6ee5d3331"
url: "https://pub.dev"
source: hosted
version: "1.1.17"
vector_math:
dependency: transitive
description:

View File

@ -31,6 +31,7 @@ dependencies:
flutter:
sdk: flutter
flutter_colorpicker: ^1.0.0
flutter_launcher_icons: ^0.13.1
# The following adds the Cupertino Icons font to your application.
# Use with the CupertinoIcons class for iOS style icons.
cupertino_icons: ^1.0.8
@ -46,13 +47,14 @@ dependencies:
json_serializable: ^6.9.5
image_cropper: ^9.1.0
intl: ^0.20.2
provider: ^6.1.2
provider: ^6.1.2
geolocator: ^12.0.0
flutter_map: ^8.0.0
latlong2: ^0.9.1
flutter_localizations:
sdk: flutter
shared_preferences: ^2.2.0
flutter_svg: ^2.0.10+1
dev_dependencies:
flutter_test:
@ -70,7 +72,6 @@ dev_dependencies:
# The following section is specific to Flutter packages.
flutter:
# The following line ensures that the Material Icons font is
# included with your application, so that you can use the icons in
# the material Icons class.
@ -78,9 +79,8 @@ flutter:
generate: true
# To add assets to your application, add an assets section, like this:
# assets:
# - images/a_dot_burr.jpeg
# - images/a_dot_ham.jpeg
assets:
- assets/images/ # This is the correct and only place to declare your assets folder.
# An image asset can refer to one or more resolution-specific "variants", see
# https://flutter.dev/to/resolution-aware-images
@ -107,3 +107,11 @@ flutter:
#
# For details regarding fonts from package dependencies,
# see https://flutter.dev/to/font-from-package
# This section needs to be at the root level, not under "flutter:"
flutter_launcher_icons:
android: "launcher_icon"
ios: true
image_path: "assets/images/rtimelogo.png"
min_sdk_android: 21
remove_alpha_ios: true