diff options
author | Arisotura <thetotalworm@gmail.com> | 2020-04-25 18:51:08 +0200 |
---|---|---|
committer | Arisotura <thetotalworm@gmail.com> | 2020-04-25 18:51:08 +0200 |
commit | a85d41c53eed50f188502925ed34674397b86550 (patch) | |
tree | e33b042b8114f7ad587257d79bad021d5e617a44 /src/libui_sdl/libui/windows/tab.cpp | |
parent | 3b3a09ed2b7a1f3d6f81ba6d1ddd7fbf17acd52d (diff) |
berp.
Diffstat (limited to 'src/libui_sdl/libui/windows/tab.cpp')
-rw-r--r-- | src/libui_sdl/libui/windows/tab.cpp | 294 |
1 files changed, 0 insertions, 294 deletions
diff --git a/src/libui_sdl/libui/windows/tab.cpp b/src/libui_sdl/libui/windows/tab.cpp deleted file mode 100644 index 93373b0..0000000 --- a/src/libui_sdl/libui/windows/tab.cpp +++ /dev/null @@ -1,294 +0,0 @@ -// 16 may 2015 -#include "uipriv_windows.hpp" - -// You don't add controls directly to a tab control on Windows; instead you make them siblings and swap between them on a TCN_SELCHANGING/TCN_SELCHANGE notification pair. -// In addition, you use dialogs because they can be textured properly; other controls cannot. (Things will look wrong if the tab background in the current theme is fancy if you just use the tab background by itself; see http://stackoverflow.com/questions/30087540/why-are-my-programss-tab-controls-rendering-their-background-in-a-blocky-way-b.) - -struct uiTab { - uiWindowsControl c; - HWND hwnd; // of the outer container - HWND tabHWND; // of the tab control itself - std::vector<struct tabPage *> *pages; - HWND parent; -}; - -// utility functions - -static LRESULT curpage(uiTab *t) -{ - return SendMessageW(t->tabHWND, TCM_GETCURSEL, 0, 0); -} - -static struct tabPage *tabPage(uiTab *t, int i) -{ - return (*(t->pages))[i]; -} - -static void tabPageRect(uiTab *t, RECT *r) -{ - // this rect needs to be in parent window coordinates, but TCM_ADJUSTRECT wants a window rect, which is screen coordinates - // because we have each page as a sibling of the tab, use the tab's own rect as the input rect - uiWindowsEnsureGetWindowRect(t->tabHWND, r); - SendMessageW(t->tabHWND, TCM_ADJUSTRECT, (WPARAM) FALSE, (LPARAM) r); - // and get it in terms of the container instead of the screen - mapWindowRect(NULL, t->hwnd, r); -} - -static void tabRelayout(uiTab *t) -{ - struct tabPage *page; - RECT r; - - // first move the tab control itself - uiWindowsEnsureGetClientRect(t->hwnd, &r); - uiWindowsEnsureMoveWindowDuringResize(t->tabHWND, r.left, r.top, r.right - r.left, r.bottom - r.top); - - // then the current page - if (t->pages->size() == 0) - return; - page = tabPage(t, curpage(t)); - tabPageRect(t, &r); - uiWindowsEnsureMoveWindowDuringResize(page->hwnd, r.left, r.top, r.right - r.left, r.bottom - r.top); -} - -static void showHidePage(uiTab *t, LRESULT which, int hide) -{ - struct tabPage *page; - - if (which == (LRESULT) (-1)) - return; - page = tabPage(t, which); - if (hide) - ShowWindow(page->hwnd, SW_HIDE); - else { - ShowWindow(page->hwnd, SW_SHOW); - // we only resize the current page, so we have to resize it; before we can do that, we need to make sure we are of the right size - uiWindowsControlMinimumSizeChanged(uiWindowsControl(t)); - } -} - -// control implementation - -static BOOL onWM_NOTIFY(uiControl *c, HWND hwnd, NMHDR *nm, LRESULT *lResult) -{ - uiTab *t = uiTab(c); - - if (nm->code != TCN_SELCHANGING && nm->code != TCN_SELCHANGE) - return FALSE; - showHidePage(t, curpage(t), nm->code == TCN_SELCHANGING); - *lResult = 0; - if (nm->code == TCN_SELCHANGING) - *lResult = FALSE; - return TRUE; -} - -static void uiTabDestroy(uiControl *c) -{ - uiTab *t = uiTab(c); - uiControl *child; - - for (struct tabPage *&page : *(t->pages)) { - child = page->child; - tabPageDestroy(page); - if (child != NULL) { - uiControlSetParent(child, NULL); - uiControlDestroy(child); - } - } - delete t->pages; - uiWindowsUnregisterWM_NOTIFYHandler(t->tabHWND); - uiWindowsEnsureDestroyWindow(t->tabHWND); - uiWindowsEnsureDestroyWindow(t->hwnd); - uiFreeControl(uiControl(t)); -} - -uiWindowsControlDefaultHandle(uiTab) -uiWindowsControlDefaultParent(uiTab) -uiWindowsControlDefaultSetParent(uiTab) -uiWindowsControlDefaultToplevel(uiTab) -uiWindowsControlDefaultVisible(uiTab) -uiWindowsControlDefaultShow(uiTab) -uiWindowsControlDefaultHide(uiTab) -uiWindowsControlDefaultEnabled(uiTab) -uiWindowsControlDefaultEnable(uiTab) -uiWindowsControlDefaultDisable(uiTab) -uiWindowsControlDefaultSetFocus(uiTab) - -static void uiTabSyncEnableState(uiWindowsControl *c, int enabled) -{ - uiTab *t = uiTab(c); - - if (uiWindowsShouldStopSyncEnableState(uiWindowsControl(t), enabled)) - return; - EnableWindow(t->tabHWND, enabled); - for (struct tabPage *&page : *(t->pages)) - if (page->child != NULL) - uiWindowsControlSyncEnableState(uiWindowsControl(page->child), enabled); -} - -uiWindowsControlDefaultSetParentHWND(uiTab) - -static void uiTabMinimumSize(uiWindowsControl *c, int *width, int *height) -{ - uiTab *t = uiTab(c); - int pagewid, pageht; - struct tabPage *page; - RECT r; - - // only consider the current page - pagewid = 0; - pageht = 0; - if (t->pages->size() != 0) { - page = tabPage(t, curpage(t)); - tabPageMinimumSize(page, &pagewid, &pageht); - } - - r.left = 0; - r.top = 0; - r.right = pagewid; - r.bottom = pageht; - // this also includes the tabs themselves - SendMessageW(t->tabHWND, TCM_ADJUSTRECT, (WPARAM) TRUE, (LPARAM) (&r)); - *width = r.right - r.left; - *height = r.bottom - r.top; -} - -static void uiTabMinimumSizeChanged(uiWindowsControl *c) -{ - uiTab *t = uiTab(c); - - if (uiWindowsControlTooSmall(uiWindowsControl(t))) { - uiWindowsControlContinueMinimumSizeChanged(uiWindowsControl(t)); - return; - } - tabRelayout(t); -} - -static void uiTabSetMinSize(uiControl *c, int w, int h) -{ - // checkme - uiTabMinimumSizeChanged(uiWindowsControl(c)); -} - -uiWindowsControlDefaultLayoutRect(uiTab) -uiWindowsControlDefaultAssignControlIDZOrder(uiTab) - -static void uiTabChildVisibilityChanged(uiWindowsControl *c) -{ - // TODO eliminate the redundancy - uiWindowsControlMinimumSizeChanged(c); -} - -static void tabArrangePages(uiTab *t) -{ - LONG_PTR controlID = 100; - HWND insertAfter = NULL; - - // TODO is this first or last? - uiWindowsEnsureAssignControlIDZOrder(t->tabHWND, &controlID, &insertAfter); - for (struct tabPage *&page : *(t->pages)) - uiWindowsEnsureAssignControlIDZOrder(page->hwnd, &controlID, &insertAfter); -} - -void uiTabAppend(uiTab *t, const char *name, uiControl *child) -{ - uiTabInsertAt(t, name, t->pages->size(), child); -} - -void uiTabInsertAt(uiTab *t, const char *name, int n, uiControl *child) -{ - struct tabPage *page; - LRESULT hide, show; - TCITEMW item; - WCHAR *wname; - - // see below - hide = curpage(t); - - if (child != NULL) - uiControlSetParent(child, uiControl(t)); - - page = newTabPage(child); - uiWindowsEnsureSetParentHWND(page->hwnd, t->hwnd); - t->pages->insert(t->pages->begin() + n, page); - tabArrangePages(t); - - ZeroMemory(&item, sizeof (TCITEMW)); - item.mask = TCIF_TEXT; - wname = toUTF16(name); - item.pszText = wname; - if (SendMessageW(t->tabHWND, TCM_INSERTITEM, (WPARAM) n, (LPARAM) (&item)) == (LRESULT) -1) - logLastError(L"error adding tab to uiTab"); - uiFree(wname); - - // we need to do this because adding the first tab doesn't send a TCN_SELCHANGE; it just shows the page - show = curpage(t); - if (show != hide) { - showHidePage(t, hide, 1); - showHidePage(t, show, 0); - } -} - -void uiTabDelete(uiTab *t, int n) -{ - struct tabPage *page; - - // first delete the tab from the tab control - // if this is the current tab, no tab will be selected, which is good - if (SendMessageW(t->tabHWND, TCM_DELETEITEM, (WPARAM) n, 0) == FALSE) - logLastError(L"error deleting uiTab tab"); - - // now delete the page itself - page = tabPage(t, n); - if (page->child != NULL) - uiControlSetParent(page->child, NULL); - tabPageDestroy(page); - t->pages->erase(t->pages->begin() + n); -} - -int uiTabNumPages(uiTab *t) -{ - return t->pages->size(); -} - -int uiTabMargined(uiTab *t, int n) -{ - return tabPage(t, n)->margined; -} - -void uiTabSetMargined(uiTab *t, int n, int margined) -{ - struct tabPage *page; - - page = tabPage(t, n); - page->margined = margined; - // even if the page doesn't have a child it might still have a new minimum size with margins; this is the easiest way to verify it - uiWindowsControlMinimumSizeChanged(uiWindowsControl(t)); -} - -static void onResize(uiWindowsControl *c) -{ - tabRelayout(uiTab(c)); -} - -uiTab *uiNewTab(void) -{ - uiTab *t; - - uiWindowsNewControl(uiTab, t); - - t->hwnd = uiWindowsMakeContainer(uiWindowsControl(t), onResize); - - t->tabHWND = uiWindowsEnsureCreateControlHWND(0, - WC_TABCONTROLW, L"", - TCS_TOOLTIPS | WS_TABSTOP, - hInstance, NULL, - TRUE); - uiWindowsEnsureSetParentHWND(t->tabHWND, t->hwnd); - - uiWindowsRegisterWM_NOTIFYHandler(t->tabHWND, onWM_NOTIFY, uiControl(t)); - - t->pages = new std::vector<struct tabPage *>; - - return t; -} |