So close, I can almost taste it! I can count the list of things left to do on one hand 😀
This week has been all about lists and getting them to display data in the way that I want. I spent the week rewriting the main, folder, and feed screens to use lists instead of popping controls into an Enyo scroller. As with any sort of UI design, it was fiddly, but I came away with something that I’m pretty happy with.
So, how’s last week’s todo list looking?
A proper list for feeds and folders with refreshing and delete buttons(Done!)A proper list for articles with swipe to star and mark read/unread(Done!)- Recurring notifications (Still on the list)
- Various bug-fixes and cleanups (off the top of my head: mark all articles in a feed as read (the button is there, just need to wire in the event),
proper handling of orientation lock,mark read as you scroll(not doing in this version. I can’t implement it with an existing enyo list, but I might be able to with a custom class.), auto close feeds/folders when all items are read. – all minor things).
Enyo’s lists are pretty good, but, as with anything, there are a few quirks to work around. Honestly, for my purposes, I think that Mojo handled lists better. Enyo’s lists are missing an easy implementation of dividers. (You have to manually show or hide the header for each item, rather than simply being able to provide a function), as well as missing swipe to delete. Additionally, Enyo lists are missing an item rendered event, as well as a swipe canceled one.
Swipe to delete, at least, was something that I could cobble together on my own. There were a few quirks that I had to work around here. First, a normal swipe will cause the swiped item to display for a second, and then disappear. I needed buttons that would stick around so that the user could press them. Fortunately, Enyo lists support a sticky item property. Unfortunately, it isn’t honoured properly, being reset each time, so it has to be set each time the swipe container is activated.
This leads to another quirk – no event is triggered when a sticky swipe item is activated. In fact, an ontap event is triggered, sending the user to the article. So, I had to set up my own “swiping” property to catch the event and cancel it if the sticky swipe item was open. I also had to manually call the list’s internal completeSwipe method as there is no documented way in the API to force a swipe to complete. But, after all that was done, I had a working swipe to delete method.
It’s also frustrating that there is no swipe canceled event. This means that in order to toggle an item’s read or starred property, you have to do a complete swipe, instead of just being able to expose the icon and then cancel the swipe. I played around with a custom class for this, extending the list kind, with a custom event, but the swipeCanceled event would always fire too early, not waiting for the animation to complete. This would have the effect of triggering a tap on the item and causing the article to load. Although, I do have an idea that I will look at implementing next week if time allows.
The last quirk that I had to deal with was the lack of an “item rendered” event. This means that I can’t look for a particular list item to trigger loading more articles. I’ll have to manually do it with a button. But, that’s a problem for next week.
There were two other bits of weirdness regarding sizing that I ran into that were notable enough to remember. The first has to do with how the width of a list item is calculated (at least in FirefoxOS). Since lists use a Flyweight Repeater pattern, you can’t use fittables (rows or columns) in list items. This makes it a little challenging to have a list item that stretches across the window. In other browsers, you can just set float:right on the column that you want on the far side of the list. But, in FirefoxOS, this causes the element to move down to the next line, as well as to float on the right side of the page. Needless to say, that doesn’t work very well. Since my sticky items at the top of my list have statically set widths, ultimately, I had to use this ugly hack:
if (enyo.platform.firefoxOS) { var width = this.$.stickySources.controls[0].controls[0].controls[1].domStyles.width; var remainder = window.innerWidth - parseInt(width) - 70; //This is calculated by taking window width less width of the all items title column, less 30px for the icon and 40px for the margins. this.$.sourceName.setStyle("width:" + width + "; font-weight: bold"); this.$.sourceUnreadCount.setStyle("width:" + remainder + "px; text-align: right; font-weight: bold"); }
But, everything now lines up nicely.
The second bit of weirdness involves the list length. When the main window is initially rendered, if the list extends off the end because some titles are more than one line, you can’t get to the last few items. The list will just bounce back. However, if you navigate to another screen and back, the window will re-render properly. The ugly hack that I did to make things work properly was to raise a window resized event to force a redraw. Now, from the user’s perspective, everything renders right the first time.
On the flip side, once it’s working it works great. Also, the re-orderable implementation is very simple, and I got that working without too many problems, and no notable quirks to speak of. All in all, I would definitely use lists again rather than trying to construct my own.
So, what’s still left to do?
- Recurring notifications
- Loading more items in a feed (I have some sample code for list paging, just need to implement it.)
- Event handling. (There are still a few Mojo events left over that need to be converted to Enyo events. ie. mark all articles in a feed as read).
- Minor bug fixes and cleanups. (off the top of my head: auto close feeds/folders when all items are read and logout. – all minor things)
Beta and a submission to the app store are just around the corner. But, I’ve only got about 2 weeks left, so I need to hurry. Fortunately, I think that I just need a couple more days… (knock on wood).
As always, lets close with the week’s screenshots:
The main view list of feeds with working delete and cancel buttons.
Articles properly split with date headers. Webkit outputs a date in the form of July 18, 2014. Gecko outputs 07/18/2014.
If you swipe right to left, it will toggle the article’s starred state. If you swipe left to right it will toggle the article’s read state.
Looking good Brent! Let me know when it’s finished. 🙂