3  * Smarty Internal Plugin Compile Foreach
 
   5  * Compiles the {foreach} {foreachelse} {/foreach} tags
 
  13  * Smarty Internal Plugin Compile Foreach Class
 
  15 class Smarty_Internal_Compile_Foreach extends Smarty_Internal_CompileBase {
 
  16         // attribute definitions
 
  17     public $required_attributes = array('from', 'item');
 
  18     public $optional_attributes = array('name', 'key'); 
 
  19     public $shorttag_order = array('from','item','key','name');
 
  22      * Compiles code for the {foreach} tag
 
  24      * @param array $args array with attributes from parser
 
  25      * @param object $compiler compiler object
 
  26      * @param array $parameter array with compilation parameter
 
  27      * @return string compiled code
 
  29     public function compile($args, $compiler, $parameter)
 
  31         $this->compiler = $compiler;
 
  32         $tpl = $compiler->template; 
 
  33         // check and get attributes
 
  34         $_attr = $this->_get_attributes($args);
 
  36         $from = $_attr['from'];
 
  37         $item = $_attr['item'];
 
  39         if (substr_compare("\$_smarty_tpl->getVariable($item)", $from,0, strlen("\$_smarty_tpl->getVariable($item)")) == 0) {
 
  40             $this->compiler->trigger_template_error("item variable {$item} may not be the same variable as at 'from'", $this->compiler->lex->taglineno);
 
  43         if (isset($_attr['key'])) {
 
  49         $this->_open_tag('foreach', array('foreach', $this->compiler->nocache, $item, $key)); 
 
  50         // maybe nocache because of nocache variables
 
  51         $this->compiler->nocache = $this->compiler->nocache | $this->compiler->tag_nocache;
 
  53         if (isset($_attr['name'])) {
 
  54             $name = $_attr['name'];
 
  56             $SmartyVarName = '$smarty.foreach.' . trim($name, '\'"') . '.';
 
  61         $ItemVarName = '$' . trim($item, '\'"') . '@'; 
 
  62         // evaluates which Smarty variables and properties have to be computed
 
  64             $usesSmartyFirst = strpos($tpl->template_source, $SmartyVarName . 'first') !== false;
 
  65             $usesSmartyLast = strpos($tpl->template_source, $SmartyVarName . 'last') !== false;
 
  66             $usesSmartyIndex = strpos($tpl->template_source, $SmartyVarName . 'index') !== false;
 
  67             $usesSmartyIteration = strpos($tpl->template_source, $SmartyVarName . 'iteration') !== false;
 
  68             $usesSmartyShow = strpos($tpl->template_source, $SmartyVarName . 'show') !== false;
 
  69             $usesSmartyTotal = strpos($tpl->template_source, $SmartyVarName . 'total') !== false;
 
  71             $usesSmartyFirst = false;
 
  72             $usesSmartyLast = false;
 
  73             $usesSmartyTotal = false;
 
  74             $usesSmartyShow = false;
 
  77         $usesPropFirst = $usesSmartyFirst || strpos($tpl->template_source, $ItemVarName . 'first') !== false;
 
  78         $usesPropLast = $usesSmartyLast || strpos($tpl->template_source, $ItemVarName . 'last') !== false;
 
  79         $usesPropIndex = $usesPropFirst || strpos($tpl->template_source, $ItemVarName . 'index') !== false;
 
  80         $usesPropIteration = $usesPropLast || strpos($tpl->template_source, $ItemVarName . 'iteration') !== false;
 
  81         $usesPropShow = strpos($tpl->template_source, $ItemVarName . 'show') !== false;
 
  82         $usesPropTotal = $usesSmartyTotal || $usesSmartyShow || $usesPropShow || $usesPropLast || strpos($tpl->template_source, $ItemVarName . 'total') !== false; 
 
  83         // generate output code
 
  85         $output .= " \$_smarty_tpl->tpl_vars[$item] = new Smarty_Variable;\n";
 
  86         $compiler->local_var[$item] = true;
 
  88             $output .= " \$_smarty_tpl->tpl_vars[$key] = new Smarty_Variable;\n";
 
  89             $compiler->local_var[$key] = true;
 
  91         $output .= " \$_from = $from; if (!is_array(\$_from) && !is_object(\$_from)) { settype(\$_from, 'array');}\n";
 
  93             $output .= " \$_smarty_tpl->tpl_vars[$item]->total= \$_smarty_tpl->_count(\$_from);\n";
 
  95         if ($usesPropIteration) {
 
  96             $output .= " \$_smarty_tpl->tpl_vars[$item]->iteration=0;\n";
 
  99             $output .= " \$_smarty_tpl->tpl_vars[$item]->index=-1;\n";
 
 102             $output .= " \$_smarty_tpl->tpl_vars[$item]->show = (\$_smarty_tpl->tpl_vars[$item]->total > 0);\n";
 
 105             if ($usesSmartyTotal) {
 
 106                 $output .= " \$_smarty_tpl->tpl_vars['smarty']->value['foreach'][$name]['total'] = \$_smarty_tpl->tpl_vars[$item]->total;\n";
 
 108             if ($usesSmartyIteration) {
 
 109                 $output .= " \$_smarty_tpl->tpl_vars['smarty']->value['foreach'][$name]['iteration']=0;\n";
 
 111             if ($usesSmartyIndex) {
 
 112                 $output .= " \$_smarty_tpl->tpl_vars['smarty']->value['foreach'][$name]['index']=-1;\n";
 
 114             if ($usesSmartyShow) {
 
 115                 $output .= " \$_smarty_tpl->tpl_vars['smarty']->value['foreach'][$name]['show']=(\$_smarty_tpl->tpl_vars[$item]->total > 0);\n";
 
 118         if ($usesPropTotal) {
 
 119                         $output .= "if (\$_smarty_tpl->tpl_vars[$item]->total > 0){\n";
 
 121                         $output .= "if (\$_smarty_tpl->_count(\$_from) > 0){\n";
 
 123                 $output .= "    foreach (\$_from as \$_smarty_tpl->tpl_vars[$item]->key => \$_smarty_tpl->tpl_vars[$item]->value){\n";
 
 125             $output .= " \$_smarty_tpl->tpl_vars[$key]->value = \$_smarty_tpl->tpl_vars[$item]->key;\n";
 
 127         if ($usesPropIteration) {
 
 128             $output .= " \$_smarty_tpl->tpl_vars[$item]->iteration++;\n";
 
 130         if ($usesPropIndex) {
 
 131             $output .= " \$_smarty_tpl->tpl_vars[$item]->index++;\n";
 
 133         if ($usesPropFirst) {
 
 134             $output .= " \$_smarty_tpl->tpl_vars[$item]->first = \$_smarty_tpl->tpl_vars[$item]->index === 0;\n";
 
 137             $output .= " \$_smarty_tpl->tpl_vars[$item]->last = \$_smarty_tpl->tpl_vars[$item]->iteration === \$_smarty_tpl->tpl_vars[$item]->total;\n";
 
 140             if ($usesSmartyFirst) {
 
 141                 $output .= " \$_smarty_tpl->tpl_vars['smarty']->value['foreach'][$name]['first'] = \$_smarty_tpl->tpl_vars[$item]->first;\n";
 
 143             if ($usesSmartyIteration) {
 
 144                 $output .= " \$_smarty_tpl->tpl_vars['smarty']->value['foreach'][$name]['iteration']++;\n";
 
 146             if ($usesSmartyIndex) {
 
 147                 $output .= " \$_smarty_tpl->tpl_vars['smarty']->value['foreach'][$name]['index']++;\n";
 
 149             if ($usesSmartyLast) {
 
 150                 $output .= " \$_smarty_tpl->tpl_vars['smarty']->value['foreach'][$name]['last'] = \$_smarty_tpl->tpl_vars[$item]->last;\n";
 
 160  * Smarty Internal Plugin Compile Foreachelse Class
 
 162 class Smarty_Internal_Compile_Foreachelse extends Smarty_Internal_CompileBase {
 
 164      * Compiles code for the {foreachelse} tag
 
 166      * @param array $args array with attributes from parser
 
 167      * @param object $compiler compiler object
 
 168      * @param array $parameter array with compilation parameter
 
 169      * @return string compiled code
 
 171     public function compile($args, $compiler, $parameter)
 
 173         $this->compiler = $compiler; 
 
 174         // check and get attributes
 
 175         $_attr = $this->_get_attributes($args);
 
 177         list($_open_tag, $nocache, $item, $key) = $this->_close_tag(array('foreach'));
 
 178         $this->_open_tag('foreachelse', array('foreachelse', $nocache, $item, $key));
 
 180         return "<?php }} else { ?>";
 
 185  * Smarty Internal Plugin Compile Foreachclose Class
 
 187 class Smarty_Internal_Compile_Foreachclose extends Smarty_Internal_CompileBase {
 
 189      * Compiles code for the {/foreach} tag
 
 191      * @param array $args array with attributes from parser
 
 192      * @param object $compiler compiler object
 
 193      * @param array $parameter array with compilation parameter
 
 194      * @return string compiled code
 
 196     public function compile($args, $compiler, $parameter)
 
 198         $this->compiler = $compiler; 
 
 199         // check and get attributes
 
 200         $_attr = $this->_get_attributes($args); 
 
 201         // must endblock be nocache?
 
 202         if ($this->compiler->nocache) {
 
 203             $this->compiler->tag_nocache = true;
 
 206         list($_open_tag, $this->compiler->nocache, $item, $key) = $this->_close_tag(array('foreach', 'foreachelse'));
 
 207         unset($compiler->local_var[$item]);
 
 209             unset($compiler->local_var[$key]);
 
 212         if ($_open_tag == 'foreachelse')
 
 215             return "<?php }} ?>";