25 Commits
Author SHA1 Message Date
me 95e9134608 build, try clearing all the architectures first. 2026-11-11 20:09:40 -07:00
me 57a211a518 build, clean up the release APK setup. 2026-11-11 19:58:35 -07:00
me d432de170d build, ensure release file is only arm64-v8a. 2026-11-11 19:30:22 -07:00
me 720866f6b4 changelog, add date for latest release. 2026-11-11 19:29:55 -07:00
me 7c7b8e473c Merge pull request '1.2.0' (#6) from dev into main
Reviewed-on: #6
2026-11-11 19:21:04 -07:00
me e7b5dd768c main, remove extra space added when trying to get VS Codium and Flutter to sync. 2026-11-11 19:08:55 -07:00
me fb76a04c58 main, keep the alarm scheduled even if app is killed. 2026-11-11 19:03:53 -07:00
me 8060c0755a main, reword notification time for smaller screens and add dashes back in. 2026-11-11 18:57:47 -07:00
me 17d69fb3a7 pubspec, increment version. 2026-11-11 08:45:16 -07:00
me b6ae6b1f10 changelog, add working version. 2026-11-11 08:44:49 -07:00
me b02ca20072 Merge branch 'main' into dev 2026-11-11 08:42:02 -07:00
me e04aa9f447 main, ensure the alarm ID gets refreshed on the screen by using setState() at the end of the function. 2026-11-11 08:36:26 -07:00
me 3bb3123a12 main, add alarm ID to switch text for now so we can see which date it's for. 2026-11-11 08:24:04 -07:00
me f0b723e158 main, fix rescheduling by making each day's alarm ID unique so that it does not cancel the alarm currently going off. 2026-11-11 08:14:47 -07:00
me 8adaecbf7d Android Studio or Flutter changes. 2026-11-11 08:13:50 -07:00
me f212f9927b Upgrade AGP. 2026-11-11 08:13:28 -07:00
me 08e9ff66b7 Upgrade Gradle (9.8.2 -> 9.9.0). 2026-11-10 20:35:04 -07:00
me cfd0ca514d settings, fix typo in comment. 2026-11-10 20:34:30 -07:00
me 66f42a5141 build, add flutter proguard file. 2026-11-10 20:34:04 -07:00
me e163a2e290 main, add output to see if the alarm going off really does schedule the next alarm. 2026-11-10 20:33:33 -07:00
me 7eaa2dc3a4 main, attempt to reschedule alarm for next day after the current day goes off. 2026-11-10 19:57:33 -07:00
me f432e0b406 changelog, update to match releases page. 2026-11-01 18:59:35 -07:00
me 220df450c3 gitignore, add more Android build and release locations. 2026-11-01 15:59:34 -07:00
me 14c75e8331 gitignore, add release and build files. 2026-11-01 15:07:45 -07:00
me eafa6ffa5f changelog, update to match release. 2026-11-01 15:07:31 -07:00
7 changed files with 86 additions and 23 deletions

No files matched your search

+7
View File
@@ -57,6 +57,10 @@ unlinked_spec.ds
**/android/**/GeneratedPluginRegistrant.java **/android/**/GeneratedPluginRegistrant.java
**/android/key.properties **/android/key.properties
*.jks *.jks
android/build
android/app/build
android/release
android/app/release
# iOS/XCode related # iOS/XCode related
**/ios/**/*.mode1v3 **/ios/**/*.mode1v3
@@ -122,6 +126,9 @@ app.*.symbols
# Gradle files # Gradle files
.gradle/ .gradle/
build/ build/
android/app/release/*
android/build/*
android/app/build/*
# Local configuration file (sdk path, etc) # Local configuration file (sdk path, etc)
local.properties local.properties
+10 -6
View File
@@ -1,18 +1,22 @@
# Changelog # Changelog
## 1.1.0 (In Development) ## 1.2.0 (2026-11-11)
- Automatically enable next day's alarm when the current day's is activated.
- Add the alarm's date to the SwitchTile text for confirming it's truly set.
## 1.1.0 (2026-11-01)
Usability improvements. Usability improvements.
- move switchtile back to its own row - move switchtile back to its own row
- allows showing text without crowding out or hiding minutes field - allows showing text without crowding out or hiding minutes field
- fix monochrome icons, source was not white which may have been causing issues - fix monochrome icons, source was not white which may have been causing issues
- begin creating tar files for Linux rather than zips, will use zstd on release - begin creating tar files for Linux rather than zips to use on release
- begin using a proper release signature rather that flutter's debug. - begin using a proper release signature rather that flutter's debug
- update internal plugin versions. - update internal plugin versions
This version may require uninstalling any previous versions before updating This version may require uninstalling any previous versions before updating due to the signature change. It is a one-time event.
due to the signature change. It is a one-time event.
## 1.0.1 (2026-09-29) ## 1.0.1 (2026-09-29)
+7 -5
View File
@@ -41,10 +41,6 @@ android {
buildTypes { buildTypes {
getByName("release") { getByName("release") {
// TODO: Add your own signing config for the release build.
// Signing with the debug keys for now, so `flutter run --release` works.
signingConfig = signingConfigs.getByName("debug")
/// 20260928 - Without minifying. /// 20260928 - Without minifying.
/// Built build/app/outputs/flutter-apk/app-release.apk (54.3MB) /// Built build/app/outputs/flutter-apk/app-release.apk (54.3MB)
/// Built build/app/outputs/flutter-apk/app-armeabi-v7a-release.apk (17.2MB) /// Built build/app/outputs/flutter-apk/app-armeabi-v7a-release.apk (17.2MB)
@@ -55,7 +51,7 @@ android {
isShrinkResources = true isShrinkResources = true
proguardFiles( proguardFiles(
getDefaultProguardFile("proguard-android-optimize.txt"), getDefaultProguardFile("proguard-android-optimize.txt"),
"proguard-rules.pro" "proguard-rules.pro",
) )
/// 20260928 - With minifying, helped some, but also used /// 20260928 - With minifying, helped some, but also used
@@ -64,6 +60,12 @@ android {
/// Built build/app/outputs/flutter-apk/app-armeabi-v7a-release.apk (16.1MB) /// Built build/app/outputs/flutter-apk/app-armeabi-v7a-release.apk (16.1MB)
/// Built build/app/outputs/flutter-apk/app-arm64-v8a-release.apk (18.8MB) /// Built build/app/outputs/flutter-apk/app-arm64-v8a-release.apk (18.8MB)
/// Built build/app/outputs/flutter-apk/app-x86_64-release.apk (20.3MB) /// Built build/app/outputs/flutter-apk/app-x86_64-release.apk (20.3MB)
ndk {
abiFilters.clear()
//noinspection ChromeOsAbiSupport
abiFilters += listOf("arm64-v8a")
}
} }
} }
} }
+5 -2
View File
@@ -1,6 +1,9 @@
#Sat Sep 12 19:36:23 MST 2026
distributionBase=GRADLE_USER_HOME distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-9.8.2-bin.zip distributionUrl=https\://services.gradle.org/distributions/gradle-9.9.0-bin.zip
networkTimeout=10000
retries=0
retryBackOffMs=500
validateDistributionUrl=true
zipStoreBase=GRADLE_USER_HOME zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists zipStorePath=wrapper/dists
+2 -2
View File
@@ -19,9 +19,9 @@ pluginManagement {
plugins { plugins {
id("dev.flutter.flutter-plugin-loader") version "1.0.0" id("dev.flutter.flutter-plugin-loader") version "1.0.0"
id("com.android.application") version "9.5.0" apply false id("com.android.application") version "9.5.1" apply false
// This will need removed in Gradle/AGP 9. JK - needs to exist otherwiese: // This will need removed in Gradle/AGP 9. JK - needs to exist otherwise:
// "Error: Your project's Kotlin version (2.2.10) is lower than Flutter's minimum supported version of 2.2.20." // "Error: Your project's Kotlin version (2.2.10) is lower than Flutter's minimum supported version of 2.2.20."
id("org.jetbrains.kotlin.android") version "2.4.21" apply false id("org.jetbrains.kotlin.android") version "2.4.21" apply false
} }
+54 -7
View File
@@ -1,6 +1,7 @@
import 'dart:io'; import 'dart:io';
import 'dart:async'; import 'dart:async';
import 'package:alarm/utils/alarm_set.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:geolocator/geolocator.dart'; import 'package:geolocator/geolocator.dart';
import 'package:shared_preferences/shared_preferences.dart'; import 'package:shared_preferences/shared_preferences.dart';
@@ -29,6 +30,7 @@ void main() async {
tz.initializeTimeZones(); tz.initializeTimeZones();
await Alarm.init(); await Alarm.init();
runApp(const SunsetAlarmApp()); runApp(const SunsetAlarmApp());
} }
@@ -61,6 +63,11 @@ class SunsetAlarmApp extends StatelessWidget {
} }
} }
int dateAsId(DateTime d) => d.year * 10000 + d.month * 100 + d.day;
int todayAsId() {
return dateAsId(DateTime.now());
}
class HomeScreen extends StatefulWidget { class HomeScreen extends StatefulWidget {
const HomeScreen({super.key}); const HomeScreen({super.key});
@@ -86,13 +93,23 @@ class _HomeScreenState extends State<HomeScreen> {
String? _minuteErrorText; String? _minuteErrorText;
bool _validTime = false; bool _validTime = false;
static const _alarmId = 1001; int _alarmId = 20260000;
@override @override
void initState() { void initState() {
super.initState(); super.initState();
_initNotifications(); _initNotifications();
_loadPrefs(); _loadPrefs();
// Reschedule alarm any time one goes off.
Alarm.ringing.listen((AlarmSet alarmSet) {
for (final alarm in alarmSet.alarms) {
if (alarm.id == todayAsId()) {
_scheduleAlarm();
break;
}
}
});
} }
Future<void> _initNotifications() async { Future<void> _initNotifications() async {
@@ -240,6 +257,10 @@ class _HomeScreenState extends State<HomeScreen> {
alarmTime = alarmTime.add(const Duration(days: 1)); alarmTime = alarmTime.add(const Duration(days: 1));
} }
_debug("_scheduleAlarm, alarmTime=${alarmTime.toIso8601String()}");
_alarmId = dateAsId(alarmTime);
_debug("_alarmId=$_alarmId");
if (Platform.isLinux) { if (Platform.isLinux) {
// Linux: use a Timer (app must stay open) // Linux: use a Timer (app must stay open)
_alarmTimer?.cancel(); _alarmTimer?.cancel();
@@ -300,9 +321,9 @@ class _HomeScreenState extends State<HomeScreen> {
androidScheduleMode: AndroidScheduleMode.alarmClock, androidScheduleMode: AndroidScheduleMode.alarmClock,
); );
_showSnack('Alarm scheduled!'); _showSnack('Alarm scheduled!');
debugPrint('DEBUG: Alarm time: ${tzAlarm.toString()}'); _debug('Alarm time: ${tzAlarm.toString()}');
debugPrint('DEBUG: Current time: ${DateTime.now().toUtc().toString()}'); _debug('Current time: ${DateTime.now().toUtc().toString()}');
debugPrint('DEBUG: ${_notifications.toString()}'); _debug('${_notifications.toString()}');
} }
// End Notification Method ***/ // End Notification Method ***/
@@ -326,7 +347,18 @@ class _HomeScreenState extends State<HomeScreen> {
stopButton: 'Dismiss', stopButton: 'Dismiss',
icon: 'ic_notification', icon: 'ic_notification',
), ),
androidStopAlarmOnTermination: false,
); );
// Skip if tomorrow's alarm already exists.
final existing = await Alarm.getAlarm(_alarmId);
if (existing == settings) {
_debug(
"Alarm already exists, skipping schedule. ${settings.toString()}",
);
return;
}
await Alarm.set(alarmSettings: settings); await Alarm.set(alarmSettings: settings);
} }
// End Alarm Method ***/ // End Alarm Method ***/
@@ -334,6 +366,10 @@ class _HomeScreenState extends State<HomeScreen> {
} else { } else {
_showSnack('Platform Not Detected - Contact Developer'); _showSnack('Platform Not Detected - Contact Developer');
} }
// If we made it this far, refresh the alarm ID on the screen.
setState(() {
_alarmId = _alarmId;
});
} }
Future<void> _toggleAlarm(bool value) async { Future<void> _toggleAlarm(bool value) async {
@@ -352,11 +388,13 @@ class _HomeScreenState extends State<HomeScreen> {
} else if (Platform.isAndroid) { } else if (Platform.isAndroid) {
// Notification Method // Notification Method
if (ANDROID_USE_NOTIF) { if (ANDROID_USE_NOTIF) {
await _notifications.cancel(id: _alarmId); //await _notifications.cancel(id: _alarmId);
await _notifications.cancelAll();
} }
// Alarm Method // Alarm Method
if (ANDROID_USE_ALARM) { if (ANDROID_USE_ALARM) {
await Alarm.stop(_alarmId); //await Alarm.stop(_alarmId);
await Alarm.stopAll();
} }
} }
_showSnack('Alarm Cancelled'); _showSnack('Alarm Cancelled');
@@ -366,6 +404,14 @@ class _HomeScreenState extends State<HomeScreen> {
ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(msg))); ScaffoldMessenger.of(context).showSnackBar(SnackBar(content: Text(msg)));
} }
void _log(String tag, String msg) {
debugPrint(tag + ": " + msg);
}
void _debug(String msg) {
_log("DEBUG", msg);
}
@override @override
void dispose() { void dispose() {
_savePrefs(); _savePrefs();
@@ -578,10 +624,11 @@ class _HomeScreenState extends State<HomeScreen> {
child: Text( child: Text(
_validTime _validTime
? _alarmEnabled ? _alarmEnabled
? "${_minutesBefore} Minute${_plural} Before @ $_alarmDisplayTime" ? "Scheduled @ ${_alarmId.toString().replaceRange(4, 4, '-').replaceRange(7, 7, '-')} $_alarmDisplayTime"
: "Sunset Alarm" : "Sunset Alarm"
: "Enter Valid Time", : "Enter Valid Time",
), ),
//
), ),
value: _validTime ? _alarmEnabled : false, value: _validTime ? _alarmEnabled : false,
onChanged: _validTime ? _toggleAlarm : null, onChanged: _validTime ? _toggleAlarm : null,
+1 -1
View File
@@ -1,7 +1,7 @@
name: sunset_alarm name: sunset_alarm
description: "Set an alarm to go off a specified time before sunset." description: "Set an alarm to go off a specified time before sunset."
publish_to: 'none' publish_to: 'none'
version: 1.1.0 version: 1.2.0
environment: environment:
sdk: ^3.7.2 sdk: ^3.7.2