summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorJaakko Keränen <jaakko.keranen@iki.fi>2021-02-26 10:26:31 +0200
committerJaakko Keränen <jaakko.keranen@iki.fi>2021-02-26 10:26:31 +0200
commitce377bd4b703b3fb6ac8ae40b9bbd1ede2e4ca26 (patch)
treee1a5d7d506a06ba26764b0892e26b0de1875365e /src
parent91a6225d8508db01574d7da2c013cb30d6a87ec8 (diff)
Visual design improvements
URL input field has a maximum width. Adjusted navbar appearance and margins. Tuned UI palette and added UI accent color preference.
Diffstat (limited to 'src')
-rw-r--r--src/app.c22
-rw-r--r--src/prefs.c1
-rw-r--r--src/prefs.h1
-rw-r--r--src/ui/color.c179
-rw-r--r--src/ui/color.h6
-rw-r--r--src/ui/documentwidget.h1
-rw-r--r--src/ui/labelwidget.c3
-rw-r--r--src/ui/util.c22
-rw-r--r--src/ui/widget.c4
-rw-r--r--src/ui/widget.h1
-rw-r--r--src/ui/window.c62
11 files changed, 184 insertions, 118 deletions
diff --git a/src/app.c b/src/app.c
index ed2c71b4..b76c4aaa 100644
--- a/src/app.c
+++ b/src/app.c
@@ -185,9 +185,9 @@ static iString *serializePrefs_App_(const iApp *d) {
185 SDL_GetWindowPosition(d->window->win, &x, &y); 185 SDL_GetWindowPosition(d->window->win, &x, &y);
186 SDL_GetWindowSize(d->window->win, &w, &h); 186 SDL_GetWindowSize(d->window->win, &w, &h);
187 appendFormat_String( 187 appendFormat_String(
188 str, "~window.setrect snap:%d width:%d height:%d coord:%d %d\n", 188 str, "~window.setrect snap:%d width:%d height:%d coord:%d %d\n",
189 snap_Window(d->window), w, h, x, y); 189 snap_Window(d->window), w, h, x, y);
190 } 190 }
191 } 191 }
192#elif !defined (iPlatformApple) 192#elif !defined (iPlatformApple)
193 if (snap_Window(d->window) == maximized_WindowSnap) { 193 if (snap_Window(d->window) == maximized_WindowSnap) {
@@ -223,6 +223,7 @@ static iString *serializePrefs_App_(const iApp *d) {
223 appendFormat_String(str, "quoteicon.set arg:%d\n", d->prefs.quoteIcon ? 1 : 0); 223 appendFormat_String(str, "quoteicon.set arg:%d\n", d->prefs.quoteIcon ? 1 : 0);
224 appendFormat_String(str, "prefs.hoverlink.changed arg:%d\n", d->prefs.hoverLink); 224 appendFormat_String(str, "prefs.hoverlink.changed arg:%d\n", d->prefs.hoverLink);
225 appendFormat_String(str, "theme.set arg:%d auto:1\n", d->prefs.theme); 225 appendFormat_String(str, "theme.set arg:%d auto:1\n", d->prefs.theme);
226 appendFormat_String(str, "accent.set arg:%d\n", d->prefs.accent);
226 appendFormat_String(str, "ostheme arg:%d\n", d->prefs.useSystemTheme); 227 appendFormat_String(str, "ostheme arg:%d\n", d->prefs.useSystemTheme);
227 appendFormat_String(str, "doctheme.dark.set arg:%d\n", d->prefs.docThemeDark); 228 appendFormat_String(str, "doctheme.dark.set arg:%d\n", d->prefs.docThemeDark);
228 appendFormat_String(str, "doctheme.light.set arg:%d\n", d->prefs.docThemeLight); 229 appendFormat_String(str, "doctheme.light.set arg:%d\n", d->prefs.docThemeLight);
@@ -521,7 +522,7 @@ static void init_App_(iApp *d, int argc, char **argv) {
521 postCommand_App("window.unfreeze"); 522 postCommand_App("window.unfreeze");
522 d->autoReloadTimer = SDL_AddTimer(60 * 1000, postAutoReloadCommand_App_, NULL); 523 d->autoReloadTimer = SDL_AddTimer(60 * 1000, postAutoReloadCommand_App_, NULL);
523 postCommand_App("document.autoreload"); 524 postCommand_App("document.autoreload");
524 d->isFinishedLaunching = iTrue; 525 d->isFinishedLaunching = iTrue;
525 /* Run any commands that were pending completion of launch. */ { 526 /* Run any commands that were pending completion of launch. */ {
526 iForEach(StringList, i, d->launchCommands) { 527 iForEach(StringList, i, d->launchCommands) {
527 postCommandString_App(i.value); 528 postCommandString_App(i.value);
@@ -1040,6 +1041,11 @@ static void updatePrefsThemeButtons_(iWidget *d) {
1040 selected_WidgetFlag, 1041 selected_WidgetFlag,
1041 colorTheme_App() == i); 1042 colorTheme_App() == i);
1042 } 1043 }
1044 for (size_t i = 0; i < max_ColorAccent; i++) {
1045 setFlags_Widget(findChild_Widget(d, format_CStr("prefs.accent.%u", i)),
1046 selected_WidgetFlag,
1047 prefs_App()->accent == i);
1048 }
1043} 1049}
1044 1050
1045static void updateDropdownSelection_(iLabelWidget *dropButton, const char *selectedCommand) { 1051static void updateDropdownSelection_(iLabelWidget *dropButton, const char *selectedCommand) {
@@ -1290,7 +1296,7 @@ iBool handleCommand_App(const char *cmd) {
1290 setSnap_Window(d->window, maximized_WindowSnap); 1296 setSnap_Window(d->window, maximized_WindowSnap);
1291 } 1297 }
1292 else { 1298 else {
1293 setSnap_Window(d->window, snap_Window(d->window) == maximized_WindowSnap ? 0 : 1299 setSnap_Window(d->window, snap_Window(d->window) == maximized_WindowSnap ? 0 :
1294 maximized_WindowSnap); 1300 maximized_WindowSnap);
1295 } 1301 }
1296 return iTrue; 1302 return iTrue;
@@ -1359,6 +1365,12 @@ iBool handleCommand_App(const char *cmd) {
1359 postCommandf_App("theme.changed auto:%d", isAuto); 1365 postCommandf_App("theme.changed auto:%d", isAuto);
1360 return iTrue; 1366 return iTrue;
1361 } 1367 }
1368 else if (equal_Command(cmd, "accent.set")) {
1369 d->prefs.accent = arg_Command(cmd);
1370 setThemePalette_Color(d->prefs.theme);
1371 postCommandf_App("theme.changed auto:1");
1372 return iTrue;
1373 }
1362 else if (equal_Command(cmd, "ostheme")) { 1374 else if (equal_Command(cmd, "ostheme")) {
1363 d->prefs.useSystemTheme = arg_Command(cmd); 1375 d->prefs.useSystemTheme = arg_Command(cmd);
1364 return iTrue; 1376 return iTrue;
@@ -1590,7 +1602,7 @@ iBool handleCommand_App(const char *cmd) {
1590 } 1602 }
1591 else if (equal_Command(cmd, "preferences")) { 1603 else if (equal_Command(cmd, "preferences")) {
1592 iWidget *dlg = makePreferences_Widget(); 1604 iWidget *dlg = makePreferences_Widget();
1593 updatePrefsThemeButtons_(dlg); 1605 updatePrefsThemeButtons_(dlg);
1594 setText_InputWidget(findChild_Widget(dlg, "prefs.downloads"), &d->prefs.downloadDir); 1606 setText_InputWidget(findChild_Widget(dlg, "prefs.downloads"), &d->prefs.downloadDir);
1595 setToggle_Widget(findChild_Widget(dlg, "prefs.hoverlink"), d->prefs.hoverLink); 1607 setToggle_Widget(findChild_Widget(dlg, "prefs.hoverlink"), d->prefs.hoverLink);
1596 setToggle_Widget(findChild_Widget(dlg, "prefs.smoothscroll"), d->prefs.smoothScrolling); 1608 setToggle_Widget(findChild_Widget(dlg, "prefs.smoothscroll"), d->prefs.smoothScrolling);
diff --git a/src/prefs.c b/src/prefs.c
index 056ae267..97ad7f48 100644
--- a/src/prefs.c
+++ b/src/prefs.c
@@ -26,6 +26,7 @@ void init_Prefs(iPrefs *d) {
26 d->dialogTab = 0; 26 d->dialogTab = 0;
27 d->useSystemTheme = iTrue; 27 d->useSystemTheme = iTrue;
28 d->theme = dark_ColorTheme; 28 d->theme = dark_ColorTheme;
29 d->accent = cyan_ColorAccent;
29 d->customFrame = iFalse; /* needs some more work to be default */ 30 d->customFrame = iFalse; /* needs some more work to be default */
30 d->retainWindowSize = iTrue; 31 d->retainWindowSize = iTrue;
31 d->uiScale = 1.0f; /* default set elsewhere */ 32 d->uiScale = 1.0f; /* default set elsewhere */
diff --git a/src/prefs.h b/src/prefs.h
index 1889c338..4bbe3ad5 100644
--- a/src/prefs.h
+++ b/src/prefs.h
@@ -38,6 +38,7 @@ struct Impl_Prefs {
38 /* Window */ 38 /* Window */
39 iBool useSystemTheme; 39 iBool useSystemTheme;
40 enum iColorTheme theme; 40 enum iColorTheme theme;
41 enum iColorAccent accent;
41 iBool customFrame; /* when LAGRANGE_CUSTOM_FRAME is defined */ 42 iBool customFrame; /* when LAGRANGE_CUSTOM_FRAME is defined */
42 iBool retainWindowSize; 43 iBool retainWindowSize;
43 float uiScale; 44 float uiScale;
diff --git a/src/ui/color.c b/src/ui/color.c
index 5d3fbaf5..9f657088 100644
--- a/src/ui/color.c
+++ b/src/ui/color.c
@@ -21,6 +21,7 @@ ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
21SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ 21SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
22 22
23#include "color.h" 23#include "color.h"
24#include "app.h"
24 25
25#include <the_Foundation/string.h> 26#include <the_Foundation/string.h>
26 27
@@ -52,10 +53,10 @@ static const iColor lightPalette_[] = {
52 { 235, 235, 235, 255 }, 53 { 235, 235, 235, 255 },
53 { 255, 255, 255, 255 }, 54 { 255, 255, 255, 255 },
54 55
55 { 142, 100, 20, 255 }, 56 { 210, 120, 10, 255 },
56 { 215, 210, 200, 255 }, 57 { 235, 215, 200, 255 },
57 { 10, 85, 112, 255 }, 58 { 10, 110, 130, 255 },
58 { 150, 205, 220, 255 }, 59 { 170, 215, 220, 255 },
59 60
60 { 255, 255, 32, 255 }, 61 { 255, 255, 32, 255 },
61 { 255, 64, 64, 255 }, 62 { 255, 64, 64, 255 },
@@ -71,14 +72,19 @@ iLocalDef void copy_(enum iColorId dst, enum iColorId src) {
71} 72}
72 73
73void setThemePalette_Color(enum iColorTheme theme) { 74void setThemePalette_Color(enum iColorTheme theme) {
75 const iPrefs *prefs = prefs_App();
74 memcpy(palette_, isDark_ColorTheme(theme) ? darkPalette_ : lightPalette_, sizeof(darkPalette_)); 76 memcpy(palette_, isDark_ColorTheme(theme) ? darkPalette_ : lightPalette_, sizeof(darkPalette_));
77 const int accentHi = (prefs->accent == cyan_ColorAccent ? cyan_ColorId : orange_ColorId);
78 const int accentLo = (prefs->accent == cyan_ColorAccent ? teal_ColorId : brown_ColorId);
79 const int altAccentHi = (prefs->accent == cyan_ColorAccent ? orange_ColorId : cyan_ColorId);
80 const int altAccentLo = (prefs->accent == cyan_ColorAccent ? brown_ColorId : teal_ColorId);
75 switch (theme) { 81 switch (theme) {
76 case pureBlack_ColorTheme: 82 case pureBlack_ColorTheme: {
77 copy_(uiBackground_ColorId, black_ColorId); 83 copy_(uiBackground_ColorId, black_ColorId);
78 copy_(uiBackgroundHover_ColorId, black_ColorId); 84 copy_(uiBackgroundHover_ColorId, black_ColorId);
79 copy_(uiBackgroundPressed_ColorId, orange_ColorId); 85 copy_(uiBackgroundPressed_ColorId, altAccentHi);
80 copy_(uiBackgroundSelected_ColorId, teal_ColorId); 86 copy_(uiBackgroundSelected_ColorId, accentLo);
81 copy_(uiBackgroundFramelessHover_ColorId, teal_ColorId); 87 copy_(uiBackgroundFramelessHover_ColorId, accentLo);
82 set_Color(uiBackgroundSidebar_ColorId, 88 set_Color(uiBackgroundSidebar_ColorId,
83 mix_Color(get_Color(black_ColorId), get_Color(gray25_ColorId), 0.55f)); 89 mix_Color(get_Color(black_ColorId), get_Color(gray25_ColorId), 0.55f));
84 copy_(uiText_ColorId, gray75_ColorId); 90 copy_(uiText_ColorId, gray75_ColorId);
@@ -88,45 +94,46 @@ void setThemePalette_Color(enum iColorTheme theme) {
88 copy_(uiTextSelected_ColorId, white_ColorId); 94 copy_(uiTextSelected_ColorId, white_ColorId);
89 copy_(uiTextFramelessHover_ColorId, white_ColorId); 95 copy_(uiTextFramelessHover_ColorId, white_ColorId);
90 copy_(uiTextDisabled_ColorId, gray25_ColorId); 96 copy_(uiTextDisabled_ColorId, gray25_ColorId);
91 copy_(uiTextShortcut_ColorId, cyan_ColorId); 97 copy_(uiTextShortcut_ColorId, accentHi);
92 copy_(uiTextAction_ColorId, cyan_ColorId); 98 copy_(uiTextAction_ColorId, accentHi);
93 copy_(uiTextCaution_ColorId, orange_ColorId); 99 copy_(uiTextCaution_ColorId, altAccentHi);
94 copy_(uiTextAppTitle_ColorId, cyan_ColorId); 100 copy_(uiTextAppTitle_ColorId, accentHi);
95 copy_(uiFrame_ColorId, black_ColorId); 101 copy_(uiFrame_ColorId, black_ColorId);
96 copy_(uiEmboss1_ColorId, gray25_ColorId); 102 copy_(uiEmboss1_ColorId, gray25_ColorId);
97 copy_(uiEmboss2_ColorId, black_ColorId); 103 copy_(uiEmboss2_ColorId, black_ColorId);
98 copy_(uiEmbossHover1_ColorId, cyan_ColorId); 104 copy_(uiEmbossHover1_ColorId, accentHi);
99 copy_(uiEmbossHover2_ColorId, teal_ColorId); 105 copy_(uiEmbossHover2_ColorId, accentLo);
100 copy_(uiEmbossPressed1_ColorId, brown_ColorId); 106 copy_(uiEmbossPressed1_ColorId, altAccentLo);
101 copy_(uiEmbossPressed2_ColorId, gray75_ColorId); 107 copy_(uiEmbossPressed2_ColorId, gray75_ColorId);
102 copy_(uiEmbossSelected1_ColorId, cyan_ColorId); 108 copy_(uiEmbossSelected1_ColorId, accentHi);
103 copy_(uiEmbossSelected2_ColorId, black_ColorId); 109 copy_(uiEmbossSelected2_ColorId, black_ColorId);
104 copy_(uiEmbossSelectedHover1_ColorId, white_ColorId); 110 copy_(uiEmbossSelectedHover1_ColorId, white_ColorId);
105 copy_(uiEmbossSelectedHover2_ColorId, cyan_ColorId); 111 copy_(uiEmbossSelectedHover2_ColorId, accentHi);
106 copy_(uiInputBackground_ColorId, black_ColorId); 112 copy_(uiInputBackground_ColorId, black_ColorId);
107 copy_(uiInputBackgroundFocused_ColorId, black_ColorId); 113 copy_(uiInputBackgroundFocused_ColorId, black_ColorId);
108 copy_(uiInputText_ColorId, gray75_ColorId); 114 copy_(uiInputText_ColorId, gray75_ColorId);
109 copy_(uiInputTextFocused_ColorId, white_ColorId); 115 copy_(uiInputTextFocused_ColorId, white_ColorId);
110 copy_(uiInputFrame_ColorId, gray25_ColorId); 116 copy_(uiInputFrame_ColorId, gray25_ColorId);
111 copy_(uiInputFrameHover_ColorId, cyan_ColorId); 117 copy_(uiInputFrameHover_ColorId, accentHi);
112 copy_(uiInputFrameFocused_ColorId, orange_ColorId); 118 copy_(uiInputFrameFocused_ColorId, altAccentHi);
113 copy_(uiInputCursor_ColorId, orange_ColorId); 119 copy_(uiInputCursor_ColorId, altAccentHi);
114 copy_(uiInputCursorText_ColorId, black_ColorId); 120 copy_(uiInputCursorText_ColorId, black_ColorId);
115 copy_(uiHeading_ColorId, cyan_ColorId); 121 copy_(uiHeading_ColorId, accentHi);
116 copy_(uiAnnotation_ColorId, teal_ColorId); 122 copy_(uiAnnotation_ColorId, accentLo);
117 copy_(uiIcon_ColorId, cyan_ColorId); 123 copy_(uiIcon_ColorId, accentHi);
118 copy_(uiIconHover_ColorId, cyan_ColorId); 124 copy_(uiIconHover_ColorId, accentHi);
119 copy_(uiSeparator_ColorId, gray25_ColorId); 125 copy_(uiSeparator_ColorId, gray25_ColorId);
120 copy_(uiMarked_ColorId, brown_ColorId); 126 copy_(uiMarked_ColorId, altAccentLo);
121 copy_(uiMatching_ColorId, teal_ColorId); 127 copy_(uiMatching_ColorId, accentLo);
122 break; 128 break;
129 }
123 default: 130 default:
124 case dark_ColorTheme: 131 case dark_ColorTheme: {
125 copy_(uiBackground_ColorId, gray25_ColorId); 132 copy_(uiBackground_ColorId, gray25_ColorId);
126 copy_(uiBackgroundHover_ColorId, gray25_ColorId); 133 copy_(uiBackgroundHover_ColorId, gray25_ColorId);
127 copy_(uiBackgroundPressed_ColorId, orange_ColorId); 134 copy_(uiBackgroundPressed_ColorId, altAccentHi);
128 copy_(uiBackgroundSelected_ColorId, teal_ColorId); 135 copy_(uiBackgroundSelected_ColorId, accentLo);
129 copy_(uiBackgroundFramelessHover_ColorId, teal_ColorId); 136 copy_(uiBackgroundFramelessHover_ColorId, accentLo);
130 set_Color(uiBackgroundSidebar_ColorId, 137 set_Color(uiBackgroundSidebar_ColorId,
131 mix_Color(get_Color(black_ColorId), get_Color(gray25_ColorId), 0.75f)); 138 mix_Color(get_Color(black_ColorId), get_Color(gray25_ColorId), 0.75f));
132 copy_(uiText_ColorId, gray75_ColorId); 139 copy_(uiText_ColorId, gray75_ColorId);
@@ -136,45 +143,46 @@ void setThemePalette_Color(enum iColorTheme theme) {
136 copy_(uiTextSelected_ColorId, white_ColorId); 143 copy_(uiTextSelected_ColorId, white_ColorId);
137 copy_(uiTextDisabled_ColorId, gray50_ColorId); 144 copy_(uiTextDisabled_ColorId, gray50_ColorId);
138 copy_(uiTextFramelessHover_ColorId, white_ColorId); 145 copy_(uiTextFramelessHover_ColorId, white_ColorId);
139 copy_(uiTextShortcut_ColorId, cyan_ColorId); 146 copy_(uiTextShortcut_ColorId, accentHi);
140 copy_(uiTextAction_ColorId, cyan_ColorId); 147 copy_(uiTextAction_ColorId, accentHi);
141 copy_(uiTextCaution_ColorId, orange_ColorId); 148 copy_(uiTextCaution_ColorId, altAccentHi);
142 copy_(uiTextAppTitle_ColorId, cyan_ColorId); 149 copy_(uiTextAppTitle_ColorId, accentHi);
143 copy_(uiFrame_ColorId, gray25_ColorId); 150 copy_(uiFrame_ColorId, gray25_ColorId);
144 copy_(uiEmboss1_ColorId, gray50_ColorId); 151 copy_(uiEmboss1_ColorId, gray50_ColorId);
145 copy_(uiEmboss2_ColorId, black_ColorId); 152 copy_(uiEmboss2_ColorId, black_ColorId);
146 copy_(uiEmbossHover1_ColorId, cyan_ColorId); 153 copy_(uiEmbossHover1_ColorId, accentHi);
147 copy_(uiEmbossHover2_ColorId, teal_ColorId); 154 copy_(uiEmbossHover2_ColorId, accentLo);
148 copy_(uiEmbossPressed1_ColorId, brown_ColorId); 155 copy_(uiEmbossPressed1_ColorId, altAccentLo);
149 copy_(uiEmbossPressed2_ColorId, white_ColorId); 156 copy_(uiEmbossPressed2_ColorId, white_ColorId);
150 copy_(uiEmbossSelected1_ColorId, cyan_ColorId); 157 copy_(uiEmbossSelected1_ColorId, accentHi);
151 copy_(uiEmbossSelected2_ColorId, black_ColorId); 158 copy_(uiEmbossSelected2_ColorId, black_ColorId);
152 copy_(uiEmbossSelectedHover1_ColorId, white_ColorId); 159 copy_(uiEmbossSelectedHover1_ColorId, white_ColorId);
153 copy_(uiEmbossSelectedHover2_ColorId, cyan_ColorId); 160 copy_(uiEmbossSelectedHover2_ColorId, accentHi);
154 set_Color(uiInputBackground_ColorId, 161 set_Color(uiInputBackground_ColorId,
155 mix_Color(get_Color(black_ColorId), get_Color(gray25_ColorId), 0.7f)); 162 mix_Color(get_Color(black_ColorId), get_Color(gray25_ColorId), 0.7f));
156 copy_(uiInputBackgroundFocused_ColorId, black_ColorId); 163 copy_(uiInputBackgroundFocused_ColorId, black_ColorId);
157 copy_(uiInputText_ColorId, gray75_ColorId); 164 copy_(uiInputText_ColorId, gray75_ColorId);
158 copy_(uiInputTextFocused_ColorId, white_ColorId); 165 copy_(uiInputTextFocused_ColorId, white_ColorId);
159 copy_(uiInputFrame_ColorId, uiInputBackground_ColorId); 166 copy_(uiInputFrame_ColorId, uiInputBackground_ColorId);
160 copy_(uiInputFrameHover_ColorId, cyan_ColorId); 167 copy_(uiInputFrameHover_ColorId, accentHi);
161 copy_(uiInputFrameFocused_ColorId, orange_ColorId); 168 copy_(uiInputFrameFocused_ColorId, altAccentHi);
162 copy_(uiInputCursor_ColorId, orange_ColorId); 169 copy_(uiInputCursor_ColorId, altAccentHi);
163 copy_(uiInputCursorText_ColorId, black_ColorId); 170 copy_(uiInputCursorText_ColorId, black_ColorId);
164 copy_(uiHeading_ColorId, cyan_ColorId); 171 copy_(uiHeading_ColorId, accentHi);
165 copy_(uiAnnotation_ColorId, teal_ColorId); 172 copy_(uiAnnotation_ColorId, accentLo);
166 copy_(uiIcon_ColorId, cyan_ColorId); 173 copy_(uiIcon_ColorId, accentHi);
167 copy_(uiIconHover_ColorId, cyan_ColorId); 174 copy_(uiIconHover_ColorId, accentHi);
168 copy_(uiSeparator_ColorId, black_ColorId); 175 copy_(uiSeparator_ColorId, black_ColorId);
169 copy_(uiMarked_ColorId, brown_ColorId); 176 copy_(uiMarked_ColorId, altAccentLo);
170 copy_(uiMatching_ColorId, teal_ColorId); 177 copy_(uiMatching_ColorId, accentLo);
171 break; 178 break;
179 }
172 case light_ColorTheme: 180 case light_ColorTheme:
173 copy_(uiBackground_ColorId, gray75_ColorId); 181 copy_(uiBackground_ColorId, gray75_ColorId);
174 copy_(uiBackgroundHover_ColorId, gray75_ColorId); 182 copy_(uiBackgroundHover_ColorId, gray75_ColorId);
175 copy_(uiBackgroundSelected_ColorId, orange_ColorId); 183 copy_(uiBackgroundSelected_ColorId, accentHi);
176 copy_(uiBackgroundPressed_ColorId, cyan_ColorId); 184 copy_(uiBackgroundPressed_ColorId, altAccentHi);
177 copy_(uiBackgroundFramelessHover_ColorId, orange_ColorId); 185 copy_(uiBackgroundFramelessHover_ColorId, accentHi);
178 set_Color(uiBackgroundSidebar_ColorId, 186 set_Color(uiBackgroundSidebar_ColorId,
179 mix_Color(get_Color(white_ColorId), get_Color(gray75_ColorId), 0.5f)); 187 mix_Color(get_Color(white_ColorId), get_Color(gray75_ColorId), 0.5f));
180 copy_(uiText_ColorId, black_ColorId); 188 copy_(uiText_ColorId, black_ColorId);
@@ -184,10 +192,10 @@ void setThemePalette_Color(enum iColorTheme theme) {
184 copy_(uiTextSelected_ColorId, black_ColorId); 192 copy_(uiTextSelected_ColorId, black_ColorId);
185 copy_(uiTextDisabled_ColorId, gray50_ColorId); 193 copy_(uiTextDisabled_ColorId, gray50_ColorId);
186 copy_(uiTextFramelessHover_ColorId, black_ColorId); 194 copy_(uiTextFramelessHover_ColorId, black_ColorId);
187 copy_(uiTextShortcut_ColorId, brown_ColorId); 195 copy_(uiTextShortcut_ColorId, accentLo);
188 copy_(uiTextAction_ColorId, brown_ColorId); 196 copy_(uiTextAction_ColorId, accentLo);
189 copy_(uiTextCaution_ColorId, teal_ColorId); 197 copy_(uiTextCaution_ColorId, altAccentLo);
190 copy_(uiTextAppTitle_ColorId, teal_ColorId); 198 copy_(uiTextAppTitle_ColorId, altAccentLo);
191 copy_(uiFrame_ColorId, gray50_ColorId); 199 copy_(uiFrame_ColorId, gray50_ColorId);
192 copy_(uiEmboss1_ColorId, white_ColorId); 200 copy_(uiEmboss1_ColorId, white_ColorId);
193 copy_(uiEmboss2_ColorId, gray50_ColorId); 201 copy_(uiEmboss2_ColorId, gray50_ColorId);
@@ -196,34 +204,34 @@ void setThemePalette_Color(enum iColorTheme theme) {
196 copy_(uiEmbossPressed1_ColorId, black_ColorId); 204 copy_(uiEmbossPressed1_ColorId, black_ColorId);
197 copy_(uiEmbossPressed2_ColorId, white_ColorId); 205 copy_(uiEmbossPressed2_ColorId, white_ColorId);
198 copy_(uiEmbossSelected1_ColorId, white_ColorId); 206 copy_(uiEmbossSelected1_ColorId, white_ColorId);
199 copy_(uiEmbossSelected2_ColorId, brown_ColorId); 207 copy_(uiEmbossSelected2_ColorId, accentLo);
200 copy_(uiEmbossSelectedHover1_ColorId, brown_ColorId); 208 copy_(uiEmbossSelectedHover1_ColorId, accentLo);
201 copy_(uiEmbossSelectedHover2_ColorId, brown_ColorId); 209 copy_(uiEmbossSelectedHover2_ColorId, accentLo);
202 copy_(uiInputBackground_ColorId, white_ColorId); 210 copy_(uiInputBackground_ColorId, white_ColorId);
203 copy_(uiInputBackgroundFocused_ColorId, white_ColorId); 211 copy_(uiInputBackgroundFocused_ColorId, white_ColorId);
204 copy_(uiInputText_ColorId, gray25_ColorId); 212 copy_(uiInputText_ColorId, gray25_ColorId);
205 copy_(uiInputTextFocused_ColorId, black_ColorId); 213 copy_(uiInputTextFocused_ColorId, black_ColorId);
206 set_Color(uiInputFrame_ColorId, 214 set_Color(uiInputFrame_ColorId,
207 mix_Color(get_Color(gray50_ColorId), get_Color(gray75_ColorId), 0.5f)); 215 mix_Color(get_Color(gray50_ColorId), get_Color(gray75_ColorId), 0.5f));
208 copy_(uiInputFrameHover_ColorId, brown_ColorId); 216 copy_(uiInputFrameHover_ColorId, accentLo);
209 copy_(uiInputFrameFocused_ColorId, teal_ColorId); 217 copy_(uiInputFrameFocused_ColorId, altAccentLo);
210 copy_(uiInputCursor_ColorId, teal_ColorId); 218 copy_(uiInputCursor_ColorId, altAccentLo);
211 copy_(uiInputCursorText_ColorId, white_ColorId); 219 copy_(uiInputCursorText_ColorId, white_ColorId);
212 copy_(uiHeading_ColorId, brown_ColorId); 220 copy_(uiHeading_ColorId, accentLo);
213 copy_(uiAnnotation_ColorId, gray50_ColorId); 221 copy_(uiAnnotation_ColorId, gray50_ColorId);
214 copy_(uiIcon_ColorId, brown_ColorId); 222 copy_(uiIcon_ColorId, accentLo);
215 copy_(uiIconHover_ColorId, brown_ColorId); 223 copy_(uiIconHover_ColorId, accentLo);
216 set_Color(uiSeparator_ColorId, 224 set_Color(uiSeparator_ColorId,
217 mix_Color(get_Color(gray50_ColorId), get_Color(gray75_ColorId), 0.5f)); 225 mix_Color(get_Color(gray50_ColorId), get_Color(gray75_ColorId), 0.5f));
218 copy_(uiMarked_ColorId, cyan_ColorId); 226 copy_(uiMarked_ColorId, altAccentHi);
219 copy_(uiMatching_ColorId, orange_ColorId); 227 copy_(uiMatching_ColorId, accentHi);
220 break; 228 break;
221 case pureWhite_ColorTheme: 229 case pureWhite_ColorTheme:
222 copy_(uiBackground_ColorId, white_ColorId); 230 copy_(uiBackground_ColorId, white_ColorId);
223 copy_(uiBackgroundHover_ColorId, gray75_ColorId); 231 copy_(uiBackgroundHover_ColorId, gray75_ColorId);
224 copy_(uiBackgroundSelected_ColorId, orange_ColorId); 232 copy_(uiBackgroundSelected_ColorId, accentHi);
225 copy_(uiBackgroundPressed_ColorId, cyan_ColorId); 233 copy_(uiBackgroundPressed_ColorId, altAccentHi);
226 copy_(uiBackgroundFramelessHover_ColorId, orange_ColorId); 234 copy_(uiBackgroundFramelessHover_ColorId, accentHi);
227 set_Color(uiBackgroundSidebar_ColorId, 235 set_Color(uiBackgroundSidebar_ColorId,
228 mix_Color(get_Color(white_ColorId), get_Color(gray75_ColorId), 0.5f)); 236 mix_Color(get_Color(white_ColorId), get_Color(gray75_ColorId), 0.5f));
229 set_Color(uiText_ColorId, 237 set_Color(uiText_ColorId,
@@ -234,19 +242,19 @@ void setThemePalette_Color(enum iColorTheme theme) {
234 copy_(uiTextDim_ColorId, gray25_ColorId); 242 copy_(uiTextDim_ColorId, gray25_ColorId);
235 copy_(uiTextSelected_ColorId, black_ColorId); 243 copy_(uiTextSelected_ColorId, black_ColorId);
236 copy_(uiTextFramelessHover_ColorId, black_ColorId); 244 copy_(uiTextFramelessHover_ColorId, black_ColorId);
237 copy_(uiTextShortcut_ColorId, brown_ColorId); 245 copy_(uiTextShortcut_ColorId, accentLo);
238 copy_(uiTextAction_ColorId, brown_ColorId); 246 copy_(uiTextAction_ColorId, accentLo);
239 copy_(uiTextCaution_ColorId, teal_ColorId); 247 copy_(uiTextCaution_ColorId, altAccentLo);
240 copy_(uiTextAppTitle_ColorId, teal_ColorId); 248 copy_(uiTextAppTitle_ColorId, altAccentLo);
241 copy_(uiFrame_ColorId, gray75_ColorId); 249 copy_(uiFrame_ColorId, gray75_ColorId);
242 copy_(uiEmboss1_ColorId, white_ColorId); 250 copy_(uiEmboss1_ColorId, white_ColorId);
243 copy_(uiEmboss2_ColorId, white_ColorId); 251 copy_(uiEmboss2_ColorId, white_ColorId);
244 copy_(uiEmbossHover1_ColorId, gray25_ColorId); 252 copy_(uiEmbossHover1_ColorId, gray25_ColorId);
245 copy_(uiEmbossHover2_ColorId, gray25_ColorId); 253 copy_(uiEmbossHover2_ColorId, gray25_ColorId);
246 copy_(uiEmbossPressed1_ColorId, black_ColorId); 254 copy_(uiEmbossPressed1_ColorId, black_ColorId);
247 copy_(uiEmbossPressed2_ColorId, teal_ColorId); 255 copy_(uiEmbossPressed2_ColorId, altAccentLo);
248 copy_(uiEmbossSelected1_ColorId, white_ColorId); 256 copy_(uiEmbossSelected1_ColorId, white_ColorId);
249 copy_(uiEmbossSelected2_ColorId, brown_ColorId); 257 copy_(uiEmbossSelected2_ColorId, accentLo);
250 copy_(uiEmbossSelectedHover1_ColorId, gray50_ColorId); 258 copy_(uiEmbossSelectedHover1_ColorId, gray50_ColorId);
251 copy_(uiEmbossSelectedHover2_ColorId, gray50_ColorId); 259 copy_(uiEmbossSelectedHover2_ColorId, gray50_ColorId);
252 copy_(uiInputBackground_ColorId, white_ColorId); 260 copy_(uiInputBackground_ColorId, white_ColorId);
@@ -254,17 +262,18 @@ void setThemePalette_Color(enum iColorTheme theme) {
254 copy_(uiInputText_ColorId, gray25_ColorId); 262 copy_(uiInputText_ColorId, gray25_ColorId);
255 copy_(uiInputTextFocused_ColorId, black_ColorId); 263 copy_(uiInputTextFocused_ColorId, black_ColorId);
256 copy_(uiInputFrame_ColorId, gray50_ColorId); 264 copy_(uiInputFrame_ColorId, gray50_ColorId);
257 copy_(uiInputFrameHover_ColorId, brown_ColorId); 265 copy_(uiInputFrameHover_ColorId, accentLo);
258 copy_(uiInputFrameFocused_ColorId, teal_ColorId); 266 copy_(uiInputFrameFocused_ColorId, altAccentLo);
259 copy_(uiInputCursor_ColorId, teal_ColorId); 267 copy_(uiInputCursor_ColorId, altAccentLo);
260 copy_(uiInputCursorText_ColorId, white_ColorId); 268 copy_(uiInputCursorText_ColorId, white_ColorId);
261 copy_(uiHeading_ColorId, brown_ColorId); 269 copy_(uiHeading_ColorId, accentLo);
262 copy_(uiAnnotation_ColorId, gray50_ColorId); 270 copy_(uiAnnotation_ColorId, gray50_ColorId);
263 copy_(uiIcon_ColorId, brown_ColorId); 271 copy_(uiIcon_ColorId, accentLo);
264 copy_(uiIconHover_ColorId, brown_ColorId); 272 copy_(uiIconHover_ColorId, accentLo);
265 copy_(uiSeparator_ColorId, gray75_ColorId); 273 set_Color(uiSeparator_ColorId,
266 copy_(uiMarked_ColorId, cyan_ColorId); 274 mix_Color(get_Color(gray50_ColorId), get_Color(gray75_ColorId), 0.67f));
267 copy_(uiMatching_ColorId, orange_ColorId); 275 copy_(uiMarked_ColorId, altAccentHi);
276 copy_(uiMatching_ColorId, accentHi);
268 break; 277 break;
269 } 278 }
270 set_Color(uiSubheading_ColorId, 279 set_Color(uiSubheading_ColorId,
@@ -274,7 +283,7 @@ void setThemePalette_Color(enum iColorTheme theme) {
274 set_Color(uiBackgroundUnfocusedSelection_ColorId, 283 set_Color(uiBackgroundUnfocusedSelection_ColorId,
275 mix_Color(get_Color(uiBackground_ColorId), 284 mix_Color(get_Color(uiBackground_ColorId),
276 get_Color(uiBackgroundSelected_ColorId), 285 get_Color(uiBackgroundSelected_ColorId),
277 isDark_ColorTheme(theme) ? 0.25f : 0.66f)); 286 theme == pureBlack_ColorTheme ? 0.5f : isDark_ColorTheme(theme) ? 0.25f : 0.66f));
278 setHsl_Color(uiBackgroundFolder_ColorId, 287 setHsl_Color(uiBackgroundFolder_ColorId,
279 addSatLum_HSLColor(get_HSLColor(uiBackgroundSidebar_ColorId), 288 addSatLum_HSLColor(get_HSLColor(uiBackgroundSidebar_ColorId),
280 0, 289 0,
diff --git a/src/ui/color.h b/src/ui/color.h
index f65600d2..8556cd72 100644
--- a/src/ui/color.h
+++ b/src/ui/color.h
@@ -33,6 +33,12 @@ enum iColorTheme {
33 max_ColorTheme 33 max_ColorTheme
34}; 34};
35 35
36enum iColorAccent {
37 cyan_ColorAccent,
38 orange_ColorAccent,
39 max_ColorAccent
40};
41
36iLocalDef iBool isDark_ColorTheme(enum iColorTheme d) { 42iLocalDef iBool isDark_ColorTheme(enum iColorTheme d) {
37 return d == pureBlack_ColorTheme || d == dark_ColorTheme; 43 return d == pureBlack_ColorTheme || d == dark_ColorTheme;
38} 44}
diff --git a/src/ui/documentwidget.h b/src/ui/documentwidget.h
index 91337a24..f922e7ea 100644
--- a/src/ui/documentwidget.h
+++ b/src/ui/documentwidget.h
@@ -43,6 +43,7 @@ const iBlock * sourceContent_DocumentWidget (const iDocumentWidget *);
43const iGmDocument * document_DocumentWidget (const iDocumentWidget *); 43const iGmDocument * document_DocumentWidget (const iDocumentWidget *);
44const iString * bookmarkTitle_DocumentWidget (const iDocumentWidget *); 44const iString * bookmarkTitle_DocumentWidget (const iDocumentWidget *);
45const iString * feedTitle_DocumentWidget (const iDocumentWidget *); 45const iString * feedTitle_DocumentWidget (const iDocumentWidget *);
46int documentWidth_DocumentWidget (const iDocumentWidget *);
46 47
47void setUrl_DocumentWidget (iDocumentWidget *, const iString *url); 48void setUrl_DocumentWidget (iDocumentWidget *, const iString *url);
48void setUrlFromCache_DocumentWidget (iDocumentWidget *, const iString *url, iBool isFromCache); 49void setUrlFromCache_DocumentWidget (iDocumentWidget *, const iString *url, iBool isFromCache);
diff --git a/src/ui/labelwidget.c b/src/ui/labelwidget.c
index 1b16a028..8cba2d00 100644
--- a/src/ui/labelwidget.c
+++ b/src/ui/labelwidget.c
@@ -227,7 +227,8 @@ static void draw_LabelWidget_(const iLabelWidget *d) {
227 bottomRight_Rect(frameRect), bottomLeft_Rect(frameRect) 227 bottomRight_Rect(frameRect), bottomLeft_Rect(frameRect)
228 }; 228 };
229 drawLines_Paint(&p, points + 2, 3, frame2); 229 drawLines_Paint(&p, points + 2, 3, frame2);
230 drawLines_Paint(&p, points, 3, frame); 230 drawLines_Paint(
231 &p, points, !isHover_Widget(w) && flags & noTopFrame_WidgetFlag ? 2 : 3, frame);
231 } 232 }
232 } 233 }
233 setClip_Paint(&p, rect); 234 setClip_Paint(&p, rect);
diff --git a/src/ui/util.c b/src/ui/util.c
index 5cdac391..3e57c2b5 100644
--- a/src/ui/util.c
+++ b/src/ui/util.c
@@ -472,8 +472,12 @@ iWidget *makeMenu_Widget(iWidget *parent, const iMenuItem *items, size_t n) {
472 iClob(newKeyMods_LabelWidget(item->label, item->key, item->kmods, item->command)), 472 iClob(newKeyMods_LabelWidget(item->label, item->key, item->kmods, item->command)),
473 frameless_WidgetFlag | alignLeft_WidgetFlag | drawKey_WidgetFlag); 473 frameless_WidgetFlag | alignLeft_WidgetFlag | drawKey_WidgetFlag);
474 updateSize_LabelWidget(label); /* drawKey was set */ 474 updateSize_LabelWidget(label); /* drawKey was set */
475 if (deviceType_App() != desktop_AppDeviceType) { 475 const iBool isCaution = startsWith_CStr(item->label, uiTextCaution_ColorEscape);
476 setFont_LabelWidget(label, uiContent_FontId); 476 if (deviceType_App() == tablet_AppDeviceType) {
477 setFont_LabelWidget(label, isCaution ? uiContentBold_FontId : uiContent_FontId);
478 }
479 else if (deviceType_App() == desktop_AppDeviceType) {
480 setFont_LabelWidget(label, isCaution ? uiLabelBold_FontId : uiLabel_FontId);
477 } 481 }
478 } 482 }
479 } 483 }
@@ -669,7 +673,8 @@ static void addTabPage_Widget_(iWidget *tabs, enum iWidgetAddPos addPos, iWidget
669 addPos); 673 addPos);
670 setFlags_Widget(buttons, hidden_WidgetFlag, iFalse); 674 setFlags_Widget(buttons, hidden_WidgetFlag, iFalse);
671 setFlags_Widget(button, selected_WidgetFlag, isSel); 675 setFlags_Widget(button, selected_WidgetFlag, isSel);
672 setFlags_Widget(button, commandOnClick_WidgetFlag | expand_WidgetFlag, iTrue); 676 setFlags_Widget(
677 button, noTopFrame_WidgetFlag | commandOnClick_WidgetFlag | expand_WidgetFlag, iTrue);
673 addChildPos_Widget(pages, page, addPos); 678 addChildPos_Widget(pages, page, addPos);
674 setFlags_Widget(page, hidden_WidgetFlag | disabled_WidgetFlag, !isSel); 679 setFlags_Widget(page, hidden_WidgetFlag | disabled_WidgetFlag, !isSel);
675} 680}
@@ -1025,7 +1030,7 @@ void updateValueInput_Widget(iWidget *d, const char *title, const char *prompt)
1025 1030
1026static iBool messageHandler_(iWidget *msg, const char *cmd) { 1031static iBool messageHandler_(iWidget *msg, const char *cmd) {
1027 /* Almost any command dismisses the sheet. */ 1032 /* Almost any command dismisses the sheet. */
1028 if (!(equal_Command(cmd, "media.updated") || 1033 if (!(equal_Command(cmd, "media.updated") ||
1029 equal_Command(cmd, "media.player.update") || 1034 equal_Command(cmd, "media.player.update") ||
1030 equal_Command(cmd, "bookmarks.request.finished") || 1035 equal_Command(cmd, "bookmarks.request.finished") ||
1031 equal_Command(cmd, "document.autoreload") || 1036 equal_Command(cmd, "document.autoreload") ||
@@ -1197,6 +1202,13 @@ iWidget *makePreferences_Widget(void) {
1197 setId_Widget(addChild_Widget(themes, iClob(new_LabelWidget("Pure White", "theme.set arg:3"))), "prefs.theme.3"); 1202 setId_Widget(addChild_Widget(themes, iClob(new_LabelWidget("Pure White", "theme.set arg:3"))), "prefs.theme.3");
1198 } 1203 }
1199 addChildFlags_Widget(values, iClob(themes), arrangeHorizontal_WidgetFlag | arrangeSize_WidgetFlag); 1204 addChildFlags_Widget(values, iClob(themes), arrangeHorizontal_WidgetFlag | arrangeSize_WidgetFlag);
1205 /* Accents. */
1206 iWidget *accent = new_Widget(); {
1207 setId_Widget(addChild_Widget(accent, iClob(new_LabelWidget("Teal", "accent.set arg:0"))), "prefs.accent.0");
1208 setId_Widget(addChild_Widget(accent, iClob(new_LabelWidget("Orange", "accent.set arg:1"))), "prefs.accent.1");
1209 }
1210 addChild_Widget(headings, iClob(makeHeading_Widget("Accent color:")));
1211 addChildFlags_Widget(values, iClob(accent), arrangeHorizontal_WidgetFlag | arrangeSize_WidgetFlag);
1200#if defined (LAGRANGE_CUSTOM_FRAME) 1212#if defined (LAGRANGE_CUSTOM_FRAME)
1201 addChild_Widget(headings, iClob(makeHeading_Widget("Custom window frame:"))); 1213 addChild_Widget(headings, iClob(makeHeading_Widget("Custom window frame:")));
1202 addChild_Widget(values, iClob(makeToggle_Widget("prefs.customframe"))); 1214 addChild_Widget(values, iClob(makeToggle_Widget("prefs.customframe")));
@@ -1327,7 +1339,7 @@ iWidget *makePreferences_Widget(void) {
1327 iClob(makeDialogButtons_( 1339 iClob(makeDialogButtons_(
1328 (iMenuItem[]){ { "Dismiss", SDLK_ESCAPE, 0, "prefs.dismiss" } }, 1))); 1340 (iMenuItem[]){ { "Dismiss", SDLK_ESCAPE, 0, "prefs.dismiss" } }, 1)));
1329 addChild_Widget(get_Window()->root, iClob(dlg)); 1341 addChild_Widget(get_Window()->root, iClob(dlg));
1330 centerSheet_Widget(dlg); 1342 centerSheet_Widget(dlg);
1331 return dlg; 1343 return dlg;
1332} 1344}
1333 1345
diff --git a/src/ui/widget.c b/src/ui/widget.c
index 2bdda691..386ba6d6 100644
--- a/src/ui/widget.c
+++ b/src/ui/widget.c
@@ -334,7 +334,7 @@ void arrange_Widget(iWidget *d) {
334 iWidget *child = as_Widget(c.object); 334 iWidget *child = as_Widget(c.object);
335 if (isCollapsed_Widget_(child)) { 335 if (isCollapsed_Widget_(child)) {
336 if (d->flags & arrangeHorizontal_WidgetFlag) { 336 if (d->flags & arrangeHorizontal_WidgetFlag) {
337 setWidth_Widget_(child, 0); 337 setWidth_Widget_(child, 0);
338 } 338 }
339 if (d->flags & arrangeVertical_WidgetFlag) { 339 if (d->flags & arrangeVertical_WidgetFlag) {
340 setHeight_Widget_(child, 0); 340 setHeight_Widget_(child, 0);
@@ -682,7 +682,7 @@ void drawBackground_Widget(const iWidget *d) {
682 iPaint p; 682 iPaint p;
683 init_Paint(&p); 683 init_Paint(&p);
684 if (d->flags & mouseModal_WidgetFlag) { 684 if (d->flags & mouseModal_WidgetFlag) {
685 p.alpha = 128; 685 p.alpha = 0x60;
686 SDL_SetRenderDrawBlendMode(renderer_Window(get_Window()), SDL_BLENDMODE_BLEND); 686 SDL_SetRenderDrawBlendMode(renderer_Window(get_Window()), SDL_BLENDMODE_BLEND);
687 int fadeColor; 687 int fadeColor;
688 switch (colorTheme_App()) { 688 switch (colorTheme_App()) {
diff --git a/src/ui/widget.h b/src/ui/widget.h
index 52833f86..c5a1a360 100644
--- a/src/ui/widget.h
+++ b/src/ui/widget.h
@@ -99,6 +99,7 @@ enum iWidgetFlag {
99#define drawBackgroundToVerticalSafeArea_WidgetFlag iBit64(44) 99#define drawBackgroundToVerticalSafeArea_WidgetFlag iBit64(44)
100#define visualOffset_WidgetFlag iBit64(45) 100#define visualOffset_WidgetFlag iBit64(45)
101#define parentCannotResize_WidgetFlag iBit64(46) 101#define parentCannotResize_WidgetFlag iBit64(46)
102#define noTopFrame_WidgetFlag iBit64(47)
102 103
103enum iWidgetAddPos { 104enum iWidgetAddPos {
104 back_WidgetAddPos, 105 back_WidgetAddPos,
diff --git a/src/ui/window.c b/src/ui/window.c
index bc19fd09..89b3d9ef 100644
--- a/src/ui/window.c
+++ b/src/ui/window.c
@@ -433,8 +433,8 @@ static uint32_t updateReloadAnimation_Window_(uint32_t interval, void *window) {
433} 433}
434 434
435static void setReloadLabel_Window_(iWindow *d, iBool animating) { 435static void setReloadLabel_Window_(iWindow *d, iBool animating) {
436 updateTextCStr_LabelWidget(findChild_Widget(d->root, "reload"), 436 iLabelWidget *label = findChild_Widget(d->root, "reload");
437 animating ? loadAnimationCStr_() : reloadCStr_); 437 updateTextCStr_LabelWidget(label, animating ? loadAnimationCStr_() : reloadCStr_);
438} 438}
439 439
440static void checkLoadAnimation_Window_(iWindow *d) { 440static void checkLoadAnimation_Window_(iWindow *d) {
@@ -495,10 +495,30 @@ static void showSearchQueryIndicator_(iBool show) {
495 (iInputWidget *) parent_Widget(indicator), -1, show ? width_Widget(indicator) : 0); 495 (iInputWidget *) parent_Widget(indicator), -1, show ? width_Widget(indicator) : 0);
496} 496}
497 497
498static int navBarAvailableSpace_(iWidget *navBar) {
499 int avail = width_Rect(innerBounds_Widget(navBar));
500 iConstForEach(ObjectList, i, children_Widget(navBar)) {
501 const iWidget *child = i.object;
502 if (~flags_Widget(child) & expand_WidgetFlag &&
503 isVisible_Widget(child) &&
504 cmp_String(id_Widget(child), "url")) {
505 avail -= width_Widget(child);
506 }
507 }
508 return avail;
509}
510
498static iBool handleNavBarCommands_(iWidget *navBar, const char *cmd) { 511static iBool handleNavBarCommands_(iWidget *navBar, const char *cmd) {
499 if (equal_Command(cmd, "window.resized")) { 512 if (equal_Command(cmd, "window.resized")) {
500 const iBool isPhone = deviceType_App() == phone_AppDeviceType; 513 const iBool isPhone = deviceType_App() == phone_AppDeviceType;
501 const iBool isNarrow = !isPhone && width_Rect(bounds_Widget(navBar)) / gap_UI < 140; 514 const iBool isNarrow = !isPhone && width_Rect(bounds_Widget(navBar)) / gap_UI < 140;
515 /* Adjust navbar padding. */ {
516 int hPad = isPhone || isNarrow ? gap_UI / 2 : gap_UI * 3 / 2;
517 int vPad = gap_UI * 3 / 2;
518 int topPad = !findWidget_App("winbar") ? gap_UI / 2 : 0;
519 setPadding_Widget(navBar, hPad, vPad / 2 + topPad, hPad, vPad / 2);
520 }
521 /* Button sizing. */
502 if (isNarrow ^ ((flags_Widget(navBar) & tight_WidgetFlag) != 0)) { 522 if (isNarrow ^ ((flags_Widget(navBar) & tight_WidgetFlag) != 0)) {
503 setFlags_Widget(navBar, tight_WidgetFlag, isNarrow); 523 setFlags_Widget(navBar, tight_WidgetFlag, isNarrow);
504 iForEach(ObjectList, i, navBar->children) { 524 iForEach(ObjectList, i, navBar->children) {
@@ -531,7 +551,9 @@ static iBool handleNavBarCommands_(iWidget *navBar, const char *cmd) {
531 } 551 }
532 arrange_Widget(get_Window()->root); 552 arrange_Widget(get_Window()->root);
533 } 553 }
534 else { 554 /* Resize the URL input field. */ {
555 iWidget *urlBar = findChild_Widget(navBar, "url");
556 urlBar->rect.size.x = iMini(navBarAvailableSpace_(navBar), 167 * gap_UI);
535 arrange_Widget(navBar); 557 arrange_Widget(navBar);
536 } 558 }
537 refresh_Widget(navBar); 559 refresh_Widget(navBar);
@@ -795,9 +817,9 @@ static void setupUserInterface_Window(iWindow *d) {
795 iWidget *div = makeVDiv_Widget(); 817 iWidget *div = makeVDiv_Widget();
796 setId_Widget(div, "navdiv"); 818 setId_Widget(div, "navdiv");
797 addChild_Widget(d->root, iClob(div)); 819 addChild_Widget(d->root, iClob(div));
798 820
799#if defined (LAGRANGE_CUSTOM_FRAME) 821#if defined (LAGRANGE_CUSTOM_FRAME)
800 /* Window title bar. */ 822 /* Window title bar. */
801 if (prefs_App()->customFrame) { 823 if (prefs_App()->customFrame) {
802 setPadding1_Widget(div, 1); 824 setPadding1_Widget(div, 1);
803 iWidget *winBar = new_Widget(); 825 iWidget *winBar = new_Widget();
@@ -852,8 +874,6 @@ static void setupUserInterface_Window(iWindow *d) {
852 /* Navigation bar. */ { 874 /* Navigation bar. */ {
853 iWidget *navBar = new_Widget(); 875 iWidget *navBar = new_Widget();
854 setId_Widget(navBar, "navbar"); 876 setId_Widget(navBar, "navbar");
855 int topPad = !findChild_Widget(div, "winbar") ? gap_UI / 2 : 0;
856 setPadding_Widget(navBar, gap_UI, topPad, gap_UI, gap_UI / 2);
857 setFlags_Widget(navBar, 877 setFlags_Widget(navBar,
858 arrangeHeight_WidgetFlag | 878 arrangeHeight_WidgetFlag |
859 resizeChildren_WidgetFlag | 879 resizeChildren_WidgetFlag |
@@ -866,6 +886,7 @@ static void setupUserInterface_Window(iWindow *d) {
866 setCommandHandler_Widget(navBar, handleNavBarCommands_); 886 setCommandHandler_Widget(navBar, handleNavBarCommands_);
867 setId_Widget(addChildFlags_Widget(navBar, iClob(newIcon_LabelWidget("\U0001f870", 0, 0, "navigate.back")), collapse_WidgetFlag), "navbar.back"); 887 setId_Widget(addChildFlags_Widget(navBar, iClob(newIcon_LabelWidget("\U0001f870", 0, 0, "navigate.back")), collapse_WidgetFlag), "navbar.back");
868 setId_Widget(addChildFlags_Widget(navBar, iClob(newIcon_LabelWidget("\U0001f872", 0, 0, "navigate.forward")), collapse_WidgetFlag), "navbar.forward"); 888 setId_Widget(addChildFlags_Widget(navBar, iClob(newIcon_LabelWidget("\U0001f872", 0, 0, "navigate.forward")), collapse_WidgetFlag), "navbar.forward");
889 addChildFlags_Widget(navBar, iClob(new_Widget()), expand_WidgetFlag);
869 iLabelWidget *idMenu = makeMenuButton_LabelWidget( 890 iLabelWidget *idMenu = makeMenuButton_LabelWidget(
870 "\U0001f464", identityButtonMenuItems_, iElemCount(identityButtonMenuItems_)); 891 "\U0001f464", identityButtonMenuItems_, iElemCount(identityButtonMenuItems_));
871 setAlignVisually_LabelWidget(idMenu, iTrue); 892 setAlignVisually_LabelWidget(idMenu, iTrue);
@@ -877,7 +898,7 @@ static void setupUserInterface_Window(iWindow *d) {
877 setUrlContent_InputWidget(url, iTrue); 898 setUrlContent_InputWidget(url, iTrue);
878 setNotifyEdits_InputWidget(url, iTrue); 899 setNotifyEdits_InputWidget(url, iTrue);
879 setTextCStr_InputWidget(url, "gemini://"); 900 setTextCStr_InputWidget(url, "gemini://");
880 addChildFlags_Widget(navBar, iClob(url), expand_WidgetFlag); 901 addChildFlags_Widget(navBar, iClob(url), 0);
881 setPadding_Widget(as_Widget(url), 0, 0, gap_UI, 0); 902 setPadding_Widget(as_Widget(url), 0, 0, gap_UI, 0);
882 /* Page information/certificate warning. */ { 903 /* Page information/certificate warning. */ {
883 iLabelWidget *lock = 904 iLabelWidget *lock =
@@ -928,7 +949,7 @@ static void setupUserInterface_Window(iWindow *d) {
928 setId_Widget(addChild_Widget( 949 setId_Widget(addChild_Widget(
929 navBar, iClob(newIcon_LabelWidget(reloadCStr_, 0, 0, "navigate.reload"))), 950 navBar, iClob(newIcon_LabelWidget(reloadCStr_, 0, 0, "navigate.reload"))),
930 "reload"); 951 "reload");
931 952 addChildFlags_Widget(navBar, iClob(new_Widget()), expand_WidgetFlag);
932 setId_Widget(addChildFlags_Widget(navBar, 953 setId_Widget(addChildFlags_Widget(navBar,
933 iClob(newIcon_LabelWidget( 954 iClob(newIcon_LabelWidget(
934 "\U0001f3e0", SDLK_h, KMOD_PRIMARY | KMOD_SHIFT, "navigate.home")), 955 "\U0001f3e0", SDLK_h, KMOD_PRIMARY | KMOD_SHIFT, "navigate.home")),
@@ -1137,7 +1158,7 @@ static SDL_HitTestResult hitTest_Window_(SDL_Window *win, const SDL_Point *pos,
1137 const int snap = snap_Window(d); 1158 const int snap = snap_Window(d);
1138 int w, h; 1159 int w, h;
1139 SDL_GetWindowSize(win, &w, &h); 1160 SDL_GetWindowSize(win, &w, &h);
1140 /* TODO: Check if inside the caption label widget. */ 1161 /* TODO: Check if inside the caption label widget. */
1141 const iBool isLeft = pos->x < gap_UI; 1162 const iBool isLeft = pos->x < gap_UI;
1142 const iBool isRight = pos->x >= w - gap_UI; 1163 const iBool isRight = pos->x >= w - gap_UI;
1143 const iBool isTop = pos->y < gap_UI && snap != yMaximized_WindowSnap; 1164 const iBool isTop = pos->y < gap_UI && snap != yMaximized_WindowSnap;
@@ -1306,7 +1327,7 @@ void init_Window(iWindow *d, iRect rect) {
1306 updateRootSize_Window_(d, iFalse); 1327 updateRootSize_Window_(d, iFalse);
1307 d->appIcon = NULL; 1328 d->appIcon = NULL;
1308#if defined (LAGRANGE_CUSTOM_FRAME) 1329#if defined (LAGRANGE_CUSTOM_FRAME)
1309 /* Load the app icon for drawing in the title bar. */ 1330 /* Load the app icon for drawing in the title bar. */
1310 if (prefs_App()->customFrame) { 1331 if (prefs_App()->customFrame) {
1311 SDL_Surface *surf = loadAppIconSurface_(appIconSize_()); 1332 SDL_Surface *surf = loadAppIconSurface_(appIconSize_());
1312 SDL_SetHint(SDL_HINT_RENDER_SCALE_QUALITY, "0"); 1333 SDL_SetHint(SDL_HINT_RENDER_SCALE_QUALITY, "0");
@@ -1416,7 +1437,7 @@ static iBool handleWindowEvent_Window_(iWindow *d, const SDL_WindowEvent *ev) {
1416#endif 1437#endif
1417 return iFalse; 1438 return iFalse;
1418 case SDL_WINDOWEVENT_MOVED: { 1439 case SDL_WINDOWEVENT_MOVED: {
1419 if (d->isMinimized) { 1440 if (d->isMinimized) {
1420 return iFalse; 1441 return iFalse;
1421 } 1442 }
1422 const iInt2 newPos = init_I2(ev->data1, ev->data2); 1443 const iInt2 newPos = init_I2(ev->data1, ev->data2);
@@ -1426,7 +1447,7 @@ static iBool handleWindowEvent_Window_(iWindow *d, const SDL_WindowEvent *ev) {
1426 return iFalse; 1447 return iFalse;
1427 } 1448 }
1428#if defined (LAGRANGE_CUSTOM_FRAME) 1449#if defined (LAGRANGE_CUSTOM_FRAME)
1429 /* Set the snap position depending on where the mouse cursor is. */ 1450 /* Set the snap position depending on where the mouse cursor is. */
1430 if (prefs_App()->customFrame) { 1451 if (prefs_App()->customFrame) {
1431 SDL_Rect usable; 1452 SDL_Rect usable;
1432 iInt2 mouse = cursor_Win32(); /* SDL is unaware of the current cursor pos */ 1453 iInt2 mouse = cursor_Win32(); /* SDL is unaware of the current cursor pos */
@@ -1473,7 +1494,7 @@ static iBool handleWindowEvent_Window_(iWindow *d, const SDL_WindowEvent *ev) {
1473 } 1494 }
1474 case SDL_WINDOWEVENT_RESIZED: 1495 case SDL_WINDOWEVENT_RESIZED:
1475 updatePadding_Window_(d); 1496 updatePadding_Window_(d);
1476 if (d->isMinimized) { 1497 if (d->isMinimized) {
1477 updateRootSize_Window_(d, iTrue); 1498 updateRootSize_Window_(d, iTrue);
1478 return iTrue; 1499 return iTrue;
1479 } 1500 }
@@ -1485,16 +1506,16 @@ static iBool handleWindowEvent_Window_(iWindow *d, const SDL_WindowEvent *ev) {
1485 //printf("normal rect set (resize)\n"); fflush(stdout); 1506 //printf("normal rect set (resize)\n"); fflush(stdout);
1486 } 1507 }
1487 updateRootSize_Window_(d, iTrue /* we were already redrawing during the resize */); 1508 updateRootSize_Window_(d, iTrue /* we were already redrawing during the resize */);
1509 postRefresh_App();
1488 return iTrue; 1510 return iTrue;
1489 case SDL_WINDOWEVENT_RESTORED: 1511 case SDL_WINDOWEVENT_RESTORED:
1490 //updateRootSize_Window_(d, iTrue); 1512 updateRootSize_Window_(d, iTrue);
1491 invalidate_Window_(d); 1513 invalidate_Window_(d);
1492 d->isMinimized = iFalse; 1514 d->isMinimized = iFalse;
1493 postRefresh_App(); 1515 postRefresh_App();
1494 return iTrue; 1516 return iTrue;
1495 case SDL_WINDOWEVENT_MINIMIZED: 1517 case SDL_WINDOWEVENT_MINIMIZED:
1496 d->isMinimized = iTrue; 1518 d->isMinimized = iTrue;
1497 //printf("minimized\n"); fflush(stdout);
1498 return iTrue; 1519 return iTrue;
1499 case SDL_WINDOWEVENT_LEAVE: 1520 case SDL_WINDOWEVENT_LEAVE:
1500 unhover_Widget(); 1521 unhover_Widget();
@@ -1507,6 +1528,7 @@ static iBool handleWindowEvent_Window_(iWindow *d, const SDL_WindowEvent *ev) {
1507 return iTrue; 1528 return iTrue;
1508 case SDL_WINDOWEVENT_TAKE_FOCUS: 1529 case SDL_WINDOWEVENT_TAKE_FOCUS:
1509 SDL_SetWindowInputFocus(d->win); 1530 SDL_SetWindowInputFocus(d->win);
1531 postRefresh_App();
1510 return iTrue; 1532 return iTrue;
1511 case SDL_WINDOWEVENT_FOCUS_GAINED: 1533 case SDL_WINDOWEVENT_FOCUS_GAINED:
1512 d->focusGainedAt = SDL_GetTicks(); 1534 d->focusGainedAt = SDL_GetTicks();
@@ -1532,13 +1554,13 @@ iBool processEvent_Window(iWindow *d, const SDL_Event *ev) {
1532 switch (ev->type) { 1554 switch (ev->type) {
1533#if defined (LAGRANGE_CUSTOM_FRAME) 1555#if defined (LAGRANGE_CUSTOM_FRAME)
1534 case SDL_SYSWMEVENT: { 1556 case SDL_SYSWMEVENT: {
1535 /* We observe native Win32 messages for better user interaction with the 1557 /* We observe native Win32 messages for better user interaction with the
1536 window frame. Mouse clicks especially will not generate normal SDL 1558 window frame. Mouse clicks especially will not generate normal SDL
1537 events if they happen on the custom hit-tested regions. These events 1559 events if they happen on the custom hit-tested regions. These events
1538 are processed only there; the UI widgets do not get involved. */ 1560 are processed only there; the UI widgets do not get involved. */
1539 processNativeEvent_Win32(ev->syswm.msg, d); 1561 processNativeEvent_Win32(ev->syswm.msg, d);
1540 break; 1562 break;
1541 } 1563 }
1542#endif 1564#endif
1543 case SDL_WINDOWEVENT: { 1565 case SDL_WINDOWEVENT: {
1544 return handleWindowEvent_Window_(d, &ev->window); 1566 return handleWindowEvent_Window_(d, &ev->window);
@@ -1778,7 +1800,7 @@ void setSnap_Window(iWindow *d, int snapMode) {
1778 return; 1800 return;
1779 } 1801 }
1780 const int snapDist = gap_UI * 4; 1802 const int snapDist = gap_UI * 4;
1781 iRect newRect = zero_Rect(); 1803 iRect newRect = zero_Rect();
1782 SDL_Rect usable; 1804 SDL_Rect usable;
1783 SDL_GetDisplayUsableBounds(SDL_GetWindowDisplayIndex(d->win), &usable); 1805 SDL_GetDisplayUsableBounds(SDL_GetWindowDisplayIndex(d->win), &usable);
1784 if (d->place.snap == fullscreen_WindowSnap) { 1806 if (d->place.snap == fullscreen_WindowSnap) {