Setting Up Elements

Written By Sean McArthur, on Thursday, June 10th 2010, 11:16pm

Once you know how much easier it is to get elements all around, you should take the time to learn how MooTools has provided a simple access API around the browser quirks for Elements. And on top of it, we’ve extended this API to things that you don’t normally find on Elements. And as cool as it is, you can easily add your own bits with ease.

Get Who? Set What?

On Elements, theres only 3 getters/setters that you need to worry yourself with: get/set, getStyle/setStyle, and store/retrieve (we’ll ignore getProperty for now).

Get/Set

The most commonly used are Element#get and Element#set. They will first check the Element.Properties object to see if a specific getter/setter exists, before defaulting to getProperty or setProperty. So for instance, you can get the href of a link, or you can get the text of an element, which will get the node value in a cross browser fashion.

<a id="myAnchor" href="/blog">Blog</a>
<div>All my <span>text</span></div>

$('myAnchor').get('href'); // '/blog'
$('myDiv').get('text'); // 'All my text'

You can do as you would expect with the setters in the same way.

$('myAnchor').set('title', 'MooTools Blog'); //sets title attribute
$('myDiv').set('text', 'other text'); //sets the innerHTML

For now, let’s just look at the other methods, and we’ll take a look at how this works later so you can add to it yourself.

Setting with Style

The other commonly used pair of methods are Element#getStyle and Element#setStyle. These should hopefully be self explanatory. Their benefit is that they normalize certain styles the browsers are inconsistent about, such as opacity.

Elemental Properties

Let’s take a look at an example that MooTools itself defines. The style property is easier to remember and read than using cssText, so that’s what MooTools does for us.

Element.Properties.style = {

    set: function(style){
        this.style.cssText = style;
    },

    get: function(){
        return this.style.cssText;
    }

};

Seeing how the style object is setup, you can easily create your own. Given a Person class, and the given HTML, we could decide it would beneficial to be able to get the instance of a Person from an element.

<div class="person person_3">
    Sean
</div>
<p>Hello</p>

Say we were to want to get a Person instance when we have this element. We would define the property on Element.Properties.

Element.Properties.person = {

    get: function() {
        var id = this.className.match(/person_(\d+)/)[1];
        if(id) return Person.getById(id);
    },

    set: function(person) {
        this
            .addClass('person')
            .addClass('person_'+person.id)
            .set('html', person.name);
    }
};

Now we can use our familiar get and set methods.

$('TestPerson').get('person'); // returns Person instance of ID 3.
$('OtherTest').set('person', new Person('John')); //turns the paragraph into a person
// <p class="person person_4">John</p>

Let’s just Store that

The third pair of methods that MooTools defines for elements is Element#store and Element#retrieve. Woah woah woah. What? You’re telling me you can get properties, and you can retrieve them? What the heck guys?

Don’t worry, it’s pretty easy to know and understand the difference once I explain it. get and set are the most common methods, and default to element attributes, like I said. In many other places, such as when you use el.get('tween'), the MooTools teams made the getter call retrieve for you. You’ve been accessing it, without knowing it.

OK, great Sean. Why should I care how you give me the values?

I hear you. You see, most of the getters/setters are used to access attributes. But what happens you want to get at or set some other kind of property. What if you want to set an actual object, or a function to the Element. I guess you could JSON encode and create a custom attribute, but that’s not good practice. And you lose out on any class info of the object, in case it was an instance of something.

These methods also help with an issue that arises when you try to store something like an Event object or an instance of something else that refers to the Element in question. Certain browsers don’t handle the circular references that well if you were to set el.prop = { someEl: el }. It can leave nasty memory leaks.

If you really want to know, behind the scenes, MooTools keeps a storage object that is totally separate from any element. Every element created gets assigned a unique id, and that id is used as a key on the storage object.

Regardless, you don’t have to do anything special for store/retrieve to work. Using our above example, it would work like so:

$('TestPerson').store('person', new Person('Sean'));
$('TestPerson').retrieve('person'); //returns the exact same Person instance

These two common pairs of methods actually have a third method that relates to each of them, which allows the destruction of each respective data location. These methods are Element#erase and Element#eliminate.

Apply this yourself

This all sounds great, I’m sure. Now when you’re writing your own classes and plugins, you can be sure to use the pre-packaged properties. However, it’s much more powerful when you can find a useful property to add that relates to your own plugins.

Sean McArthur is a software developer at Blazonco.com who is madly in love with MooTools. Most of his contributions involve sharing tips and information about MooTools (and programming in general) at his blog and on Twitter.

4 Responses to “Setting Up Elements”

  1. con says:

    Thanks for this great article! I use a lot of direct referencing with elements the way you describe as bad practice: el.prop = { someEl: el } instead of el.store(..) (mostly because of lazyness :) it’s quicker to write ;) - Is there a way to find (possible) memory leaks easily? I suggest they also depend on different browsers and how good their garbage collection is working?

  2. Timothy says:

    Pretty cool. Going to try these out soon.

  3. Sean McArthur says:

    @con: I don’t know of much that will help you to find memory leaks other than to leave the browser open for a while and watch if it’s memory usages has steadily gained in the Task Manager.

    The main culprit is, of course, Internet Explorer. The memory leak is explained well here and here. They touch on the issue IE has with garbage collecting objects with circular references.

  4. con says:

    Thanks Sean, this looks very useful.