Better support for R9M EU (#5487)
[opentx.git] / radio / src / gui / 128x64 / gui.h
blob316f70a883aab6c99e448417d8eff2463e7d33a5
1 /*
2 * Copyright (C) OpenTX
4 * Based on code named
5 * th9x - http://code.google.com/p/th9x
6 * er9x - http://code.google.com/p/er9x
7 * gruvin9x - http://code.google.com/p/gruvin9x
9 * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html
11 * This program is free software; you can redistribute it and/or modify
12 * it under the terms of the GNU General Public License version 2 as
13 * published by the Free Software Foundation.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
21 #ifndef _GUI_H_
22 #define _GUI_H_
24 #include "gui_common.h"
25 #include "menus.h"
26 #include "popups.h"
28 #define MENUS_SCROLLBAR_WIDTH 0
30 #if defined(PCBX7)
31 #define HEADER_LINE 0
32 #define HEADER_LINE_COLUMNS
33 #else
34 #define HEADER_LINE 1
35 #define HEADER_LINE_COLUMNS 0,
36 #endif
38 #define COLUMN_X 0
39 #define drawFieldLabel(x, y, str) lcdDrawTextAlignedLeft(y, str)
41 #define NUM_BODY_LINES (LCD_LINES-1)
42 #define MENU_HEADER_HEIGHT FH
43 #define MENU_INIT_VPOS 0
45 #define CURVE_SIDE_WIDTH (LCD_H/2)
46 #define CURVE_CENTER_X (LCD_W-CURVE_SIDE_WIDTH-2)
47 #define CURVE_CENTER_Y (LCD_H/2)
49 #define MIXES_2ND_COLUMN (12*FW)
51 // Temporary no highlight
52 extern uint8_t noHighlightCounter;
53 #define NO_HIGHLIGHT() (noHighlightCounter > 0)
54 #define START_NO_HIGHLIGHT() do { noHighlightCounter = 25; } while(0)
57 #if !defined(CPUM64)
58 void drawSlider(coord_t x, coord_t y, uint8_t value, uint8_t max, uint8_t attr);
59 #elif defined(GRAPHICS)
60 void display5posSlider(coord_t x, coord_t y, uint8_t value, uint8_t attr);
61 #define drawSlider(x, y, value, max, attr) lcdDrawNumber(x, y, value, attr|LEFT)
62 #else
63 #define drawSlider(x, y, value, max, attr) lcdDrawNumber(x, y, value, attr|LEFT)
64 #endif
66 #if defined(NAVIGATION_POT1)
67 extern int16_t p1valdiff;
68 #else
69 #define p1valdiff 0
70 #endif
72 #if defined(NAVIGATION_POT2)
73 extern int8_t p2valdiff;
74 #else
75 #define p2valdiff 0
76 #endif
78 extern int8_t checkIncDec_Ret; // global helper vars
80 #define EDIT_SELECT_MENU -1
81 #define EDIT_SELECT_FIELD 0
82 #define EDIT_MODIFY_FIELD 1
83 #define EDIT_MODIFY_STRING 2
84 extern int8_t s_editMode; // global editmode
86 // checkIncDec flags
87 #define EE_GENERAL 0x01
88 #define EE_MODEL 0x02
89 #define NO_INCDEC_MARKS 0x04
90 #define INCDEC_SWITCH 0x08
91 #define INCDEC_SOURCE 0x10
92 #define INCDEC_REP10 0x40
93 #define NO_DBLKEYS 0x80
95 #if defined(CPUARM)
96 #define INCDEC_DECLARE_VARS(f) uint8_t incdecFlag = (f); IsValueAvailable isValueAvailable = NULL
97 #define INCDEC_SET_FLAG(f) incdecFlag = (f)
98 #define INCDEC_ENABLE_CHECK(fn) isValueAvailable = fn
99 #define CHECK_INCDEC_PARAM(event, var, min, max) checkIncDec(event, var, min, max, incdecFlag, isValueAvailable)
100 #elif defined(CPUM64)
101 #define INCDEC_DECLARE_VARS(f)
102 #define INCDEC_SET_FLAG(f)
103 #define INCDEC_ENABLE_CHECK(fn)
104 #define CHECK_INCDEC_PARAM(event, var, min, max) checkIncDec(event, var, min, max, EE_MODEL)
105 #else
106 #define INCDEC_DECLARE_VARS(f) uint8_t incdecFlag = (f)
107 #define INCDEC_SET_FLAG(f) incdecFlag = (f)
108 #define INCDEC_ENABLE_CHECK(fn)
109 #define CHECK_INCDEC_PARAM(event, var, min, max) checkIncDec(event, var, min, max, incdecFlag)
110 #endif
112 // mawrow special values
113 #define TITLE_ROW ((uint8_t)-1)
114 #define HIDDEN_ROW ((uint8_t)-2)
116 #if defined(CPUARM)
117 struct CheckIncDecStops {
118 const int count;
119 const int stops[];
120 int min() const
122 return stops[0];
124 int max() const
126 return stops[count-1];
128 bool contains(int value) const
130 for (int i=0; i<count; ++i) {
131 int stop = stops[i];
132 if (value == stop)
133 return true;
134 else if (value < stop)
135 return false;
137 return false;
140 extern const CheckIncDecStops &stops100;
141 extern const CheckIncDecStops &stops1000;
142 extern const CheckIncDecStops &stopsSwitch;
143 #define INIT_STOPS(var, ...) \
144 const int _ ## var[] = { __VA_ARGS__ }; \
145 const CheckIncDecStops &var = (const CheckIncDecStops&)_ ## var;
146 #define CATEGORY_END(val) \
147 (val), (val+1)
148 int checkIncDec(event_t event, int val, int i_min, int i_max, unsigned int i_flags=0, IsValueAvailable isValueAvailable=NULL, const CheckIncDecStops &stops=stops100);
149 #else
150 int16_t checkIncDec(event_t event, int16_t i_pval, int16_t i_min, int16_t i_max, uint8_t i_flags=0);
151 #endif
153 #if defined(CPUM64)
154 int8_t checkIncDecModel(event_t event, int8_t i_val, int8_t i_min, int8_t i_max);
155 int8_t checkIncDecModelZero(event_t event, int8_t i_val, int8_t i_max);
156 int8_t checkIncDecGen(event_t event, int8_t i_val, int8_t i_min, int8_t i_max);
157 #else
158 #define checkIncDecModel(event, i_val, i_min, i_max) checkIncDec(event, i_val, i_min, i_max, EE_MODEL)
159 #define checkIncDecModelZero(event, i_val, i_max) checkIncDec(event, i_val, 0, i_max, EE_MODEL)
160 #define checkIncDecGen(event, i_val, i_min, i_max) checkIncDec(event, i_val, i_min, i_max, EE_GENERAL)
161 #endif
163 #define CHECK_INCDEC_MODELVAR(event, var, min, max) \
164 var = checkIncDecModel(event, var, min, max)
166 #define CHECK_INCDEC_MODELVAR_ZERO(event, var, max) \
167 var = checkIncDecModelZero(event, var, max)
169 #if defined(CPUARM)
170 #define CHECK_INCDEC_MODELVAR_CHECK(event, var, min, max, check) \
171 var = checkIncDec(event, var, min, max, EE_MODEL, check)
172 #define CHECK_INCDEC_MODELVAR_ZERO_CHECK(event, var, max, check) \
173 var = checkIncDec(event, var, 0, max, EE_MODEL, check)
174 #else
175 #define CHECK_INCDEC_MODELVAR_CHECK(event, var, min, max, check) \
176 var = checkIncDec(event, var, min, max, EE_MODEL)
177 #define CHECK_INCDEC_MODELVAR_ZERO_CHECK(event, var, max, check) \
178 CHECK_INCDEC_MODELVAR_ZERO(event, var, max)
179 #endif
181 #if defined(CPUARM)
182 #define AUTOSWITCH_ENTER_LONG() (attr && event==EVT_KEY_LONG(KEY_ENTER))
183 #define CHECK_INCDEC_SWITCH(event, var, min, max, flags, available) \
184 var = checkIncDec(event, var, min, max, (flags)|INCDEC_SWITCH, available)
185 #define CHECK_INCDEC_MODELSWITCH(event, var, min, max, available) \
186 CHECK_INCDEC_SWITCH(event, var, min, max, EE_MODEL, available)
187 #elif defined(AUTOSWITCH)
188 #define AUTOSWITCH_ENTER_LONG() (attr && event==EVT_KEY_LONG(KEY_ENTER))
189 #define CHECK_INCDEC_SWITCH(event, var, min, max, flags, available) \
190 var = checkIncDec(event, var, min, max, (flags)|INCDEC_SWITCH)
191 #define CHECK_INCDEC_MODELSWITCH(event, var, min, max, available) \
192 CHECK_INCDEC_SWITCH(event, var, min, max, EE_MODEL, available)
193 #else
194 #define AUTOSWITCH_ENTER_LONG() (0)
195 #define CHECK_INCDEC_SWITCH(event, var, min, max, flags, available) \
196 CHECK_INCDEC_MODELVAR(event, var, min, max)
197 #define CHECK_INCDEC_MODELSWITCH(event, var, min, max, available) \
198 CHECK_INCDEC_MODELVAR(event, var, min, max)
199 #endif
201 #if defined(CPUARM)
202 #define CHECK_INCDEC_MODELSOURCE(event, var, min, max) \
203 var = checkIncDec(event,var,min,max,EE_MODEL|INCDEC_SOURCE|NO_INCDEC_MARKS, isSourceAvailable)
204 #elif defined(AUTOSOURCE)
205 #define CHECK_INCDEC_MODELSOURCE(event, var, min, max) \
206 var = checkIncDec(event,var,min,max,EE_MODEL|INCDEC_SOURCE|NO_INCDEC_MARKS)
207 #else
208 #define CHECK_INCDEC_MODELSOURCE CHECK_INCDEC_MODELVAR
209 #endif
211 #define CHECK_INCDEC_GENVAR(event, var, min, max) \
212 var = checkIncDecGen(event, var, min, max)
214 #if defined(PCBTARANIS)
215 #define CURSOR_ON_LINE() (menuHorizontalPosition < 0)
216 #else
217 #define CURSOR_ON_LINE() (0)
218 #endif
220 void check(event_t event, uint8_t curr, const MenuHandlerFunc *menuTab, uint8_t menuTabSize, const pm_uint8_t *horTab, uint8_t horTabMax, vertpos_t maxrow);
221 void check_simple(event_t event, uint8_t curr, const MenuHandlerFunc *menuTab, uint8_t menuTabSize, vertpos_t maxrow);
222 void check_submenu_simple(event_t event, uint8_t maxrow);
224 void title(const pm_char * s);
225 #define TITLE(str) title(str)
227 #if defined(CPUARM)
228 #define MENU_TAB(...) const uint8_t mstate_tab[] = __VA_ARGS__
229 #else
230 #define MENU_TAB(...) static const pm_uint8_t mstate_tab[] PROGMEM = __VA_ARGS__
231 #endif
233 #if defined(PCBX7)
234 #define MENU_CHECK(tab, menu, lines_count) \
235 check(event, menu, tab, DIM(tab), mstate_tab, DIM(mstate_tab)-1, lines_count)
236 #else
237 #define MENU_CHECK(tab, menu, lines_count) \
238 check(event, menu, tab, DIM(tab), mstate_tab, DIM(mstate_tab)-1, (lines_count)-1)
239 #endif
241 #define MENU(title, tab, menu, lines_count, ...) \
242 MENU_TAB(__VA_ARGS__); \
243 MENU_CHECK(tab, menu, lines_count); \
244 TITLE(title)
246 #if defined(PCBX7)
247 #define SIMPLE_MENU_NOTITLE(tab, menu, lines_count) \
248 check_simple(event, menu, tab, DIM(tab), lines_count);
249 #define SUBMENU_NOTITLE(lines_count, ...) { \
250 MENU_TAB(__VA_ARGS__); \
251 check(event, 0, NULL, 0, mstate_tab, DIM(mstate_tab)-1, lines_count); \
253 #define SUBMENU(title, lines_count, ...) \
254 MENU_TAB(__VA_ARGS__); \
255 check(event, 0, NULL, 0, mstate_tab, DIM(mstate_tab)-1, lines_count); \
256 TITLE(title)
257 #define SIMPLE_SUBMENU_NOTITLE(lines_count) \
258 check_submenu_simple(event, lines_count);
259 #else
260 #define SIMPLE_MENU_NOTITLE(tab, menu, lines_count) \
261 check_simple(event, menu, tab, DIM(tab), (lines_count)-1);
262 #define SUBMENU_NOTITLE(lines_count, ...) { \
263 MENU_TAB(__VA_ARGS__); \
264 check(event, 0, NULL, 0, mstate_tab, DIM(mstate_tab)-1, (lines_count)-1); \
267 #define SUBMENU(title, lines_count, ...) \
268 MENU_TAB(__VA_ARGS__); \
269 check(event, 0, NULL, 0, mstate_tab, DIM(mstate_tab)-1, (lines_count)-1); \
270 TITLE(title)
272 #define SIMPLE_SUBMENU_NOTITLE(lines_count) \
273 check_submenu_simple(event, (lines_count)-1);
277 #endif
279 #define SIMPLE_MENU(title, tab, menu, lines_count) \
280 SIMPLE_MENU_NOTITLE(tab, menu, lines_count); \
281 TITLE(title)
283 #define SIMPLE_SUBMENU(title, lines_count) \
284 SIMPLE_SUBMENU_NOTITLE(lines_count); \
285 TITLE(title)
287 #if defined(CPUARM)
288 typedef int choice_t;
289 #else
290 typedef int8_t choice_t;
291 #endif
293 choice_t editChoice(coord_t x, coord_t y, const pm_char * label, const pm_char *values, choice_t value, choice_t min, choice_t max, LcdFlags attr, event_t event);
294 uint8_t editCheckBox(uint8_t value, coord_t x, coord_t y, const pm_char * label, LcdFlags attr, event_t event);
295 int8_t editSwitch(coord_t x, coord_t y, int8_t value, LcdFlags attr, event_t event);
297 #define ON_OFF_MENU_ITEM(value, x, y, label, attr, event) value = editCheckBox(value, x, y, label, attr, event)
299 #if defined(CPUARM) && defined(GVARS)
300 #define GVAR_MENU_ITEM(x, y, v, min, max, attr, editflags, event) editGVarFieldValue(x, y, v, min, max, attr, editflags, event)
301 #else
302 #define GVAR_MENU_ITEM(x, y, v, min, max, attr, editflags, event) editGVarFieldValue(x, y, v, min, max, attr, event)
303 #endif
305 #if defined(GVARS) && defined(CPUARM)
306 int16_t editGVarFieldValue(coord_t x, coord_t y, int16_t value, int16_t min, int16_t max, LcdFlags attr, uint8_t editflags, event_t event);
307 void drawGVarName(coord_t x, coord_t y, int8_t index, LcdFlags flags=0);
308 void drawGVarValue(coord_t x, coord_t y, uint8_t gvar, gvar_t value, LcdFlags flags=0);
309 #elif defined(GVARS)
310 int16_t editGVarFieldValue(coord_t x, coord_t y, int16_t value, int16_t min, int16_t max, LcdFlags attr, event_t event);
311 #else
312 int16_t editGVarFieldValue(coord_t x, coord_t y, int16_t value, int16_t min, int16_t max, LcdFlags attr, event_t event);
313 #endif
315 void gvarWeightItem(coord_t x, coord_t y, MixData * md, LcdFlags attr, event_t event);
317 #if defined(GVARS)
318 #define displayGVar(x, y, v, min, max) GVAR_MENU_ITEM(x, y, v, min, max, 0, 0, 0)
319 #else
320 #define displayGVar(x, y, v, min, max) lcdDraw8bitsNumber(x, y, v)
321 #endif
323 #if defined(CPUARM)
324 void editName(coord_t x, coord_t y, char * name, uint8_t size, event_t event, uint8_t active, LcdFlags attr=ZCHAR);
325 #else
326 void editName(coord_t x, coord_t y, char * name, uint8_t size, event_t event, uint8_t active);
327 #endif
329 #if defined(CPUM64)
330 #define editSingleName(x, y, label, name, size, event, active) editName(x, y, name, size, event, active)
331 #else
332 void editSingleName(coord_t x, coord_t y, const pm_char * label, char * name, uint8_t size, event_t event, uint8_t active);
333 #endif
335 uint8_t editDelay(coord_t y, event_t event, uint8_t attr, const pm_char * str, uint8_t delay);
336 #define EDIT_DELAY(x, y, event, attr, str, delay) editDelay(y, event, attr, str, delay)
338 #define WARNING_TYPE_ASTERISK 0
339 #define WARNING_TYPE_CONFIRM 1
340 #define WARNING_TYPE_INPUT 2
342 extern const pm_char * warningText;
343 extern const pm_char * warningInfoText;
344 extern uint8_t warningInfoLength;
345 extern uint8_t warningResult;
346 extern uint8_t warningType;
348 #define COPY_MODE 1
349 #define MOVE_MODE 2
350 extern uint8_t s_copyMode;
351 extern int8_t s_copySrcRow;
352 extern int8_t s_copyTgtOfs;
353 extern uint8_t s_currIdx;
354 extern uint8_t s_curveChan;
355 extern uint8_t s_copySrcIdx;
356 extern uint8_t s_copySrcCh;
357 extern int8_t s_currCh;
358 extern uint8_t s_maxLines;
360 #if defined(SDCARD)
361 #define STATUS_LINE_LENGTH 32
362 extern char statusLineMsg[STATUS_LINE_LENGTH];
363 void showStatusLine();
364 void drawStatusLine();
365 #else
366 #define drawStatusLine()
367 #endif
369 #if defined(CPUARM)
370 #define TEXT_FILENAME_MAXLEN 40
371 extern char s_text_file[TEXT_FILENAME_MAXLEN];
372 void menuTextView(event_t event);
373 void pushMenuTextView(const char *filename);
374 void pushModelNotes();
375 #endif
377 #define LABEL(...) (uint8_t)-1
379 #define CURSOR_MOVED_LEFT(event) (IS_ROTARY_LEFT(event) || EVT_KEY_MASK(event) == KEY_LEFT)
380 #define CURSOR_MOVED_RIGHT(event) (IS_ROTARY_RIGHT(event) || EVT_KEY_MASK(event) == KEY_RIGHT)
382 #if defined(ROTARY_ENCODERS)
383 #define CASE_EVT_ROTARY_BREAK case EVT_ROTARY_BREAK:
384 #define CASE_EVT_ROTARY_LONG case EVT_ROTARY_LONG:
385 #else
386 #define CASE_EVT_ROTARY_BREAK
387 #define CASE_EVT_ROTARY_LONG
388 #endif
390 #if defined(ROTARY_ENCODER_NAVIGATION)
391 #define IS_ROTARY_LEFT(evt) (evt == EVT_ROTARY_LEFT)
392 #define IS_ROTARY_RIGHT(evt) (evt == EVT_ROTARY_RIGHT)
393 #define IS_ROTARY_BREAK(evt) (evt == EVT_ROTARY_BREAK)
394 #define IS_ROTARY_LONG(evt) (evt == EVT_ROTARY_LONG)
395 #define IS_ROTARY_EVENT(evt) (EVT_KEY_MASK(evt) >= 0x0e)
396 void repeatLastCursorMove(event_t event);
397 #define REPEAT_LAST_CURSOR_MOVE() { if (EVT_KEY_MASK(event) >= 0x0e) putEvent(event); else repeatLastCursorMove(event); }
398 #define MOVE_CURSOR_FROM_HERE() if (menuHorizontalPosition > 0) REPEAT_LAST_CURSOR_MOVE()
399 #else
400 #define IS_ROTARY_LEFT(evt) (0)
401 #define IS_ROTARY_RIGHT(evt) (0)
402 #define IS_ROTARY_BREAK(evt) (0)
403 #define IS_ROTARY_LONG(evt) (0)
404 #define IS_ROTARY_EVENT(evt) (0)
405 void repeatLastCursorMove(event_t event);
406 #define REPEAT_LAST_CURSOR_MOVE() repeatLastCursorMove(event)
407 #define MOVE_CURSOR_FROM_HERE() REPEAT_LAST_CURSOR_MOVE()
408 #endif
410 // TODO enum
411 #if defined(PCBX7)
412 #define EDIT_MODE_INIT 0
413 #else
414 #define EDIT_MODE_INIT -1
415 #endif
417 #if defined(CPUM64)
418 #define editNameCursorPos menuHorizontalPosition
419 #else
420 extern uint8_t editNameCursorPos;
421 #endif
423 #if defined(VIRTUAL_INPUTS)
424 uint8_t getExposCount();
425 void insertExpo(uint8_t idx);
426 void deleteExpo(uint8_t idx);
427 uint8_t getMixesCount();
428 void insertMix(uint8_t idx);
429 void deleteMix(uint8_t idx);
430 #endif
432 typedef int (*FnFuncP) (int x);
433 void drawFunction(FnFuncP fn, uint8_t offset=0);
435 void onSourceLongEnterPress(const char *result);
437 uint8_t switchToMix(uint8_t source);
439 void deleteExpoMix(uint8_t expo, uint8_t idx);
441 void drawCheckBox(coord_t x, coord_t y, uint8_t value, LcdFlags attr);
443 extern const pm_uchar sticks[] PROGMEM;
445 void drawSplash();
446 void drawSecondSplash();
447 void drawScreenIndex(uint8_t index, uint8_t count, uint8_t attr);
448 void drawStick(coord_t centrex, int16_t xval, int16_t yval);
449 void drawPotsBars();
450 void doMainScreenGraphics();
452 void drawProgressBar(const char * label, int num, int den);
453 void drawSleepBitmap();
455 #if !defined(CPUM64)
456 void drawVerticalScrollbar(coord_t x, coord_t y, coord_t h, uint16_t offset, uint16_t count, uint8_t visible);
457 #endif
459 #if defined(PCBTARANIS)
460 void drawAlertBox(const pm_char * title, const pm_char * text, const char * action);
461 #endif
463 #if defined(VOICE)
464 #define ALERT_SOUND_ARG , uint8_t sound
465 #else
466 #define ALERT_SOUND_ARG
467 #endif
469 void showAlertBox(const pm_char * title, const pm_char * text, const char * action ALERT_SOUND_ARG);
471 #define SET_SCROLLBAR_X(x)
472 #define LOAD_MODEL_BITMAP()
474 #define IS_MAIN_VIEW_DISPLAYED() menuHandlers[0] == menuMainView
475 #if defined(TELEMETRY_FRSKY)
476 #define IS_TELEMETRY_VIEW_DISPLAYED() menuHandlers[0] == menuViewTelemetryFrsky
477 #else
478 #define IS_TELEMETRY_VIEW_DISPLAYED() false
479 #endif
480 #define IS_OTHER_VIEW_DISPLAYED() false
482 #if defined(CPUARM)
483 void editCurveRef(coord_t x, coord_t y, CurveRef & curve, event_t event, LcdFlags flags);
484 #endif
486 #if defined(FLIGHT_MODES)
487 void displayFlightModes(coord_t x, coord_t y, FlightModesType value);
488 FlightModesType editFlightModes(coord_t x, coord_t y, event_t event, FlightModesType value, uint8_t attr);
489 #else
490 #define displayFlightModes(...)
491 #endif
493 #endif // _GUI_H_