tags:

views:

245

answers:

4

I am trying to extend a class and override one of its methods. lets call that class A. My class, class B, is overiding a protected method. Class C extends class A and Class D extends class C. Inside of Class D, the method I am trying to overwrite is also extended here and that calls parent::mymethodimoverriding. That method does not exist in class C so it goes to it in class A. That is the method I am overiding in class B and obviously you can't extend A with B and have those changes show up in D since it does not fall in line with the class hierarchy. I might be wrong, so correct me please.

so if my class b is called and ran then class D gets called it runs the method in A and overwrites what I had set. I am thinking there must be a way to get this to work, I am just missing something.

Here is an example, as you can see in class A there is a call to setTitle and it is set to "Example" In my class I set it to "NewExample". My class is getting called before class D so when class D is called it goes back to the parent and sets the title back to "Example". What I would like to happen is class B runs and sets it to do what I need it to then class D run and instead of it hitting the class I am extending for it to hit my class instead. the thing is I don't think I can make class D extend my class. so now it is hitting the class I am extending

class A{
  protected function _thefunction(){
    setTitle("Example");
  }
}

class B extends A{
  protected function _thefunction(){
    My new code here
    setTitle("NewExample");
  }
}

class C extends A{
  nothing that matters in here for what I am doing
}

class D extends C{
  protected function _thefunction(){
    parent::_thefunction();
    additional code here
  }
}

I tried doing

class D extends C{
  protected function _thefunction(){
    B::_thefunction();
    additional code here
  }
}

and I got errors about it not being a static method

+1  A: 

From what I can understand _thefunction() does something to another object($headBlock?). Your class (B) changes something in that object, then class D goes and changes it back to something else. Only way to fix this is to somehow disable D's intereference or have class B's method run after it.

You could use inheritance by having C inherit B instead of A, although I don't know what side-effects these might have to the structure of your program.

Edit: Seeing as this is Magento we are talking about, maybe you should ask specifically about Magento either in SO or the Magento forums. There's very little you can't override in it; maybe you've taken a wrong turn somewhere in your approach?

Manos Dilaverakis
Yeah you are correct, it is changing it back when it calls the parent method. I am working in the Magento ecommerce framework and its not that easy for me to just change class d to extend b. I tried to disable the interference by having it call myclass::thefunction but of course I got an error saying something about it not being a static method.
dan.codes
Yeah, I could post this in the Magento tag, but I figured it was more of a OOP PHP thing for me then that. I understand you can override anything, I have done a lot of it, but I just got stuck when overiding something that is also overridden by another class. maybe I will rewrite it for there.
dan.codes
+1  A: 

That is the method I am overiding in class B and obviously you can't extend A with B and have those changes show up in D since it does not fall in line with the class hierarchy. I might be wrong, so correct me please.

I'm afraid you're right here. If you don't rework the whole concept there's not much you can do.

I tried to disable the interference by having it call myclass::thefunction but of course I got an error saying something about it not being a static method.

Are you able to modify class D? I don't understand this part. If so, you wouldn't be asking this question in the first place, I presume.

Maybe some specifics about Magento could help? There's probably some other way to achieve the desired outcome.

Karol Piczak
I can modify class D, but when modifying it, I couldn't get it to call my class instead of parent. Am I just missing something stupid?
dan.codes
I don't know the specifics. What do you do in the class A parent function? Do you really need to call it from D? Dirty workaround is to getTitle() before you call the parent function and setTitle() after you do it. But on the concept level it's flawed.
Karol Piczak
+1  A: 

What you are trying to do probably can't be done for at least of two reasons:

  1. Method _thefunction() is protected in B so it is accessible only for B and it's descendants.
  2. You can't call method of object B for object of class D because D is not neither B nor descendant of B.
Kamil Szot
Yeah, I understand all that, I guess I just was looking for what I could do to make it so my stuff doesn't get overridden.
dan.codes
+1  A: 

You are trying to call B::_theFunciton() but the method in B is protected (meaning that all access to that method is reserved for its own class or any subclasses, which D is not, the class hierarchy for D is... A->C->D, no B in there.)

The function is also not static, so you cant reference it like B::blah()

If you really want this then you could define _theFunction as public static, however if you really think that is an object related method then the only good practice way is to be a subclass from it.

Matt
Thanks, that is exactly what I thought, I knew I can't do B::blah() after I tried it because of it not being static. I guess I am a little confused when you say "however if you really think that is an object related method then the only good practice way is to be a subclass from it."
dan.codes