Reputation: 916
I have a very simple OO class structure and cannot get my head around why the child class is not inheriting the properties and methods from the parent.
This is a basic example of my set up:
//Main class:
class Main{
//construct
public function Main(){
//get data from model
$data = $model->getData();
//Get the view
$view = new View();
//Init view
$view->init( $data );
//Get html
$view->getHTML();
}
}
//Parent View class
class View{
public $data, $img_cache;
public function init( $data ){
$this->data = $data;
$this->img_cache = new ImageCache();
}
public function getHTML(){
//At this point all data is intact (data, img_cache)
$view = new ChildView();
//After getting reference to child class all data is null
//I expected it to return a reference to the child class and be able to
//call the parent methods and properties using this object.
return $view->html();
}
}
//Child View Class
class ChildView{
public function html(){
//I get a fatal error here: calling img_cache on a non-object.
//But it should have inherited this from the parent class surely?
return '<img src="'.$this->img_cache->thumb($this->data['img-src']).'"/>';
}
}
So I expected the child class to inherit the properties and methods from the parent. Then when I get a reference to the child class it should be able to use the img_cache
object. But I get a fatal error here: Call to a member function thumb() on a non-object
.
Where have I gone wrong with this?
Upvotes: 0
Views: 1634
Reputation: 8214
You don't create a subclass by instantiating it. You make it extends
the superclass.
Then you can make an abstract method in an abstract superclass (or make a default implementation if you don't want it to be abstract), and implement it in the subclass that extends
the superclass by declaring a method with the same name.
//Main class:
class Main{
//construct
public function Main(){
//get data from model
$data = $model->getData();
//Get the view
$view = new ChildView(); // <--- changed
//Init view
$view->init( $data );
//Get html
$view->getHTML();
}
}
//Parent View class
abstract class View{ // <--- changed
public $data, $img_cache;
public function init( $data ){
$this->data = $data;
$this->img_cache = new ImageCache();
}
public abstract function getHTML(); // <--- changed
}
//Child View Class
class ChildView extends View{ // <--- changed
public function getHTML(){ // <--- changed
//I get a fatal error here: calling img_cache on a non-object.
//But it should have inherited this from the parent class surely?
return '<img src="'.$this->img_cache->thumb($this->data['img-src']).'"/>';
}
}
In simple words, the child class and the parent class have the same instance. They just contain code from different classes, but they are still the same object. Only the same object can get the same properties.
BTW, use __construct
for constructors (public function __construct
instead of public function Main
. Using the class name as the constructor name is very old-fashioned and is probably going to get deprecated (not sure if it already is).
Upvotes: 0
Reputation: 3080
You need to specify the inheritance with extends the base class http://php.net/manual/en/keyword.extends.php
Try this for your child class
//Child View Class
class ChildView extends View{
public function html(){
//I get a fatal error here: calling img_cache on a non-object.
//But it should have inherited this from the parent class surely?
return '<img src="'.$this->img_cache->thumb($this->data['img-src']).'"/>';
}
}
Also as @ferdynator says, you are instantiating the parent, not the child, so your Main
class also needs to be changed to instantiate ChildView
, not the parent View
//Main class:
class Main{
//construct
public function Main(){
//get data from model
$data = $model->getData();
//Get the view
$view = new ChildView();
//Init view
$view->init( $data );
//Get html
$view->getHTML();
}
}
Upvotes: 6