ViewRendererIntroducción El ayudante ViewRenderer está diseñado para
satisfacer los siguientes objetivos: Eliminar la necesidad de instanciar objetos de vista
dentro de los controladores; los objetos de vista quedarán
registrados automáticamente con el contralor.Establece automáticamente el script de vista, el ayudante,
y los paths de los filtros basados en el módulo actual.
Asocia automáticamente el nombre del módulo actual como un
prefijo de clase para las clases ayudante y filtro. Crea un objeto de vista, disponible globalmente para todos
los controladores y acciones despachados.Permite al desarrollador establecer por defecto las
opciones de renderizado para todos los controladores.
Agrega la capacidad para renderizar automáticamente los
scripts de vista sin ninguna intervención.Permite al desarrollador crear sus propias
especificaciones para el path base de vistas y para el path
de los scripts de vista. Si realiza un _forward() ,
redirecciona, o render() manualmente,
el autorendering no se llevará a cabo, como está realizando
cualquiera de estas acciones le está diciendo al
ViewRenderer que usted está
determinando su propia salida. El ViewRenderer está habilitado por
defecto. Puede desactivarlo vía parámetro del front controller
noViewRenderer
($front->setParam('noViewRenderer',true))
o eliminando al ayudante del stack de ayudantes (
Zend_Controller_Action_HelperBroker::removeHelper('viewRenderer')
). Si desea modificar los settings del
ViewRenderer antes de despachar el
front controller, puede hacerlo en una de las dos maneras: Instanciar y registrar su propio objeto
ViewRenderer y pasarlo al
ayudante: setView($view)
->setViewSuffix('php');
Zend_Controller_Action_HelperBroker::addHelper($viewRenderer);
]]> Inicializar y/o recuperar un objeto
ViewRenderer por demanda via el
ayudante: setView($view)
->setViewSuffix('php');
]]>API En su uso más básico, simplemente instancie a
ViewRenderer y páselo al ayudante de
acciones. La forma más fácil para instanciar y registrar de una sola
vez es utilizando el método del ayudante
getStaticHelper() : La primera vez que se instancia un controlador de acción, se
disparará ViewRenderer para instanciar al
objeto vista. Cada vez que el controlador es instanciado, se llama
al método init() de
ViewRenderer , que lo llevará a establecer
la propiedad del controlador de acción, y llama a
addScriptPath() con un path relativo al
módulo actual; este será llamado con un prefijo de clase nombrada
después del módulo actual, haciendo efectivamente el namespacing de
todas las clases de ayudantes y filtros que define para el módulo. Cad vez que llama a postDispatch() ,
este llamará a render() para la acción
actual. Como ejemplo, considere la siguiente clase:view->foo = 'bar';
}
}
...
// en uno de sus scripts de vista:
$this->foo(); // llama a Foo_View_Helper_Foo::foo()
]]> El ViewRenderer también define una serie de
accededores para permitir establecer y recuperar opciones de vista: setView($view) le permite
establecer el objeto vista para
ViewRenderer . Se vuelve como una
propiedad de clase pública $view .
setNeverRender($flag = true) puede
ser utilizado para activar o desactivar globalmente el
autorendering, es decir, para todos los controladores. Si es
verdadero, postDispatch() no
llamará automáticamente a render()
en el controlador actual.
getNeverRender() recupera el
valor actual. setNoRender($flag = true) puede ser
utilizado para activar o desactivar el autorendering. Si es
verdadero, postDispatch() no
llamará automáticamente a render()
en el controlador actual. Este ajuste se reseteará cada vez
que se llame a preDispatch() (es
decir, usted necesita establecer este flag para cada
controlador para el cual no quiera que el autorenderering se
ejecute). getNoRender() recupera el
valor actual. setNoController($flag = true) pude
ser usado para decirle a render()
que no busque el script de acción en un subdirectorio
nombrado después de que el controlador (que es el
comportamiento por defecto)
getNoController() recupere el
valor actual. setNeverController($flag = true) es
análogo a setNoController() , pero
trabaja a un nivel global -- es decir, que no se reseteará
por cada acción ejecutada.
getNeverController() recupera
el valor actual. setScriptAction($name) puede ser
utilizado para especificar el script de acción a renderizar.
$name debe ser el nombre del script
menos el sufijo del archivo (y sin el subdirectorio del
controlador, a menos que noController
se haya activado). Si no se ha especificado, busca un script
de vista nombrado después de la acción en el objeto
solicitud. getScriptAction()
recupera el valor actual. setResponseSegment($name) puede ser
utilizado para especificar qué segmento del objeto respuesta
nombrado renderizar. Si no se especifica, se hace en el
segmento por defecto.
getResponseSegment() recupera
el valor actual. initView($path, $prefix, $options)
puede ser llamado para especificar el path base de las
vistas, prefijos de clase para scripts de ayudantes y
filtros, y las opciones de ViewRenderer
. Puede pasar cualquiera de los siguientes flags:
neverRender ,
noRender ,
noController ,
scriptAction , y
responseSegment . setRender($action = null, $name = null,
$noController = false) le permite
establecer cualquier scriptAction ,
responseSegment , y
noController en un pase.
direct() es un alias a este
método, permitiéndole llamar a este método fácilmente dede
su controlador: _helper->viewRenderer('foo');
// render form.phtml al segmento de respuesta de 'html', sin usar un
// subdirectorio de scripts de controladores de acción:
$this->_helper->viewRenderer('form', 'html', true);
]]>setRender() y
direct() realmente no
renderiza el script de vista, sino que establece
indicaciones que postDispatch()
y render() utlizarán para
renderizar la vista. El constructor le permite opcionalmente pasar el objeto vista y
las opciones de ViewRenderer ; acepta los
mismos flags que initView() : 'UTF-8'));
$options = array('noController' => true, 'neverRender' => true);
$viewRenderer =
new Zend_Controller_Action_Helper_ViewRenderer($view, $options);
]]>Hay varios métodos adicionales para personalizar especificaciones
del path, usados para determinar el path base del script de vista
para añadir al objeto vista, y el path del script de vista a usar
cuando esté autodeterminando el script de vista a renderizar. Cada
uno de estos métodos toma uno o más de los siguientes
localizadores::moduleDir hace referencia a la actual
directorio base del módulo(por convención, el directorio
padre del directorio del módulo controlador). :module hace referencia al nombre del
módulo actual. :controller hace referencia al nombre
del controlador actual. :action hace referencia al nombre de la
acción actual. :suffix hace referencia al sufijo del
script de vista (que puede ser definido via
setViewSuffix() ). Los métodos para controlar las especificaciones del path
son:setViewBasePathSpec($spec) le
permite cambiar la especificación del path utilizada para
determinar el path base para añadir al objeto vista. La
especificación por defecto es
:moduleDir/views . Puede recuperar
la especificación actual en cualquier momento usando
getViewBasePathSpec() . setViewScriptPathSpec($spec) le
permite cambiar el path de la especificación utilizada para
determinar el path a un script de vista individual (menos el
path de la base del script de vista). La especificación por
defecto es :controller/:action.:suffix
. Puede recuperar la especificación actual en cualquier
momento usando
getViewScriptPathSpec() .
setViewScriptPathNoControllerSpec($spec)
le permite cambiar el path de la especificación utilizado
para determinar el path a un script de vista individual
cuando noController está activado
(menos el path base del script de vista). La especificación
por defecto es :action.:suffix . Puede
recuperar la especificación actual en cualquier momento
usando
getViewScriptPathNoControllerSpec()
. Para un control más refinado sobre el path de especificaciones,
puede usar Zend_Filter_Inflector . Bajo el capó,
ViewRenderer ya usa un inflector para
realizar mapeos del path. Para interactuar con el inflector -- ya
sea para establecerlo para uso propio, o para modificar el inflector
por defecto, se pueden utilizar los siguientes métodos: getInflector() recupera el
inflector. Si no existe todavía en
ViewRenderer , se crea uno
utilizando las reglas predeterminadas. Por defecto, utiliza reglas de referencias estáticas para
el sufijo y directorio de módulos, así como una meta
estática; esto permite que diversas propiedades de
ViewRenderer tengan la capacidad de
modificar dinámicamente al inflector. setInflector($inflector,
$reference) permite establecer un inflector
personalizado para usar con
ViewRenderer . Si
$reference es verdadero, establecerá
el sufijo y directorio de módulos como referencias estáticas
a las propiedades de ViewRenderer , así
como al objetivo. Convenciones por Defecto para Lookup El ViewRenderer hace algún tipo de
normalización del path para facilitar la búsqueda de los scripts
de vista. Las reglas predeterminadas son los siguientes: :module : MixedCase y
camelCasedWords están separados por guiones, y el string
completo se convierte a minúsculas. Por ejemplo:
"FooBarBaz" pasa a ser "foo-bar-baz". Internamente, el inflector utiliza los filtros
Zend_Filter_Word_CamelCaseToDash
y Zend_Filter_StringToLower .
:controller : MixedCase y
camelCasedWords están separados por guiones; los
subrayados se convierten en separadores de directorio ,
y el string emitido a minúsculas. Ejemplos: "
FooBar " pasa a ser
"foo-bar"; " FooBar_Admin " pasa
a ser " foo-bar/admin ". Internamente, el inflector utiliza los filtros
Zend_Filter_Word_CamelCaseToDash
,
Zend_Filter_Word_UnderscoreToSeparator
, y Zend_Filter_StringToLower .
:action : MixedCase y
camelCasedWords están separados por guiones; los
caracteres no alfanuméricos son traducidos a guiones, y
el string emitido a minúsculas. Ejemplos: "fooBar" pasa
a ser "foo-bar"; "foo-barBaz" pasa a ser "foo-bar-baz". Internamente, el inflector utiliza los filtros
Zend_Filter_Word_CamelCaseToDash
, Zend_Filter_PregReplace , y
Zend_Filter_StringToLower .
Los últimos temas en la API de
ViewRenderer son los métodos para
determinar realmente los paths de los scripts de vista y el
rendering de las vistas. Estos incluyen: renderScript($script, $name)
permite renderizar un script con una ruta que especifique,
opcionalmente a un segmento nombrado del path. Cuando se
utiliza este método, ViewRenderer no
autodetermina el nombre del script, en cambio pasa
directamente a $script el argumento
directamente al método del objeto vista
render() . Una vez que la vista ha sido renderizada al objeto
respuesta, se establece noRender
para evitar accidentalmente renderizar el mismo script
de vista varias veces. Por defecto,
Zend_Controller_Action::renderScript()
le delega a ViewRenderer el método
renderScript() . getViewScript($action, $vars) crea
el path a un script de vista basado en la acción pasada y/o
cualquier variables pasadas en $vars .
Las claves para este array pueden incluir cualquiera de las
claves de especificación de paths ('moduleDir', 'module',
'controller', 'action', y 'suffix'). Se utilizarán
cualquiera de la variables pasadas; de lo contrario, se
utilizarán valores basados en la petición actual. getViewScript() utilizará tanto a
viewScriptPathSpec o
viewScriptPathNoControllerSpec
sobre la base establecida del flag
noController . Los delimitadores de palabras encontrados en un módulo,
controlador o nombres de acción serán reemplazados por
guiones ('-'). Así pues, si tiene el nombre de controlador '
foo.bar ' y la acción '
baz:bat ', utilizando la
especificación por defecto del path se traducirá en un path
al script de vista '
foo-bar/baz-bat.phtml '. Por defecto,
Zend_Controller_Action::getViewScript()
delega el método
getViewScript() de
ViewRenderer . render($action, $name,
$noController) comprueba primero para ver
si bien $name o
$noController se han pasado, y si es
así, establece los flags apropiados (responseSegment y
noController, respectivamente) en
ViewRenderer . A continuación, pasa
el argumento $action , si hay alguno, a
getViewScript() . Por último,
pasa el path calculado del script de vista a
renderScript() . Hay que ser conscientes de los efectos secundarios al
usar render() : los valores que
usted pasa para el nombre del segmento respuesta y para
el flag noController persistirán en el objeto. Además,
noRender será establecido después de completar la
renderización. Por defecto,
Zend_Controller_Action::render()
delega a ViewRenderer el método
render() . renderBySpec($action, $vars, $name)
permite pasar variables de especificación del path a fin de
determinar el path para la creación del script de vista.
Este pasa $action y
$vars a
getScriptPath() , y luego pasa
el path del script resultante y $name a
renderScript() . Ejemplos Uso BásicoUso Básico En lo más básico, usted simplemente inicializa y registra el
ayudante ViewRenderer con el ayudante
broker en su bootstrap, y luego establecer las variables en sus
métodos de acción. view->foo = 'bar';
}
// No hace rendering, ya que salta a otra acción; la nueva acción
// realizará cualquier rendering
public function bazAction()
{
$this->_forward('index');
}
// No hace rendering, ya que redirecciona a otra ubicación
public function batAction()
{
$this->_redirect('/index');
}
}
]]>Convenciones de Nombres: Delimitadores de Palabras en
Controladores y Nombres de Acción Si su controlador o nombre de acción está compuesto por
varias palabras, el despachador exige que estos sean separados
de la URL por un path específico y caracteres
delimitadores de palabras. El ViewRenderer
reemplaza cualquier delimitador de paths encontrado en el nombre
del controlador con el delimitador actual ('/'), y cualquier
delimitador de palabra encontrado con un guión ('-') cuando crea
paths. Así, una llamada a la acción
/foo.bar/baz.bat despachará a
FooBarController::bazBatAction() en
FooBarController.php , el cual
renderizaría a foo-bar/baz-bat.phtml ; una
llamada a la acción /bar_baz/baz-bat
despachará a
Bar_BazController::bazBatAction()
en Bar/BazController.php (note la
separación del path) y renderiza
bar/baz/baz-bat.phtml . Tener en cuenta que el en el segundo ejemplo, el módulo es
todavía el módulo por defecto, pero que, debido a la existencia
de un separador de paths, el controlador recibe el nombre
Bar_BazController , en
Bar/BazController.php . El
ViewRenderer imita la jerarquía del
directorio del controlador. Deshabilitando Autorender Para algunas acciones o controladores, usted puede querer
apagar el autorendering -- por ejemplo, si quiere emitir un tipo
diferente de salida ( XML ,
JSON , etc), o si simplemente no desea
emitir nada. Tiene dos opciones: apagar todos los casos de
autorendering ( setNeverRender() ), o
simplemente desactivarlo para la acción actual (
setNoRender() ). _helper->viewRenderer->setNoRender();
}
}
// Bat clase del controlador, bar módulo:
class Bar_BatController extends Zend_Controller_Action
{
public function preDispatch()
{
// Nunca auto renderizar las acciones de este controlador
$this->_helper->viewRenderer->setNoRender();
}
}
]]> En muchos casos, no tiene sentido desactivar el autorendering
globalmente (ala setNeverRender() ), y
la única cosa que puede ganar de
ViewRenderer es el autosetup del objeto
de vista. Eligiendo Un Script de Vista Diferente Algunas situaciones requieren renderizar un script diferente
al llamado después de la acción. Por ejemplo, si tiene un
controlador que tiene tanto las acciones de agregar y de editar,
ambos pueden mostrar la misma vista 'form', aunque con
diferentes valores establecidos. Puede cambiar fácilmente el
nombre del script usado tanto con
setScriptAction() ,
setRender() , o llamando al
ayudante como un método, que invocará a
setRender() . _helper->viewRenderer('form');
}
public function editAction()
{
// Render 'bar/form.phtml' en lugar de 'bar/edit.phtml'
$this->_helper->viewRenderer->setScriptAction('form');
}
public function processAction()
{
// hacer alguna validación...
if (!$valid) {
// Render 'bar/form.phtml' en lugar de 'bar/process.phtml'
$this->_helper->viewRenderer->setRender('form');
return;
}
// de otra manera, continuar procesando...
}
}
]]>Modificando la Vista Registrada ¿Y si se necesita modificar el objeto vista -- por ejemplo,
cambiar el ayudante de paths, o la codificación?. Puede hacerlo
ya sea por modificar el objeto vista establecido en su
controlador, o arrebatándole el objeto vista a
ViewRenderer ; ambas son referencias al
mismo objeto. view->setEncoding('UTF-8');
}
public function bazAction()
{
// Obtener el objeto vista y establecer
// el callback de escape a 'htmlspecialchars'
$view = $this->_helper->viewRenderer->view;
$view->setEscape('htmlspecialchars');
}
}
]]>Ejemplos de Uso AvanzadoCambiando las Especificaciones del Path En algunas circunstancias, puede decidir que las
especificaciones del path por defecto no se adaptan a su sitio.
Por ejemplo, usted puede querer tener un árbol único de
plantillas al que puede dar acceso a sus diseñadores (esto es
muy típico cuando se utiliza Smarty , por ejemplo). En ese caso, puede querer
embeber los datos de la especificación del path base de la
vista, y crear una especificación alternativa para el script de
vista del path ellos mismos. Para los fines de este ejemplo, supongamos que el path base
de las vistas debería ser '
/opt/vendor/templates ', y que desea
para que los scripts de vista sean referenciados por '
:moduleDir/:controller/:action.:suffix
'; si el flag noController ha sido
establecido, quiere renderizar fuera del nivel superior en lugar
de en un subdirectorio ( ':action.:suffix
'). Por último, que quiere utilizar 'tpl' como el sufijo del
nombre de archivo del script de vista. setViewBasePathSpec('/opt/vendor/templates')
->setViewScriptPathSpec(':module/:controller/:action.:suffix')
->setViewScriptPathNoControllerSpec(':action.:suffix')
->setViewSuffix('tpl');
Zend_Controller_Action_HelperBroker::addHelper($viewRenderer);
]]>Rendering Múltiples Scripts de Vista desde una Sola
Acción A veces, puede que necesite renderizar múltiples scripts de
vista desde una sola acción. Esto es muy sencillo -- simplemente
hacer múltiples llamadas a render() : model es el modelo actual
$this->view->results =
$this->model->find($this->_getParam('query', '');
// render() por defecto lo delega al ViewRenderer
// Render primero al from de búsqueda y luego los resultados
$this->render('form');
$this->render('results');
}
public function formAction()
{
// No hacer nada; ViewRenderer hace autorender del script de vista
}
}
]]>