Dónal
Dónal

Reputation: 187399

Prototype event handler

I've defined the following HTML elements

<span class="toggle-arrow">▼</span>
<span class="toggle-arrow" style="display:none;">▶</span>

When I click on one of the elements the visibility of both should be toggled. I tried the following Prototype code:

$$('.toggle-arrow').each(function(element) {
    element.observe('click', function() {
        $(element).toggle();
    });
});

but it doesn't work. I know everything would be much simpler if I used jQuery, but unfortunately this is not an option:

Upvotes: 1

Views: 129

Answers (3)

kstubs
kstubs

Reputation: 808

Off the cuff:

function toggleArrows(e) {
  e.stop();

  // first discover clicked arow
  var clickedArrow = e.findElement();

// second hide all arrows
  $$('.toggle-arrow').invoke('hide');

// third find arrow that wasn't clicked
  var arw = $$('.toggle-arrow').find(function(a) {
    return a.identify() != clickedArrow.identify();
  });

// fourth complete the toggle
  if(arw)
     arw.show();

}

Wire the toggle arrow function in document loaded event like this

document.on('click','.toggle-arrow', toggleArrows.bindAsEventListener());

That's it, however you would have more success if you took advantage of two css classes of: arrow and arrow-selected. Then you could easily write your selector using these class names to invoke your hide/show "toggle" with something like:

function toggleArrows(e) {
    e.stop();

    $$('.toggle-arrow').invoke('hide');
    var arw = $$('.toggle-arrow').reject(function(r) { 
        r.hasClassName('arrow-selected'); });

    $$('.arrow-selected').invoke('removeClassName', 'arrow-selected');

    arw.show();
    arw.addClassName('arrow-selected');

}

Upvotes: 0

Ian
Ian

Reputation: 50933

Instead of iterating through all arrows in the collection, you can use the invoke method, to bind the event handlers, as well as toggling them. Here's an example:

var arrows = $$('.toggle-arrow');
arrows.invoke("observe", "click", function () {
    arrows.invoke("toggle");
});

DEMO: http://jsfiddle.net/ddMn4/

Upvotes: 4

dontGoPlastic
dontGoPlastic

Reputation: 1782

I realize this is not quite what you're asking for, but consider something like this:

<div class="toggle-arrow-container">
    <span class="toggle-arrow" style="color: pink;">▶</span>
    <span class="toggle-arrow" style="display:none; color: orange;">▶</span>
</div>

document.on('click', '.toggle-arrow-container .toggle-arrow', function(event, el) {
    var buddies = el.up('.toggle-arrow-container').select('.toggle-arrow');
    buddies.invoke('toggle');
});

This will allow you to have multiple "toggle sets" on the page. Check out the fiddle: http://jsfiddle.net/nDppd/

Hope this helps on your Prototype adventure.

Upvotes: 0

Related Questions