├── .gitattributes ├── images ├── PumpAnswer.jpg ├── PumpStatus.jpg ├── WizardAnswer.jpg ├── Watchface_Update.png ├── WizardFromWatch.jpg └── Command_Flowchart.png └── README.md /.gitattributes: -------------------------------------------------------------------------------- 1 | # Auto detect text files and perform LF normalization 2 | * text=auto 3 | -------------------------------------------------------------------------------- /images/PumpAnswer.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rifkyprayoga/AAPS-Tizen-Specification/HEAD/images/PumpAnswer.jpg -------------------------------------------------------------------------------- /images/PumpStatus.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rifkyprayoga/AAPS-Tizen-Specification/HEAD/images/PumpStatus.jpg -------------------------------------------------------------------------------- /images/WizardAnswer.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rifkyprayoga/AAPS-Tizen-Specification/HEAD/images/WizardAnswer.jpg -------------------------------------------------------------------------------- /images/Watchface_Update.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rifkyprayoga/AAPS-Tizen-Specification/HEAD/images/Watchface_Update.png -------------------------------------------------------------------------------- /images/WizardFromWatch.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rifkyprayoga/AAPS-Tizen-Specification/HEAD/images/WizardFromWatch.jpg -------------------------------------------------------------------------------- /images/Command_Flowchart.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rifkyprayoga/AAPS-Tizen-Specification/HEAD/images/Command_Flowchart.png -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # AAPS - Tizen specification (draft) 2 | 3 | ## How it works 4 | 5 | ### Watchface update flowchart and description 6 | 7 | 8 | 9 | | **N°** | **Description** | **Module** | 10 | | ------ | ------------------------------------------------------------ | ------------------------------------------ | 11 | | **1** | **Share a new BG Value**
Triggered by new BG value received from plugins | AAPS Plugin | 12 | | **2** | **Share a new basal Value**
Triggered by new basal value received from plugins | AAPS Plugin | 13 | | **3** | **Change Wear settings**
In Wear plugin, some watchface settings are available in AAPS (ie CSF, detailed IOB, ...) and other settings are in watch. => If you change settings in AAPS, it updates watchface | AAPS UI | 14 | | **4** | **Click on "Resend all data" button**
This button (in Wear Plugin) allow user to refresh all data in watchface (usefull when you first connect your watch, in that case graph only contains basal data, and only last BG value, you can resend all BG value for graph) | AAPS UI | 15 | | **5** | **Send single data to watchface**
There is only the last BG point sent every 5 minutes (probably to have a shorter communication and less consumption) | WatchUpdaterService, TizenUpdaterService | 16 | | **6** | **Send an array of data to watchface**
The data structure is different to include all BG values for the last 5 hours) | WatchUpdaterService, TizenUpdaterService | 17 | | **7** | **Request Watchface update**
On single data received, all informations of watchface are updated, basal rates are updated in graph, and the last BG value is added in graph. When an array of data is received, it also updates all the BG points in the graph | Tizen Service, WearOS Service | 18 | | **8** | **Update watchface and graph**
Update watchface and graph (at least every 5 minutes...) | Watchface | 19 | | **9** | **Click on "Open settings on wear" button**
This button (in Wear Plugin) allow user to launch setting menu in watch | AAPS UI | 20 | | **10** | **Send request for setting menu to watchface**
Send a message to watch to request settings menu | WatchUpdaterService, TizenUpdaterService | 21 | | **11** | **Receive command from watch**
Request (Control Command) settings screen in UI App. | Tizen Service, WearOS Service | 22 | | **12** | **show setting menu in watch**
Show Setting menu included in Tizen or WearOS AAPS UI Application | UI App | 23 | 24 | 25 | 26 | ### Command flowchart and description 27 | 28 | 29 | 30 | | **N°** | **Description** | **Module** | 31 | | ------ | ------------------------------------------------------------ | ------------------------------------------ | 32 | | **1** | **Request for command**
Not available today in current wearOS watchface I made a [PR #2404](https://github.com/MilosKozak/AndroidAPS/pull/2404) to allow this functionality with up to 5 areas available (Up, Down, Left, Right and Center) => In my PR, you can select for each area which command is affected (settings in watch). => All background is available for access to main menu => Chart is "reserved" for time scaling (that's why in some watchfaces you have only 4 areas available) | Watchface | 33 | | **2** | **Request for main menu**
It's the current access on wear OS to dedicated commands (double tap on BG value, generally on top of watchface) | Watchface | 34 | | **3** | **Launch UI application** | TizenOS | 35 | | **4** | **show main menu**
You can access from this menu to: - Commands (i.e. Bolus, eCarbs, Wizard, Temp Target, …) - Settings (i.e. watchface settings, main menu settings, interface settings) - Status (Loop, pump, CPP, TDI) | UI App | 36 | | **5** | **Select a command from menu**
If parameters are needed for selected command, go to next step, otherwise go directly to step 7 | UI App | 37 | | **6** | **Launch dedicated Interface for selected command**
User can enter different parameters (according to selected command) - eCarbs command: Carbs (g), start time (min), duration (h) - Bolus command: Insulin (U), Carbs (g) - Wizard command: Carbs (g), percentage (optional) - TT command: Duration (min default 60), Target (percentage) - Profile switch (CPP): Time offset (h), percentage Different layout are available for UI in wearOS, but I think we could make it easier on Tizen watch with rotary wheel Slide left between each parameter Finally there is a button ta validate entries and send command | UI App | 38 | | **7** | **Send command to AAPS**
An async. formated message is broadcasted to AAPS (including the command and parameters) Once command is sent, User interface is closed and watchface is shown again | Tizen Service, WearOS Service | 39 | | **8** | **Receive command from watch**
Message is received and decoded to get parameters. If necessary request is done to other plugin to get requested informations | WatchUpdaterService, TizenUpdaterService | 40 | | **9** | **Send answer to watch and request acknowledgment**
The response message is prepared based on the command sent and the return of the plugins concerned. In the case of treatment actions, an acknowledgment is required to execute the action (bolus, carbs, TT ...) | WatchUpdaterService, TizenUpdaterService | 41 | | **10** | **Receive response from AAPS**
An async. message is received by the listener service which runs in the background in the watch. The listener service launches a standard user interface for showing the response and, if necessary, approve the action. | Tizen Service, WearOS Service | 42 | | **11** | **show answer sent by AAPS**
Standard interface to show answer. - if it's a status request (i.e. pump status, loop status) then then "Check button on second sheet" is just for closing UI and go back to watchface - if it's a action command (i.e. Insulin, Carbs, TT, ...) then the "Check button" is for sending an acknowledge to AAPS and do action (Bolus, record Carbs...) | UI App | 43 | | **12** | **Send confirmation to AAPS**
An async. formated message is broadcasted to AAPS to confirm action | Tizen Service, WearOS Service | 44 | | **13** | **Receive confirmation from watch**
If acknowledge message is received by AAPS, requested action is sent to dedicated plugin to be executed. | WatchUpdaterService, TizenUpdaterService | 45 | 46 | ### Action interface on WearOS / Tizen and associated broadcasts 47 | 48 | #### First example: Wizard action from watch (with acknowledge) 49 | 50 | - When you select in main menu "Wizard" (Assistant in screenshot), you have 1 or 2 screens to enter parameters (percentage is optional, according to settings). 51 | 52 | You enter Carbs amount (with +/- buttons), then swipe left between screen to enter the other parameters, until you reach the validation button. 53 | 54 | 55 | 56 | 57 | 58 | - Watch send an "initiate action string" to AAPS (path "/nightscout_watch_initiateactionstring" on WearOS, channel "initiate action string", number xxx on Tizen watch) with string below: (note: to be confirmed in Tizen if plain text or if json string) 59 | 60 | ``` 61 | wizard2 45 100 (default interface without percentage parameter) 62 | wizard2 45 80 (above example with percentage enable in settings) 63 | ``` 64 | 65 | - The request action received by xxxUpdaterService is sent as String to ActionStringHandler (see below) 66 | 67 | - ActionStringHandler decode, assure interface with all other plugins, generate a standard answer (rTitle, rMessage and rAction) 68 | - This message is sent to watch threw a dataMap structure (WearOS), or JSON string (Tizen) 69 | 70 | 71 | 72 | In above picture Title = CONFIRM, Message = Carbs: 45g, ... 73 | 74 | Slide left (WearOS), to be decide according to interface in Tizen, tick button to confirm action 75 | 76 | - Watch send a "confirm action string", which is decoded in ActionStringHandler, and if it matches with initiate action string and if it is within Timeout then action is done in AAPS. 77 | 78 | #### Second example: Pump status request (without acknowledge) 79 | 80 | - When you select in Main Menu > Status > "Pump" (Pompe in screenshot), (it's a simple command with no parameters, a resquest status is sent to AAPS: 81 | 82 | 83 | 84 | Message sent: 85 | 86 | ``` 87 | status pump 88 | ``` 89 | 90 | - ActionStringHandler decode, request information to other plugins, and generate the same kind of answer than for wizard or any other action (with rTitle, rMessage, rAction) 91 | 92 | 93 | 94 | Here Title = STATUS PUMP, message is longer and start with "Last conn: ..." (Dernière conn : ... in screenshot) 95 | 96 | For long messages, you have to swipe up to see the bottom of message, and swipe left to reach the button that closes the screen. 97 | 98 | 99 | 100 | ## Android Studio SDK 101 | 102 | Installing sdk accessory in android studio follow **[this link](https://developer.samsung.com/mobile/galaxy-sdk-getting-started.html)**, see **[download page](https://developer.samsung.com/galaxy-accessory/download.html)** and **[sdk file](https://developer.samsung.com/galaxy-accessory/download.html?download=/glxyaccessory/file/694edfd4-d023-4e44-a34c-bb028852c53a)** 103 | 104 | ## Android Wear plugin 105 | 106 | to be completed 107 | 108 | 109 | 110 | ## Tizen package structure 111 | 112 | ### Samsung documentation 113 | 114 | #### Tizen Studio install 115 | 116 | [Prerequisites (Java Dev Kit version is very important)](https://developer.tizen.org/development/tizen-studio/download/prerequisites) 117 | 118 | [Download Tizen Studio](https://developer.tizen.org/development/tizen-studio/download) 119 | 120 | [Preparing the SAP Server Test Environment](https://developer.samsung.com/galaxy-watch-develop/creating-your-first-app/native-companion/galaxy-watch-emulator.html) 121 | 122 | [Installing Certificate Extension](https://developer.samsung.com/galaxy-watch-develop/getting-certificates/install.html) 123 | 124 | **[Creating Certificates](https://developer.samsung.com/galaxy-watch-develop/getting-certificates/create.html)** 125 | 126 | DUID are in Distributor certificate 127 | 128 | DUID for Emulators : (1rst DUID for emulators v4.0, v5.0 and v5.5, 2nd DUID for v2.3.1, v2.3.2 and v3.0) 129 | 130 | ``` 131 | 1.0#ROYexsr3ytkS8Dr348OGkUKnyMk= 132 | 133 | 1.0#OYbnFSmxwxVOk62e/cz11DU+J90= 134 | ``` 135 | 136 | **[Managing Certificate Profile](https://developer.samsung.com/galaxy-watch-develop/getting-certificates/manage.html)** 137 | 138 | **[Extending Certificate Expiry](https://developer.samsung.com/galaxy-watch-develop/getting-certificates/extend.html)** 139 | 140 | Certificate duration is only one year... 141 | 142 | **[Connect your watch to computer](https://developer.samsung.com/galaxy-watch-design/studio/faq.html#Why_cant_I_connect_to_my_device)** 143 | 144 | After having enable debugger mode 145 | 146 | - Turn Off bluetooth 147 | - set display alway active 148 | - enable wifi 149 | - power off your watch near your PC (wifi access point) 150 | - Turn your watch on 151 | 152 | don't forget to reboot your watch after setting debugger mode 153 | 154 | wait 30-60 s after reboot keeping your eyes on it to enable RSA key 155 | 156 | 157 | 158 | ### .net (Visual Studio and Xamarin plugin) 159 | 160 | to be completed 161 | 162 | 163 | 164 | ### native (Tizen Studio) 165 | 166 | - You can not package an UI app with watch app. Go through the **Table: Combinations** in [**this link**](https://developer.tizen.org/ko/development/training/native-application/application-development-process?langredirect=1) to know about possible packaging combinations in detail. 167 | - UI App can include Service and Widget sub-project 168 | - Watchface can only include Service sub-project 169 | - To develop multi-packaged project in Tizen, you may follow **Developing Multiple Projects as a Combined Package** section in **[this link](https://developer.tizen.org/development/training/native-application/application-development-process#develop)**. 170 | - To do communication between android app and Tizen app please go through **Build your First Companion type application** section in **[this link](https://developer.samsung.com/galaxy-watch/develop/creating-your-first-app)**. 171 | - To debug your application, you may try various application debugging methods e.g. debugging with logs as described in **[this link](https://developer.tizen.org/ko/development/training/native-application/application-development-process/debugging-applications?langredirect=1#methods)**. 172 | - You may try creating another app to enter Carbs quantity, Insulin Quantity, etc data and launch it from watchface app. In that case, you may follow **[this link](https://developer.tizen.org/development/guides/native-application/application-management/application-controls)**. 173 | - this describe how we can launch (through **Application Control**) UI commands from service (when AAPS request acknowledge from watch) or from a watchface (when we want to launch a command) 174 | 175 | 176 | 177 | ## Data exchange 178 | 179 | ### Service configuration 180 | 181 | #### accessoryservices.xml: (android side) 182 | 183 | Note don't use @Strings/xxx in xml file (crash with ) 184 | 185 | - serviceProfile1 186 | 187 | - id="/androidaps/tizen" 188 | - name="androidaps_tizen" 189 | - role="provider" or "consumer" 190 | - serviceImpl="info.nightscout.androidaps.plugins.general.wear.tizenintegration.TizenUpdaterService" 191 | - serviceChannel : 104 (for tests), 192 | - 110: Tizen resend data request 193 | - 115: Tizen cancel bolus 194 | - 120: Tizen confirm action 195 | - 121: AAPS action confirmation request 196 | - 125: Tizen initiate action 197 | - to be completed 198 | 199 | 200 | 201 | 202 | - serviceProfile2 (not implemented, and to be confirm) 203 | 204 | - id="/androidaps/tizen/watchface" 205 | 206 | - name="androidaps_tizen_watchface" 207 | 208 | - id="/androidaps/tizen" 209 | - name="androidaps_tizen" 210 | - role="provider" 211 | 212 | - serviceImpl="info.nightscout.androidaps.plugins.general.wear.tizenintegration.TizenUpdaterService" 213 | 214 | - serviceChannel : 105 (tests) 215 | 216 | - action send data (sendData and resendData) 217 | - action send status 218 | - action send basals 219 | 220 | 221 | 222 | ### Watchface data 223 | 224 | to be completed (keyword, data structure) 225 | 226 | ### List of commands 227 | 228 | to be completed (keyword, data structure) 229 | 230 | #### Command received by TizenUpdaterService 231 | 232 | Method: 233 | 234 | ```java 235 | public void onReceive(int channelID, byte[] data) 236 | ``` 237 | 238 | 239 | 240 | | Path | Action | 241 | | --------------------------------------- | ---------------------------------------------------- | 242 | | WEARABLE_RESEND_CH = 110 | resendData() | 243 | | WEARABLE_CANCELBOLUS_CH = 115 | cancelBolus() | 244 | | WEARABLE_INITIATE_ACTIONSTRING_CH = 120 | ActionStringHandler.handleInitiate(actionstring) | 245 | | WEARABLE_CONFIRM_ACTIONSTRING_CH = 125 | ActionStringHandler.handleConfirmation(actionstring) | 246 | 247 | 248 | 249 | #### Command received by WatchUpdaterService 250 | 251 | Method: 252 | 253 | ```java 254 | public void onMessageReceived(MessageEvent event) 255 | ``` 256 | 257 | ```java 258 | String path = event.getPath(); 259 | ``` 260 | 261 | ```java 262 | String actionstring = new String(event.getData()); 263 | ``` 264 | 265 | 266 | 267 | | Path | Action | 268 | | ------------------------------------------------------------ | ---------------------------------------------------- | 269 | | WEARABLE_RESEND_PATH = "/nightscout_watch_data_resend" | resendData() | 270 | | WEARABLE_CANCELBOLUS_PATH = "/nightscout_watch_cancel_bolus" | cancelBolus() | 271 | | WEARABLE_INITIATE_ACTIONSTRING_PATH = "/nightscout_watch_initiateactionstring" | ActionStringHandler.handleInitiate(actionstring) | 272 | | WEARABLE_CONFIRM_ACTIONSTRING_PATH = "/nightscout_watch_confirmactionstring" | ActionStringHandler.handleConfirmation(actionstring) | 273 | 274 | 275 | 276 | #### ActionStringHandler : Class of Wear plugin 277 | 278 | methods: 279 | 280 | 1. **For build an answer after an Initiate action String sent by watch:** 281 | 282 | ```java 283 | public synchronized static void handleInitiate(String actionstring) 284 | ``` 285 | 286 | Responses messages has always the same structure (3 strings with a title, a response and an action contains the action that watch should answer to confirm Action: 287 | 288 | ``` 289 | WearPlugin.getPlugin().requestActionConfirmation(rTitle, rMessage, rAction); 290 | ``` 291 | 292 | Note: When an initiate Action String does not require a confirmation, rAction is set to statusmessage or info. 293 | 294 | 2. **For intent actions (only for fill, bolus, temptarget, wizard2, cppset, changeRequest and ecarb)** 295 | 296 | ``` 297 | public synchronized static void handleConfirmation(String actionString) 298 | ``` 299 | 300 | 301 | 302 | Note: action string is split in ActionStringHandler with regex "\\\s+" 303 | 304 | | Keyword (act[0]) | 1rst param (act[1]) | 2nd param (act[2]) | 3rd param (act[3]) | 4th param (act[4]) | 305 | | ------------------- | --------------------------------------- | -------------------------------- | -------------------------------- | ------------------------ | 306 | | fillpreset | "1"
"2"
"3" | | | | 307 | | fill | amount
stringToDouble | | | | 308 | | bolus | insulin
stringToDouble | carbs
stringToDouble | | | 309 | | temptarget | isMGDL
parseBoolean | duration
stringToInt | low
stringToDouble | high
stringToDouble | 310 | | status | "pump"
"loop" | | | | 311 | | wizard2 | carbsBeforeConstraints
stringToInt | percentage
Integer.parseInt | | | 312 | | opencpp | | | | | 313 | | cppset | timeshift | percentage | | | 314 | | tddstats | | | | | 315 | | ecarbs | carbs
stringToInt | starttime (min)
stringToInt | duration (hour)
stringToInt | | 316 | | changeRequest | | | | | 317 | | cancelChangeRequest | | | | | 318 | 319 | Timeout : 65s 320 | 321 | rTitle : Title of response (text) 322 | 323 | rMessage : detailled answer (text) 324 | 325 | rAction : action for acknowledge 326 | 327 | ```java 328 | WearPlugin.getPlugin().requestActionConfirmation(rTitle, rMessage, rAction) 329 | ``` 330 | 331 | 332 | 333 | ```java 334 | public synchronized static void handleConfirmation(String actionString) 335 | ``` 336 | 337 | action string split with regex "\\\s+" 338 | 339 | 340 | 341 | ## Settings 342 | 343 | To be decide if we include watchface settings (background color, hidden or visible informations, ...) in UI application in watch, or in AAPS wear plugin (dedicated screen prepared but empty today). 344 | 345 | At least we need an setting menu in UI application for user interface (which command is available in main menu) 346 | 347 | 348 | 349 | ## --------------------------------------------------------------------------------