Does mnemonics in bound labels (and push buttons) work in Base forms?

I’ve put a push button on my form. Its label is “Make ~print version”. When in normal display (not edit) this puts a line under “p”. This sort of responds to Alt-P on my keyboard: if the cursor is not “caught” in a subform data grid it does actually put focus on the button and execute it.

I’ve just put a combo box on my form. It is configured with a label field, with the text “Search for i~nvoice no.:”. Again, I see a nice line under the “n” of “invoice”. But pressing Alt-N on my keyboard does not take focus to the combo box, regardless of where the cursor is. In fact going Alt-N causes focus to jump to a subform data grid.

I wondered whether a different key combo might be needed, so I tried Shift-Alt-N, and AltGr-N, etc.

Maybe it’s my OS? (W10).

Anyone know if this mnemonic stuff can be made to work satisfactorily in Base forms? Ideally what I want is for the button to actually execute on Alt-P, regardless of where my cursor is, and for focus to go to the combo box if I go Alt-N, regardless of where my cursor is.

Further observations re label for combo box
I put the tilde before “v” of “invoice”. Alt-V then drops down the “View” menu of the application. Maybe there’s a way to disable display of these menus. But that seems academic because I then tried with a tilde before “C” and then before “S”. These don’t have corresponding application menus. But again, for no discernible reason, pressing Alt-C or Alt-S with the focus in a control on the main form causes focus to go to the subform data grid.
… and what’s strange with both these latter experiments is that pressing other Alt-[?] combinations does nothing. In other words the framework seems to be aware that it’s being asked to change the focus to another form component… but gets it wrong.

When creating a form with wizards the label fields will be connected with the input fields. Second entry of Properties → General of a input-field should be Label Field. Press the button with 3 and connect to the label field.
Might be you didn’t connect the fields?

1 Like

Thanks… interesting.
.
I tried again … but this time I created the label before running the wizard to create the combo box. It didn’t ask for a linked label during the wizard process, but when I configured the combo box to use the label afterwards I found that it worked. So thanks for that tip. Most peculiar.
.
However, the problem of the cursor getting “trapped” inside the subform data grid remains. I.e. if the cursor is in there, none of these mnemonics attached to controls in the main form is operative…
.
Whereas, for example, the mnemonics to bring down the application menus still work from inside the subform.

For jumping from subform to mainform I had created a macro. Please have a look at Base Guide Forms (Record input an navigation), which is a translated version of the German Base Handbuch.

biblio_form_subform.odt (15.5 KB)
has mnemonic shortcuts on first letters of the main form labels. The labels are
~Identifier
~Publisher
~Title
~Author

@Villeroy : The example won’t work if cursor is inside the table control.

Yes, the table control is the culprit. However, it works somehow with single controls and form property “Cycle” = “Current page”.
biblio_form_subform2.odt (14.3 KB)

… highly dysfunctional. I find that although I am able to use RobertG’s method (creating the label first, using the wizard to create the combo box/list box), actually this always leaves the box with a tab order of 0, meaning that if I press Return in it, the form moves to the next record … and without even triggering a “key release” event.
.
If I change the tab order to anything but 0, the mnemonic navigation stops working. If I disable the tabbing for the box control, the mnemonic navigation stops working.
.
Ideally what I want to do is to be able to choose a member of the list and then press Return key, and for that to take me to that record. I.e. a navigation list box (in fact an OO list box is more like combo boxes from other frameworks), a pretty ordinary element in a database form, with intuitive keystroke handling.
.
Looks like I am now faced with the task of trying to understand the whole mechanism of how keystrokes are intercepted, and of trying to cancel the default handling of them by the framework. Which I’m sure will be copiously documented somewhere (joke).
.
And that’s also going to be needed to jump out of the subform (NB I did look at that macro in the Base manual … bit clunky but useful for some purposes no doubt).

Hm, may be easier than I dreaded:

def on_load(self, load_event):
    desktop = XSCRIPTCONTEXT.getDesktop()
    component = desktop.getCurrentComponent() 
    import uno, unohelper
    from com.sun.star.awt import XKeyHandler
    class KeyHandler(unohelper.Base, XKeyHandler):
        def keyPressed(self, event):
            logger.info(f'event {event}')
            return False
        def keyReleased(self, event):
            logger.info(f'event {event}')
            return False
    component.CurrentController.addKeyHandler(KeyHandler())

This on_loaded macro is attached to the “When loading” event of a form. If you return False events are handled by the framework, but returning True appears to be a way of vetoing default handling. Looks promising.

Here is how it works with macro of Base Guide:
Beispiel_Cursorsprung_Subform_Mainform_Firebird.odb (14.7 KB)
But you are right. There are many (little) bugs:

  • Jumping to fields will only work with tab order ‘0’
  • Label fields have to appear first in Form Navigator
  • Automatic jump in sub form won’t work any more, so there has to be added another button with macro

Have written Bug 155401 for tab order ‘0’. Might be the automatic jump to subform will work if this bug will be solved.

This is totally broken. When I open your form in edit mode, then turn off design mode, the mnemonics trigger the macro buttons. When I open the form directly, the whole thing fails. Alt+R triggers the Form menu, Alt+N triggers nothing.

@Villeroy : Have downloaded the uploaded file. Activated macros. Cursor is inside “ID”. Could set Alt+k, Alt+t and Alt+j without any problem. This fields are part of the main form. With Alt+j I will get the sub form.

Could press Alt+n or Alt+r in the sub form. It will set next row or new row in main form and cursor to main form.

See I have written something wrong in description in the form: Jumping to new row and next row by Alt+… works only when started in sub form, not also.
Have added two buttons in main form. So it will work also with shortcuts in main form:
Beispiel_Cursorsprung_Subform_Mainform_Firebird.odb (14.8 KB)

Still does not work consistently for me.

  • I open the form

  • hit Alt+J (jump to subform) → OK

  • hit Alt+R (next row) and the parent form moves to the next record.

  • I open the form for editing, turn off design mode

  • hit Alt+J (jump to subform) → OK

  • hit Alt+R (next row) and the subform’s button [next Row] gets the focus but is not triggered.

  • next Alt+R moves the focus to the parent form’s button [next Row].

Tested with LO 7.5.2 on Linux and Windows
Since 2005 the tab controller works differently in design mode and in read-only mode which is a nightmare if you are picky with user interfaces (I’m not).

That’s why I had created it for. MainForm should change row and cursor moves to this next row. Seems you are expecting something else. This thread was about changing from subform to mainform. If you only wish this behavior the buttons should do nothing, must only be visible.

Have used like @Villeroy described with Cycle → Current page. Works well here in Linux for all fields, also from table controls to other fields. So I won’t need any macro code here.

Now there is a user with Mac. How do shortcuts run with Mac?

Suggesting my own solution here. It really is practical though, and completely defeats all the annoyances and dysfunctionality described in this thread. It works even when the cursor is in a subform.
.
This method should be attached to the “When loading” event of the form.

def on_load(mgr_self, event):
    desktop = XSCRIPTCONTEXT.getDesktop()
    component = desktop.getCurrentComponent() 
    draw_page = component.DrawPage
    current_controller = component.CurrentController
    import unohelper
    from com.sun.star.awt import KeyModifier
    from com.sun.star.awt import Key as AwtKey
    from com.sun.star.awt import XKeyHandler

    listbox = draw_page.Forms[0].inv_no_listbox
    listbox_view = current_controller.getControl(listbox)
    class KeyHandler(unohelper.Base, XKeyHandler):
        def keyPressed(self, event):
            if event.KeyCode == AwtKey.C:
                # if this is *just* Alt-C (no other modifiers permitted):
                if event.Modifiers == KeyModifier.MOD2:
                    if not listbox_view.hasFocus():
                        listbox_view.setFocus() # hurrah, jumps to control!!

                        # prevent default framework handling:
                        return True

            # trigger recordset navigation on the list box, based on the selected value
            if event.KeyCode == AwtKey.RETURN and event.Modifiers == 0: # no modifiers
                if listbox_view.hasFocus():
                    logger.info(f'--> inv_no_listbox has focus!!! SelectedValue {listbox.SelectedValue}')
                    # ... at this point: use the selected value to navigate to another record

                    # prevent default framework handling:
                    return True
           
            # everything else, default keypress-handling     
            return False

    current_controller.addKeyHandler(KeyHandler())

… if you really wanted to go crazy with the automation you could examine the labels attached to the form controls and set up these pseudo-mnemonics based on detection of tildes in the labels!