Witaj Gościu! ( Zaloguj | Rejestruj )

Forum PHP.pl

> Klasa tpl, i parsowanie {SECTION} od smarty'iego
radziel
post
Post #1





Grupa: Zarejestrowani
Postów: 103
Pomógł: 0
Dołączył: 25.04.2003
Skąd: Olsztyn

Ostrzeżenie: (0%)
-----


Napisałem sobie na własny użytek taką oto klase do obsługi szablonów (jako alternatywe dla Smarty, gdyż on baaaardzo opóźnia mój skrypt(tak bylo pod PHP4) i nie dziala pod PHP5 :/)

[php:1:7869633014]<?php
class template
{
var $parsed;
var $unparse;
var $blocks;

var $dir;

function __construct($dir)
{
$this->_setDir($dir);
}

function _setDir($dir)
{
if (is_dir($dir))
{
$this-> dir = $dir;
return true;
}
else
{
die("[TEMPLATE]Root dir no exists!");
}
}
function Assign($var, $value=null)
{
if(is_array($var))
{
reset($var);
foreach ($var as $name => $val)
{
$this -> blocks[$name] = $val;
}
}
else
{
$this -> blocks[$var] = $value;
}
}

function Display($file)
{
$this -> unparse = @file($dir . $file . '.tpl');
echo $this -> _parse();
}

function _parse()
{
$this -> parse = '';
for ($i=0; $i<= count($this->unparse); $i++)
{
$line = $this -> unparse[$i];
$found = array();

if(preg_match_all("#{(.+?)}#is", $line, $found))
{
foreach ($found[1] as $block)
{
$block_names[]='{'.$block.'}';
$block_values[] = $this -> blocks[$block];
}
$line = str_replace($block_names, $block_values, $line);
}

$this -> parsed .= $line;
}
unset($this->unparse);
return $this -> parsed;
}
function _parseSectionTag()
{
// e? co tu napisac?
}


}
?>[/php:1:7869633014]

Jak już pewnie niektórzy zauważyli jest to modyfikacja kodu ze strony Webcity.pl Dodalem pare rzeczy, usunełem niepotrzebne ale...
Mam problem ze znacznikiem {SECTION}{SECTION} uzywam go bardzo czesto więc musze napisać odpowiedni parser dla niego...

Kompletnie nie wiem jak za to się zabrać... Przykladowy tpl:
Kod
<table border="1">

  {section name=config_value loop=$data}

    <tr>

      <td>{$data[config_value].name}</td>

      <td>{$data[config_value].value}</td>

    </tr>

  {/section}

</table>


Składnia jest taka sama jak u smartiego...
Przeglądałem kod SMARTY'iego, ale nie mogę wyciągnąć funcji za to odpowiedzialnej... strasznie zakręcone to wszystko :/

Ma ktoś pomysł jak to rozwiązać? Niech rzuci kodem, albo niech da jakas wskazówke (IMG:http://forum.php.pl/style_emoticons/default/tongue.gif)
Go to the top of the page
+Quote Post
 
Start new topic
Odpowiedzi (1 - 10)
Bora
post
Post #2





Grupa: Zarejestrowani
Postów: 270
Pomógł: 0
Dołączył: 15.06.2003

Ostrzeżenie: (0%)
-----


kiedyś napisałem coś takiego:

[php:1:7d21b2379c]<?php
class template
{
var $file;
var $inc = array("default" => "");
var $blocks = array("default" => "");
var $moduls = array("default" => "");
function load($file){
$file = "pages/".$_SESSION['page']."/templates/".$file.".tpl";
if(file_exists($file)){
$plik = fopen($file, 'r');
$unparsed = fread($plik, filesize($file));
fclose($plik);
}else{
die("brak pliku $file");
}
// wylapuje moduły
preg_match_all( "#[INCLUDE:(.+?)]#is", $unparsed, $include);
$unparsed = preg_replace("#[INCLUDE:(.+?)]#is","{INCLUDE:$1}", $unparsed);
$unparsed = str_replace("n", "|ent|", $unparsed);
preg_match_all( '/[MODUL.*](.+)[/MODUL.*]/Uise', $unparsed, $znalezione);
// zamienia moduły na ich odpowiedniki
$unparsed =
preg_replace('/[MODUL:(.*?)](.*?)[/MODUL:(.*?)]/i','{MODUL:$1}',
$unparsed);
$unparsed = str_replace("|ent|", "n", $unparsed);
$znalezione[0] = str_replace("|ent|", "n", $znalezione[0]);
$znalezione[1] = str_replace("|ent|", "n", $znalezione[1]);
$mod = array();
foreach ($znalezione[0] as $i_parser){
preg_match("/[MODUL:(.*?)]/i",$i_parser, $znal);
$pref = $znal[1];
$m = preg_replace('/[MODUL:(.*?)]/i','', $i_parser);
$m = preg_replace('/[/MODUL:(.*?)]/i','', $m);
$mod["$pref"]=$m;
}
// wyłapuje include i wstawia pliki
foreach ($include[0] as $i_parser){
preg_match("/[INCLUDE:(.*?)]/i",$i_parser, $znal);
$in = preg_replace("#[INCLUDE:(.+?)]#is","$1", $i_parser);
$pref = $znal[1];
$prefix = $znal[1];
$pref = "templates/".$pref.".tpl";
if(file_exists($pref)){
$plik = fopen($pref, 'r');
$files = fread($plik, filesize($pref));
$unparsed = str_replace('{INCLUDE:'.$prefix.'}',$files, $unparsed);
fclose($plik);
}else{
die("brak pliku $pref");
}
}
$this -> moduls = $znalezione[1];
$this -> mods = $mod;
$this -> unparsed = $unparsed;
return true;
}
function parse($unparsed,$blocks = array()){
if(preg_match_all('#{(.+?)}#is', $unparsed, $found)){
$parsed = $unparsed;
foreach($found[1] as $block){
// var_dump($block);
// var_dump($blocks);
$parsed = str_replace('{'.$block.'}', $blocks[$block], $parsed);
}
}
return $parsed;
}
}
class modul
{
var $file;
var $mod;
var $blocks = array("default" => "");
var $moduls = array("default" => "");
function parse($unparsed,$blocks = array()){
if(preg_match_all('#{(.+?)}#is', $unparsed, $found)){
$parsed = $unparsed;
foreach($found[1] as $block){
$parsed = str_replace('{'.$block.'}', $blocks[$block], $parsed);
}
}
return $parsed;
}
}
?>[/php:1:7d21b2379c]

[xml:1:7d21b2379c]<!--- [MODUL:koment] dolna czesc-->
<tr>
<td class="forum1">
autor:{koment:autor} - {koment:kasuj} - data:{koment:data}
<br>
{koment:tresc}
<br>
{koment:ip} - {koment:host}
</td>
</tr>
<!--- [/MODUL:koment] dolna czesc-->[/xml:1:7d21b2379c]


może ci sie przyda

update to jest bardzo stary kod i juz nie pammiętam jak działał. ale patrząc w zródło stronki jest strasznie zawiłe.

* * * * * * * * * * * * * * * * * * *
Post nr: [100] (IMG:http://forum.php.pl/style_emoticons/default/smile.gif) trza to oblać (IMG:http://forum.php.pl/style_emoticons/default/smile.gif)
Go to the top of the page
+Quote Post
radziel
post
Post #3





Grupa: Zarejestrowani
Postów: 103
Pomógł: 0
Dołączył: 25.04.2003
Skąd: Olsztyn

Ostrzeżenie: (0%)
-----


Hm... ciekawe...

Ma może ktoś jeszcze jakieś pomysły?
Go to the top of the page
+Quote Post
Bora
post
Post #4





Grupa: Zarejestrowani
Postów: 270
Pomógł: 0
Dołączył: 15.06.2003

Ostrzeżenie: (0%)
-----


jesatem w trakcie pisana niedługo dam gotową klase
Go to the top of the page
+Quote Post
gulldarek
post
Post #5





Grupa: Zarejestrowani
Postów: 156
Pomógł: 15
Dołączył: 13.09.2003
Skąd: London

Ostrzeżenie: (0%)
-----


Bora: nie wiem czy widziałeś kod z vbulletina któy wkleiłem do mojego wątku o szablonach. Może się przydać (IMG:http://forum.php.pl/style_emoticons/default/smile.gif)

Ps. Daj znać jak ją skończysz (IMG:http://forum.php.pl/style_emoticons/default/winksmiley.jpg)
Go to the top of the page
+Quote Post
Bora
post
Post #6





Grupa: Zarejestrowani
Postów: 270
Pomógł: 0
Dołączył: 15.06.2003

Ostrzeżenie: (0%)
-----


Napiałem radzi sobie narazie tylko z 1 subsekcją , próbowałem z zagnieżdżonymi ale narazie nie wychodzi.

[php:1:94a80b8b43]<?php
class template
{
var $parsed;
var $unparse;
var $blocks;
var $lines;

var $dir;

//function __construct($dir)
function template($dir)
{
$this->_setDir($dir);
}

function _setDir($dir)
{
if (is_dir($dir))
{
$this-> dir = $dir;
return true;
}
else
{
die("[TEMPLATE]Root dir no exists!");
}
}
function Assign($var, $value=null)
{
if (strstr($var, '.') )
{
$var = explode('.',$var);
for ($i=0;$i<count($value);++$i)
{
$this -> blocks[$var['0']][$i][$var['1']] = $value;
}
}else{
$this -> blocks[$var] = $value;
}
}

function Display($file)
{
$this -> unparse = file($dir . $file . '.tpl');
$fh = fopen($dir . $file . '.tpl', "r");
$this -> unparse = chop(fread($fh, filesize($dir . $file . '.tpl')));
$i=0;
while ( ereg( '{section name', $this->unparse) )
{
$this -> _parseTab();
++$i;
if ($i>6){exit('za dluga petla');}
}
$this -> unparse = $this->_parse($this -> unparse);
echo $this -> unparse ;
}

function _parseTab()
{
$line = $this -> unparse;
preg_match( '/{section name=(.+?)}(.*){/section}/is', $line, $found);
$line = preg_replace( '/{section name=(.*)}(.+){/section}/is',
$this->_parse_intab($found['2'],$this->blocks[$found['1']]['0'],$found['1'])
,$line);
$line = str_replace('{tmp}', '', $line);
$this->unparse = $line;
return false;
}


function _parse($line)
{
$found = array();

if(preg_match_all("#{(.+?)}#is", $line, $found))
{
foreach ($found['1'] as $block)
{
$block = str_replace('$', '', $block);
$block_names='{$'.$block.'}';
$block_values = $this -> blocks[$block];
$line = str_replace($block_names, $block_values, $line);
}
$line = str_replace($block_names, $block_values, $line);
}
return $line;
}

function _parse_intab($line,$val,$mod)
{

$found = array();
$count_var = count($val);
if(preg_match_all("#{[$]{$mod}[.](.+?)}#is", $line, $found))
{
foreach ($found['1'] as $block)
{
$block_mod = $block['0'];
$block_names='{$'.$mod.".".$block.'}';
$block_values = $this->blocks[$mod]['0'][$block]['0'];
if (!empty($lines))
{
$lines=explode('{tmp}',$lines);
for ($i=0;$i<$count_var;++$i)
{
$lines[$i] = str_replace($block_names, $block_values[$i], $lines[$i]);
}
$lines=implode('{tmp}',$lines);
}else{
for ($i=0;$i<$count_var;++$i)
{
$lines[$i] = str_replace($block_names,
$block_values[$i], $line);

}
$lines=implode('{tmp}',$lines);
}
}
}
return $lines;
}
}
?>[/php:1:94a80b8b43]


Kod
test Parsera - {$tpl}-

<table border="1">

  {section name=config_value}

    <tr>

      <td>[{$config_value.name}]</td>

      <td>[{$config_value.value}]</td>

    </tr>

  {/section}



</table>


[php:1:94a80b8b43]<?php
include('tpl_class.php');
$tpl= new template('.');
$tpl->Assign("config_value.id",array('aaa1i','bbbb2i','cccc3i'));
$tpl->Assign("config_value.name",array(array('aaa1n','bbbb2n','cccc3n')));
$tpl->Assign("config_value.value",array(array('aaa1v','bbbb2v','cccc3v')));
$tpl->Assign("config_test.name",array(array('configa1v','configb2v','configc3v')));
$tpl->Assign('tpl','templates');
$tpl = $tpl->Display('tpl');
?>[/php:1:94a80b8b43]

UPDATE

wersja poprawiona
Go to the top of the page
+Quote Post
gulldarek
post
Post #7





Grupa: Zarejestrowani
Postów: 156
Pomógł: 15
Dołączył: 13.09.2003
Skąd: London

Ostrzeżenie: (0%)
-----


Bora: teraz przydalaby sie eszcze funkcja do parsowania <if>'ow...
Go to the top of the page
+Quote Post
radziel
post
Post #8





Grupa: Zarejestrowani
Postów: 103
Pomógł: 0
Dołączył: 25.04.2003
Skąd: Olsztyn

Ostrzeżenie: (0%)
-----


Bora: nieco musisz zmodyfikowac te parsowanie sectionów
Kod
<table border="1">

  {section name=config_value loop=$data}

    <tr>

      <td>{$data[config_value].name}</td>

      <td>{$data[config_value].value}</td>

    </tr>

  {/section}

</table>


powininieneś w assign podawać tylko assign($data), parser sam powinien podstawic (jezeli to tablica) odpowiednie wartości za $data[config_value].name i $data[config_value].value...

Te dane w tych kwadratowych nawiasach to info ze ta zmienna nalezy do sekcji config_value.

Przydałoby się jeszcze aby parsował loop i tyle razy powtarzał ten kod ile ma $data tych "indexów" w sobie.. to by oszczedziło nieco czasu przy zmianie klas ze smarty na tą...

Sorry ze tak pisze jak dla lamera, ale chce zeby tez poczatkujacy to zrozumieli (IMG:http://forum.php.pl/style_emoticons/default/smile.gif)

Czekam az beda dzialac zagnieżdzone sectiony (IMG:http://forum.php.pl/style_emoticons/default/winksmiley.jpg) Dobrze sie zapowiada (IMG:http://forum.php.pl/style_emoticons/default/smile.gif)
Go to the top of the page
+Quote Post
Bora
post
Post #9





Grupa: Zarejestrowani
Postów: 270
Pomógł: 0
Dołączył: 15.06.2003

Ostrzeżenie: (0%)
-----


teraz męcze sie z wyrażniem regularnym , które mnie przerasta

mam coś takiego:
Kod
{section name=config_value}

    <tr>

      <td>[{$config_value.name}]</td>

      <td>[{$config_value.value}]</td>

    </tr>

    {section name=config_test}[[{$config_test.name}]]{/section}

  {/section}

licze ilosc otwartych subsekcji
[php:1:17fb8f4b41]<?php
substr_count($found['0'], '{section name');
?>[/php:1:17fb8f4b41]
i teraz zaczyna sei jazda , chce wyciągnąć z tego stringa który kończyłby sie po zamknięciu ostatniej otwartej subsekcji czyli w tym przypadku po 2gim
Kod
{/section}


UPDATE
powyższy kod poprawiony[/code]
Go to the top of the page
+Quote Post
Bora
post
Post #10





Grupa: Zarejestrowani
Postów: 270
Pomógł: 0
Dołączył: 15.06.2003

Ostrzeżenie: (0%)
-----


Tak jak chciałęś radziel Assign jak w smarty co do sposobu czytania z tpl zostawiam to na pozniej jak juz bede miał gotowe wyrażenie.


[php:1:a29cc6a01f]<?php
include('tpl_class.php');
$tpl= new template('.');
$tpl->Assign("config_test",array(array('configa1v','configb2v','configc3v')));
$tpl->Assign("config_value",array('name'=>array('aaa1n','bbbb2n','cccc3n'),'value'=>array('aaa1v','bbbb2v','cccc3v')));
$tpl->Assign('tpl','templates');
$tpl = $tpl->Display('tpl');
?>[/php:1:a29cc6a01f]

Kod
test Parsera - {$tpl}-

<table border="1">

  {section name=config_value}

    <tr>

      <td>[{$config_value.name}]</td>

      <td>[{$config_value.value}]</td>

    </tr>



  {/section}

</table>



[php:1:a29cc6a01f]<?php
class template
{
var $parsed;
var $unparse;
var $blocks;

var $dir;

//function __construct($dir)
function template($dir)
{
$this->_setDir($dir);
}

function _setDir($dir)
{
if (is_dir($dir))
{
$this-> dir = $dir;
return true;
}
else
{
die("[TEMPLATE]Root dir no exists!");
}
}
function Assign($var, $value=null)
{
if (is_array($value))
{
$wymiar=count($value);
if ($wymiar==1)
{
foreach ($value as $val)
{
$this -> blocks[$var] = $val;
}
}else{
$klucze = array_keys($value);
foreach ($klucze as $klucz)
{
foreach ($value[$klucz] as $val)
{
$this -> blocks[$var][$klucz][] = $val;
}
}
}
}else{
$this -> blocks[$var] = $value;
}
}

function Display($file)
{
$this -> unparse = file($dir . $file . '.tpl');
$fh = fopen($dir . $file . '.tpl', "r");
$this -> unparse = chop(fread($fh, filesize($dir . $file . '.tpl')));
$i=0;
while ( ereg( '{section name', $this->unparse) )
{
$this -> _parseTab();
++$i;
if ($i>6){exit('za dluga petla');}
}
$this -> unparse = $this->_parse($this -> unparse);
echo $this -> unparse ;
}

function _parseTab()
{
$line = $this -> unparse;
preg_match( '/{section name=(.+?)}(.*){/section}/is', $line, $found);
$line = preg_replace( '/{section name=(.*)}(.+){/section}/is', $this->_parse_intab($found['2'],$this->blocks[$found['1']]['0'],$found['1']),$line);
$line = str_replace('{tmp}', '', $line);
$this->unparse = $line;
return false;
}


function _parse($line)
{
$found = array();

if(preg_match_all("#{(.+?)}#is", $line, $found))
{
foreach ($found['1'] as $block)
{
$block = str_replace('$', '', $block);
$block_names='{$'.$block.'}';
$block_values = $this -> blocks[$block];
$line = str_replace($block_names, $block_values, $line);
}
$line = str_replace($block_names, $block_values, $line);
}
return $line;
}

function _parse_intab($line,$val,$mod)
{

$found = array();

if(preg_match_all("#{[$]{$mod}[.](.+?)}#is", $line, $found))
{
foreach ($found['1'] as $block)
{
$block_names='{$'.$mod.".".$block.'}';
$block_values = $this->blocks[$mod][$block];
$count_var = count($this->blocks[$mod][$block]);
if (!empty($lines))
{
$lines=explode('{tmp}',$lines);
for ($i=0;$i<$count_var;++$i)
{
$lines[$i] = str_replace($block_names, $block_values[$i], $lines[$i]);
}
$lines=implode('{tmp}',$lines);
}else{
for ($i=0;$i<$count_var;++$i)
{
$lines[$i] = str_replace($block_names, $block_values[$i], $line);

}
$lines=implode('{tmp}',$lines);
}
}
}
return $lines;
}
}

?>[/php:1:a29cc6a01f]
Go to the top of the page
+Quote Post
radziel
post
Post #11





Grupa: Zarejestrowani
Postów: 103
Pomógł: 0
Dołączył: 25.04.2003
Skąd: Olsztyn

Ostrzeżenie: (0%)
-----


Jako że temat dotyczy powyższego, postanowiłem napisać w tymże temacie (IMG:http://forum.php.pl/style_emoticons/default/winksmiley.jpg)

Problem:
Powiedzmy dostaję zmienną o wartości "{$data[testowa].name}" a chce przekształcić ten string na "$data['name']" wie ktoś jak to zrobic? Nie mogę wyrazenia ułożyć - to moja słaba strona (IMG:http://forum.php.pl/style_emoticons/default/sad.gif)
Go to the top of the page
+Quote Post

Reply to this topicStart new topic
2 Użytkowników czyta ten temat (2 Gości i 0 Anonimowych użytkowników)
0 Zarejestrowanych:

 



RSS Aktualny czas: 24.08.2025 - 19:52