Hi Perrin,

nice idea, however, calling the parent of show in the extended show
fires the event too early (it fires 'show' before the mask tween is
completed).
http://mootools.net/shell/JfhBn/2/

but how about this one:
http://mootools.net/shell/JfhBn/3/

kept the 'hide' as you had it, because we can fade out first, then run
the orignal hide which in turn calls hideMask.
added a new showMask that calls the parent one after the fade in (and
after the original show is called)


On Jan 7, 11:07 pm, Perrin Perrin <[email protected]> wrote:
> Hey Rolf, I modified your example to work without having to do any renaming,
> and still keep all of the logic in the
> See the 'hide' method.
>
> http://mootools.net/shell/JfhBn/1/
>
> --Perrin
>
>
>
> On Thu, Jan 7, 2010 at 3:16 PM, Rolf -nl <[email protected]> wrote:
> > In-depth answer!
> > You lost me at first with the explanation how the classes work etc,
> > but after reading it two times and the combination with my "problem" I
> > think it's clear :)
> > I understand anyway why this.parent doesn't exists anymore.
>
> > The renaming of the parent method in the Init method of a class is a
> > quick way to get around it, indeed it feels hacky.. I will not use it
> > (also, because you say it's hacky, if I came up with the idea I might
> > have thought it was a smart hack, hehehe).
>
> > I will probably just copy the parent's method, leave 80% of it like it
> > is and add what I need. Done.
>
> > Thanks!
>
> > On Jan 5, 10:37 pm, Aaron Newton <[email protected]> wrote:
> > > You are delving into the depths of how Class works, so this is going to
> > get
> > > a little complicated.
>
> > > All methods of classes are wrapped in a function that then calls the
> > > function in question. So if you pass an object to Class that has a
> > > *foo* method,
> > > Class returns a constructor that when invoked returns an object that has
> > a *
> > > foo* method that calls the original one.
>
> > > var fooBase = {
> > >   foo: function(){ alert('foo'); }};
>
> > > var Foo = new Class(fooBase);
> > > var myFoo = new Foo();
> > > myFoo.foo(); //alerts "foo"
>
> > > When we call the *foo* method on our instance, we're really calling the
> > > wrapper that the Class constructor put around the *foo* method on our
> > > fooBase object. This wrapper therefore knows when *foo* is being called,
> > and
> > > before it calls the original *foo* it defines *this.parent*. It doesn't
> > look
> > > like this, but here's a very simple illustration:
>
> > > instanceOfFoo.foo = function(){
> > >   this.someVar = 'blah';
> > >   this.originalFooMethod();
> > >   delete this.someVar;
>
> > > };
>
> > > So only while our original method is being run is *this.parent* defined
> > (and
> > > only if there is a parent method on the prototype).
>
> > > If you think about it, that's the only way this could work, because *
> > > this.parent *has to point at different things depending on which method
> > is
> > > calling it. *this* is our instance, and the *parent* property of our
> > > instance changes depending on the method. Removing it after a method is
> > > called is the only way to allow the next method to call it.
>
> > > So, let's look at your code:
>
> > >   showMask: function() {
> > >     var fn = function() {
> > >       this.parent();
> > >     }.bind(this);
> > >     this.element.tween('opacity',
> > this.options.opacity).get('tween').chain(
> > > fn);
> > >   },
>
> > > Your method calls *element.tween*, which starts an effect. After the
> > effect
> > > it calls your function, which references *this.parent*. But this
> > > asynchronous method call is going to occur *after* the *showMask* method
> > > exits, which means that *this.parent *has been deleted, right?
>
> > > So, how do you extend a class and add this kind of effect? The only
> > > mechanism to do this is to rename the original methods:
>
> > > var Foo.Extended = new Class({
> > >   Extends: Foo,
> > >   initialize: function(){
> > >     this._foo = this.foo;
> > >     this.foo = this._newFoo;
> > >   },
> > >   _newFoo: function(){
> > >    (function(){
> > >      this.parent();
> > >    }).delay(1000, this);
> > >   }});
>
> > > var myFoo = new Foo.Extended();
> > > myFoo.foo(); //waits 1 second, alert's "foo"
>
> > > This is hacky and in general a bad practice.
>
> > > If you look at the showMask method in Spinner, which completely
> > overwrites
> > > the method from Mask (it does not call this.parent), you can see how it
> > does
> > > this fading in. Note that I *could* have done this method renaming from
> > the
> > > example above, but that method renaming is more brittle than I prefer.
> > I've
> > > only used the technique on a very few occasions.
>
> > > On Tue, Jan 5, 2010 at 11:55 AM, Rolf -nl <[email protected]>
> > wrote:
> > > > I've extended more's Mask so I can apply an opacity tween effect to
> > > > the mask... (and still have all the benefits of Mask, else I could use
> > > > DWalsh's Overlay...)
>
> > > > Earlier I tried a simple way to extend Mask, just changing the
> > > > showMask and hideMask methods:
> > > >http://mootools.net/shell/A65x7/
>
> > > > But then I get the error: The method "parent" cannot be called.
> > > > Q1. Why can't I call the this.parent() methods showMask and hideMask?
>
> > > > Then I extended it in another way (needed to use it, so, went for the
> > > > easy way out):
> > > >http://mootools.net/shell/PMpZM/
>
> > > > In the original Mask show (and hide) methods it says:
> > > > this.showMask.apply(this, arguments);
>
> > > > Q2: When are these methods (show/hide) getting any arguments?

Reply via email to