Open Source & Free  

Downloads, Callbacks, Signature & More

Downloads, Callbacks, Signature & More

Header Image

We’ve had a busy week working with several customers on various tasks/issues as well as the documentation
which is practically unrecognizable by now (more than 600 pages by now). As a result a lot of small fixes and
enhancements were made to the code as well as one new niche component.

ConnectionRequest.downloadImageToStorage

We have multiple ways to download an image and our general favorite is the URLImage.
However, the URLImage assumes
that you know the size of the image in advance or that you are willing to resize it. In that regard it works great for
some use cases but not so much for others.

In those other cases we usually recommend one of the Util methods.
However, that might not always be appropriate since some edge cases might require more complex
manipulation of requests e.g. making a POST request to get an image.

Adding global headers is another use case but you can use
addDefaultHeader
to add those.

To make this process simpler we added a set of helper methods to
ConnectionRequest that downloads images directly.

These methods complement the Util methods but go a bit further and feature very terse syntax e.g. we can just
download a ConnectionRequest to Storage using code like this:

request.downloadImageToStorage(url, (img) -> theImageIsHereDoSomethingWithIt(img));

New Callback & Callback Dispatcher

You will notice that the terse code above accepted an argument that isn’t an ActionListener or a Runnable
since it passes an Image object in the callback.

Historically we had a little known interface in Codename One that was inspired by GWT called
Callback. This interface
was used mainly for webservice calls so it had onSuccess/onError methods and a generic based response.

With Java 8 lambdas it occurred to us that it makes more sense to split this interface into two interfaces so
we can write more terse code and so we now have:
SuccessCallback &
FailureCallback.

These are pretty convenient and I’m pretty sure we’ll use them elsewhere.

Signature

As part of his work for a customer Steve implemented the SignatureComponent.
This allows an app to show a surface where the user can scribble a signature to approve a contract or detail
within the app.

The Signature Component

Simple usage of the SignatureComponent class looks like this:

Form hi = new Form("Signature Component");
hi.setLayout(new BoxLayout(BoxLayout.Y_AXIS));
hi.add("Enter Your Name:");
hi.add(new TextField());
hi.add("Signature:");
SignatureComponent sig = new SignatureComponent();
sig.addActionListener((evt)-> {
    System.out.println("The signature was changed");
    Image img = sig.getSignatureImage();
    // Now we can do whatever we want with the image of this signature.
});
hi.addComponent(sig);
hi.show();

Small Changes

Component.remove()

We added the ability to do Component.remove().
This is really shorthand syntax for the somewhat contrived getParent() syntax but it’s also pretty helpful when
we aren’t sure if there is a parent.

So in effect it saves us the cost of an additional if statement.

Generic Action Listener & NetworkEvent Callbacks

Up until now NetworkEvent
was pretty painful to use. E.g. if you wanted to monitor networking code via a listener you always had to
downcast to the NetworkEvent e.g.:

NetworkManager.getInstance().addErrorListener(new ActionListener() {
    public void actionPerformed(ActionEvent ev) {
        NetworkEvent e = (NetworkEvent)ev;
        // do something...
    }
});

Or with Java 8 syntax:

NetworkManager.getInstance().addErrorListener((ev) -> {
    NetworkEvent e = (NetworkEvent)ev;
    // do something...
});

This sucks and made us constantly rethink our decision to use ActionListener everywhere…​

Until we suddenly realized we can generify ActionListener which is now ActionListener<T>. As a result
we made all the listener events in NetworkManager and ConnectionRequest use NetworkEvent
as the generic and the result is that this works:

NetworkManager.getInstance().addErrorListener((networkEventInstance) -> {
    // do something...
});

Shorter Padding/Margin Syntax

I’ve been writing a lot of demos and one of the things I try to do when writing demo code is to keep it as self
contained as possible so it will work on your machines.

This is sometimes challenging as providing things such as theme instructions to reproduce my results is probably
not intuitive. So to reproduce some behaviors I use Style manipulation code rather than themes which are superior
but harder to convey in a manual.

As part of that I was manipulating margin and wanted to make sure the margin is in DIPs (millimeters). The common
code for this is:

cmp.getAllStyles().setMarginUnit(Style.UNIT_TYPE_DIPS, Style.UNIT_TYPE_DIPS, Style.UNIT_TYPE_DIPS, Style.UNIT_TYPE_DIPS);

This applies to all 4 sides of the margin/padding but if this seems redundant to you then you are not the only one…​

So from now on if you have less than 4 elements only the first one will count so this statement will be equivalent:

cmp.getAllStyles().setMarginUnit(Style.UNIT_TYPE_DIPS);

This also applies to padding so you can use that syntax there.

8 Comments

Leave a Reply