I have huge project and in some point of extending it I want to do something $this
in subclass Y
(which inherits from X
) pointing to X
when method from Y
called from X
:) I can't interfere to much in class structure and I want to do it NICELY without any "helpers", additional constructor parameters with "controller path" or something like that.
So the problem is: when I instantiate ControllerGallery
it calls constructor which calls parent contructor (from ControllerResource
which is parent of ControllerGallery
). But in parent constructor (ControllerResource
), variable $this
is pointing to ControllerGallery
, not ControllerResource
.
I know that when I instantiate class, there is only one object which is created (only "ControllerGallery
", not: "ControllerGallery
and it's parent ControllerResource
"), and that's the problem. My question is: how to achieve the result which is shown below? Any suggestions?
<?php
abstract class Controller {
function getParentController()
{
return null;
}
function getController(){
return $this;
}
}
class ControllerResource extends Controller
{
protected $CONTROLLER_PATH = 'Resource';
protected $scripts;
function __construct(){
$this->addScript($this->CONTROLLER_PATH.DIRECTORY_SEPARATOR.'general_resource_support_script.js');
}
function addScript($name){
$this->scripts[] = $name;
}
function getParentController()
{
return parent::getController();
}
function getScriptPaths(){
return $this->scripts;
}
}
class ControllerProduct extends ControllerResource
{
protected $CONTROLLER_PATH = 'Product';
function __construct(){
parent::__construct();
$this->addScript($this->CONTROLLER_PATH.DIRECTORY_SEPARATOR.'product_support_scripts.js');
}
}
class ControllerGallery extends ControllerResource
{
protected $CONTROLLER_PATH = 'Gallery';
function __construct(){
parent::__construct();
$this->addScript($this->CONTROLLER_PATH.DIRECTORY_SEPARATOR.'gallery_scripts.js');
}
}
$controllerProduct = new ControllerProduct();
$controllerGallery = new ControllerGallery();
echo('<pre>');
print_r($controllerProduct->getScriptPaths());
print_r($controllerGallery->getScriptPaths());
echo('</pre>');
echo('
<pre>
<b>SHOULD BE:</b>
Array
(
[0] => <b>Resource</b>\general_resource_support_script.js
[1] => Product\product_support_scripts.js
)
Array
(
[0] => <b>Resource</b>\general_resource_support_script.js
[1] => Gallery\gallery_scripts.js
)
</pre>
');
?>
And we get the result:
Array
(
[0] => Product\general_resource_support_script.js
[1] => Product\product_support_scripts.js
)
Array
(
[0] => Gallery\general_resource_support_script.js
[1] => Gallery\gallery_scripts.js
)
But it should be:
Array
(
[0] => Resource\general_resource_support_script.js
[1] => Product\product_support_scripts.js
)
Array
(
[0] => Resource\general_resource_support_script.js
[1] => Gallery\gallery_scripts.js
)
protected $CONTROLLER_PATH
is declared in both, ControllerResource
and ControllerProduct
classes. In PHP you can redeclare public and protected method, but since ControllerProduct extends ControllerResource
value of that variable will be the value in derived class. If you change the visibility of $CONTROLLER_PATH
property to private it will belong to that class only and will not be overridden.