Changeset dc5c303 in mainline for uspace/lib/ui/src/menubar.c


Ignore:
Timestamp:
2023-12-28T13:59:23Z (14 months ago)
Author:
GitHub <noreply@…>
Children:
6b66de6b
Parents:
42c2e65 (diff), f87ff8e (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
git-author:
boba-buba <120932204+boba-buba@…> (2023-12-28 13:59:23)
git-committer:
GitHub <noreply@…> (2023-12-28 13:59:23)
Message:

Merge branch 'master' into topic/packet-capture

File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/ui/src/menubar.c

    r42c2e65 rdc5c303  
    3535
    3636#include <adt/list.h>
     37#include <ctype.h>
    3738#include <errno.h>
    3839#include <gfx/color.h>
     
    4546#include <ui/control.h>
    4647#include <ui/paint.h>
    47 #include <ui/menu.h>
    4848#include <ui/menubar.h>
     49#include <ui/menudd.h>
     50#include <ui/wdecor.h>
    4951#include <ui/window.h>
    5052#include "../private/menubar.h"
    5153#include "../private/resource.h"
     54#include "../private/wdecor.h"
     55#include "../private/window.h"
    5256
    5357enum {
     
    9599        mbar->ui = ui;
    96100        mbar->window = window;
    97         list_initialize(&mbar->menus);
     101        list_initialize(&mbar->menudds);
     102
     103        if (window->mbar == NULL)
     104                window->mbar = mbar;
     105
    98106        *rmbar = mbar;
    99107        return EOK;
     
    106114void ui_menu_bar_destroy(ui_menu_bar_t *mbar)
    107115{
    108         ui_menu_t *menu;
     116        ui_menu_dd_t *mdd;
    109117
    110118        if (mbar == NULL)
    111119                return;
    112120
    113         /* Destroy menus */
    114         menu = ui_menu_first(mbar);
    115         while (menu != NULL) {
    116                 ui_menu_destroy(menu);
    117                 menu = ui_menu_first(mbar);
     121        if (mbar->window->mbar == mbar)
     122                mbar->window->mbar = NULL;
     123
     124        /* Destroy menu drop-downs */
     125        mdd = ui_menu_dd_first(mbar);
     126        while (mdd != NULL) {
     127                ui_menu_dd_destroy(mdd);
     128                mdd = ui_menu_dd_first(mbar);
    118129        }
    119130
     
    155166        gfx_rect_t rect;
    156167        gfx_color_t *bg_color;
    157         ui_menu_t *menu;
     168        ui_menu_dd_t *mdd;
    158169        const char *caption;
    159170        gfx_coord_t width;
     
    189200        fmt.valign = gfx_valign_top;
    190201
    191         menu = ui_menu_first(mbar);
    192         while (menu != NULL) {
    193                 caption = ui_menu_caption(menu);
     202        mdd = ui_menu_dd_first(mbar);
     203        while (mdd != NULL) {
     204                caption = ui_menu_dd_caption(mdd);
    194205                width = ui_text_width(res->font, caption) + 2 * hpad;
    195206                tpos.x = pos.x + hpad;
     
    200211                rect.p1.y = mbar->rect.p1.y;
    201212
    202                 if (menu == mbar->selected) {
     213                if (mdd == mbar->selected) {
    203214                        fmt.color = res->wnd_sel_text_color;
    204215                        fmt.hgl_color = res->wnd_sel_text_hgl_color;
     
    223234
    224235                pos.x += width;
    225                 menu = ui_menu_next(menu);
     236                mdd = ui_menu_dd_next(mdd);
    226237        }
    227238
     
    241252 *
    242253 * @param mbar Menu bar
    243  * @param menu Menu to select (or deselect if selected) or @c NULL
     254 * @param mdd Menu drop-down to select (or deselect if selected) or @c NULL
    244255 * @param openup Open menu even if not currently open
    245256 * @param idev_id Input device ID associated with the selecting seat
    246257 */
    247 void ui_menu_bar_select(ui_menu_bar_t *mbar, ui_menu_t *menu, bool openup,
     258void ui_menu_bar_select(ui_menu_bar_t *mbar, ui_menu_dd_t *mdd, bool openup,
    248259    sysarg_t idev_id)
    249260{
    250         ui_menu_t *old_menu;
     261        ui_menu_dd_t *old_mdd;
    251262        gfx_rect_t rect;
    252263        bool was_open;
    253264
    254         old_menu = mbar->selected;
    255 
    256         mbar->selected = menu;
    257 
    258         /* Close previously open menu */
    259         if (old_menu != NULL && ui_menu_is_open(old_menu)) {
     265        old_mdd = mbar->selected;
     266
     267        mbar->selected = mdd;
     268
     269        /* Close previously open menu drop-down */
     270        if (old_mdd != NULL && ui_menu_dd_is_open(old_mdd)) {
    260271                was_open = true;
    261                 (void) ui_menu_close(old_menu);
     272                (void) ui_menu_dd_close(old_mdd);
    262273        } else {
    263274                was_open = false;
     
    270281                if (openup || was_open) {
    271282                        /*
    272                          * Open the newly selected menu if either
    273                          * the old menu was open or @a openup was
     283                         * Open the newly selected menu drop-down if either
     284                         * the old menu drop-down was open or @a openup was
    274285                         * specified.
    275286                         */
    276                         (void) ui_menu_open(mbar->selected, &rect, idev_id);
     287                        (void) ui_menu_dd_open(mbar->selected, &rect, idev_id);
    277288                }
    278         }
     289
     290                mbar->active = true;
     291        } else {
     292                mbar->active = false;
     293        }
     294}
     295
     296/** Select first drop-down.
     297 *
     298 * @param mbar Menu bar
     299 * @param openup @c true to open drop-down if it was not open
     300 * @param idev_id Input device ID
     301 */
     302void ui_menu_bar_select_first(ui_menu_bar_t *mbar, bool openup,
     303    sysarg_t idev_id)
     304{
     305        ui_menu_dd_t *mdd;
     306
     307        mdd = ui_menu_dd_first(mbar);
     308        ui_menu_bar_select(mbar, mdd, openup, idev_id);
     309}
     310
     311/** Select last drop-down.
     312 *
     313 * @param mbar Menu bar
     314 * @param openup @c true to open drop-down if it was not open
     315 * @param idev_id Input device ID
     316 */
     317void ui_menu_bar_select_last(ui_menu_bar_t *mbar, bool openup,
     318    sysarg_t idev_id)
     319{
     320        ui_menu_dd_t *mdd;
     321
     322        mdd = ui_menu_dd_last(mbar);
     323        ui_menu_bar_select(mbar, mdd, openup, idev_id);
     324}
     325
     326/** Select system menu.
     327 *
     328 * @param mbar Menu bar
     329 * @param openup @c true to open drop-down if it was not open
     330 * @param idev_id Input device ID
     331 */
     332void ui_menu_bar_select_sysmenu(ui_menu_bar_t *mbar, bool openup,
     333    sysarg_t idev_id)
     334{
     335        ui_wdecor_sysmenu_hdl_set_active(mbar->window->wdecor, true);
     336
     337        if (openup)
     338                ui_window_send_sysmenu(mbar->window, idev_id);
    279339}
    280340
     
    289349void ui_menu_bar_left(ui_menu_bar_t *mbar, sysarg_t idev_id)
    290350{
    291         ui_menu_t *nmenu;
     351        ui_menu_dd_t *nmdd;
     352        bool sel_sysmenu = false;
     353        bool was_open;
    292354
    293355        if (mbar->selected == NULL)
    294356                return;
    295357
    296         nmenu = ui_menu_prev(mbar->selected);
    297         if (nmenu == NULL)
    298                 nmenu = ui_menu_last(mbar);
    299 
    300         if (nmenu != mbar->selected)
    301                 ui_menu_bar_select(mbar, nmenu, false, idev_id);
     358        nmdd = ui_menu_dd_prev(mbar->selected);
     359        if (nmdd == NULL) {
     360                if ((mbar->window->wdecor->style & ui_wds_sysmenu_hdl) != 0) {
     361                        sel_sysmenu = true;
     362                } else {
     363                        nmdd = ui_menu_dd_last(mbar);
     364                }
     365        }
     366
     367        was_open = mbar->selected != NULL &&
     368            ui_menu_dd_is_open(mbar->selected);
     369
     370        if (nmdd != mbar->selected)
     371                ui_menu_bar_select(mbar, nmdd, false, idev_id);
     372
     373        /*
     374         * Only open sysmenu *after* closing the previous menu, avoid
     375         * having multiple popup windows at the same time.
     376         */
     377        if (sel_sysmenu)
     378                ui_menu_bar_select_sysmenu(mbar, was_open, idev_id);
    302379}
    303380
     
    312389void ui_menu_bar_right(ui_menu_bar_t *mbar, sysarg_t idev_id)
    313390{
    314         ui_menu_t *nmenu;
     391        ui_menu_dd_t *nmdd;
     392        bool sel_sysmenu = false;
     393        bool was_open;
    315394
    316395        if (mbar->selected == NULL)
    317396                return;
    318397
    319         nmenu = ui_menu_next(mbar->selected);
    320         if (nmenu == NULL)
    321                 nmenu = ui_menu_first(mbar);
    322 
    323         if (nmenu != mbar->selected)
    324                 ui_menu_bar_select(mbar, nmenu, false, idev_id);
     398        nmdd = ui_menu_dd_next(mbar->selected);
     399        if (nmdd == NULL) {
     400                if ((mbar->window->wdecor->style & ui_wds_sysmenu_hdl) != 0) {
     401                        sel_sysmenu = true;
     402                } else {
     403                        nmdd = ui_menu_dd_first(mbar);
     404                }
     405        }
     406
     407        was_open = mbar->selected != NULL &&
     408            ui_menu_dd_is_open(mbar->selected);
     409
     410        if (nmdd != mbar->selected)
     411                ui_menu_bar_select(mbar, nmdd, false, idev_id);
     412
     413        /*
     414         * Only open sysmenu *after* closing the previous menu, avoid
     415         * having multiple popup windows at the same time.
     416         */
     417        if (sel_sysmenu)
     418                ui_menu_bar_select_sysmenu(mbar, was_open, idev_id);
    325419}
    326420
     
    355449
    356450        if (event->key == KC_ENTER || event->key == KC_DOWN) {
    357                 if (mbar->selected != NULL && !ui_menu_is_open(mbar->selected)) {
     451                if (mbar->selected != NULL &&
     452                    !ui_menu_dd_is_open(mbar->selected)) {
    358453                        ui_menu_bar_entry_rect(mbar, mbar->selected,
    359454                            &rect);
    360                         ui_menu_open(mbar->selected, &rect, event->kbd_id);
     455                        ui_menu_dd_open(mbar->selected, &rect, event->kbd_id);
    361456                }
    362457
     
    364459        }
    365460
    366         if (event->c != '\0' && !ui_menu_is_open(mbar->selected)) {
     461        if (event->c != '\0' && !ui_menu_dd_is_open(mbar->selected)) {
    367462                /* Check if it is an accelerator. */
    368463                ui_menu_bar_press_accel(mbar, event->c, event->kbd_id);
     
    407502void ui_menu_bar_press_accel(ui_menu_bar_t *mbar, char32_t c, sysarg_t kbd_id)
    408503{
    409         ui_menu_t *menu;
     504        ui_menu_dd_t *mdd;
    410505        char32_t maccel;
    411506
    412         menu = ui_menu_first(mbar);
    413         while (menu != NULL) {
    414                 maccel = ui_menu_get_accel(menu);
    415                 if (c == maccel) {
    416                         ui_menu_bar_select(mbar, menu, true, kbd_id);
     507        mdd = ui_menu_dd_first(mbar);
     508        while (mdd != NULL) {
     509                maccel = ui_menu_dd_get_accel(mdd);
     510                if ((char32_t)tolower(c) == maccel) {
     511                        ui_menu_bar_select(mbar, mdd, true, kbd_id);
    417512                        return;
    418513                }
    419514
    420                 menu = ui_menu_next(menu);
     515                mdd = ui_menu_dd_next(mdd);
    421516        }
    422517}
     
    433528        gfx_coord2_t pos;
    434529        gfx_rect_t rect;
    435         ui_menu_t *menu;
     530        ui_menu_dd_t *mdd;
    436531        const char *caption;
    437532        gfx_coord_t width;
     
    454549        pos_id = event->pos_id;
    455550
    456         menu = ui_menu_first(mbar);
    457         while (menu != NULL) {
    458                 caption = ui_menu_caption(menu);
     551        mdd = ui_menu_dd_first(mbar);
     552        while (mdd != NULL) {
     553                caption = ui_menu_dd_caption(mdd);
    459554                width = ui_text_width(res->font, caption) + 2 * hpad;
    460555
     
    468563                        mbar->active = true;
    469564
    470                         /* Open the menu, close if already open. */
    471                         if (menu == mbar->selected)
    472                                 ui_menu_bar_select(mbar, NULL, false, pos_id);
    473                         else
    474                                 ui_menu_bar_select(mbar, menu, true, pos_id);
     565                        /* Open the menu, if not already open. */
     566                        if (mdd != mbar->selected)
     567                                ui_menu_bar_select(mbar, mdd, true, pos_id);
    475568
    476569                        return ui_claimed;
     
    478571
    479572                pos.x += width;
    480                 menu = ui_menu_next(menu);
     573                mdd = ui_menu_dd_next(mdd);
    481574        }
    482575
     
    487580 *
    488581 * @param mbar Menu bar
    489  * @param menu Menu whose entry's rectangle is to be returned
     582 * @param mdd Menu drop-down whose entry's rectangle is to be returned
    490583 * @param rrect Place to store entry rectangle
    491584 */
    492 void ui_menu_bar_entry_rect(ui_menu_bar_t *mbar, ui_menu_t *menu,
     585void ui_menu_bar_entry_rect(ui_menu_bar_t *mbar, ui_menu_dd_t *mdd,
    493586    gfx_rect_t *rrect)
    494587{
     
    496589        gfx_coord2_t pos;
    497590        gfx_rect_t rect;
    498         ui_menu_t *cur;
     591        ui_menu_dd_t *cur;
    499592        const char *caption;
    500593        gfx_coord_t width;
     
    511604        pos = mbar->rect.p0;
    512605
    513         cur = ui_menu_first(mbar);
     606        cur = ui_menu_dd_first(mbar);
    514607        while (cur != NULL) {
    515                 caption = ui_menu_caption(cur);
     608                caption = ui_menu_dd_caption(cur);
    516609                width = ui_text_width(res->font, caption) + 2 * hpad;
    517610
     
    520613                rect.p1.y = mbar->rect.p1.y;
    521614
    522                 if (cur == menu) {
     615                if (cur == mdd) {
    523616                        *rrect = rect;
    524617                        return;
     
    526619
    527620                pos.x += width;
    528                 cur = ui_menu_next(cur);
     621                cur = ui_menu_dd_next(cur);
    529622        }
    530623
     
    544637        mbar->active = true;
    545638        if (mbar->selected == NULL)
    546                 mbar->selected = ui_menu_first(mbar);
     639                mbar->selected = ui_menu_dd_first(mbar);
    547640
    548641        (void) ui_menu_bar_paint(mbar);
    549642}
    550643
     644/** Deactivate menu bar.
     645 *
     646 * @param mbar Menu bar
     647 */
    551648void ui_menu_bar_deactivate(ui_menu_bar_t *mbar)
    552649{
    553650        ui_menu_bar_select(mbar, NULL, false, 0);
    554         mbar->active = false;
    555651}
    556652
Note: See TracChangeset for help on using the changeset viewer.