Commit graph

1019 commits

Author SHA1 Message Date
Ben Wiederhake
6b75a4dfc3 Everywhere: Mark overridden methods 'override'
This is good practice, and fixes some IDE warnings.
2021-11-02 22:56:53 +01:00
thislooksfun
fc411695c7 LibGUI: Keep autocomplete open after applying 'layout: ' 2021-11-02 17:53:22 +01:00
thislooksfun
7a2c8452f1 LibGUI: Don't re-trigger the autocomplete box when the timer fires
Previously there was a situation where the autocomplete box would
appear to "jump" to the side. This was due to the following race
condition:

1. Start typing, thus triggering the autocomplete timer to start
2. Manually trigger autocomplete before the timer finishes
3. Continue typing
4. The autocomplete timer now fires

When the timer fires it causes the autocomplete box to show, which, if
it is already shown, has the effect of moving the box to the current
cursor position.
2021-11-02 17:53:22 +01:00
thislooksfun
d5baf1c1fa LibGUI: Allow autocomplete to stay open after applying
Previously the autocomplete box would always close after applying a
suggestion. This is the desired behavior in almost all cases, but there
are some situations (like autocompleting paths) where it would be nicer
to keep the autocomplete box open after applying the suggestion.
2021-11-02 17:53:22 +01:00
thislooksfun
352f593958 LibGUI: Add and use TextEditor::hide_autocomplete()
There were cases where the autocomplete box was being hidden but the
autocomplete timer wasn't being cancelled.
2021-11-02 17:53:22 +01:00
thislooksfun
aea9ba3b42 LibGUI: Refactor out common code
This is prepping for a future commit.
2021-11-02 17:53:22 +01:00
thislooksfun
713b6badb0 LibGUI: Add AutocompleteProvider::has_suggestions() 2021-11-02 17:53:22 +01:00
thislooksfun
1bf428d296 LibGUI: Add missing #include 2021-11-02 17:53:22 +01:00
thislooksfun
6bd16cc309 LibGUI: Always pre-select the first autocomplete suggestion
Previously we would only pre-select the row the first time the box
was shown, which is not ideal. Now we behave like other editors.
2021-11-02 17:53:22 +01:00
thislooksfun
86ea41970d LibGUI: Hide autocomplete on any event other than typing
Moving the cursor to a different location, by any means, should
dismiss the autocomplete popup. This is the behavior of virtually
every editor/IDE out there, and it is really annoying (and
confusing) when our autocomplete doesn't behave like that.
2021-11-02 17:53:22 +01:00
thislooksfun
0627ed9900 LibGUI: Always show a box when the user requests autocomplete
Previously if there were no suggestions, we simply wouldn't show the
autocomplete popup at all. This is functional, but when there are no
resultes it does leave the user wondering if it actually worked.

Now, if the user requests autocomplete and we do have requests, it
behaves exactly as before, but if there' aren't any we now show a box
with the message "No suggestions" to show the user that we got the
request, there just isn't anything to suggest.
2021-11-02 17:53:22 +01:00
thislooksfun
6c776d267a LibGUI: Remove unnecessary braces 2021-11-02 17:53:22 +01:00
thislooksfun
4e5bf5c138 LibGUI: Abstract out even more duplicated logic 2021-11-02 17:53:22 +01:00
thislooksfun
d4eef0f17d LibGUI: Abstract out and name repeated logic 2021-11-02 17:53:22 +01:00
thislooksfun
d73d044f2b LibGUI: Suggest classes when typing identifiers
We now suggest classes even if the line does not start with an @.
After all, we now have fuzzy matching, so why *shouldn't* "color"
match @GUI::ColorInput as well as background_color?
2021-11-02 17:53:22 +01:00
thislooksfun
22a955b2d7 LibGUI: Abstract out widget and layout class matching 2021-11-02 17:53:22 +01:00
thislooksfun
e1e856132c LibGUI: Don't suggest widgets inside layouts
Having a widget inside a layout is meaningless, so why suggest them in
the first place?
2021-11-02 17:53:22 +01:00
thislooksfun
e403796842 LibGUI: Abstract out some duplicated logic for suggesting properties
A lot of the code in this area is duplicated, which is not great. In
fact this also fixes a bug where suggested partially matched props
would include read-only properties, since that check had only been
added to one of the two loops.
2021-11-02 17:53:22 +01:00
thislooksfun
4143f6f906 LibGUI: Make sure that children are actually widgets
Previously this section of code would blindly add *anything* as a child
as long as it has been registered as an object. Since there is no
guarentee that those objects are, in fact, Widgets, this feels like a
logical fallacy.

For example, up until this change, this is perfectly valid GML:

```
@GUI::Widget {
    layout: @GUI::VerticalBoxLayout {
    }

    @GUI::VerticalBoxLayout {
    }
}
```

What exactly does it do? Who knows! It doesn't seem to *break*, but I
think we can all agree it shouldn't be valid.

Instead, we now actually verify that the registered class inherets from
GUI::Widget before adding it as a child. We also error if it's not,
which should hopefully help new GML writers from forgetting to write
'layout: ' before the layout definition and being confused as to why
it's not working.
2021-11-02 17:53:22 +01:00
thislooksfun
eb3ca64819 LibGUI: Dynamically process layouts from GML files
There are only two layouts at the moment, but that could (and probably
will) change in the future. Why limit ourselves by hardcoding these
checks when we can do it dynamically instead?
2021-11-02 17:53:22 +01:00
thislooksfun
03b52e26f0 LibGUI: Use fuzzy matching for GML suggestions 2021-11-02 17:53:22 +01:00
thislooksfun
1a3ea0c892 LibGUI: Add myself to the copyright header 2021-11-02 17:53:22 +01:00
thislooksfun
49b4dfd6cd LibGUI: Suggest 'layout' even before the user starts typing 2021-11-02 17:53:22 +01:00
thislooksfun
8863fe5852 LibGUI: Remove unused check
This check was removed as it will now never trigger.

The completion has the suffix ': ' on it, and the key does not.
Therefore if the user has not yet typed the ':', it will not be equal,
and after they do the check on line 167 will fail so the entry won't be
in the list to begin with.
2021-11-02 17:53:22 +01:00
thislooksfun
9a70ae1593 LibGUI: Automatically append ': ' after autocompleted GML properties 2021-11-02 17:53:22 +01:00
thislooksfun
f7f9d09e72 LibGUI: Remove GUI::AutocompleteProvider::Entry::kind
The only code using it was removed in the previous commit.
2021-11-02 17:53:22 +01:00
thislooksfun
f699dbdc3f HackStudio+LibGUI: Handle #include quotes and brackets in the engine
Previously we had a special case in order to auto-append quotes or
angle brackets to #include statements. After the previous commit this
is no longer necessary.
2021-11-02 17:53:22 +01:00
thislooksfun
a5b3c3f85f LibGUI: Allow completion suggestions to fill and display different text
There are times when it is nice to display one suggestion but fill
something different. This lays the groundwork for allowing
GMLAutocompleteProvider to automatically add ': ' to the end of
suggested properties, while keeping the ': ' suffix from cluttering up
the suggestion UI.
2021-11-02 17:53:22 +01:00
thislooksfun
96029a4ac6 LibGUI: Replace the already typed text when autocompleting
This was a great optimization before, but it locks us out of some neat
features, like fuzzy matching.
2021-11-02 17:53:22 +01:00
thislooksfun
f8c98cbf55 LibGUI: Show autocomplete for Layout properties 2021-11-02 17:53:22 +01:00
thislooksfun
b0122744a6 LibGUI: Match layout classes even after you start typing
The previous commit fixed the issue with layout classes not being
suggested at all, but there was still another issue. Once you started
typing the class name a different suggester would take over and only
show widgets. This commit makes it so it still only suggests layouts
in that situation.

This, combined with the last commit, makes autocompleting layouts way
more discoverable and user-friendly. :^)
2021-11-02 17:53:22 +01:00
thislooksfun
f048d16be5 LibGUI: Correctly suggest layout classes
Previously when the GMLAutocompleteProvider was invoked just after the
'layout:' tag it would suggest nothing. This is because Layouts do not
inherit from Widget, so the two checks would always eliminate every
suggestion from the list. This patch makes it always suggest any
(registered) object that inherits from GUI::Layout.

This should make layouts more discoverable and easier to quickly use.
2021-11-02 17:53:22 +01:00
thislooksfun
989c111d65 LibGUI: Remove unnecessary curly braces
Not needed for the commit, but I always try to leave the code nicer
than I found it. :)
2021-11-02 17:53:22 +01:00
thislooksfun
416988cc7f LibGUI: Register layouts with inheritance 2021-11-02 17:53:22 +01:00
thislooksfun
6dc2749795 LibGUI: Register GUI::Layout
This will be used later to check inheritence.
2021-11-02 17:53:22 +01:00
thislooksfun
c3b0b9057e LibCore+LibGUI: Make ObjectClassRegistration::construct() nullable
This lays the groundwork for allowing the registration of abstract
core objects, which will be needed for improved GML autocomplete.
2021-11-02 17:53:22 +01:00
Ben Wiederhake
59619572d6 LibThreading: Remove redundant method 2021-11-02 11:07:26 +01:00
Marco Cutecchia
116bb4888f LibGUI: Support using a bitmap as override cursor 2021-10-31 12:37:49 +01:00
Noah Haasis
05aeff1c4d LibGUI: Focus next tab after closing active tab
Focus the next tab after closing the currently active tab.
If the tab being closed is the last one then the new last
tab is active.
2021-10-30 17:13:25 +03:30
Sam Atkins
859975f6bd LibGUI: Add MetricRole and PathRole to GUI::Variant
This is needed for making them editable in the ThemeEditor, like
ColorRole is.
2021-10-28 11:23:44 +02:00
Filiph Sandström
c6247fe414 Everywhere: Rename back-click to backward-click
This matches the current forward-click terminology.
2021-10-27 22:05:58 +03:00
Filiph Sandström
d6a0726302 Everywhere: Rename left/right-click to primary/secondary
This resolves #10641.
2021-10-27 22:05:58 +03:00
Andreas Kling
f27d768745 LibGUI: Don't force flush pending paints whenever mouse moves
This patch removes a hack that forced any pending repaints to happen
immediately whenever you moved the mouse over a window.

The purpose of that mechanism was to ensure that quick button presses
still show up visually, and since that is now accomplished via
Widget::repaint(), we no longer need this.
2021-10-23 17:57:05 +02:00
Andreas Kling
d196fbce5b LibGUI: Repaint buttons immediately on mouse up/down events
This ensures that rapidly clicking a button doesn't look like it's
"swallowing" some of the mouse events.

This already worked okay due to a hack in Window, but this will allow us
to get rid of that hack.
2021-10-23 17:54:59 +02:00
Andreas Kling
24651f854c LibGUI: Add Widget::repaint() to force an immediate repaint
In most situations, Widget::update() is preferable, since that allows us
to coalesce repaints and avoid redundant work, reducing system load.

However, there are some cases where you really want a paint to happen
right away, to make sure that the user has a chance to see a short-lived
visual state.
2021-10-23 17:53:11 +02:00
Andreas Kling
da86f4e384 LibGUI: Use move semantics in GUI::MultiPaintEvent 2021-10-23 17:38:38 +02:00
Andreas Kling
79f2e8ae2a LibGUI: Make exclusive button group act as a single focusable unit
Before this change, using the Tab key would cycle through all the
individual buttons in an exclusive group (e.g radio buttons.)
This felt wrong, since a group of exclusive buttons is really a single
logical input with a limited number of possible choices.

This patch makes such groups behave as a single focusable unit instead,
by dynamically updating the focus policies so that only the currently
checked button is focusable.

We also allow keyboard navigation within the button group via the arrow
keys. This had to be specialized in GUI::AbstractButton, since the
default behavior of arrow keys is to traverse the focus chain.
2021-10-23 16:10:44 +02:00
Andreas Kling
0d8373287c LibGUI: Add GUI::KeyEvent::is_arrow_key() 2021-10-23 16:10:44 +02:00
Andreas Kling
d91732f959 LibGUI: Mark GUI::RadioButton as "checkable"
Any AbstractButton that uses the "checked" state should mark itself
"checkable", this was a weird oversight.
2021-10-23 16:10:44 +02:00
Andreas Kling
649cb67f28 LibGUI: Don't paint TextEditor selection in non-focused widgets
Showing the selection in non-focused text editors was not really useful,
since refocusing the widget would clear or change the selection
immediately anyway.

Note that TextEditors in inactive windows can still be the focused
widget within that window, and will still be painted with an "inactive"
looking selection.
2021-10-21 23:23:25 +02:00