`

Zend Framework 1.10.1 理解和使用 Zend 表单装饰器之三:装饰器分层

 
阅读更多

如果你在紧随上一节的内容,你可能会注意到一个装饰器的 render() 方法接受一个单独的参数,$content。它预期为一个字符串。render() 然后接受这个字符串,并决定是要替换它,附加在它后面,或者前置它前面。这允许你拥有一个装饰器的链条——它允许你创建只呈现元素的元数据的一个子集的装饰器,然后把这些装饰器分层来为这个元素建造全部的标记。

让我们看一下在实践中它是如何工作的。

对于大部分的表单元素类型来说,以下的装饰器被使用:

  • ViewHelper(使用一个标准表单视图帮助器来呈现表单 input)。
  • Errors(通过一个无序列表呈现验证错误)。
  • Description(呈现附加在元素上任何描述;通常用于提示 tooltips)。
  • HtmlTag(用一个 <dd> 标签包括以上的全部)
  • Label(呈现放置在以上内容之前的标签 label,用一个 <dt> 标记包围。

你将会注意到每个这些装饰器做一件事情,对存储在表单元素里的一个元数据的片断进行操作:Erros 装饰器扒下验证错误并呈现它;Label 装饰器只扒下 label 标签并呈现它。这使得独立的装饰器十分清晰,可重复,而且,更重要的,可测试。

同时,$content 参数进入什么地方扮演角色:每一个装饰器的 render() 方法被设计成接受内容,然后替换它(通常是通过包围它的方法来达到这个目的),前置在它,或者附加到它的后面。

所以,最好把装饰的过程看作从内而外创建一个洋葱。

为了简化这个过程,我们会看一下上一节提到的例子,想到:

让我们现在去掉 label 的功能,为它建立一个分离的装饰器。

现在,这可能看起来很棒,但这有一个问题:到目前为止,最后的装饰器率先冲过了终点,然后覆盖了一切。取决于你最后注册的,你最后将只得到 input,或者只是 label。

为了克服这点,简单的把传递给 $content 的内容和标记合并:

当你想从编程角度上选择原来的内容是应该前置还是附加到新的标记(markup)的时候,上面的方法就会有问题了。幸运的是,为此已经有了一个标准的机制;Zend_Form_Decorator_Abstract 有一个为与之匹配的进行替换并且定义一些常量的概念。另外,它允许在它们两个之间指定一个分割符。让我们使用这些:

注意上面我为每一个转换默认的例子,这将假设 labels 放置在内容前面,input 附加到内容后面。

现在,让我们用这些创建一个表单元素:

这个将会如何工作?当我们调用 render(),元素将迭代大量附在它身上的装饰器,对每一个装饰器都调用 render()。它会传递一个空的字符串给最开始的那个,然后创建的任何内容将会被传递给下一个,以此类推:

初始化的内容是一个空的字符串:''。 ''被传递给 SimpleInput 装饰器,然后它会产生一个表单的 input,附加到空的字符串上:<input id="bar-foo" name="bar[foo]" type="text" value="test" />。 input 然后会当作内容传递给 SimpleLabel 装饰器,产生一个 label,并且前置在原始内容的前面;默认的分割符是一个 PHP_EOL 字符,会给我们以下:<label for="bar-foo"> /n<input id="bar-foo" name="bar[foo]" type="text" value="test" />。

但是请等一下!如果出于某种原因,你想 label 出现在 input 的后面怎么办?还记得 placement 标记吗?你可把它作为一个选项传递给装饰器。最简单的方法是,在元素创建过程中,把一个选项数组连同装饰器传递给它:

注意在传递选项的时候,你必须把装饰器包裹在一个数组内;这会提示给构造函数,有可选项。装饰器的名字是那个数组的第一个元素,选项以一个数组传递给那个数组的第二个元素。

上面的结果以标记输出是 <input id="bar-foo" name="bar[foo]" type="text" value="test" />/n<label for="bar-foo">。

使用这个技巧,你可以获得以特定元素或表单的元数据为目标的装饰器,以及创建只和那个元数据相关的标记(markup)。我们的洋葱就是结果。

这种方法有利有弊。首先,不好的方面:

应用更复杂。你不得不更注意你使用的装饰器和为了按照正确的顺序来创建标记(markup)你要如何布置。 资源更集中。更多的装饰器意味着更多的对象;被在一个表单内的元素的数量相乘成倍增加,最后你可能会严重使用资源。缓存在这有用。

但是优点是令人信服的:

可重用的装饰器。通过这个技巧你真的可以创建可重用的装饰器,因为你不必担心复杂的标记(markup),只是标记一个元素或者表单元数据或是它们的一些片断。 极大的扩展性。理论上你可以通过很小数量的装饰器产生你希望的任何标记组合。

以上的例子是 Zend_Form 内置的装饰器的目标用法,但是你经常还是很难理解,装饰器如何互动来创建最后的标记(markup)。出于这个原因,1.7以后的版本,增加了一些扩展功能,来使呈现独立的装饰器变得有可能——这将和 Rails 类似的简单的呈现表单。在下一节我们会看到它。

分享到:
评论

相关推荐

    libzip-1.10.1.tar.gz

    libzip的源代码和文档都是开放的,开发者可以通过阅读源码和官方文档深入理解其内部机制,以便更好地利用这个库。 总的来说,libzip库在1.10.1版本中不仅保持了原有的强大功能,还进一步优化了安全性、性能和易用性...

    svn 1.10.1

    汉化使得中国用户能够更容易地理解和操作SVN,避免了语言障碍,提高了使用体验。 "汉化包"是实现软件汉化的一组文件,通常由社区成员或者开发者提供,将原本的英文界面转换为中文。汉化包的使用可以极大地降低非...

    synergy1.10.1.rar

    标题中的"synergy1.10.1.rar"是一个压缩包文件,其版本号为1.10.1,通常这种格式的文件是使用RAR压缩算法打包的,它可能包含了软件安装所需的所有文件。RAR是一种常见的文件压缩格式,由WinRAR软件创建,允许用户将...

    hdf5-1.10.1.tar.gz

    HDF5(Hierarchical Data Format 5)是一种用于存储和管理大量复杂数据的开源文件格式。...对于开发者来说,理解和掌握HDF5的使用可以极大地提高数据处理和分析的效率,特别是在处理大规模科学数据或深度学习模型时。

    parquet-column-1.10.1-API文档-中文版.zip

    赠送jar包:parquet-column-1.10.1.jar; 赠送原API文档:parquet-column-1.10.1-javadoc.jar; 赠送源代码:parquet-column-1.10.1-...人性化翻译,文档中的代码和结构保持不变,注释和说明精准翻译,请放心使用。

    heritrix-1.10.1

    2. **解析器**:Heritrix支持多种解析引擎,如HTML解析器和XML解析器,用于提取和理解网页内容。解析器可以识别出链接,以便进一步抓取,也可以处理JavaScript和其他动态内容。 3. **存储器**:抓取到的数据会被...

    jquery-ui-1.10.1.custom.zip

    《jQuery UI 1.10.1 自定义版本详解》 jQuery UI 是一个基于 jQuery JavaScript 库的可扩展用户界面库。...通过理解其核心特性、组件和自定义方法,开发者可以更好地利用这一库来提升项目的用户体验。

    PyVISA-1.10.1_pyvisa_pyvisaSCPI_Pyvisa1.10.1_

    标题"PyVISA-1.10.1_pyvisa_pyvisaSCPI_Pyvisa1.10.1_"暗示了我们讨论的是PyVISA的1.10.1版本,同时提到了与`pyvisa`和`pyvisaSCPI`相关的元素。`pyvisa`是PyVISA的核心库,而`pyvisaSCPI`则是针对基于SCPI...

    parquet-hadoop-1.10.1-API文档-中文版.zip

    赠送jar包:parquet-hadoop-1.10.1.jar 赠送原API文档:parquet-hadoop-1.10.1-javadoc.jar 赠送源代码:parquet-hadoop-1.10.1-...人性化翻译,文档中的代码和结构保持不变,注释和说明精准翻译,请放心使用。

    jquery-1.10.1中文汉化二版

    jQuery 1.10.1是该库的一个重要版本,虽然现在已经有更新的版本,但1.10.1仍然在很多项目中被广泛使用,它的稳定性和兼容性得到了充分验证。 1. **基本用法**: jQuery的使用通常始于一个熟悉的$(document).ready...

    numpy-1.10.1.zip

    Numpy是Python编程语言中的一个核心库,专用于科学计算,尤其在处理多维数据时。这个"numpy-1.10.1.zip"文件是一个包含Numpy 1.10.1版本源代码的...正确安装和理解Numpy的特性是提升Python编程效率的关键步骤之一。

    libpcap-1.10.1.tar.gz

    **libpcap 源码安装详解** libpcap 是一个强大的开源库,主要用于网络数据包...通过理解其工作原理和API,开发者可以创建各种自定义的网络监控解决方案。正确安装和使用libpcap,有助于提升网络运维的效率和安全性。

    绿色vscode-1.10.1

    VSCode 1.10.1绿色版让用户能够在不干扰现有系统设置的情况下运行和使用这个编辑器,这对于共享电脑或在受限环境下的开发者尤其方便。 **核心特性** 1. **多语言支持**:VSCode内置了对JavaScript、TypeScript、...

    apache-ant-1.10.1

    这个"apache-ant-1.10.1"压缩包包含的是Ant的1.10.1版本,它是对早期版本的更新,提供了一系列改进和新特性。 Ant的核心是一个基于XML的任务驱动系统,它通过XML文件(通常称为build.xml)来定义构建过程。这个XML...

    SVN1.10.1安装包及汉化包

    SVN(Subversion)是一种广泛使用的版本控制系统,用于管理软件项目的源代码和其他文件。它允许开发者在团队中协作,跟踪每一次更改,同时提供回溯和恢复功能。SVN1.10.1是Subversion的一个特定版本,包含了若干增强...

    jquery-ui-1.10.1

    《jQuery UI 1.10.1:构建交互式网页的强大工具》 jQuery UI 是一个基于 jQuery JavaScript 库的开源项目,它提供了丰富的用户界面组件和交互效果,为开发者提供了构建功能丰富的、交互性强的网页应用的强大支持。...

    Tensorflow-1.10.1-源码

    Tensorflow-1.10.1-源码 Tensorflow-1.10.1-源码 Tensorflow-1.10.1-源码 Tensorflow-1.10.1-源码 Tensorflow-1.10.1-源码 Tensorflow-1.10.1-源码 Tensorflow-1.10.1-源码 Tensorflow-1.10.1-源码 Tensorflow-...

    flink-1.10.1-bin-scala_2.12.tgz

    《Apache Flink 1.10.1:流处理与批处理框架的深入解析》 Apache Flink 是一个开源的流处理和批处理框架,它以其高性能、低延迟以及对实时数据流处理的强大支持而备受关注。Flink 1.10.1 版本的发布,进一步提升了...

    poco-1.10.1-all-src-dll.zip

    而“poco-1.10.1-all-build”则可能包含了预编译的库文件和构建系统,方便用户快速在特定平台上集成和使用Poco。通常,这样的构建目录会包括不同平台和配置的编译结果,如动态库、静态库、头文件等。对于那些不打算...

Global site tag (gtag.js) - Google Analytics