Subversion Repositories Sigmater

Rev

Blame | Last modification | View Log | Download | RSS feed

<?php

/******************************************************************************

  Titolo:        DynaCombus (also known as aligner)
  Versione:      v5.3

  Creato:        March   16, 2002  23:55:57
  Aggiornato:    January 23, 2003  19:27:18

  Autore:        Maxim Maletsky (maxim@php.net)

  Descrizione:   DunaCombus e la classe per formattare e visualizzare i dati
                 nei campi <SELECT> di puro HTML per una presentazione dati
                 più prattico, usando un algorithmo logico dinamico e stabile.

                 Una volta chiamato, DynaCombus, ricevendo un array, usa
                 i parametri predefini nello sdcript, e crea una SELECT con
                 i dati allineati per una visione più precisa.

                 Le utilità principali di DunaCombus consitono di una
                 consistenza del layout HTML sulla pagina, permettendo cosi
                 una stabilità della presentazione molto utile per la creazione
                 dei programmi PHP stand-alone. Usa una logica ben precisa e
                 stabile per la rappresentazione della tabella SELECT.

                 Creato ed inteso come il componente chiave per
                 il progetto di Catasto.

  Features:      1. Stand-Alone look and feel.
                 2. 100% personalizzabile layout con una estrema semplicità,
                    usabilità e dynamicità. A punto il nome.
                 3. Crea una lista scrollabile senza mai ricorrere a frames
                 4. Seleziona dalla lista (per un submit) più record alla volta
                 5. Crea le liste dei dati dinamicamente, e più facile
                 6. Stabilità di layout - le variazioni dei dati non
                    influiscono sulla misura della SELECT che rimarrebbe
                    comunque fissata (personalizabile)

******************************************************************************/

if(!function_exists('getmicrotime')) {
        function getmicrotime(){
                list($usec, $sec) = explode(" ",microtime());
                return ((float)$usec + (float)$sec);
        }
}

//include_once 'DynaCache.inc.php';

Class DC {

        /**********************************************************
                Variabili Publici
         *********************************************************/
        var $tag            = Array();

        /**********************************************************
                Variabili Privati
         *********************************************************/
        var $data           = Array();
        var $params         = Array();
        var $width          = 0;
        var $default_params = Array();
        var $private_params = Array();
        var $defined_tags   = False;
        var $display        = '';
        var $header         = '';
        var $current_spacer = '';
        var $current_tag    = '';
        var $r              = 0;
        var $c              = 0;
        var $cache_obj;
        var $tmp_rows       = Array();


        var $cache          = False;
        var $debug          = False;

        /**********************************************************
                Funzione:      assign_default_tags()
                Ritorno:       True

                La funzione assign_default_tags() e usata aer creare
                i valori di default per i variabili piu importanti che
                non siano gia assegnati da utente durante la
                costruzione della combo.
         *********************************************************/

        function assign_default_tags() {
                /**********************************************************
                        OVERWRITE

                        Controlla se la riga deve avere la precedenza o la
                        colonna. Settata per default per la colonna.

                        L'ordine di OVERWRITE sara lo stesso come nelle
                        prossime due righe (prevale quella superiore)
                 *********************************************************/
                $this->default_params['table']['overwrite'][] = 'cols';
                $this->default_params['table']['overwrite'][] = 'rows';

                /**********************************************************
                        MARGINS

                        I margini della tabella, ovvero le distanze minime
                        fra le colonne
                 *********************************************************/
                $this->default_params['table']['margins'] = 1;

                /**********************************************************
                        ALIGN

                        Allegniamento. Default SINISTRO
                 *********************************************************/
                $this->default_params['table']['align'] = 'left';

                /**********************************************************
                        SELECTED

                        Allegniamento. Default SINISTRO
                 *********************************************************/
                $this->default_params['table']['selected'] = '';

                /**********************************************************
                        DISABLED

                        Disabilitazione. Default 0
                 *********************************************************/
                $this->default_params['table']['disabled'] = '';

                /**********************************************************
                        Carattere di Spazio

                        Default uno spazion vuoto ' '
                 *********************************************************/
                $this->default_params['table']['spacer'] = ' ';

                /**********************************************************
                        Lunghezza di bordo

                        Default 0
                 *********************************************************/
                $this->default_params['table']['border'] = 0;

                /**********************************************************
                        Stile

                        font DEVE essere 'Courier New'
                 *********************************************************/
                $this->default_params['table']['style'] = 'font-weight: 500; font-size: 11px;';

                /**********************************************************
                        ALIGN

                        Allegniamento. Default CENTER
                 *********************************************************/
                $this->default_params['header']['align'] = 'center';

                /**********************************************************
                        ALIGN

                        Allegniamento. Default CENTER
                 *********************************************************/
                $this->default_params['header']['tr_align'] = 'center';

                /**********************************************************
                        ALIGN

                        Allegniamento. Default CENTER
                 *********************************************************/
                $this->default_params['header']['bgcolor'] = '#CCCCCC';


                /**********************************************************
                        ALIGN

                        Allegniamento. Default CENTER
                 *********************************************************/
                $this->default_params['title']['align'] = 'center';

                /**********************************************************
                        Class

                        Class di default e `cl'
                 *********************************************************/
                $this->default_params['title']['class'] = 'cl';

                /**********************************************************
                        Class

                        Class di default e `cl'
                 *********************************************************/
                $this->default_params['title']['empty'] = '&nbsp;';

                /**********************************************************
                        Tag di controllo

                        Strutturato come: sezione : parametro : esressione
                        regolare da confrontare
                 *********************************************************/
                $this->control_tags = Array(

                /**********************************************************
                        Tabella
                 *********************************************************/
                         'table' => Array(

                                // Larghezza della combo (numerico)
                                // 'width'        => '\\d+'

                                // Altezza della combo, ovvero <SELECT SIZE=***> (numerico)
                                 'height'       => '\\d+'

                                // Numero di collonne (numerico)
                                ,'columns'      => '\\d+'

                                // Numero delle Righe (numerico)
                                ,'rows'         => '\\d+'

                                // Grandezza delle margini tra le colonne (numerico)
                                ,'margins'      => '\\d+'

                                // Mergine Sinistro (numerico)
                                ,'margin_left'  => '\\d+'

                                // Mergine Destro (numerico)
                                ,'margin_right' => '\\d+'

                                // Bordo (numerico)
                                ,'border'       => '\\d+'

                                // Riga selezionata (numerico)
                                // ,'selected'     => '\\d+'

                                // Aliniamento ('left', 'right' oppure 'center')
                                ,'align'        => 'left|center|right'

                                // Cache (numerico)
                                // ,'cache'        => 'yes|no|0|1'

                                // Precedenza tra le colonne o righe ('cols' o 'rows')
                                ,'overwrite'    => 'cols|rows'

                                // Nome della combo ovvero <SELECT NAME=***> (stringa)
                                ,'name'         => '.+'

                                // Carattere usato per creare lo Spazio  (stringa)
                                ,'spacer'       => '.+'

                                // Carattere usato per creare il Bordo  (stringa)
                                ,'border_char'  => '.+'

                                // Opzione di multiselect ovvero <SELECT MULTIPLE>
                                // (True '1' o False '0')
                                ,'multiple'     => '1'

                                // Opzione di disabilitazione <SELECT DISABLED>
                                // (True '1' o False '0')
                                ,'disabled'     => '1'

                                // Stile aggiuntivo  (stringa)
                                ,'style'        => '.*'

                                // ID della combo ovvero <SELECT id=***>  (stringa)
                                ,'id'           => '.+'

                                // ID della combo ovvero <SELECT id=***>  (stringa)
                                ,'zerofill'     => '1'

                                // Left trim
                                ,'ltrim'        => '1'

                                // Parametri addizionali per lo <SELECT>  (stringa)

                                // IMPORTANTE!!!

                                // PARAMETRO 'ADD' DEVE ESSERE L'ULTIMO PARAMETRO
                                // SPECIFICATO! NESSUN ALTRO PARAMETRO SEQUENTE A
                                // 'ADD' VERREBBE INTERPRETTATO, E COMUNQUE, CREEREBBE
                                // DEI PROBLEMI GRAVI ALLA VISUALIZZAZIONE DI DYNACOMBUS
                                ,'add'          => '.+'
                        )

                        ,'cols' => Array(

                                // Larghezza della combo (numerico)
                                 'width'        => '\\d+'

                                // Grandezza delle margini tra le colonne (numerico)
                                ,'margins'      => '\\d+'

                                // Mergine Sinistro (numerico)
                                ,'margin_left'  => '\\d+'

                                // Mergine Destro (numerico)
                                ,'margin_right' => '\\d+'

                                // Aliniamento ('left', 'right' oppure 'center')
                                ,'align'        => 'left|center|right'

                                // Carattere usato per creare lo Spazio  (stringa)
                                ,'spacer'       => '.+'

                                // Carattere usato per creare il Bordo  (stringa)
                                ,'border_char'  => '.+'
                        )

                        ,'rows' => Array(

                                // Aliniamento ('left', 'right' oppure 'center')
                                 'align'        => 'left|center|right'

                                // Carattere usato per creare lo Spazio  (stringa)
                                ,'spacer'       => '.+'

                                // Carattere usato per creare il Bordo  (stringa)
                                ,'border_char'  => '.+'

                                // Riga selezionata (numerico)
                                ,'selected'     => '1'

                                // Stile aggiuntivo  (stringa)
                                ,'style'        => '.*'

                                // ID della combo ovvero <SELECT id=***>  (stringa)
                                ,'id'           => '.+'

                                // IMPORTANTE!!!

                                // PARAMETRO 'ADD' DEVE ESSERE L'ULTIMO PARAMETRO
                                // SPECIFICATO! NESSUN ALTRO PARAMETRO SEQUENTE A
                                // 'ADD' VERREBBE INTERPRETTATO, E COMUNQUE, CREEREBBE
                                // DEI PROBLEMI GRAVI ALLA VISUALIZZAZIONE DI DYNACOMBUS
                                ,'add'          => '.+'
                        )

                /**********************************************************
                        Header
                 *********************************************************/
                        ,'header' => Array(

                                // Altezza della combo, ovvero <SELECT SIZE=***> (numerico)
                                 'height'       => '\\d+'

                                // Aliniamento ('left', 'right' oppure 'center')
                                ,'align'        => 'left|center|right'

                                // Aliniamento ('left', 'right' oppure 'center')
                                ,'tr_align'    => 'left|center|right'

                                // Colore di background  (stringa)
                                ,'bgcolor'      => '.+'

                                // Stile aggiuntivo  (stringa)
                                ,'style'        => '.*'

                                // Stile aggiuntivo  (stringa)
                                ,'class'        => '.*'

                                // ID della combo ovvero <SELECT id=***>  (stringa)
                                ,'id'           => '.+'

                                // IMPORTANTE!!!

                                // PARAMETRO 'ADD' DEVE ESSERE L'ULTIMO PARAMETRO
                                // SPECIFICATO! NESSUN ALTRO PARAMETRO SEQUENTE A
                                // 'ADD' VERREBBE INTERPRETTATO, E COMUNQUE, CREEREBBE
                                // DEI PROBLEMI GRAVI ALLA VISUALIZZAZIONE DI DYNACOMBUS
                                ,'add'          => '.+'
                        )

                        ,'title' => Array(

                                // Aliniamento ('left', 'right' oppure 'center')
                                 'align'        => 'left|center|right'

                                // Il testo per la creazione del titolo  (stringa)
                                ,'text'         => '.+'

                                // Stile aggiuntivo  (stringa)
                                ,'style'        => '.+'

                                // Stile aggiuntivo  (stringa)
                                ,'class'        => '.+'

                                // Colore di background  (stringa)
                                ,'bgcolor'      => '.+'

                                // ID della combo ovvero <SELECT id=***>  (stringa)
                                ,'id'           => '.+'

                                // Wrap
                                ,'wrap'         => '1'

                                // NoWrap)
                                ,'nowrap'       => '1'

                                // IMPORTANTE!!!

                                // PARAMETRO 'ADD' DEVE ESSERE L'ULTIMO PARAMETRO
                                // SPECIFICATO! NESSUN ALTRO PARAMETRO SEQUENTE A
                                // 'ADD' VERREBBE INTERPRETTATO, E COMUNQUE, CREEREBBE
                                // DEI PROBLEMI GRAVI ALLA VISUALIZZAZIONE DI DYNACOMBUS
                                ,'add'          => '.+'
                        )
                );

                Return True;
        }



        /**********************************************************
            Funzione:      set_session()
            Argomenti:     $key
                              stringa,
                              (Chiave: <OPTION VALUE=***>)

            Ritorno:       string ($chiave per essere usata
                                   nella modalita sessione)


            Funzione liquidata.

            Avrebbe creato un array per la sessione e ritornato
            la sua chiave
         *********************************************************/
        function set_session($key) {
                Return $key;
        }



        /**********************************************************
            Funzione:      add_row()
            Argomenti:     $row
                              array,
                              (Array della riga)

            Ritorno:       True


            Riceve array dei dati per la DynaCombus riga per riga
            e gli registra nelle variabili privati.

         *********************************************************/
        function add_row($row) {
                $this->tmp_rows[] = $row;
                Return True;
        }


        function add_rows($array) {

                $this->make_tags();
                foreach($array as $row) {
                        /**********************************************************
                                Creaa i tags per quelli non defiti precedentamente
                         *********************************************************/
                        $this->r++;
                        $key = -1;

                        /**********************************************************
                                Se ce un limite sulle righe ci fermiamo qui
                         *********************************************************/
                        if(isset($this->params['table']['rows']) and $this->r>$this->params['table']['rows']+0)
                                Return True;

                        /**********************************************************
                                Ciclo delle righe ci
                         *********************************************************/
                        foreach($row as $fake_key=>$val) {
                                $key++;

                                /**********************************************************
                                        Smetiamo fare i cicli inutili se siamo fuori il
                                        limite specificato delle colonne
                                 *********************************************************/
                                if(isset($this->params['table']['columns']) and $key>$this->params['table']['columns']+0)
                                        Break;

                                /**********************************************************
                                        Assegna il primo valore [0] come <OPTION VALUE>
                                 *********************************************************/
                                if($key==0) {
                                        $this->data['row'][$this->r]['key'] = $this->set_session($val);
                                        Continue;
                                }

                                /**********************************************************
                                        Crea la cella
                                 *********************************************************/
                                $this->data['row'][$this->r][$key]['data'] = $val;

                                /**********************************************************
                                        Memorizza la lunghezza
                                 *********************************************************/
                                $this->data['row'][$this->r][$key]['length'] = strlen($val);

                                /**********************************************************
                                        Calcola la massima lunghezza della colonna
                                 *********************************************************/
                                if($this->data['row'][$this->r][$key]['length']>=@$this->data['params']['cols']['width'][$key]) {
                                        $this->data['params']['cols']['width'][$key] = $this->data['row'][$this->r][$key]['length'];
                                }

                                /**********************************************************
                                        Calcola il numero massimo delle colonne
                                 *********************************************************/
                                if(!isset($this->params['table']['columns']) and $key>@$this->private_params['table']['columns'])
                                        $this->private_params['table']['columns'] = $key;
                        }
                }

                Return True;
        }



        /**********************************************************

            Funzione:      row_left()
            Ritorno:       Array (spazio SINISTRO , spazio DESTRO)


            Allineamento SINISTRO
            Allocazione delle lunghezze per DESTRO e SINISTRO.

         *********************************************************/
        function row_left() {
                Return Array(
                        0,
                        $this->remained
                );
        }



        /**********************************************************

            Funzione:      row_right()
            Ritorno:       Array (spazio SINISTRO , spazio DESTRO)


            Allineamento DESTRO
            Allocazione delle lunghezze per DESTRO e SINISTRO.

         *********************************************************/
        function row_right() {
                Return Array(
                        $this->remained,
                        0
                );
        }



        /**********************************************************

            Funzione:      row_center()
            Ritorno:       Array (spazio SINISTRO , spazio DESTRO)


            Allineamento CENTRO
            Allocazione delle lunghezze per DESTRO e SINISTRO.

         *********************************************************/
        function row_center() {
                $num = $this->remained/2;
                Return Array(
                        floor($num),
                        ceil($num)
                );
        }



        /**********************************************************

            Funzione:      overlap()
            Argomenti:     $parameter
                              string,
                              (nome del parametro)

            Ritorno:       string (valore del parametro)


            Calcola se il valore da utilizzare per un parametro
            basandosi sulla precedenza usata della configurazione.

            Prova prima il valore disponibile, se sono
            disponbibili entrambi usa quello appartenete
            alla proprieta di precedenza

         *********************************************************/
        function overlap($parameter) {
                for($i=0; $i<=1; $i++)
                        if(isset($this->params[$this->params['table']['overwrite'][$i]][$this->{$this->params['table']['overwrite'][$i]}][$parameter]))
                                Return $this->params[$this->params['table']['overwrite'][$i]][$this->{$this->params['table']['overwrite'][$i]}][$parameter];
                Return @$this->params['table'][$parameter];
        }



        /**********************************************************

            Funzione:      combiner()
            Argomenti:     $num
                              intero,
                              (numero di ripetizione della stringa)

            Ritorno:       string (stringa ripetuta N volte)


            Ripete una stringa N numero di volte

         *********************************************************/
        function combiner($num) {
                Return str_repeat($this->current_spacer, $num);
        }



        /**********************************************************

            Funzione:      Creator()

            L'algorithmo chiave della DynaCombus.

            Crea un ciclo di tutte le righe multiplicando per
            ogni colonna e crea una stringa HTML quasi pronta
            per la visuallizazione

         *********************************************************/
        function Creator() {
                /**********************************************************
                        Il ciclo delle righe
                 *********************************************************/
                for($this->rows=1; $this->rows<=$this->params['table']['rows']; $this->rows++) {

                        /**********************************************************
                                Presetta i parametri per ogni opzione
                         *********************************************************/
                        @$this->output .= "<option value=\"{$this->data['row'][$this->rows]['key']}\"";

                        if(isset($this->params['rows'][$this->rows]['style']))
                                $this->output .= " style=\"{$this->params['rows'][$this->rows]['style']}\"";

                        if(isset($this->params['rows'][$this->rows]['id']))
                                $this->output .= " id=\"{$this->params['rows'][$this->rows]['id']}\"";

                        if(isset($this->params['rows'][$this->rows]['add']))
                                $this->output .= " {$this->params['rows'][$this->rows]['add']}";

                        if(isset($this->params['rows'][$this->rows]['selected']))
                                $this->output .= ' selected';

                        $this->output .= '>';

                        if(!isset($this->params['table']['ltrim']))
                                $this->output .= ' &nbsp;';

                        /**********************************************************
                                Il ciclo delle colonne
                         *********************************************************/
                        for($this->cols=1; $this->cols<=$this->params['table']['columns']; $this->cols++) {

                                /**********************************************************
                                        Prepara i valori per ognio colonna
                                 *********************************************************/
                                $align = $this->overlap('align');
                                $this->current_spacer = $this->overlap('spacer');
                                $this->remained = @$this->data['params']['cols']['width'][$this->cols] - @$this->data['row'][$this->rows][$this->cols]['length'];

                                if($this->rows == 1 and $this->cols == 1)
                                        $this->params['cols'][1]['total'] = 2;


                                /**********************************************************
                                        Algorithmo di larghezza.

                                        Ritorna una variabile privata REMAINED per un uso
                                        indispensabile allineando le colonne

                                        Usato ad ogni ciclo
                                 *********************************************************/
                                if(isset($this->params['cols'][$this->cols]['width'])) {
                                        $width = @$this->params['cols'][$this->cols]['margin_left']+@$this->data['params']['cols']['width'][$this->cols]+@$this->params['cols'][$this->cols]['margin_right'];
                                        $difference = $this->params['cols'][$this->cols]['width']-$width;

                                        if($difference>0)
                                                $this->remained = $this->remained + $difference;
                                }

                                /**********************************************************
                                        Algorithmo di bordo.

                                        Calcola le precedenze del bordo e modifica le
                                        lunghezze delle colonne

                                        Usata una prima volta sola
                                 *********************************************************/
                                if(isset($this->params['table']['border']) and $this->params['table']['border']>0 and $this->cols>1) {
                                        $border_char = $this->overlap('border_char');

                                        $output = strlen($border_char) ? str_repeat($border_char, $this->params['table']['border']) : $this->combiner($this->params['table']['border']);

                                        $this->output .= $output;

                                        if($this->rows == 1)
                                                @$this->params['cols'][$this->cols]['total'] += strlen($output);
                                }

                                /**********************************************************
                                        Algorithmo di allineamento.

                                        Chiama la funzione dinamicamente basandosi sulla
                                        definizione allineamento per la colonna

                                        Usato ad ogni ciclo 

                                                                                **
                                                                                        Modificato il 23/07/2003 per problemi con il rilevamento
                                                                                        dinamico del metodo richiesto
                                                                                **
                                 *********************************************************/
                                 if (method_exists($this,"row_$align"))
                                                                        $values = $this->{"row_$align"}();
                                                                 else
                                                                        $values = $this->row_left();


                                /**********************************************************
                                        Algorithmo di output.

                                        Compone una stringa basandosi su tutti i valori
                                        precreati sopra

                                        Usato ad ogni ciclo
                                 *********************************************************/
                                 /**********************************************************
                                        Ritorno della colonna
                                 *********************************************************/

                                $output = $this->combiner($values[0]+$this->params['cols'][$this->cols]['margin_left']) . @$this->data['row'][$this->rows][$this->cols]['data'] . $this->combiner($values[1]+$this->params['cols'][$this->cols]['margin_right']);

                                $this->output .= htmlspecialchars($output);

                                if($this->rows == 1) {
                                        @$this->params['cols'][$this->cols]['total'] += strlen($output);
                                        $this->width += $this->params['cols'][$this->cols]['total'];
                                }
                        }

                        /**********************************************************
                                Ritorno della riga
                         *********************************************************/
                        $this->output .= "</option>\n";
                }
        }



        /**********************************************************

            Funzione:      parser()
            Argomenti:     $tag
                              stringa,
                              (la stringa dei definizioni della DC)

            Ritorno:       string (Array interno dei parametri)


            Parsa la stringa dei parametri passata alla DynaCombus
            e importa i valori

         *********************************************************/
        function parser($tag) {
                $tag = trim($tag);
                /**********************************************************
                        Parsa la stringa
                 *********************************************************/
                preg_match_all("/([^\s=]+)[\s]*=[\s]*[\\\"']([^\\\"']*)[\\\"']/", $tag, $parsed);
                for($i=0; $i<sizeof($parsed[0]); $i++) {
                        /**********************************************************
                                Tutto in minuscolo
                         *********************************************************/
                        $key = strtolower($parsed[1][$i]);

                        /**********************************************************
                                Controllo per il parametro ADD
                         *********************************************************/
                        if($key=='add' and $this->control_tags[$this->current_tag][$key]) {
                                $haystack = strrev($tag);
                                $pos = strpos($haystack, strrev($parsed[0][$i]));
                                if(!$pos)
                                        $checked = $parsed[2][$i];
                                else {
                                        $remained = $parsed[0][$i].strrev(substr($haystack, 1, $pos-1));
                                        $checked = substr(trim(substr($remained, strpos($remained, '=')+1)), 1);
                                }
                        }
                        else {
                                /**********************************************************
                                        Rimpiazza '-' con '_'.
                                        Non vogliamo iernamente nessun '-'
                                 *********************************************************/
                                $key = str_replace('-', '_', $key);
                                /**********************************************************
                                        Controlla se il tag ricevuto e riconosciuto
                                        dalla DynaCombus. Se non lo e - verra ignorato
                                 *********************************************************/
                                $checked = (@$this->control_tags[$this->current_tag][$key] and preg_match("/^(".@$this->control_tags[$this->current_tag][$key].")+$/i", $parsed[2][$i])) ? ($key=='text'? $parsed[2][$i] : strtolower($parsed[2][$i])) : False;
                        }
                        if($checked !== False) {
                                $result[$key] = $checked;
                        }
                }
                Return is_array(@$result) ? $result : False;
        }



        /**********************************************************

            Funzione:      make_tags()

            Ritorno:       True


            Assegna i parametri passati dal utente nella
            configurazione interna della DynaCombus

            make_tags viene chiamata durante la chiamata al
            methodo DYSPLAY e ad ogni chiamata della ADD_ROW.
            Comunque, dato che per ogni parametro si parsa una
            volta sola questo e abbastanza dinamico e gestibile

         *********************************************************/
        function make_tags() {

                /**********************************************************
                        Se i tag non si sono - non si va avanti
                 *********************************************************/
                if(!isset($this->tag))
                        Return False;

                /**********************************************************
                        Se entrato per la prima volta si assegnano i valori
                        di default come la prima cosa (non si sa mai se ne
                        avremo abastanza tempo dopo)
                 *********************************************************/
                if(!$this->default_params)
                        $this->assign_default_tags();

                if($this->debug)
                        $time_start = getmicrotime();

                if($this->cache) {

                        if(!$this->cache_obj) {
                                $this->cache_obj = new DynaCache('DynaCombus');
                        }

                        $fname  = md5(serialize($this->tag));
                        $rc = $this->cache_obj->read($fname, $result);
                }
                else
                        $rc = True;

                if(!$rc) {
                        $this->params = $result;
                }

                else {

                        // Debug
                        if($this->debug)
                                echo "Params ::: \$this->cache_obj->read : [$rc]<br>";

                        // Loop
                        foreach($this->tag as $key=>$val) {
                                $this->current_tag = $key;
                                /**********************************************************
                                        Ci limitiamo solo con i tag che si servono
                                 *********************************************************/
                                if(!is_array($val)) {
                                        /**********************************************************
                                                Parsa e ritonaci l'array dei valori
                                         *********************************************************/
                                        $parsed_result = $this->parser($val);
                                        /**********************************************************
                                                Mischia i variabili importati
                                         *********************************************************/
                                        if($parsed_result)
                                                $this->params[$key] = @array_merge($this->params[$key], $parsed_result);
                                }
                                else {
                                        /**********************************************************
                                                Cols e Rows sono i sotto array, per cio vengolno
                                                trattati diversamente
                                         *********************************************************/
                                        foreach($val as $td_k=>$td_v) {
                                                /**********************************************************
                                                        Estrae la chiave
                                                 *********************************************************/
                                                preg_match_all("/(\d+)[^\d]*/", $td_k, $td_keys);
                                                /**********************************************************
                                                        Parsa
                                                 *********************************************************/
                                                $parsed_result = $this->parser($td_v);
                                                if($parsed_result) {
                                                        for($i=0; $i<sizeof($td_keys[1]); $i++) {
                                                                /**********************************************************
                                                                        Importa l'array
                                                                 *********************************************************/
                                                                @$this->params[$key][$td_keys[1][$i]] = array_merge($this->params[$key][$td_keys[1][$i]], $parsed_result);
                                                        }
                                                }
                                        }
                                }
                        }

                        if($this->cache)
                                $rc    = $this->cache_obj->write($fname, @$this->params, 60*5);

                        if($this->debug)
                                echo "Params ::: \$this->cache_obj->write : [$rc]<br>";
                }

                if($this->debug)
                        echo "Params ::: Timer : " . round((getmicrotime()-$time_start)*1000, 3) . "<br>";

                /**********************************************************
                        Ucidi il parametro TAG, non vogliamo rifarlo
                        ancora come se non bastasse
                 *********************************************************/
                unset($this->tag);

                Return True;
        }



        /**********************************************************

            Funzione:      display()
            Argomenti:     $array
                              array,
                              defaukt=False,
                              (array dei dati)

            Ritorno:       string (output HTML della <SELECT ***>)


            Funzione principale per visuallizare il contenuto dei
            dati nella <SELECT>. Si basa sui parametri passati
            alla DynaCombus ed e capace di importare i dati
            preformattati da se stessa.

         *********************************************************/
        function display($array=False) {

                /**********************************************************
                        Crea i tag se non sono gia creati
                 *********************************************************/
                $this->make_tags();
                /**********************************************************
                        Se entrato per la prima volta si assegnano i valori
                        di default
                 *********************************************************/
                if(!$this->default_params)
                        $this->assign_default_tags();

                /**********************************************************
                        Se i dati sono passati alla funzione, un loop imitera
                        le chiamate all add_row
                 *********************************************************/

                if(is_array($array))
                        foreach($array as $row)
                                $this->add_row($row);

                if($this->debug)
                        $time_start = getmicrotime();

                if($this->cache) {
                        if(!$this->cache_obj) {
                                $this->cache_obj = new DynaCache('DynaCombus');
                        }

                        $fname         = md5(md5(serialize($this->params)) . md5(serialize($this->tmp_rows)));
                        $rc            = $this->cache_obj->read("display_$fname", $data);
                }
                else {
                        $rc    = 1;
                }

                if(!$rc) {
                        $this->params  = $data[0];
                        $output        = $data[1];
                }
                else {

                        // Debug
                        if($this->debug)
                                echo "Data ::: \$this->cache_obj->read : [$rc]<br>";

                        $this->add_rows($this->tmp_rows);

                        /**********************************************************
                                Perfezione dei parametri DynaCombus.

                                Molti parametri verrano cambiati qua dato che non
                                tutto e possibile. Anche, per molti parametri non
                                passati qui ci verrano assegnati dei valori iniziali
                         *********************************************************/

                        /**********************************************************
                                Specifica chi tra colonne e row abbia la precedenza
                         *********************************************************/
                        if(!isset($this->params['table']['overwrite']))
                                $this->params['table']['overwrite'] = $this->default_params['table']['overwrite'];
                        else {
                                $specified = $this->params['table']['overwrite'];
                                unset($this->params['table']['overwrite']);
                                $this->params['table']['overwrite'] = Array(
                                        $specified,
                                        ($specified=='cols' ? 'rows' : 'cols')
                                );
                        }

                        /**********************************************************
                                Numero delle colonne
                         *********************************************************/
                        if(!isset($this->params['table']['columns'])) {
                                if(!$this->r) {
                                        @krsort($this->params['cols']);
                                        @reset($this->params['cols']);
                                        $this->params['table']['columns'] = @key($this->params['cols']);
                                }
                                else
                                        $this->params['table']['columns'] = $this->private_params['table']['columns'];
                        }

                        /**********************************************************
                                Aggiusta la tabella con ZeroFill
                         *********************************************************/
                        if(isset($this->params['table']['zerofill']) and $this->params['table']['zerofill']>0)
                                while($this->params['table']['height'] > $this->r)
                                        $this->add_row(Array());

                        /**********************************************************
                                Numero delle righe
                         *********************************************************/
                        if(!isset($this->params['table']['rows']))
                                $this->params['table']['rows'] = $this->r ? $this->r : 1;

                        /**********************************************************
                                Altezza della tabella
                         *********************************************************/
                        if(!isset($this->params['table']['height']))
                                $this->params['table']['height'] = $this->params['table']['rows'];



                        /**********************************************************
                                Allineamento della tabella
                         *********************************************************/
                        if(!isset($this->params['table']['align']))
                                $this->params['table']['align'] = $this->default_params['table']['align'];

                        /**********************************************************
                                I margini delle colonne
                         *********************************************************/
                        if(!@$this->params['table']['margins'])
                                $this->params['table']['margins'] = $this->default_params['table']['margins'];

                        if(!@$this->params['table']['margin_left'])
                                $this->params['table']['margin_left'] = $this->params['table']['margins'];

                        if(!@$this->params['table']['margin_right'])
                                $this->params['table']['margin_right'] = $this->params['table']['margins'];

                        /**********************************************************
                                I *VERI* valori delle margini delle colonne.

                                Il fatto e che ci sarebbe da prendere in
                                considerazione quale tra cols o rows ha la precedenza
                                per dare un valore giusto ai margins. Sono utilizzati
                                cosi come sono, quindi hanno bisogno di una
                                precisione totale
                         *********************************************************/
                        for($i=1; $i<=$this->params['table']['columns']; $i++) {

                                /**********************************************************
                                        Sinistro
                                 *********************************************************/
                                if(!@$this->params['cols'][$i]['margin_left'])
                                        $this->params['cols'][$i]['margin_left'] = @$this->params['cols'][$i]['margins'] ? $this->params['cols'][$i]['margins'] : $this->params['table']['margin_left'];

                                /**********************************************************
                                        Destro
                                 *********************************************************/
                                if(!@$this->params['cols'][$i]['margin_right'])
                                        $this->params['cols'][$i]['margin_right'] = isset($this->params['cols'][$i]['margins']) ? $this->params['cols'][$i]['margins'] : $this->params['table']['margin_right'];


                                /**********************************************************
                                        Heder
                                 *********************************************************/
                                if(!@$this->params['title'][$i]['class'])
                                        $this->params['title'][$i]['class'] = $this->default_params['title']['class'];

                                if(!@$this->params['title'][$i]['align'])
                                        $this->params['title'][$i]['align'] = $this->default_params['title']['align'];
                        }

                        if(!@$this->params['header']['align'])
                                $this->params['header']['align'] = $this->default_params['header']['align'];

                        if(!@$this->params['header']['tr_align'])
                                $this->params['header']['tr_align'] = $this->default_params['header']['tr_align'];

                        if(!@$this->params['header']['bgcolor'])
                                $this->params['header']['bgcolor'] = $this->default_params['header']['bgcolor'];

                        /**********************************************************
                                La riga preselezionata. <OPTION SELECTED>
                         *********************************************************/
                        if(!isset($this->params['table']['selected']))
                                $this->params['table']['selected'] = $this->default_params['table']['selected'];

                        /**********************************************************
                                Carattere di spazio
                         *********************************************************/
                        if(!isset($this->params['table']['spacer']))
                                $this->params['table']['spacer'] = $this->default_params['table']['spacer'];

                        /**********************************************************
                                Stile (CSS) della tabella
                         *********************************************************/
                        if(!isset($this->params['table']['style']))
                                $this->params['table']['style'] = $this->default_params['table']['style'];

                        $this->params['title'][0]['text'] = $this->params['title'][$this->params['table']['columns']+1]['text'] = $this->default_params['title']['empty'];

                        /**********************************************************
                                Crea la DynaCombus. Tutta la magia si svolge qui.
                         *********************************************************/
                        $this->Creator();

                        /**********************************************************
                                Stile SPAN per a tabella
                         *********************************************************/
                        $output  = "\n\n\n<span style=\"font-family: Courier New; {$this->params['table']['style']}\" class=\"sel\">";

                        /**********************************************************
                                Output

                                qui vengono aggiunti tutti gli atributi provenienti
                                dagli array della configurazione
                         *********************************************************/
                        $output .= sprintf(
                                 "\n<select %s size=%d %s style=\"font-family: Courier New; %s\" class=\"sel\" %s %s %s>\n\n"

                                ,isset($this->params['table']['name'])       ? "name=\"{$this->params['table']['name']}\""        : ''
                                ,isset($this->params['table']['height'])     ? $this->params['table']['height']                   : ''
                                ,isset($this->params['table']['id'])         ? "id=\"$this->params['table']['id']\""              : ''
                                ,isset($this->params['table']['style'])      ? $this->params['table']['style']                    : ''
                                ,isset($this->params['table']['multiple'])   ? "multiple"                                         : ''
                                ,isset($this->params['table']['disabled'])   ? "disabled"                                         : ''
                                ,isset($this->params['table']['add'])        ? $this->params['table']['add']                      : ''
                        );

                        /**********************************************************
                                Output

                                La compressione degli spazi.
                         *********************************************************/
                        $output .= str_replace('  ', ' &nbsp;', str_replace(' <', '&nbsp;<', $this->output)) . "\n\n\n";
                        $output .= "\n\n</select>";
                        $output .= "\n</span>\n\n\n";

                        if($this->cache) {
                                $rc    = $this->cache_obj->write("display_$fname", Array($this->params, $output), 60*5);
                        }

                        if($this->debug)
                                echo "Data ::: \$this->cache_obj->write : [$rc]<br>";
                }

                if($this->debug)
                        echo "Data ::: Timer : " . round((getmicrotime()-$time_start)*1000, 3) . "<br>";

                /**********************************************************
                        Ritorna l'HTML. Arrivederci e grazie :-)
                 *********************************************************/
                $this->display = $output;
                Return $this->display;
        }


        /**********************************************************

            Funzione:      header()
            Argomenti:     none

            Ritorno:       array


            Calcola le percentuali delle collonne rispetto alla
            largezza di dynacombo

         *********************************************************/
        function header($array=False) {

                $size = 7;

                if(!strlen($this->display))
                        $this->display($array);

                if($this->debug)
                        $time_start = getmicrotime();

                if($this->cache) {
                        if(!$this->cache_obj) {
                                $this->cache_obj = new DynaCache('DynaCombus');
                        }

                        $fname         = md5(md5(serialize($this->params)) . md5(serialize($this->tmp_rows)));
                        $rc            = $this->cache_obj->read("header_$fname", $output);
                }
                else {
                        $rc    = 1;
                }

                if($rc) {

                        // Debug
                        if($this->debug)
                                echo "Header ::: \$this->cache_obj->read : [$rc]<br>";


                        $this->header = Array();

                        for($this->cols=1; $this->cols<=$this->params['table']['columns']; $this->cols++) {
                                $this->header[$this->cols] = round(($this->params['cols'][$this->cols]['total']*$size), 0);
                        }

                        $this->header[0]                                   = 2;
                        $this->header[$this->params['table']['columns']+1] = 19;
                        $this->header['tot']                               = array_sum($this->header)-5;

                        $output['start'] = sprintf(
                                 "\n<table border=0 align='%s' cellpadding=0 cellspacing=0 width=%d %s %s %s %s>\n"
                                ."        <tr %s %s>\n"

                                ,$this->params['header']['align']
                                ,$this->header['tot']
                                ,isset($this->params['header']['class'])    ? "class='{$this->params['header']['class']}'"       : ''
                                ,isset($this->params['header']['style'])    ? "style='{$this->params['header']['style']}'"       : ''
                                ,isset($this->params['header']['id'])       ? "id='{$this->params['header']['id']}'"             : ''
                                ,isset($this->params['header']['add'])      ? "add='{$this->params['header']['add']}'"           : ''
                                ,isset($this->params['header']['tr_align']) ? "align='{$this->params['header']['tr_align']}'"    : ''
                                ,isset($this->params['header']['bgcolor'])  ? "bgcolor='{$this->params['header']['bgcolor']}'"   : ''
                        );

                        for($h=0; $h<$this->params['table']['columns']+2; $h++) {
                                $null = (($h==0 or $h==$this->params['table']['columns']+1) or !@strlen($this->params['title'][$h]['text']))? True : False;

                                $output['start'] .= sprintf(
                                         "                <td %s %s %s width=%d align='%s' %s %s %s>%s</td>\n"
                                        ,$null                                                   ? "style='font-size:1px;'"                         : ''
                                        ,(isset($this->params['title'][$h]['class']) and !$null) ? "class='{$this->params['title'][$h]['class']}'"  : ''
                                        ,(isset($this->params['title'][$h]['style']) and !$null) ? "style='{$this->params['title'][$h]['style']}'"  : ''
                                        ,$this->header[$h]
                                        ,(!$null)? $this->params['title'][$h]['align']                                                              : ''
                                        ,isset($this->params['title'][$h]['wrap'])               ? 'wrap'                                           : ''
                                        ,isset($this->params['title'][$h]['nowrap'])             ? 'nowrap'                                         : ''
                                        ,isset($this->params['title'][$h]['add'])                ? $this->params['title'][$h]['add']                : ''
                                        ,@strlen($this->params['title'][$h]['text'])             ? $this->params['title'][$h]['text']               : $this->params['title'][0]['text']
                                );
                        }

                        $output['start'] .= "        </tr>\n";
                        $output['start'] .= "        <tr valign='top' align='left'>\n";
                        $output['start'] .= "                <td colspan=" . ($this->params['table']['columns']+2) . ">";

                        $output['end']    = "</td>\n";
                        $output['end']   .= "        </tr>\n";
                        $output['end']   .= "</table>\n\n";

                        if($this->cache) {
                                $rc    = $this->cache_obj->write("header_$fname", $output, 60*5);
                        }

                        if($this->debug)
                                echo "Header ::: \$this->cache_obj->write : [$rc]<br>";
                }

                if($this->debug)
                        echo "Header ::: Timer : " . round((getmicrotime()-$time_start)*1000, 3) . "<br>";

                Return $output['start'] . $this->display . $output['end'];
        }
}



/**********************************************************
        Esempio di una chiamata:


require_once('./include/DynaCombus.inc.php');

        function nomi() {
                Return Array(

                         Array(
                                 'nome'        => 'Maxim'
                                ,'cognome'     => 'Maletsky'
                                ,'email'       => 'maxim@php.net'
                                ,'indirizzo'   => 'via Augusto Armellini'
                                ,'citta'       => 'Roma'
                                ,'paese'       => 'Italia'
                        )

                        ,Array(
                                 'nome'        => 'Marco'
                                ,'cognome'     => 'Trovini'
                                ,'email'       => 'marco@non.so'
                                ,'indirizzo'   => 'via Cissadove'
                                ,'citta'       => 'Aprilia'
                                ,'paese'       => 'Italia'
                        )

                        ,Array(
                                 'nome'        => 'Alessandra'
                                ,'cognome'     => 'Rossi'
                                ,'email'       => 'non@si.sa'
                                ,'indirizzo'   => 'Via Dondesta'
                                ,'citta'       => 'Roma'
                                ,'paese'       => 'Italia'
                        )
                );
        }


        $DC = new DC;

        $DC->tag['table']  = 'name="nomi" height="13" border="2" columns="6" add="onChange=\'window.status = this.options[this.selectedIndex].text;\'"';

        // cols:
        $DC->tag['cols']['1,2 | 4,5']  = 'width="10" align="center"';
        $DC->tag['cols']['3']          = 'width="16"';
        $DC->tag['cols']['4,5']        = 'align="right"';
        $DC->tag['cols']['6']          = 'width="8" align="left" margin-right="2"';

        foreach(nomi() as $key=>$val) {

                // Sciegliamoci una chiave.
                // Composta dal NOME e COGNOME con striscetta come il separatore
                $chiave = $val['nome'] . '-' . $val['cognome'];

                $DC->add_row(
                        Array(
                                 $chiave
                                ,$val['nome']
                                ,$val['cognome']
                                ,$val['email']
                                ,$val['indirizzo']
                                ,$val['citta']
                                ,$val['paese']
                        )
                );
                $s++;

                // controllo di riga selezionata
                if(!$selected and $UnaCondizione == True) {
                        $selected = $s;
                }
        }

        // Aggiungera il colore verde per lo sfondo, colore bianco per il testo
        $DC_prot->tag['rows'][$selected]  = 'style="color:#ffffff; weight:900; background-color:#00CC00;"';

        // La riga numerata $selected sara selezionata con <OPTION SELECTED>
        $DC_dett->tag['rows'][$selected]  = 'selected="1"';


        echo "<form method='GET' action='$_SERVER['PHP_SELF']'>\n";

        echo "        <tr valign='top'>\n";

        echo "                <td>\n";
        echo                        $DC->header();
        echo "                </td>\n";
        echo "        </tr>";

        echo "        <tr valign='top'>\n";
        echo "                <td  colspan=6>\n";
        echo "                        <input type='submit' name='   ok   ' value='Submit Combo'>\n";
        echo "                </td>\n";
        echo "        </tr>\n";

        echo "</table>\n";
        echo "</form>\n";

 *********************************************************/
?>