New API to read Caps-Lock and Num-Lock state

Kevin Rushforth kevin.rushforth at oracle.com
Tue Jan 19 13:12:10 UTC 2021


I also think that the suggestion of using Optional<Boolean> is a very 
good one, and more clearly expresses the "unknown" case without having 
to invent a new enum and without the problems that throwing an unchecked 
exception could cause.

Thanks.

-- Kevin

On 1/18/2021 12:20 AM, Nir Lisker wrote:
> Looking at the use case for this request, which is to warn the user while
> typing in password fields, I tried to write some simple code for it using
> the Optional approach:
>
>          Optional<Boolean> result = Platform.isKeyLocked(KeyCode.CAPS+LOCK);
>          result.ifPresentOrElse(on -> label.setText("Caps Lock is " + (on ?
> "on" : "off")),
>                                 () -> label.setText("Check Caps Lock"));
>
> In practical terms, a key event listener would need to be added to the
> password field to react to Caps Lock presses, and that will call the code
> above.
> I think that this is the best option.
>
> On Sun, Jan 17, 2021 at 8:10 PM Frederic Thevenet <thevenet.fred at free.fr>
> wrote:
>
>> I realize that my suggestion was somewhat unclear, apology about that.
>>
>> I wasn't suggesting that we return null to count as the third state, but
>> indeed that we leverage the isPresent state of the optional, alongside
>> with the two states provided by the Boolean, e.g:
>>
>> isKeyLocked(KeyCode.NUM_LOCK).ifPresent(locked-> {
>>       // The num_lock key exists on the current platform
>>       if (locked){
>>           // React to the key being locked
>>       } else {
>>           // Or to the key not being locked
>>       });
>>
>>
>> On 17/01/2021 18:31, Jonathan Giles wrote:
>>> A method returning Optional should never return null, as that undoes
>>> the contract that Optional is supposed to represent, which is to avoid
>>> NPEs by never being null itself, only empty in the absence of a
>>> returned value. For this reason, an Optional should be considered two
>>> state rather than three state.
>>>
>>> -- Jonathan
>>> (Tapped on a touch device)
>>>
>>> On Mon, 18 Jan 2021, 12:29 am Frederic Thevenet,
>>> <thevenet.fred at free.fr <mailto:thevenet.fred at free.fr>> wrote:
>>>
>>>      Hi,
>>>
>>>       From the perspective of the application developer, I think
>>>      throwing a
>>>      runtime exception if the key does not exists on a given platform is
>>>      potentially risky, as the API provided no hints that a given key
>>>      might
>>>      not exists an other platforms, and this oversight will only manifest
>>>      itself at runtime, on said platform.
>>>
>>>      With the other two proposed solution (three-state return and Checked
>>>      exception) the API itself reminds its would be consumer that they
>>>      should
>>>      consider a case where the operation is invalid.
>>>
>>>      I'm personally not keen on checked exceptions in such a scenario
>>>      either,
>>>      as it would require an extra API to check for the existence of a
>>>      given
>>>      key on the current platform, or condemn developers to implement
>>>      conditional logic via exception catching (or require developer to
>>>      know
>>>      what specific keys exists on what platform before-hand to do the
>>>      check).
>>>
>>>      Given all that, my personal preference would go to a three state
>>>      return
>>>      solution.
>>>
>>>      On that topic, is there anything that would preclude the use of an
>>>      Optional<Boolean> to represent these three states, if we want to
>>>      avoid
>>>      introducing new enums?  It seems to me its semantics aligns quite
>>>      nicely
>>>      with the problem at hand.
>>>
>>>      Fred
>>>
>>>
>>>      On 16/01/2021 17:41, Kevin Rushforth wrote:
>>>      > Hi Jonathan,
>>>      >
>>>      > Thanks for the suggestion. I thought about it as well. We could do
>>>      > that, but it seems like overkill. I'll reconsider if enough others
>>>      > favor the idea. As for the exception, my thinking is to use
>>>      > UnsupportedOperationException, which is what the equivalent AWT
>>>      method
>>>      > uses. FWIW, I don't generally like checked exceptions; we don't
>>>      define
>>>      > any such exceptions in JavaFX and I wouldn't want to start now.
>>>      >
>>>      > -- Kevin
>>>      >
>>>      >
>>>      > On 1/16/2021 12:46 AM, Jonathan Giles wrote:
>>>      >> Hi friends,
>>>      >>
>>>      >> Just to throw out an alternate API approach (which I would not go
>>>      >> anywhere near close to saying is a better approach), we could
>>>      >> consider a three-value enum getter API:
>>>      >>
>>>      >> public static KeyLockState Platform::getKeyLockState(KeyCode
>>>      keyCode);
>>>      >>
>>>      >> Where KeyLockState = { LOCKED, NOT_LOCKED, NOT_PRESENT }
>>>      >>
>>>      >> I'll be the first to argue against yet another enum, but I
>>>      wanted to
>>>      >> throw this out there as an alternate approach that avoids the
>>>      needs
>>>      >> for checked exceptions (which is what I assume is meant by
>>>      'throw an
>>>      >> exception', as opposed to throwing a runtime exception).
>>>      >>
>>>      >> -- Jonathan
>>>      >>
>>>      >> On Sat, Jan 16, 2021 at 6:40 AM Kevin Rushforth
>>>      >> <kevin.rushforth at oracle.com <mailto:kevin.rushforth at oracle.com>
>>>      <mailto:kevin.rushforth at oracle.com
>>>      <mailto:kevin.rushforth at oracle.com>>> wrote:
>>>      >>
>>>      >>     For JavaFX 17, I am planning to add a minor enhancement to
>>>      read the
>>>      >>     state of the keyboard lock keys, specifically, Caps-Lock,
>>>      >>     Num-Lock, and
>>>      >>     maybe Scroll-Lock (although I might defer the latter to a
>>>      future
>>>      >>     version
>>>      >>     since it will be more difficult to test, and doesn't seem as
>>>      >> useful).
>>>      >>
>>>      >>     This is currently tracked by JDK-8259680 [1].
>>>      >>
>>>      >>     The proposed API would be something like:
>>>      >>
>>>      >>              public static boolean Platform::isKeyLocked(KeyCode
>>>      >> keyCode);
>>>      >>
>>>      >>     One question is whether we should throw an exception if the
>>>      key
>>>      >> state
>>>      >>     cannot be read on a particular system (e.g., Num Lock on
>>>      macOS),
>>>      >>     which
>>>      >>     is what the similar AWT API does. I don't have a strong
>>>      opinion on
>>>      >>     that
>>>      >>     poont, although I wouldn't want to throw an exception if the
>>>      >> keyboard
>>>      >>     doesn't have the key in question, as long the system is able
>> to
>>>      >>     read the
>>>      >>     state accurately.
>>>      >>
>>>      >>     Comments are welcome.
>>>      >>
>>>      >>     -- Kevin
>>>      >>
>>>      >>     [1] https://bugs.openjdk.java.net/browse/JDK-8259680
>>>      <https://bugs.openjdk.java.net/browse/JDK-8259680>
>>>      >>     <https://bugs.openjdk.java.net/browse/JDK-8259680
>>>      <https://bugs.openjdk.java.net/browse/JDK-8259680>>
>>>      >>
>>>      >
>>>



More information about the openjfx-dev mailing list