PHP设计模式(八)装饰器模式Decorator实例详解【(5)
以创建一个php脚本使用FormHandler类来产生HTML表单:
<form action=”formpage.php” method=”post”>
<?php
$post =& Post::autoFill();
$form = FormHandler::build($post);
foreach($form as $widget) {
echo $widget->paint(), "<br>\n";
}
?>
<input type=”submit” value=”Submit”>
</form>
现在,你已经拥有了个提交给它自身并且能保持posted数据的表单处理(form handler) 类。
现在。我们继续为表单添加一些验证机制。方法是编辑另一个组件装饰器类来表达一个“invalid”状态并扩展FormHandler类增加一个validate()方法以处理组件示例数组。如果组件非法(“invalid”),我们通过一个“invalid”类将它包装在<span>元素中。
<?php
class Invalid extends WidgetDecorator {
function paint() {
return '<span class="invalid">'.$this->widget->paint().'</span>';
}
}
FormHandler新加方法validate:
/**
* 实现
*
*/
class FormHandler {
function build(&$post) {
return array(
new ConcreteDecoratorLabeled('First Name', new ConcreteComponentTextInput('fname', $post->get('fname')))
,new ConcreteDecoratorLabeled('Last Name', new ConcreteComponentTextInput('lname', $post->get('lname')))
,new ConcreteDecoratorLabeled('Email', new ConcreteComponentTextInput('email', $post->get('email')))
);
}
function validate(&$form, &$post) {
$valid = true;
// first name required
if (!strlen($post->get('fname'))) {
$form[0] =& new Invalid($form[0]);
$valid = false;
}
// last name required
if (!strlen($post->get('lname'))) {
$form[1] =& new Invalid($form[1]);
$valid = false;}
// email has to look real
if (!preg_match('~\w+@(\w+\.)+\w+~'
,$post->get('email'))) {
$form[2] =& new Invalid($form[2]);
$valid = false;
}
return $valid;
}
}
最后结果:
<html>
<head>
<title>Decorator Example</title>
<style type="text/css">
.invalid {color: red; }
.invalid input { background-color: red; color: yellow; }
#myform input { position: absolute; left: 110px; width: 250px; font-weight: bold;}
</style>
</head>
<body>
<form action="<?php echo $_SERVER["PHP_SELF"]; ?>" method="post">
<div id="myform">
<?php
$pos =& Post::autoFill();
$form = FormHandler::build($post);
if ($_POST) { FormHandler::validate($form, $post);
}
foreach($form as $widget) {
echo $widget->paint(), "<br>\n";
}
?>
</div>
<input type="submit" value="Submit">
</form>
</body>
</html>
9. 装饰器模式与其他相关模式
1)Adapter 模式:Decorator模式不同于Adapter模式,因为装饰仅改变对象的职责而
