Hanut сказал:Приведите пример. Не смог понять.
Вообще для начала: то что я делаю - мини парсер шаблонов. Он мне не столько для пользования, сколько для понимания сути работы регулярных выражений и самих шаблонизаторов (я помню Вы мне советовали не писать свой шаблонизатор в виду того, что это долго, но у меня времени куча, могу хоть 5 лет писать
) Поэтому вот код:
Сам класс шаблонизатора:
<?php
Class Template {
public $PAGE;
public $HREF;
public $DOCTYPE;
public $META;
public $SCRIPTS;
public $CSS;
public $tags_array = array();
public $active_temp;
function __construct() {
if(isset($_COOCKIE['templates'])) {
$this->active_temp = $_COOCKIE['templates'];
} else {
$this->active_temp = "default";
}
$this->tags_array = array(
"{{USER_NAME}}" => $_SESSION['user_name'],
"{{USER_id}}" => $_SESSION['user_id'],
"{{USER_IMAGE}}" => "<img alt='{USER_ID}' src='users/{USER_ID}/images/avatar.jpeg' class='user_image'>",
"{{HEAD}}" => file_get_contents(GLOBAL_TEMPLATE_DIR . $this->active_temp . "/head.tpl"),
"{{AJAX}}" => file_get_contents(GLOBAL_TEMPLATE_DIR . $this->active_temp . "/ajax.script"),
"{{LOGIN_FORM}}" => file_get_contents(GLOBAL_TEMPLATE_DIR . $this->active_temp . "/login.tpl"),
);
}
private function findTags($page) {
if(preg_match_all('/\{\{(.+?)\}\}/i',$page,$matches,PREG_SET_ORDER) != 0 ) {
return true;
} else {
return false;
}
}
private function parseTags($page) {
$areTAGS = true;
while($areTAGS == TRUE) {
if(preg_match_all('/\{\{(?!if)(.+?)\}\}/i',$page,$matches,PREG_SET_ORDER) != 0 ) {
$page = strtr($page, $this->tags_array);
} else {
$areTAGS = false;
}
}
return $page;
}
private function findLogic($page) {
if(preg_match_all('/\{\[if\s(.+?)\]\}(.+?)\{\[else\]\}(.+?)\{\[endif\]\}/i',$page,$matches,PREG_SET_ORDER) != 0) {
return $matches;
} else {
return false;
}
}
private function parseLogic($page,$logic) {
$content = '';
preg_match_all('/([^\}]*)\{\[if\s(.+?)\]\}(.+?)\{\[else\]\}(.+?)\{\[endif\]\}/i',$page,$matches,PREG_SET_ORDER);
$content = $content . $matches[0][1];
foreach ($logic as $value) {
switch ($value[2]) {
case "LOGGEDIN":
if($VARS['LOGGEDIN']) {
$content = $content . $value[3];
} else {
$content = $content . $value[4];
}
break;
case "ADMIN":
if($VARS['ADMIN']) {
$content = $content . $value[3];
} else {
$content = $content . $value[4];
}
break;
}
}
return $content;
}
public function parseTpl($page) {
$begin = $this->get_real_time();
$toParse = true;
while($toParse) {
$tags = $this->findTags($page);
if($tags) {
$page = $this->parseTags($page);
}
$logic = $this->findLogic($page);
if($logic) {
$page = $this->parseLogic($page,$logic);
}
if($tags == false && $logic == false) {
$toParse = false;
}
}
$end = $this->get_real_time() - $begin;
$page = "<!-- HPEngine --> \n" . $page . " \n<!-- Страница сгенерирована за $end секунд -->";
return "$page";
}
private function set_in_place($content) {
echo $content;
}
public function loadPage($ajax) {
if($ajax) {
$content = file_get_contents(GLOBAL_TEMPLATE_DIR . $this->active_temp . '/' . $this->HREF . '.tpl');
$content = $this->parseTpl($content);
$this->set_in_place($content);
} else {
$CONTENT = <<<CONTENT
$this->DOCTYPE
<html>
<head>
$this->META
$this->SCRIPTS
{{HEAD}}
</head>
<body>
$this->PAGE
</body>
</html>
CONTENT;
$page = $this->parseTpl($CONTENT);
echo $page;
}
}
public function get_real_time() {
list ( $seconds, $microSeconds ) = explode( ' ', microtime() );
return (( float ) $seconds + ( float ) $microSeconds);
}
}
?>
Часть engine.php
<?php
$MYSQL = new Mysql;
$TEMPLATE = new Template;
$PARSER = new Parser;
$TEMPLATE->HREF = $page;
$SCRIPTS = "<script type='text/javascript'>\nvar JavaScriptFilesList = {";
$dir = ROOT_DIR . "engine/javascript";
$SCRIPTS .= searchFiles($dir,'*.js');
$dir = ROOT_DIR . "templates/" . $TEMPLATE->active_temp . "/javascript";
$SCRIPTS .= searchFiles($dir,'*.js');
$dir = ROOT_DIR . "templates/" . $TEMPLATE->active_temp . "/javascript/" . $TEMPLATE->HREF;
$SCRIPTS .= searchFiles($dir,'*.js');
$SCRIPTS = $SCRIPTS . "\n}\n";
$CSS = "\nvar CSSFilesList = {";
$dir = ROOT_DIR . "templates/" . $TEMPLATE->active_temp . "/css/" . $TEMPLATE->HREF;
$CSS .= searchFiles($dir,'*.css');
$dir = ROOT_DIR . "templates/" . $TEMPLATE->active_temp . "/css";
$CSS .= searchFiles($dir,'*.css');
$SCRIPTS .= $CSS;
$SCRIPTS = $SCRIPTS . "\n}\n" . file_get_contents(GLOBAL_ENGINE_DIR . "javascript/global/dynamicLoad") . "\n</script>";
$PAGECONTENT = file_get_contents(GLOBAL_TEMPLATE_DIR . $TEMPLATE->active_temp . '/' . $TEMPLATE->HREF . '.tpl');
$TEMPLATE->PAGE = $PAGECONTENT;
$TEMPLATE->SCRIPTS = $SCRIPTS;
?>
index.php (часть)
<?php
$TEMLATE->HREF = 'admin'; // допустим
$TEMPLATE->loadPage(false);
?>
Класс db и functions.php приводить смысла нет, так как там все понятно.
В коде класса есть функция parseLogic() Она состоит из 2х частей: 1) отбирает контент до начала логики, 2) парсит логику. Возьмем, к примеру, страницу входа в админпанель. Вот admin.tpl:
<a href="http://www.haprog.com">
<img alt="HAPROG" src="/templates/default/images/logo.png" class="logo">
</a>
<div class="block round">
<fieldset>
<legend class="block_header">
Вход в админпанель
</legend>
<div class="container">
<form id="admin_login">
<input type="text" placeholder="login" name="login" class="round"><br>
<input type="password" placeholder="mypassword" name="password" class="round"><br>
<button class="button" onclick="logMe(admin_login); return false;">Войти</button>
</form>
</div>
</fieldset>
<div id="preview">
</div>
</div>
{[if ADMIN]}text{[else]}text{[endif]}
В итоге, если страница должна быть такая:
<!-- HPEngine -->
<!DOCTYPE>
<html>
<head>
<meta charset=>
<meta author=>
<script type='text/javascript'>
var JavaScriptFilesList = {
'ajax.js' : 'engine/javascript/',
'engine.js' : 'engine/javascript/',
'common.js' : 'templates/default/javascript/',
}
var CSSFilesList = {
'common.css' : 'templates/default/css/',
}
function dynamicLoad(filesToLoad) {
var i = 0;
var fileRef = new Array();
var fName = new Array();
for(var key in filesToLoad) {
var fileType = key.substr(-2);
var fileName = key;
var fileSRC = filesToLoad[key];
if(fileType=="js") {
fileRef[i] = document.createElement('script');
fileRef[i].setAttribute("type","text/javascript");
fileRef[i].setAttribute("src", fileSRC + fileName);
fName[i] = fileName;
} else if(fileType=="ss") {
fileRef[i]=document.createElement("link");
fileRef[i].setAttribute("rel", "stylesheet");
fileRef[i].setAttribute("type", "text/css");
fileRef[i].setAttribute("href", fileSRC + fileName);
fName[i] = fileName;
}
if (typeof fileRef[i]!="undefined") {
document.getElementsByTagName("head")[0].appendChild(fileRef[i]);
};
i = i + 1;
};
for (i = 0; i<fileRef.length; i++) {
setCallbacks(fileRef[i], fName[i]);
};
}
function setCallbacks(fileRef, fName) {
fileRef.onload = function() {
console.log(fName + " loaded successfully");
}
fileRef.onerror = function() {
console.log("Some error occurred with loading " +fName);
};
}
dynamicLoad(CSSFilesList);
dynamicLoad(JavaScriptFilesList);
</script>
<!-- Вывод пользовательской части тега <HEAD> (например, скрипты с внешних ресурсов и скрипты не входящие в список файлов-->
</head>
<body>
<a href="http://www.haprog.com">
<img alt="HAPROG" src="/templates/default/images/logo.png" class="logo">
</a>
<div class="block round">
<fieldset>
<legend class="block_header">
Вход в админпанель
</legend>
<div class="container">
<form id="admin_login">
<input type="text" placeholder="login" name="login" class="round"><br>
<input type="password" placeholder="mypassword" name="password" class="round"><br>
<button class="button" onclick="logMe(admin_login); return false;">Войти</button>
</form>
</div>
</fieldset>
<div id="preview">
</div>
</div>
text
</body>
</html>
<!-- Страница сгенерирована за 0.00069880485534668 секунд -->
Скрипт ее выводит такой:
<!-- HPEngine -->
dynamicLoad(CSSFilesList);
dynamicLoad(JavaScriptFilesList);
</script>
<!-- Вывод пользовательской части тега <HEAD> (например, скрипты с внешних ресурсов и скрипты не входящие в список файлов-->
</head>
<body>
<a href="http://www.haprog.com">
<img alt="HAPROG" src="/templates/default/images/logo.png" class="logo">
</a>
<div class="block round">
<fieldset>
<legend class="block_header">
Вход в админпанель
</legend>
<div class="container">
<form id="admin_login">
<input type="text" placeholder="login" name="login" class="round"><br>
<input type="password" placeholder="mypassword" name="password" class="round"><br>
<button class="button" onclick="logMe(admin_login); return false;">Войти</button>
</form>
</div>
</fieldset>
<div id="preview">
</div>
</div>
<!-- Страница сгенерирована за 0.013168096542358 секунд -->
Т.е. реглярное выражение вырезает все, что стоит до последней "}", и НЕ присваивает это переменной