feat(reminder): add alarm scheduling, RN bridge, and ring activity/service - #265
Draft
LUPENGHAN wants to merge 5 commits into
Draft
feat(reminder): add alarm scheduling, RN bridge, and ring activity/service#265LUPENGHAN wants to merge 5 commits into
LUPENGHAN wants to merge 5 commits into
Conversation
Part of 1024XEngineer#263. The zero-dependency slice of the timeflow-alarm native module: AlarmContract (shared constants), DayRulerView and AlarmRingUi (the hand-drawn ring-screen UI -- colors, typefaces, entrance animation, pill buttons, self-ticking clock). None of these three import anything else in the module, so this compiles standalone; the scheduling/RN bridge/ring Activity+Service classes that DO reference each other are a separate PR on top of this one. Also the app-level scaffolding: app.config.js (replaces static app.json so plugins can read env vars), the withTimeflowAlarm config plugin, and the new package dependency. Not included: Baidu location module -- dropped entirely per 1024XEngineer#263's decision to use system geofencing instead.
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
This was referenced Aug 17, 2026
react-native.config.js still registered the deleted modules/timeflow-baidu-location for autolinking, package-lock.json still had an extraneous entry for it, and CI still exported a TIMEFLOW_BAIDU_LOCATION_API_KEY placeholder for a plugin that's no longer registered in app.config.js. None of these broke anything (Expo silently skips the missing directory) but all three kept describing an integration 1024XEngineer#263 said to drop entirely. Verified: tsc/eslint clean, `expo prebuild --platform android --no-install` still succeeds.
LUPENGHAN
force-pushed
the
feature/reminder-native-core
branch
from
August 17, 2026 05:19
7303a4f to
f4c1579
Compare
Code review (PR 1024XEngineer#264): formatDate() constructed a new SimpleDateFormat on every call, including every 20-second RingRoot tick for as long as the ring screen is visible -- unnecessary allocation on a repeating timer. Cached as a static final field; its locale is hardcoded to Locale.CHINA so there's no correctness risk. formatClock() is left as a fresh SimpleDateFormat per call since it uses Locale.getDefault(), which can change at runtime -- caching it would risk showing a stale locale, not worth it for this level of savings.
…rvice Part of 1024XEngineer#263. The rest of the timeflow-alarm module: AlarmScheduler (AlarmManager scheduling + SharedPreferences persistence + reboot/update rescheduling), AlarmReceiver/BootReceiver (broadcast entry points), AlarmModule/AlarmNativeBridge/AlarmPackage (the RN-facing surface), and RingActivity/AlarmSoundService (the full-screen ring Activity/Service, built on the AlarmRingUi toolkit from the previous PR). These 8 files reference each other directly (e.g. AlarmReceiver constructs AlarmSoundService, RingActivity calls back into AlarmScheduler/AlarmNativeBridge) and are compiled together as one Gradle module regardless of PR boundaries, so they can't be split further without introducing string-based/reflective class lookups purely to shrink the diff -- not worth the runtime-safety tradeoff.
LUPENGHAN
force-pushed
the
feature/reminder-native-core
branch
from
August 17, 2026 07:00
f4c1579 to
c2f0e82
Compare
Code review (PR 1024XEngineer#265): AlarmSoundService.firedNotified was a service-lifetime boolean, not per-alarm. If a second alarm fired while the service was already ringing a first one (two reminders scheduled a few minutes apart), onStartCommand's `if (!firedNotified)` guard was already tripped, so notifyFired() -- and with it the only signal JS gets that this alarm rang -- was silently skipped for every alarm after the first, even though its persisted record was still deleted via removeFromSavedAlarms(). Keyed the guard by alarmId instead. Also extracted the alarmId/scheduleId/title extraction-and-fallback logic (legacy-<requestCode> id, scheduleIdForAlarm lookup, default title) that AlarmSoundService and RingActivity each reimplemented identically into AlarmContract.ExtractedExtras, so the two can't drift. Not fixed: AlarmNativeBridge.consumeDispositions() clears its SharedPreferences buffer before the JS caller has durably persisted what it returned, so a process death in that window loses the disposition. Fixing it needs a two-phase consume/ack contract on the JS side, which doesn't exist yet in this stack -- flagging for the wiring PR instead of half-fixing the native side alone.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
关联 Issue
Part of #263
依赖 #264(先合,这个 draft 里现在的 diff 会包含 #264 还没合的内容,等它合了 rebase 一下就会瘦身)
改动
验证
npx tsc --noEmit、npx eslint .全绿本轮不含