home *** CD-ROM | disk | FTP | other *** search
/ PC Professionell 2004 December / PCpro_2004_12.ISO / files / webserver / tsw / TSW_3.4.0.exe / Apache2 / perl / Views.pod < prev    next >
Encoding:
Text File  |  2004-01-30  |  19.6 KB  |  643 lines

  1. #============================================================= -*-perl-*-
  2. #
  3. # Template::Manual::Views
  4. #
  5. # DESCRIPTION
  6. #   This section describes dynamic views: a powerful but experimental
  7. #   new feature in version 2.01 of the Template Toolkit.
  8. #
  9. # AUTHOR
  10. #   Andy Wardley  <abw@andywardley.com>
  11. #
  12. # COPYRIGHT
  13. #   Copyright (C) 1996-2001 Andy Wardley.  All Rights Reserved.
  14. #   Copyright (C) 1998-2001 Canon Research Centre Europe Ltd.
  15. #
  16. #   This module is free software; you can redistribute it and/or
  17. #   modify it under the same terms as Perl itself.
  18. #
  19. # REVISION
  20. #   
  21. #
  22. #========================================================================
  23.  
  24.  
  25. #------------------------------------------------------------------------
  26. # IMPORTANT NOTE
  27. #   This documentation is generated automatically from source
  28. #   templates.  Any changes you make here may be lost.
  29. #   The 'docsrc' documentation source bundle is available for download
  30. #   from http://www.template-toolkit.org/docs.html and contains all
  31. #   the source templates, XML files, scripts, etc., from which the
  32. #   documentation for the Template Toolkit is built.
  33. #------------------------------------------------------------------------
  34.  
  35. =head1 NAME
  36.  
  37. Template::Manual::Views - Template Toolkit views (experimental)
  38.  
  39. =head1 DESCRIPTION
  40.  
  41. This section describes dynamic views: a powerful but experimental new
  42. feature in version 2.01 of the Template Toolkit.
  43.  
  44. A view is effectively a collection of templates and/or variable
  45. definitions which can be passed around as a self-contained unit.  This
  46. then represents a particular interface or presentation style for other
  47. objects or items of data.
  48.  
  49. You can use views to implement custom "skins" for an application or
  50. content set.  You can use them to help simplify the presentation of
  51. common objects or data types.  You can even use then to automate the
  52. presentation of complex data structures such as that generated in an
  53. XML::DOM tree or similar.  You let an iterator do the walking, and the
  54. view does the talking (or in this case, the presenting).  Voila - you
  55. have view independant, structure shy traversal using templates.  
  56.  
  57. In general, views can be used in a number of different ways to achieve
  58. several different things.  They elegantly solve some problems which
  59. were otherwise difficult or complicated, and make easy some things
  60. that were previously hard.
  61.  
  62. At the moment, they're still very experimental.  The directive syntax
  63. and underlying API are likely to change quite considerably over the 
  64. next version or two.  Please be very wary about building your 
  65. multi-million dollar e-commerce solutions based around this feature.
  66.  
  67. =head2 Views as Template Collectors/Providers
  68.  
  69. The VIEW directive starts a view definition and includes a name by
  70. which the view can be referenced.  The view definition continues up to
  71. the matching END directive.
  72.  
  73.     [% VIEW myview %]
  74.        ...
  75.     [% END %]
  76.  
  77. The first role of a view is to act as a collector and provider of templates.
  78. The include() method can be called on a view to effectively do the same 
  79. thing as the INCLUDE directive.  The template name is passed as the first 
  80. argument, followed by any local variable definitions for the template.
  81.  
  82.     [% myview.include('header', title='The Title') %]
  83.  
  84.     # equivalent to
  85.     [% INCLUDE header  title='The Title' %] 
  86.  
  87. Views accept a number of configuration options which can be used to control
  88. different aspects of their behaviour.  The 'prefix' and 'suffix' options 
  89. can be specified to add a fixed prefix and/or suffix to the name of each template.
  90.  
  91.     [% VIEW myview 
  92.          prefix = 'my/'
  93.          suffix = '.tt2' ;
  94.        END
  95.     %]
  96.  
  97. Now the call 
  98.  
  99.     [% myview.include('header', title='The Title') %]
  100.  
  101. is equivalent to
  102.  
  103.     [% INCLUDE my/header.tt2  title='The Title' %]
  104.  
  105. Views provide an AUTOLOAD method which maps method names to the
  106. include() method.  Thus, the following are all equivalent:
  107.  
  108.     [% myview.include('header', title='Hello World') %]
  109.     [% myview.include_header(title='Hello World') %]
  110.     [% myview.header(title='Hello World') %]
  111.  
  112. =head2 Local BLOCK Definitions
  113.  
  114. A VIEW definition can include BLOCK definitions which remain local to
  115. the view.   A request for a particular template will return a BLOCK,
  116. if defined, in preference to any other template of the same name.
  117.  
  118.     [% BLOCK foo %]
  119.        public foo block
  120.     [% END %]
  121.  
  122.     [% VIEW plain %]
  123.        [% BLOCK foo %]
  124.        plain foo block
  125.        [% END %]
  126.     [% END %]
  127.  
  128.     [% VIEW fancy %]
  129.        [% BLOCK foo %]
  130.        fancy foo block
  131.        [% END %]
  132.     [% END %]
  133.  
  134.     [% INCLUDE foo %]        # public foo block
  135.     [% plain.foo %]        # plain foo block 
  136.     [% fancy.foo %]        # fancy foo block 
  137.  
  138. In addition to BLOCK definitions, a VIEW can contain any other
  139. template directives.  The entire VIEW definition block is processed to
  140. initialise the view but no output is generated (this may change RSN -
  141. and get stored as 'output' item, subsequently accessible as [%
  142. view.output %]).  However, directives that have side-effects, such as
  143. those that update a variable, will have noticable consequences.
  144.  
  145. =head2 Preserving Variable State within Views
  146.  
  147. Views can also be used to save the values of any existing variables,
  148. or to create new ones at the point at which the view is defined.
  149. Unlike simple template metadata (META) which can only contain static
  150. string values, the view initialisation block can contain any template
  151. directives and generate any kind of dynamic output and/or data items.
  152.  
  153.     [% VIEW my_web_site %]
  154.        [% view.title   = title or 'My Cool Web Site' %]
  155.        [% view.author  = "$abw.name, $abw.email" %]
  156.        [% view.sidebar = INCLUDE my/sidebar.tt2 %]
  157.     [% END %]
  158.  
  159. Note that additional data items can be specified as arguments to the VIEW
  160. directive.  Anything that doesn't look like a configuration parameter is 
  161. assumed to be a data item.  This can be a little hazardous, of course, because
  162. you never know when a new configuration item might get added which interferes 
  163. with your data.
  164.  
  165.     [% VIEW my_web_site
  166.         # config options
  167.         prefix = 'my/'
  168.         # misc data
  169.         title   = title or 'My Cool Web Site'
  170.         author  = "$abw.name, $abw.email"
  171.         sidebar = INCLUDE my/sidebar.tt2 
  172.     %]
  173.        ...
  174.     [% END %]
  175.  
  176. Outside of the view definition you can access the view variables as, for
  177. example:
  178.  
  179.     [% my_web_site.title %]
  180.  
  181. One important feature is the equivalence of simple variables and templates.
  182. You can implement the view item 'title' as a simple variable, a template
  183. defined in an external file, possibly with a prefix/suffix automatically
  184. appended, or as a local BLOCK definition within the [% VIEW %] ... [% END %]
  185. definition.  If you use the syntax above then the view will Do The Right
  186. Thing to return the appropriate output.
  187.  
  188. At the END of the VIEW definition the view is "sealed" to prevent you
  189. from accidentally updating any variable values.  If you attempt to change
  190. the value of a variable after the END of the VIEW definition block then
  191. an 'view' error will be thrown.
  192.  
  193.     [% TRY; 
  194.          my_web_site.title = 'New Title';
  195.        CATCH;
  196.          error;
  197.        END
  198.     %]
  199.  
  200. The error above will be reported as:
  201.  
  202.     view error - cannot update item in sealed view: title
  203.  
  204. The same is true if you pass a parameter to a view variable.  This is
  205. interpreted as an attempt to update the variable and will raise the same
  206. warning.
  207.  
  208.     [% my_web_site.title('New Title') %]    # view error!
  209.  
  210. You can set the 'silent' parameter to have the view ignore these
  211. parameters and simply return the variable value. 
  212.  
  213.     [% VIEW my_web_site
  214.             silent = 1
  215.         title  = title or 'My Cool Web Site'
  216.         # ... ;
  217.        END
  218.     %]
  219.  
  220.     [% my_web_site.title('Blah Blah') %]   # My Cool Web Site
  221.  
  222. Alternately, you can specify that a view is unsealed allowing existing
  223. variables to be updated and new variables defined.
  224.  
  225.     [% VIEW my_web_site
  226.             sealed = 0
  227.         title  = title or 'My Cool Web Site'
  228.         # ... ;
  229.        END
  230.     %]
  231.  
  232.     [% my_web_site.title('Blah Blah') %]   # Blah Blah
  233.     [% my_web_site.title %]                # Blah Blah
  234.  
  235. =head2 Inheritance, Delegation and Reuse
  236.  
  237. Views can be inherited from previously defined views by use of the 'base'
  238. parameter.  This example shows how a base class view is defined which 
  239. applies a 'view/default/' prefix to all template names.
  240.  
  241.     [% VIEW my.view.default
  242.             prefix = 'view/default/';
  243.        END
  244.     %]
  245.  
  246. Thus the directive:
  247.  
  248.     [% my.view.default.header(title='Hello World') %]
  249.  
  250. is now equivalent to:
  251.  
  252.     [% INCLUDE view/default/header title='Hello World' %]
  253.  
  254. A second view can be defined which specifies the default view as a 
  255. base.
  256.  
  257.     [% VIEW my.view.fancy
  258.             base   = my.view.default
  259.             prefix = 'view/fancy/';
  260.        END
  261.     %]
  262.  
  263. Now the directive:
  264.  
  265.     [% my.view.fancy.header(title='Hello World') %]
  266.  
  267. will resolve to:
  268.  
  269.     [% INCLUDE view/fancy/header title='Hello World' %]
  270.  
  271. or if that doesn't exist, it will be handled by the base view as:
  272.  
  273.     [% INCLUDE view/default/header title='Hello World' %]
  274.  
  275. When a parent view is specified via the 'base' parameter, the
  276. delegation of a view to its parent for fetching templates and accessing
  277. user defined variables is automatic.  You can also implement your own
  278. inheritance, delegation or other reuse patterns by explicitly
  279. delegating to other views.
  280.  
  281.     [% BLOCK foo %]
  282.        public foo block
  283.     [% END %]
  284.  
  285.     [% VIEW plain %]
  286.        [% BLOCK foo %]
  287.        <plain>[% PROCESS foo %]</plain>
  288.        [% END %]
  289.     [% END %]
  290.  
  291.     [% VIEW fancy %]
  292.        [% BLOCK foo %]
  293.        [% plain.foo | replace('plain', 'fancy') %]
  294.        [% END %]
  295.     [% END %]
  296.  
  297.     [% plain.foo %]    # <plain>public foo block</plain>
  298.     [% fancy.foo %]    # <fancy>public foo block</fancy>
  299.  
  300. Note that the regular INCLUDE/PROCESS/WRAPPER directives work entirely
  301. independantly of views and will always get the original, unaltered
  302. template name rather than any local per-view definition.
  303.  
  304. =head2 Self-Reference
  305.  
  306. A reference to the view object under definition is available with the
  307. VIEW ... END block by its specified name and also by the special name
  308. 'view' (similar to the C<my $self = shift;> in a Perl method or the
  309. 'this' pointer in C++, etc).  The view is initially unsealed allowing
  310. any data items to be defined and updated within the VIEW ... END
  311. block.  The view is automatically sealed at the end of the definition
  312. block, preventing any view data from being subsequently changed.
  313.  
  314. (NOTE: sealing should be optional.  As well as sealing a view to prevent
  315. updates (SEALED), it should be possible to set an option in the view to 
  316. allow external contexts to update existing variables (UPDATE) or even 
  317. create totally new view variables (CREATE)).
  318.  
  319.     [% VIEW fancy %]
  320.        [% fancy.title  = 'My Fancy Title' %]
  321.        [% fancy.author = 'Frank Open' %]
  322.        [% fancy.col    = { bg => '#ffffff', bar => '#a0a0ff' } %]
  323.     [% END %]
  324.  
  325. or
  326.  
  327.     [% VIEW fancy %]
  328.        [% view.title  = 'My Fancy Title' %]
  329.        [% view.author = 'Frank Open' %]
  330.        [% view.col    = { bg => '#ffffff', bar => '#a0a0ff' } %]
  331.     [% END %]
  332.  
  333. It makes no real difference in this case if you refer to the view by
  334. its name, 'fancy', or by the general name, 'view'.  Outside of the
  335. view block, however, you should always use the given name, 'fancy':
  336.  
  337.     [% fancy.title  %]
  338.     [% fancy.author %]
  339.     [% fancy.col.bg %]
  340.  
  341. The choice of given name or 'view' is much more important when it
  342. comes to BLOCK definitions within a VIEW.  It is generally recommended
  343. that you use 'view' inside a VIEW definition because this is guaranteed
  344. to be correctly defined at any point in the future when the block gets
  345. called.  The original name of the view might have long since been changed
  346. or reused but the self-reference via 'view' should always be intact and 
  347. valid.
  348.  
  349. Take the following VIEW as an example:
  350.  
  351.     [% VIEW foo %]
  352.        [% view.title = 'Hello World' %]
  353.        [% BLOCK header %]
  354.        Title: [% view.title %]
  355.        [% END %]
  356.     [% END %]
  357.  
  358. Even if we rename the view, or create a new 'foo' variable, the header
  359. block still correctly accesses the 'title' attribute of the view to
  360. which it belongs.  Whenever a view BLOCK is processed, the 'view'
  361. variable is always updated to contain the correct reference to the
  362. view object to which it belongs.
  363.  
  364.     [% bar = foo %]
  365.     [% foo = { title => "New Foo" } %]  # no problem
  366.     [% bar.header %]                    # => Title: Hello World
  367.  
  368. =head2 Saving References to External Views
  369.  
  370. When it comes to view inheritance, it's always a good idea to take a
  371. local copy of a parent or delegate view and store it as an attribute
  372. within the view for later use.  This ensures that the correct view
  373. reference is always available, even if the external name of a view
  374. has been changed.
  375.  
  376.     [% VIEW plain %]
  377.        ...
  378.     [% END %]
  379.  
  380.     [% VIEW fancy %]
  381.        [% view.plain = plain %]
  382.        [% BLOCK foo %]
  383.        [% view.plain.foo | replace('plain', 'fancy') %]
  384.        [% END %]
  385.     [% END %]
  386.  
  387.     [% plain.foo %]        # => <plain>public foo block</plain>
  388.     [% plain = 'blah' %]    # no problem
  389.     [% fancy.foo %]        # => <fancy>public foo block</fancy>
  390.  
  391.  
  392. =head2 Views as Data Presenters
  393.  
  394. Another key role of a view is to act as a dispatcher to automatically
  395. apply the correct template to present a particular object or data
  396. item.  This is handled via the print() method.
  397.  
  398. Here's an example:
  399.  
  400.     [% VIEW foo %]
  401.  
  402.        [% BLOCK text %]
  403.           Some text: [% item %]
  404.        [% END %]
  405.  
  406.        [% BLOCK hash %]
  407.           a hash:
  408.           [% FOREACH key = item.keys.sort -%]
  409.              [% key %] => [% item.$key %]
  410.           [% END -%]
  411.        [% END %]
  412.  
  413.        [% BLOCK list %]
  414.           a list: [% item.sort.join(', ') %]
  415.        [% END %]
  416.  
  417.     [% END %]
  418.  
  419. We can now use the view to print text, hashes or lists.  The print()
  420. method includes the right template depending on the typing of the
  421. argument (or arguments) passed.
  422.  
  423.     [% some_text = 'I read the news today, oh boy.' %]
  424.     [% a_hash    = { house => 'Lords', hall => 'Albert' } %]
  425.     [% a_list    = [ 'sure', 'Nobody', 'really' ] %]
  426.  
  427.     [% view.print(some_text) %]
  428.             # Some text: I read the news today, oh boy.
  429.  
  430.     [% view.print(a_hash) %]
  431.             # a hash:
  432.                              hall => Albert
  433.                              house => Lords
  434.     [% view.print(a_list) %]
  435.             # a list: Nobody, really, sure
  436.  
  437.  
  438. You can also provide templates to print objects of any other class.
  439. The class name is mapped to a template name with all non-word
  440. character sequences such as '::' converted to a single '_'.
  441.  
  442.     [% VIEW foo %]
  443.        [% BLOCK Foo_Bar %]
  444.           a Foo::Bar object: 
  445.               thingies: [% view.print(item.thingies) %]
  446.                doodahs: [% view.print(item.doodahs)  %]
  447.        [% END %]
  448.     [% END %]
  449.  
  450.     [% USE fubar = Foo::Bar(...) %]
  451.  
  452.     [% foo.print(fubar) %]
  453.  
  454. Note how we use the view object to display various items within the 
  455. objects ('thingies' and 'doodahs').  We don't need to worry what 
  456. kind of data these represent (text, list, hash, etc) because we can
  457. let the view worry about it, automatically mapping the data type to 
  458. the correct template.
  459.  
  460. Views may define their own type =E<gt> template map.
  461.  
  462.     [% VIEW foo 
  463.          map = { TEXT  => 'plain_text',
  464.          ARRAY => 'show_list', 
  465.          HASH  => 'show_hash',
  466.          My::Module => 'template_name'
  467.          default    => 'any_old_data'
  468.                }
  469.     %]
  470.     [% BLOCK plain_text %]
  471.            ...
  472.         [% END %]
  473.        
  474.         ...
  475.  
  476.     [% END %]
  477.  
  478. They can also provide a 'default' map entry, specified as part of the 'map'
  479. hash or as a parameter by itself.
  480.  
  481.  
  482.     [% VIEW foo 
  483.          map     = { ... },
  484.          default = 'whatever'
  485.     %]
  486.        ...
  487.     [% END %]
  488.  
  489. or
  490.  
  491.     [% VIEW foo %]
  492.        [% view.map     = { ... }
  493.           view.default = 'whatever'
  494.        %]
  495.        ...
  496.     [% END %]
  497.  
  498. The print() method provides one more piece of magic.  If you pass it a
  499. reference to an object which provides a present() method, then the 
  500. method will be called passing the view as an argument.  This then gives
  501. any object a chance to determine how it should be presented via the 
  502. view.
  503.  
  504.     package Foo::Bar;
  505.  
  506.     ...
  507.  
  508.     sub present {
  509.     my ($self, $view) = @_;
  510.     return "a Foo::Bar object:\n"
  511.          . "thingies: " . $view.print($self->{ _THINGIES }) . "\n"
  512.              . "doodahs: " . $view.print($self->{ _DOODAHS }) . "\n";
  513.     }
  514.  
  515. The object is free to delve deeply into its innards and mess around with
  516. its own private data, before presenting the relevant data via the view.
  517. In a more complex example, a present() method might walk part of a tree
  518. making calls back against the view to present different nodes within the 
  519. tree.  We may not want to expose the internal structure of the tree
  520. (because that would break encapsulation and make our presentation code
  521. dependant on it) but we want to have some way of walking the tree and 
  522. presenting items found in a particular manner.
  523.  
  524. This is known as Structure Shy Traversal.  Our view object doesn't require
  525. prior knowledge about the internal structure of any data set to be able
  526. to traverse it and present the data contained therein.  The data items
  527. themselves, via the present() method, can implement the internal iterators
  528. to guide the view along the right path to presentation happiness.
  529.  
  530. The upshot is that you can use views to greatly simplify the display
  531. of data structures like XML::DOM trees.  The documentation for the 
  532. Template::Plugins::XML::DOM module contains an example of this.  In 
  533. essence, it looks something like this:
  534.  
  535. XML source:
  536.  
  537.     <user name="Andy Wardley">
  538.     <project id="iCan" title="iCan, but theyCan't"/>
  539.     <project id="p45"  title="iDid, but theyDidn't"/>
  540.     </user>
  541.  
  542. TT View:
  543.  
  544.     [% VIEW fancy %]
  545.        [% BLOCK user %]
  546.           User: [% item.name %]
  547.                 [% item.content(myview) %]
  548.        [% END %]
  549.  
  550.        [% BLOCK project %]
  551.             Project: [% project.id %] - [% project.name %]
  552.        [% END %]
  553.     [% END %]
  554.  
  555. Generate view:
  556.  
  557.     [% USE dom = XML.DOM %]
  558.     [% fancy.print(dom.parse(xml_source)) %]
  559.  
  560. Output:
  561.  
  562.           User: Andy Wardley
  563.             Project: iCan - iCan, but theyCan't
  564.             Project: p45 - iDid, but theyDidn't
  565.  
  566. The same approach can be applied to many other areas.  Here's an example from 
  567. the File/Directory plugins.
  568.  
  569.     [% VIEW myview %]
  570.        [% BLOCK file %]
  571.           - [% item.name %]
  572.        [% END %]
  573.     
  574.        [% BLOCK directory %]
  575.           * [% item.name %]
  576.             [% item.content(myview) FILTER indent %]
  577.        [% END %]
  578.     [% END %]
  579.  
  580.     [% USE dir = Directory(dirpath) %]
  581.     [% myview.print(dir) %]
  582.  
  583. And here's the same approach use to convert Pod documentation to any 
  584. other format via template.
  585.  
  586.     [%    # load Pod plugin and parse source file into Pod Object Model
  587.     USE Pod;
  588.     pom = Pod.parse_file(my_pod_file);
  589.         
  590.     # define view to map all Pod elements to "pod/html/xxx" templates
  591.     VIEW pod2html
  592.         prefix='pod/html';
  593.     END;
  594.         
  595.     # now print document via view (i.e. as HTML)
  596.     pod2html.print(pom) 
  597.     %]
  598.  
  599. Here we simply define a template prefix for the view which causes the
  600. view to look for 'pod/html/head1', 'pod/html/head2', 'pod/html/over' 
  601. as templates to present the different sections of the parsed Pod document.
  602.  
  603. There are some examples in the Template Toolkit test suite: t/pod.t and 
  604. t/view.t which may shed some more light on this.  See the distribution
  605. sub-directory 'examples/pod/html' for examples of Pod -E<gt> HTML templates.
  606.  
  607. (This documentation is incomplete but I'm not going to get it 100% pefect
  608. until the syntax and API stabilise).
  609.  
  610. =head1 AUTHOR
  611.  
  612. Andy Wardley E<lt>abw@andywardley.comE<gt>
  613.  
  614. L<http://www.andywardley.com/|http://www.andywardley.com/>
  615.  
  616.  
  617.  
  618.  
  619. =head1 VERSION
  620.  
  621. Template Toolkit version 2.13, released on 30 January 2004.
  622.  
  623. =head1 COPYRIGHT
  624.  
  625.   Copyright (C) 1996-2004 Andy Wardley.  All Rights Reserved.
  626.   Copyright (C) 1998-2002 Canon Research Centre Europe Ltd.
  627.  
  628. This module is free software; you can redistribute it and/or
  629. modify it under the same terms as Perl itself.
  630.  
  631.  
  632.  
  633. =cut
  634.  
  635. # Local Variables:
  636. # mode: perl
  637. # perl-indent-level: 4
  638. # indent-tabs-mode: nil
  639. # End:
  640. #
  641. # vim: expandtab shiftwidth=4:
  642.