Шаблон проектирования Decorator позволяет динамически присоединять новые обязанности к объекту. Это гибкая альтернатива наследованию. Она полезно, если вы обнаружите, что добавление функций в проект может быть сложным.
Нам нужно отображать различные типы объектов на странице HTML. Начнем с создания интерфейса, который будет общим для всех этих объектов:
interface DisplayableInterface
{
public function display();
}
Затем мы создаем класс наших отображаемых объектов. Эти классы будут реализовывать интерфейс DisplayableInterface. Например, мы хотим иметь возможность отображать сообщение:
class Message implements DisplayableInterface
{
private $message;
public function __construct(string $message)
{
$this->message = $message;
}
public function display()
{
echo $this->message;
}
}
Теперь, если вы хотите опубликовать сообщение, выполните:
$message = new Message('message');
$message->display();
Теперь представьте, что позже вам нужно добавить функции для отображения сообщения. Например, вам нужно применять стили (жирный, курсив и т. д).
Первым делом будем использовать наследования путем создания класса, в который наследует класс Message.
Но в некоторых случая наследование может быть сложным для создания (слишком много модификаций, слишком много классов для создания и т. д.). Вы также можете динамически добавлять обязанности к объекту. В этих случаях декоратор должен использоваться.
Начнем с создания декоратора, который является абстрактным классом и должен реализовать интерфейс DisplayableInterface:
abstract class MessageDecorator implements DisplayableInterface
{
protected $displayableMessage;
public function __construct(DisplayableInterface $displayTableMessage)
{
$this->displayTableMessage = $displayableMessage;
}
}
Затем мы создаем новые классы ответственности. Эти классы расширяют MessageDecorator. Они реализуют метод display().
Мы начинаем с выделения жирным:
class BoldMessage extends MessageDecorator
{
public function display()
{
echo '<strong>';
$this->displayableMessage->display();
echo '</strong>';
}
}
Затем курсив:
class ItalicMessage extends MessageDecorator
{
public function display()
{
echo '<em>';
$this->displayableMessage->display();
echo '</em>';
}
}
Теперь мы можем протестировать наш код. Благодаря декоратору вы можете добавить функции цепочки. Например, если вы хотите отобразить текст жирным курсивом:
$message = new Message('message');
$messageDecore = new ItalicMessage(new BoldMessage($message));
$messageDecore->display();
Спасибо, за отличную статью!