Writing a Sencha Touch Application, Part 4

This is the last of a four-part series on how to write a Sencha Touch application. If you’re new to the series, here are the links to the previous installments:

In part 3 of this tutorial we worked on the Note Editor and added the ability to create notes. It is time now to let our users edit and delete notes. Let’s work on the edit note feature first.

Disclosure events in a Sencha Touch List

When the person using the application touches a note’s disclosure button in the Notes List view, the selected note should be displayed in the Edit Note view:

We can complete this feature by implementing the onItemDisclosure handler of the notes list. Here’s the code:

NotesApp.views.notesList = new Ext.List({
    id: 'notesList',
    store: 'NotesStore',
    onItemDisclosure: function (record) {
        var selectedNote = record;
        NotesApp.views.noteEditor.load(selectedNote);
        NotesApp.views.viewport.setActiveItem('noteEditor', { type: 'slide', direction: 'left' });
    },
    itemTpl: '
<div class="list-item-title">{title}</div>' +
        '<div class="list-item-narrative">{narrative}</div>',
    listeners: {
        'render': function (thisComponent) {
            thisComponent.getStore().load();
        }
    }
});

The handler function accepts the selected note as a parameter. What we need to do in the handler is load the note in the editor utilizing the editor’s load() method, and then, make the Note Editor view active via a call to the viewport’s setActiveItem().

Very cool. At this point we can switch over to the emulator, where we should be able to edit notes.

Removing records from a data store

Deleting notes is also very easy. The Trash button on the Note Editor view’s bottom toolbar will trigger this function. We need to change the button’ handler like so:

NotesApp.views.noteEditorBottomToolbar = new Ext.Toolbar({
    dock: 'bottom',
    items: [
        { xtype: 'spacer' },
        {
            iconCls: 'trash',
            iconMask: true,
            handler: function () {

                var currentNote = NotesApp.views.noteEditor.getRecord();
                var notesList = NotesApp.views.notesList;
                var notesStore = notesList.getStore();

                if (notesStore.findRecord('id', currentNote.data.id)) {
                    notesStore.remove(currentNote);
                }

                notesStore.sync();

                notesList.refresh();
                NotesApp.views.viewport.setActiveItem('notesListContainer', { type: 'slide', direction: 'right' });
            }
        }
    ]
});

After acquiring references to the current note, the notes list and the notes data store, we use the store’s findRecord() function to find and remove the note loaded on the editor.

Next, we call sync() on the store to make the removal permanent, and proceed to re-render the notes list and make the Notes List view active.

This procedure is similar to the one we followed when we implemented the Save Note feature, although in this case we’re deleting the note, not saving it.

A quick check on the emulator should confirm that we can now delete notes.

Grouping items in a Sencha Touch List

One last thing we want to do is, in the Notes List view, render the notes grouped by date. This will make it easier for our users to work with their notes.

First, we need to tell our notesList Ext.List that it needs to render its items grouped. We can do this using the grouped config option like so:

NotesApp.views.notesList = new Ext.List({
    id: 'notesList',
    store: 'NotesStore',
    grouped: true,
    emptyText: '<div style="margin: 5px;">No notes cached.</div>',
    onItemDisclosure: function (record) {
        var selectedNote = record;
        NotesApp.views.noteEditor.load(selectedNote);
        NotesApp.views.viewport.setActiveItem('noteEditor', { type: 'slide', direction: 'left' });
    },
    itemTpl: '<div class="list-item-title">{title}</div>' +
        '<div class="list-item-narrative">{narrative}</div>',
    listeners: {
        'render': function (thisComponent) {
            thisComponent.getStore().load();
        }
    }
});

Then, we need to override the getGroupString() function of the NotesStore:

Ext.regStore('NotesStore', {
    model: 'Note',
    sorters: [{
        property: 'date',
        direction: 'DESC'
    }],
    proxy: {
        type: 'localstorage',
        id: 'notes-app-store'
    },
    getGroupString: function (record) {
        if (record && record.data.date) {
            return record.get('date').toDateString();
        } else {
            return '';
        }
    }
});

You can define the grouping behavior of the store using the groupField property and the getGoupString() function.

The getGroupString() function returns the string to group on, based on the store’s data model’s properties. By default, getGroupString() returns the value of the groupField property. In our case we want to use the value of the note’s date as the group’s header, but we want to format the value as a date.

If we check the emulator, the notes taken the same day should render under the same group header:

We made it!

This is pretty much it. A very simple Sencha Touch application and an easy way to learn some of the features of the Sencha Touch framework.

I hope you take this app to the next level as you learn more about the framework. :-)

And don’t forget to leave a comment letting me know the Sencha Touch topics about which you would like me to write.

Download the Notes App: Notes-App-v1.0.zip

Here’s the rest of the series:

Want To Learn More?

My Sencha Touch books will teach you how to create an application from scratch.

Comments

Leave a Reply

Your email address will not be published. Required fields are marked *