summaryrefslogtreecommitdiff
path: root/src/ui
diff options
context:
space:
mode:
authorJaakko Keränen <jaakko.keranen@iki.fi>2021-03-12 20:03:21 +0200
committerJaakko Keränen <jaakko.keranen@iki.fi>2021-03-12 20:05:46 +0200
commit088eb5f137c38bdcde4fc2e80fd40cf7c07fce9b (patch)
tree7b08fd3df1fb8f9efd0865b3d9fc49a38b3ad7f3 /src/ui
parent9d73378d21f4644bf0e39fb09025553a0fff7cc4 (diff)
Window: Embed reload button; sidebar context menu
Diffstat (limited to 'src/ui')
-rw-r--r--src/ui/widget.c11
-rw-r--r--src/ui/widget.h1
-rw-r--r--src/ui/window.c103
3 files changed, 83 insertions, 32 deletions
diff --git a/src/ui/widget.c b/src/ui/widget.c
index e9a162e3..4d2728b7 100644
--- a/src/ui/widget.c
+++ b/src/ui/widget.c
@@ -972,9 +972,9 @@ iAny *hitChild_Widget(const iWidget *d, iInt2 coord) {
972 if (found) return found; 972 if (found) return found;
973 } 973 }
974 } 974 }
975 if ((d->flags & overflowScrollable_WidgetFlag || class_Widget(d) != &Class_Widget || 975 if ((d->flags & (overflowScrollable_WidgetFlag | hittable_WidgetFlag) ||
976 d->flags & mouseModal_WidgetFlag) && ~d->flags & unhittable_WidgetFlag && 976 class_Widget(d) != &Class_Widget || d->flags & mouseModal_WidgetFlag) &&
977 contains_Widget(d, coord)) { 977 ~d->flags & unhittable_WidgetFlag && contains_Widget(d, coord)) {
978 return iConstCast(iWidget *, d); 978 return iConstCast(iWidget *, d);
979 } 979 }
980 return NULL; 980 return NULL;
@@ -1199,8 +1199,9 @@ static void printTree_Widget_(const iWidget *d, int indent) {
1199 cstr_String(text_LabelWidget((const iLabelWidget *) d)), 1199 cstr_String(text_LabelWidget((const iLabelWidget *) d)),
1200 cstr_String(command_LabelWidget((const iLabelWidget *) d))); 1200 cstr_String(command_LabelWidget((const iLabelWidget *) d)));
1201 } 1201 }
1202 printf("size:%dx%d flags:%08llx\n", d->rect.size.x, d->rect.size.y, 1202 printf("size:%dx%d [%d..%d %d:%d] flags:%08llx%s\n", d->rect.size.x, d->rect.size.y,
1203 (long long unsigned int) d->flags); 1203 d->padding[0], d->padding[2], d->padding[1], d->padding[3],
1204 (long long unsigned int) d->flags, d->flags & tight_WidgetFlag ? " tight" : "");
1204 iConstForEach(ObjectList, i, d->children) { 1205 iConstForEach(ObjectList, i, d->children) {
1205 printTree_Widget_(i.object, indent + 1); 1206 printTree_Widget_(i.object, indent + 1);
1206 } 1207 }
diff --git a/src/ui/widget.h b/src/ui/widget.h
index 94a2d4a1..37c8efdc 100644
--- a/src/ui/widget.h
+++ b/src/ui/widget.h
@@ -107,6 +107,7 @@ enum iWidgetFlag {
107#define chevron_WidgetFlag iBit64(52) 107#define chevron_WidgetFlag iBit64(52)
108#define drawBackgroundToBottom_WidgetFlag iBit64(53) 108#define drawBackgroundToBottom_WidgetFlag iBit64(53)
109#define dragged_WidgetFlag iBit64(54) 109#define dragged_WidgetFlag iBit64(54)
110#define hittable_WidgetFlag iBit64(55)
110 111
111enum iWidgetAddPos { 112enum iWidgetAddPos {
112 back_WidgetAddPos, 113 back_WidgetAddPos,
diff --git a/src/ui/window.c b/src/ui/window.c
index 2f7a2988..16f217a3 100644
--- a/src/ui/window.c
+++ b/src/ui/window.c
@@ -86,6 +86,26 @@ static iBool handleRootCommands_(iWidget *root, const char *cmd) {
86 } 86 }
87 return iTrue; 87 return iTrue;
88 } 88 }
89 else if (equal_Command(cmd, "contextclick")) {
90 iBool showBarMenu = iFalse;
91 if (equal_Rangecc(range_Command(cmd, "id"), "buttons")) {
92 const iWidget *sidebar = findWidget_App("sidebar");
93 const iWidget *sidebar2 = findWidget_App("sidebar2");
94 const iWidget *buttons = pointer_Command(cmd);
95 if (hasParent_Widget(buttons, sidebar) ||
96 hasParent_Widget(buttons, sidebar2)) {
97 showBarMenu = iTrue;
98 }
99 }
100 if (equal_Rangecc(range_Command(cmd, "id"), "navbar")) {
101 showBarMenu = iTrue;
102 }
103 if (showBarMenu) {
104 openMenu_Widget(findWidget_App("barmenu"), coord_Command(cmd));
105 return iTrue;
106 }
107 return iFalse;
108 }
89 else if (equal_Command(cmd, "focus.set")) { 109 else if (equal_Command(cmd, "focus.set")) {
90 setFocus_Widget(findWidget_App(cstr_Rangecc(range_Command(cmd, "id")))); 110 setFocus_Widget(findWidget_App(cstr_Rangecc(range_Command(cmd, "id"))));
91 return iTrue; 111 return iTrue;
@@ -495,8 +515,9 @@ static iBool willPerformSearchQuery_(const iString *userInput) {
495static void showSearchQueryIndicator_(iBool show) { 515static void showSearchQueryIndicator_(iBool show) {
496 iWidget *indicator = findWidget_App("input.indicator.search"); 516 iWidget *indicator = findWidget_App("input.indicator.search");
497 setFlags_Widget(indicator, hidden_WidgetFlag, !show); 517 setFlags_Widget(indicator, hidden_WidgetFlag, !show);
498 setContentPadding_InputWidget( 518 iInputWidget *url = (iInputWidget *) parent_Widget(indicator);
499 (iInputWidget *) parent_Widget(indicator), -1, show ? width_Widget(indicator) : 0); 519 setContentPadding_InputWidget(url, -1, contentPadding_InputWidget(url).left +
520 (show ? width_Widget(indicator) : 0));
500} 521}
501 522
502static int navBarAvailableSpace_(iWidget *navBar) { 523static int navBarAvailableSpace_(iWidget *navBar) {
@@ -527,17 +548,18 @@ static iBool handleNavBarCommands_(iWidget *navBar, const char *cmd) {
527 setFlags_Widget(navBar, tight_WidgetFlag, isNarrow); 548 setFlags_Widget(navBar, tight_WidgetFlag, isNarrow);
528 iForEach(ObjectList, i, navBar->children) { 549 iForEach(ObjectList, i, navBar->children) {
529 iWidget *child = as_Widget(i.object); 550 iWidget *child = as_Widget(i.object);
530 setFlags_Widget( 551 setFlags_Widget(child, tight_WidgetFlag, isNarrow);
531 child, tight_WidgetFlag, isNarrow);
532 if (isInstance_Object(i.object, &Class_LabelWidget)) { 552 if (isInstance_Object(i.object, &Class_LabelWidget)) {
533 iLabelWidget *label = i.object; 553 iLabelWidget *label = i.object;
534 updateSize_LabelWidget(label); 554 updateSize_LabelWidget(label);
535 } 555 }
536 } 556 }
537 /* Note that InputWidget uses the `tight` flag to adjust its inner padding. */ 557 /* Note that InputWidget uses the `tight` flag to adjust its inner padding. */
558 /* TODO: Is this redundant? See `updateMetrics_Window_()`. */
559 const int embedButtonWidth = width_Widget(findChild_Widget(navBar, "navbar.lock"));
538 setContentPadding_InputWidget(findChild_Widget(navBar, "url"), 560 setContentPadding_InputWidget(findChild_Widget(navBar, "url"),
539 width_Widget(findChild_Widget(navBar, "navbar.lock")) * 0.75, 561 embedButtonWidth * 0.75f,
540 -1); 562 embedButtonWidth * 0.75f);
541 } 563 }
542 if (isPhone) { 564 if (isPhone) {
543 static const char *buttons[] = { 565 static const char *buttons[] = {
@@ -559,6 +581,7 @@ static iBool handleNavBarCommands_(iWidget *navBar, const char *cmd) {
559 iWidget *urlBar = findChild_Widget(navBar, "url"); 581 iWidget *urlBar = findChild_Widget(navBar, "url");
560 urlBar->rect.size.x = iMini(navBarAvailableSpace_(navBar), 167 * gap_UI); 582 urlBar->rect.size.x = iMini(navBarAvailableSpace_(navBar), 167 * gap_UI);
561 arrange_Widget(navBar); 583 arrange_Widget(navBar);
584 printTree_Widget(urlBar);
562 } 585 }
563 refresh_Widget(navBar); 586 refresh_Widget(navBar);
564 postCommand_Widget(navBar, "layout.changed id:navbar"); 587 postCommand_Widget(navBar, "layout.changed id:navbar");
@@ -833,10 +856,11 @@ static void updateMetrics_Window_(iWindow *d) {
833 iWidget *fprog = findChild_Widget(navBar, "feeds.progress"); 856 iWidget *fprog = findChild_Widget(navBar, "feeds.progress");
834 iWidget *docProg = findChild_Widget(navBar, "document.progress"); 857 iWidget *docProg = findChild_Widget(navBar, "document.progress");
835 iWidget *indSearch = findChild_Widget(navBar, "input.indicator.search"); 858 iWidget *indSearch = findChild_Widget(navBar, "input.indicator.search");
836 setPadding_Widget(as_Widget(url), 0, gap_UI, gap_UI, gap_UI); 859 setPadding_Widget(as_Widget(url), 0, gap_UI, 0, gap_UI);
837 navBar->rect.size.y = 0; /* recalculate height based on children (FIXME: shouldn't be needed) */ 860 navBar->rect.size.y = 0; /* recalculate height based on children (FIXME: shouldn't be needed) */
838 updateSize_LabelWidget((iLabelWidget *) lock); 861 updateSize_LabelWidget((iLabelWidget *) lock);
839 setContentPadding_InputWidget((iInputWidget *) url, width_Widget(lock) * 0.75, -1); 862 setContentPadding_InputWidget((iInputWidget *) url, width_Widget(lock) * 0.75,
863 width_Widget(lock) * 0.75);
840 fprog->rect.pos.y = gap_UI; 864 fprog->rect.pos.y = gap_UI;
841 docProg->rect.pos.y = gap_UI; 865 docProg->rect.pos.y = gap_UI;
842 indSearch->rect.pos.y = gap_UI; 866 indSearch->rect.pos.y = gap_UI;
@@ -909,6 +933,7 @@ static void setupUserInterface_Window(iWindow *d) {
909 iWidget *navBar = new_Widget(); 933 iWidget *navBar = new_Widget();
910 setId_Widget(navBar, "navbar"); 934 setId_Widget(navBar, "navbar");
911 setFlags_Widget(navBar, 935 setFlags_Widget(navBar,
936 hittable_WidgetFlag | /* context menu */
912 arrangeHeight_WidgetFlag | 937 arrangeHeight_WidgetFlag |
913 resizeChildren_WidgetFlag | 938 resizeChildren_WidgetFlag |
914 arrangeHorizontal_WidgetFlag | 939 arrangeHorizontal_WidgetFlag |
@@ -925,8 +950,9 @@ static void setupUserInterface_Window(iWindow *d) {
925 "\U0001f464", identityButtonMenuItems_, iElemCount(identityButtonMenuItems_)); 950 "\U0001f464", identityButtonMenuItems_, iElemCount(identityButtonMenuItems_));
926 setAlignVisually_LabelWidget(idMenu, iTrue); 951 setAlignVisually_LabelWidget(idMenu, iTrue);
927 setId_Widget(addChildFlags_Widget(navBar, iClob(idMenu), collapse_WidgetFlag), "navbar.ident"); 952 setId_Widget(addChildFlags_Widget(navBar, iClob(idMenu), collapse_WidgetFlag), "navbar.ident");
953 iInputWidget *url;
928 /* URL input field. */ { 954 /* URL input field. */ {
929 iInputWidget *url = new_InputWidget(0); 955 url = new_InputWidget(0);
930 setFlags_Widget(as_Widget(url), resizeHeightOfChildren_WidgetFlag, iTrue); 956 setFlags_Widget(as_Widget(url), resizeHeightOfChildren_WidgetFlag, iTrue);
931 setSelectAllOnFocus_InputWidget(url, iTrue); 957 setSelectAllOnFocus_InputWidget(url, iTrue);
932 setId_Widget(as_Widget(url), "url"); 958 setId_Widget(as_Widget(url), "url");
@@ -934,13 +960,14 @@ static void setupUserInterface_Window(iWindow *d) {
934 setNotifyEdits_InputWidget(url, iTrue); 960 setNotifyEdits_InputWidget(url, iTrue);
935 setTextCStr_InputWidget(url, "gemini://"); 961 setTextCStr_InputWidget(url, "gemini://");
936 addChildFlags_Widget(navBar, iClob(url), 0); 962 addChildFlags_Widget(navBar, iClob(url), 0);
963 const int64_t embedFlags =
964 noBackground_WidgetFlag | frameless_WidgetFlag | unpadded_WidgetFlag |
965 (deviceType_App() == desktop_AppDeviceType ? tight_WidgetFlag : 0);
937 /* Page information/certificate warning. */ { 966 /* Page information/certificate warning. */ {
938 iLabelWidget *lock = 967 iLabelWidget *lock =
939 addChildFlags_Widget(as_Widget(url), 968 addChildFlags_Widget(as_Widget(url),
940 iClob(newIcon_LabelWidget("\U0001f513", SDLK_i, KMOD_PRIMARY, "document.info")), 969 iClob(newIcon_LabelWidget("\U0001f513", SDLK_i, KMOD_PRIMARY, "document.info")),
941 noBackground_WidgetFlag | frameless_WidgetFlag | moveToParentLeftEdge_WidgetFlag | 970 embedFlags | moveToParentLeftEdge_WidgetFlag);
942 unpadded_WidgetFlag |
943 (deviceType_App() == desktop_AppDeviceType ? tight_WidgetFlag : 0));
944 setId_Widget(as_Widget(lock), "navbar.lock"); 971 setId_Widget(as_Widget(lock), "navbar.lock");
945 setFont_LabelWidget(lock, defaultSymbols_FontId); 972 setFont_LabelWidget(lock, defaultSymbols_FontId);
946 updateTextCStr_LabelWidget(lock, "\U0001f512"); 973 updateTextCStr_LabelWidget(lock, "\U0001f512");
@@ -979,10 +1006,12 @@ static void setupUserInterface_Window(iWindow *d) {
979 iClob(queryInd), 1006 iClob(queryInd),
980 moveToParentRightEdge_WidgetFlag | hidden_WidgetFlag); 1007 moveToParentRightEdge_WidgetFlag | hidden_WidgetFlag);
981 } 1008 }
1009 /* Reload button. */
1010 iLabelWidget *reload = newIcon_LabelWidget(reloadCStr_, 0, 0, "navigate.reload");
1011 setId_Widget(as_Widget(reload), "reload");
1012 addChildFlags_Widget(as_Widget(url), iClob(reload), embedFlags | moveToParentRightEdge_WidgetFlag);
1013 updateSize_LabelWidget(reload);
982 } 1014 }
983 setId_Widget(addChild_Widget(
984 navBar, iClob(newIcon_LabelWidget(reloadCStr_, 0, 0, "navigate.reload"))),
985 "reload");
986 addChildFlags_Widget(navBar, iClob(new_Widget()), expand_WidgetFlag); 1015 addChildFlags_Widget(navBar, iClob(new_Widget()), expand_WidgetFlag);
987 setId_Widget(addChildFlags_Widget(navBar, 1016 setId_Widget(addChildFlags_Widget(navBar,
988 iClob(newIcon_LabelWidget( 1017 iClob(newIcon_LabelWidget(
@@ -1028,7 +1057,7 @@ static void setupUserInterface_Window(iWindow *d) {
1028 addChild_Widget(buttons, iClob(newIcon_LabelWidget(add_Icon, 0, 0, "tabs.new"))), 1057 addChild_Widget(buttons, iClob(newIcon_LabelWidget(add_Icon, 0, 0, "tabs.new"))),
1029 "newtab"); 1058 "newtab");
1030 } 1059 }
1031 /* Side bars. */ { 1060 /* Sidebars. */ {
1032 iWidget *content = findChild_Widget(d->root, "tabs.content"); 1061 iWidget *content = findChild_Widget(d->root, "tabs.content");
1033 iSidebarWidget *sidebar1 = new_SidebarWidget(left_SideBarSide); 1062 iSidebarWidget *sidebar1 = new_SidebarWidget(left_SideBarSide);
1034 addChildPos_Widget(content, iClob(sidebar1), front_WidgetAddPos); 1063 addChildPos_Widget(content, iClob(sidebar1), front_WidgetAddPos);
@@ -1105,17 +1134,25 @@ static void setupUserInterface_Window(iWindow *d) {
1105 } 1134 }
1106#endif 1135#endif
1107 updatePadding_Window_(d); 1136 updatePadding_Window_(d);
1108 iWidget *tabsMenu = makeMenu_Widget(d->root, 1137 /* Context menus. */ {
1109 (iMenuItem[]){ 1138 iWidget *tabsMenu = makeMenu_Widget(d->root,
1110 { close_Icon " Close Tab", 0, 0, "tabs.close" }, 1139 (iMenuItem[]){
1111 { copy_Icon " Duplicate Tab", 0, 0, "tabs.new duplicate:1" }, 1140 { close_Icon " Close Tab", 0, 0, "tabs.close" },
1112 { "---", 0, 0, NULL }, 1141 { copy_Icon " Duplicate Tab", 0, 0, "tabs.new duplicate:1" },
1113 { "Close Other Tabs", 0, 0, "tabs.close toleft:1 toright:1" }, 1142 { "---", 0, 0, NULL },
1114 { barLeftArrow_Icon " Close Tabs To Left", 0, 0, "tabs.close toleft:1" }, 1143 { "Close Other Tabs", 0, 0, "tabs.close toleft:1 toright:1" },
1115 { barRightArrow_Icon " Close Tabs To Right", 0, 0, "tabs.close toright:1" }, 1144 { barLeftArrow_Icon " Close Tabs To Left", 0, 0, "tabs.close toleft:1" },
1116 }, 1145 { barRightArrow_Icon " Close Tabs To Right", 0, 0, "tabs.close toright:1" },
1117 6); 1146 },
1118 setId_Widget(tabsMenu, "doctabs.menu"); 1147 6);
1148 setId_Widget(tabsMenu, "doctabs.menu");
1149 iWidget *barMenu = makeMenu_Widget(d->root,
1150 (iMenuItem[]) {
1151 { "Toggle Left Sidebar", 0, 0, "sidebar.toggle" },
1152 { "Toggle Right Sidebar", 0, 0, "sidebar2.toggle" },
1153 }, 2);
1154 setId_Widget(barMenu, "barmenu");
1155 }
1119 /* Global keyboard shortcuts. */ { 1156 /* Global keyboard shortcuts. */ {
1120 addAction_Widget(d->root, 'l', KMOD_PRIMARY, "navigate.focus"); 1157 addAction_Widget(d->root, 'l', KMOD_PRIMARY, "navigate.focus");
1121 addAction_Widget(d->root, 'f', KMOD_PRIMARY, "focus.set id:find.input"); 1158 addAction_Widget(d->root, 'f', KMOD_PRIMARY, "focus.set id:find.input");
@@ -1695,6 +1732,18 @@ iBool processEvent_Window(iWindow *d, const SDL_Event *ev) {
1695 paste.key.timestamp = SDL_GetTicks(); 1732 paste.key.timestamp = SDL_GetTicks();
1696 wasUsed = dispatchEvent_Widget(widget, &paste); 1733 wasUsed = dispatchEvent_Widget(widget, &paste);
1697 } 1734 }
1735 if (event.type == SDL_MOUSEBUTTONDOWN && event.button.button == SDL_BUTTON_RIGHT) {
1736 /* A context menu may still get triggered here. */
1737 const iWidget *hit = hitChild_Widget(d->root, init_I2(event.button.x, event.button.y));
1738 while (hit && isEmpty_String(id_Widget(hit))) {
1739 hit = parent_Widget(hit);
1740 }
1741 if (hit) {
1742 postCommandf_App("contextclick id:%s ptr:%p coord:%d %d",
1743 cstr_String(id_Widget(hit)), hit,
1744 event.button.x, event.button.y);
1745 }
1746 }
1698 } 1747 }
1699 if (isMetricsChange_UserEvent(&event)) { 1748 if (isMetricsChange_UserEvent(&event)) {
1700 updateMetrics_Window_(d); 1749 updateMetrics_Window_(d);