Friday, 20 January 2012

Touch Interfaces

Although I should really be working on the shed or just getting some fresh air, I kept poking away at the kobo code.

I thought i'd try to implement a copy of the 'date setting' thing: the one on the kobo is really slow and hard to use for some reason and I wanted to verify that it wasn't a fault of the device ...


(this is similar-but-not the same as the kobo date setting page)

Rather than copy the same interface (which is based on selecting what to change and up/down buttons), I came up with a different one based on more 'standard' widgets: dropdown menu's and sliders.



I'm also using a new 'requester' class, which is a modal window which opens centered on the screen.

Of course, the problem with writing your own toolkit is you need to write all those things too ... but I managed to get those working eventually. The popup menu will try to align with the selected item, otherwise it fits to the screen.

I hit my first snag when trying to create requesters: the event loop iterates through a list of gadgets, but that ended up changing during the update since I was adding a new window ... so my first solution was to hack the popups in separately to the Screen class: it needs to track them for events anyway. I knew that although I wasn't hitting it at the moment, there was also a potential for multi-thread issues as well, so I attempted to create a work-around for that too. I removed access to the children of a Group gadget, and forced access through a synchronous interface which makes a copy of the list. Although it can potentially access stale data, it should eventually catch up.



I'm using a layout class for the layout of the menu content, so although it's not shown, the 'day' selector uses a grid layout and lists the day numbers in quasi-calendar format.



For the year I thought i'd try something different - a slider bubble, which just goes away once you lift your finger.



In action ... showing the faster update mode. I can also set it to update synchronously - in this case you get no artefacts, but it only updates about 3fps.

I also poked around with the update manager a fair bit. I had been just shipping repaint events to another thread and letting it merge them if it happened to have a few in the queue. But this meant the display would update quickly as soon as something changed and then usually the rest of the updates for handling that input would happen later: i.e. at least 2 updates (which are slow if you're waiting for them). So I now have it merge the updates as they come in, and only fire them off after processing input events. There is still some issues with this for the e-ink, e.g. if you do anything on an input 'pressed' event such as highlighting a button, and then perform the action on the 'released' event you still end up having to wait for at least one redundant updates - which again is slow if you're synchornising with the e-ink.

I also experimented with an 'invert' display every now and then: e.g. when a requester is closed. This is needed to clean up the e-ink fully. Here I hit some snags with synchronisation with the device driver although I have it sort of working. Sometimes it inverts the old data first, and then inverts the final data, even though i'm ensuring the updates are being sent in order. I am just using the same update maker though, so it probably has something to do with that.

Finally, I tried to work out how to resume from suspend but got nowhere - I can suspend the box but it wont resume on any button presses and I have to do a hardware reset.

No comments: