X-Git-Url: https://git.donarmstrong.com/?a=blobdiff_plain;f=program%2Finclude%2Frcube_template.php;fp=program%2Finclude%2Frcube_template.php;h=5e45fb6e466f9e5f98fbaa84fb112276769cdda9;hb=3adad46e27086084a8b28a32fc4fbc953dbfef6c;hp=2173784b67f5f11e5962a2ee41c747202d4ffb3f;hpb=48e8459231a1efa3e97284d07a328776a5b7485b;p=roundcube.git
diff --git a/program/include/rcube_template.php b/program/include/rcube_template.php
index 2173784..5e45fb6 100755
--- a/program/include/rcube_template.php
+++ b/program/include/rcube_template.php
@@ -32,7 +32,6 @@ class rcube_template extends rcube_html_page
{
var $app;
var $config;
- var $task = '';
var $framed = false;
var $pagetitle = '';
var $env = array();
@@ -40,6 +39,7 @@ class rcube_template extends rcube_html_page
var $js_commands = array();
var $object_handlers = array();
+ public $type = 'html';
public $ajax_call = false;
/**
@@ -54,9 +54,13 @@ class rcube_template extends rcube_html_page
$this->app = rcmail::get_instance();
$this->config = $this->app->config->all();
+ $this->browser = new rcube_browser();
//$this->framed = $framed;
- $this->task = $task;
+ $this->set_env('task', $task);
+
+ // load the correct skin (in case user-defined)
+ $this->set_skin($this->config['skin']);
// add common javascripts
$javascript = 'var '.JS_OBJECT_NAME.' = new rcube_webmail();';
@@ -104,6 +108,54 @@ class rcube_template extends rcube_html_page
}
+ /**
+ * Getter for the current page title
+ *
+ * @return string The page title
+ */
+ public function get_pagetitle()
+ {
+ if (!empty($this->pagetitle)) {
+ $title = $this->pagetitle;
+ }
+ else if ($this->env['task'] == 'login') {
+ $title = rcube_label(array('name' => 'welcome', 'vars' => array('product' => $this->config['product_name'])));
+ }
+ else {
+ $title = ucfirst($this->env['task']);
+ }
+
+ return $title;
+ }
+
+
+ /**
+ * Set skin
+ */
+ public function set_skin($skin)
+ {
+ if (!empty($skin) && is_dir('skins/'.$skin) && is_readable('skins/'.$skin))
+ $skin_path = 'skins/'.$skin;
+ else
+ $skin_path = $this->config['skin_path'] ? $this->config['skin_path'] : 'skins/default';
+
+ $this->app->config->set('skin_path', $skin_path);
+ $this->config['skin_path'] = $skin_path;
+ }
+
+ /**
+ * Check if a specific template exists
+ *
+ * @param string Template name
+ * @return boolean True if template exists
+ */
+ public function template_exists($name)
+ {
+ $filename = $this->config['skin_path'] . '/templates/' . $name . '.html';
+
+ return (is_file($filename) && is_readable($filename));
+ }
+
/**
* Register a template object handler
*
@@ -190,7 +242,7 @@ class rcube_template extends rcube_html_page
* @uses self::$js_commands
* @uses self::$object_handlers
*/
- public public function reset()
+ public function reset()
{
$this->env = array();
$this->js_env = array();
@@ -200,6 +252,20 @@ class rcube_template extends rcube_html_page
}
+ /**
+ * Redirect to a certain url
+ *
+ * @param mixed Either a string with the action or url parameters as key-value pairs
+ * @see rcmail::url()
+ */
+ public function redirect($p = array())
+ {
+ $location = $this->app->url($p);
+ header('Location: ' . $location);
+ exit;
+ }
+
+
/**
* Send the request output to the client.
* This will either parse a skin tempalte or send an AJAX response
@@ -257,28 +323,19 @@ class rcube_template extends rcube_html_page
private function parse($name = 'main', $exit = true)
{
$skin_path = $this->config['skin_path'];
-
- // read template file
- $templ = '';
$path = "$skin_path/templates/$name.html";
- if (($fp = fopen($path, 'r')) === false) {
- $message = '';
- ob_start();
- fopen($path, 'r');
- $message.= ob_get_contents();
- ob_end_clean();
+ // read template file
+ if (($templ = @file_get_contents($path)) === false) {
raise_error(array(
'code' => 501,
'type' => 'php',
'line' => __LINE__,
'file' => __FILE__,
- 'message' => 'Error loading template for '.$name.': '.$message
+ 'message' => 'Error loading template for '.$name
), true, true);
return false;
}
- $templ = fread($fp, filesize($path));
- fclose($fp);
// parse for specialtags
$output = $this->parse_conditions($templ);
@@ -286,9 +343,9 @@ class rcube_template extends rcube_html_page
// add debug console
if ($this->config['debug_level'] & 8) {
- $this->add_footer('
'
);
}
$output = $this->parse_with_globals($output);
@@ -323,13 +380,7 @@ class rcube_template extends rcube_html_page
implode(',', $args)
);
}
- // add command to set page title
- if ($this->ajax_call && !empty($this->pagetitle)) {
- $out .= sprintf(
- "this.set_pagetitle('%s');\n",
- JQ((!empty($this->config['product_name']) ? $this->config['product_name'].' :: ' : '') . $this->pagetitle)
- );
- }
+
return $out;
}
@@ -414,26 +465,38 @@ class rcube_template extends rcube_html_page
* @todo Get rid off eval() once I understand what this does.
* @todo Extend this to allow real conditions, not just "set"
* @param string Condition statement
- * @return boolean True if condition is met, False is not
+ * @return boolean True if condition is met, False if not
*/
private function check_condition($condition)
{
- $condition = preg_replace(
+ return eval("return (".$this->parse_expression($condition).");");
+ }
+
+
+ /**
+ * Parses expression and replaces variables
+ *
+ * @param string Expression statement
+ * @return string Expression statement
+ */
+ private function parse_expression($expression)
+ {
+ return preg_replace(
array(
'/session:([a-z0-9_]+)/i',
- '/config:([a-z0-9_]+)/i',
+ '/config:([a-z0-9_]+)(:([a-z0-9_]+))?/i',
'/env:([a-z0-9_]+)/i',
- '/request:([a-z0-9_]+)/ie'
+ '/request:([a-z0-9_]+)/i',
+ '/cookie:([a-z0-9_]+)/i'
),
array(
"\$_SESSION['\\1']",
- "\$this->config['\\1']",
+ "\$this->app->config->get('\\1',get_boolean('\\3'))",
"\$this->env['\\1']",
- "get_input_value('\\1', RCUVE_INPUT_GPC)"
+ "get_input_value('\\1', RCUBE_INPUT_GPC)",
+ "\$_COOKIE['\\1']"
),
- $condition);
-
- return eval("return (".$condition.");");
+ $expression);
}
@@ -443,11 +506,28 @@ class rcube_template extends rcube_html_page
*
* @param string Input string to parse
* @return string Altered input string
+ * @todo Use DOM-parser to traverse template HTML
* @todo Maybe a cache.
*/
private function parse_xml($input)
{
- return preg_replace('/]+)>/Uie', "\$this->xml_command('\\1', '\\2')", $input);
+ return preg_replace_callback('/]+)>/Ui', array($this, 'xml_command_callback'), $input);
+ }
+
+
+ /**
+ * This is a callback function for preg_replace_callback (see #1485286)
+ * It's only purpose is to reconfigure parameters for xml_command, so that the signature isn't disturbed
+ */
+ private function xml_command_callback($matches)
+ {
+ $str_attrib = isset($matches[2]) ? $matches[2] : '';
+ $add_attrib = isset($matches[3]) ? $matches[3] : array();
+
+ $command = $matches[1];
+ //matches[0] is the entire matched portion of the string
+
+ return $this->xml_command($command, $str_attrib, $add_attrib);
}
@@ -487,14 +567,13 @@ class rcube_template extends rcube_html_page
// include a file
case 'include':
$path = realpath($this->config['skin_path'].$attrib['file']);
- if ($fsize = filesize($path)) {
+ if (is_readable($path)) {
if ($this->config['skin_include_php']) {
$incl = $this->include_php($path);
}
- else if ($fp = fopen($path, 'r')) {
- $incl = fread($fp, $fsize);
- fclose($fp);
- }
+ else {
+ $incl = file_get_contents($path);
+ }
return $this->parse_xml($incl);
}
break;
@@ -541,23 +620,20 @@ class rcube_template extends rcube_html_page
}
return $ver;
}
+ if ($object=='steptitle') {
+ return Q($this->get_pagetitle());
+ }
if ($object=='pagetitle') {
- $task = $this->task;
$title = !empty($this->config['product_name']) ? $this->config['product_name'].' :: ' : '';
-
- if (!empty($this->pagetitle)) {
- $title .= $this->pagetitle;
- }
- else if ($task == 'login') {
- $title = rcube_label(array('name' => 'welcome', 'vars' => array('product' => $this->config['product_name'])));
- }
- else {
- $title .= ucfirst($task);
- }
-
+ $title .= $this->get_pagetitle();
return Q($title);
}
break;
+
+ // return code for a specified eval expression
+ case 'exp':
+ $value = $this->parse_expression($attrib['expression']);
+ return eval("return Q($value);");
// return variable
case 'var':
@@ -581,6 +657,9 @@ class rcube_template extends rcube_html_page
case 'session':
$value = $_SESSION[$name];
break;
+ case 'cookie':
+ $value = htmlspecialchars($_COOKIE[$name]);
+ break;
}
if (is_array($value)) {
@@ -617,7 +696,7 @@ class rcube_template extends rcube_html_page
* @todo Remove all inline JS calls and use jQuery instead.
* @todo Remove all sprintf()'s - they are pretty, but also slow.
*/
- private function button($attrib)
+ public function button($attrib)
{
static $sa_buttons = array();
static $s_button_count = 100;
@@ -629,8 +708,6 @@ class rcube_template extends rcube_html_page
return '';
}
- $browser = new rcube_browser();
-
// try to find out the button type
if ($attrib['type']) {
$attrib['type'] = strtolower($attrib['type']);
@@ -659,10 +736,6 @@ class rcube_template extends rcube_html_page
$attrib = $sa_buttons[$command];
}
- // set border to 0 because of the link arround the button
- if ($attrib['type']=='image' && !isset($attrib['border'])) {
- $attrib['border'] = 0;
- }
if (!$attrib['id']) {
$attrib['id'] = sprintf('rcmbtn%d', $s_button_count++);
}
@@ -677,7 +750,7 @@ class rcube_template extends rcube_html_page
$attrib['alt'] = Q(rcube_label($attrib['alt']));
}
// set title to alt attribute for IE browsers
- if ($browser->ie && $attrib['title'] && !$attrib['alt']) {
+ if ($this->browser->ie && $attrib['title'] && !$attrib['alt']) {
$attrib['alt'] = $attrib['title'];
unset($attrib['title']);
}
@@ -702,10 +775,13 @@ class rcube_template extends rcube_html_page
// make valid href to specific buttons
if (in_array($attrib['command'], rcmail::$main_tasks)) {
- $attrib['href'] = Q(rcmail_url(null, null, $attrib['command']));
+ $attrib['href'] = rcmail_url(null, null, $attrib['command']);
}
else if (in_array($attrib['command'], $a_static_commands)) {
- $attrib['href'] = Q(rcmail_url($attrib['command']));
+ $attrib['href'] = rcmail_url($attrib['command']);
+ }
+ else if ($attrib['command'] == 'permaurl' && !empty($this->env['permaurl'])) {
+ $attrib['href'] = $this->env['permaurl'];
}
}
@@ -760,18 +836,18 @@ class rcube_template extends rcube_html_page
array(
'style', 'class', 'id', 'width',
'height', 'border', 'hspace',
- 'vspace', 'align', 'alt',
+ 'vspace', 'align', 'alt', 'tabindex'
)
);
$btn_content = sprintf('
', $this->abs_url($attrib['image']), $attrib_str);
if ($attrib['label']) {
$btn_content .= ' '.$attrib['label'];
}
- $link_attrib = array('href', 'onclick', 'onmouseover', 'onmouseout', 'onmousedown', 'onmouseup', 'title');
+ $link_attrib = array('href', 'onclick', 'onmouseover', 'onmouseout', 'onmousedown', 'onmouseup', 'title', 'target');
}
else if ($attrib['type']=='link') {
$btn_content = $attrib['label'] ? $attrib['label'] : $attrib['command'];
- $link_attrib = array('href', 'onclick', 'title', 'id', 'class', 'style');
+ $link_attrib = array('href', 'onclick', 'title', 'id', 'class', 'style', 'tabindex', 'target');
}
else if ($attrib['type']=='input') {
$attrib['type'] = 'button';
@@ -784,7 +860,7 @@ class rcube_template extends rcube_html_page
$attrib,
array(
'type', 'value', 'onclick',
- 'id', 'class', 'style'
+ 'id', 'class', 'style', 'tabindex'
)
);
$out = sprintf('', $attrib_str);
@@ -866,9 +942,10 @@ class rcube_template extends rcube_html_page
$_SESSION['temp'] = true;
- $input_user = new html_inputfield(array('name' => '_user', 'id' => 'rcmloginuser', 'size' => 30, 'autocomplete' => 'off'));
- $input_pass = new html_passwordfield(array('name' => '_pass', 'id' => 'rcmloginpwd', 'size' => 30));
+ $input_user = new html_inputfield(array('name' => '_user', 'id' => 'rcmloginuser', 'size' => 30) + $attrib);
+ $input_pass = new html_passwordfield(array('name' => '_pass', 'id' => 'rcmloginpwd', 'size' => 30) + $attrib);
$input_action = new html_hiddenfield(array('name' => '_action', 'value' => 'login'));
+ $input_tzone = new html_hiddenfield(array('name' => '_timezone', 'id' => 'rcmlogintz', 'value' => '_default_'));
$input_host = null;
if (is_array($default_host)) {
@@ -884,7 +961,7 @@ class rcube_template extends rcube_html_page
}
}
}
- else if (!strlen($default_host)) {
+ else if (empty($default_host)) {
$input_host = new html_inputfield(array('name' => '_host', 'id' => 'rcmloginhost', 'size' => 30));
}
@@ -895,7 +972,7 @@ class rcube_template extends rcube_html_page
$table = new html_table(array('cols' => 2));
$table->add('title', html::label('rcmloginuser', Q(rcube_label('username'))));
- $table->add(null, $input_user->show(get_input_value('_user', RCUVE_INPUT_POST)));
+ $table->add(null, $input_user->show(get_input_value('_user', RCUBE_INPUT_POST)));
$table->add('title', html::label('rcmloginpwd', Q(rcube_label('password'))));
$table->add(null, $input_pass->show());
@@ -903,10 +980,11 @@ class rcube_template extends rcube_html_page
// add host selection row
if (is_object($input_host)) {
$table->add('title', html::label('rcmloginhost', Q(rcube_label('server'))));
- $table->add(null, $input_host->show(get_input_value('_host', RCUVE_INPUT_POST)));
+ $table->add(null, $input_host->show(get_input_value('_host', RCUBE_INPUT_POST)));
}
$out = $input_action->show();
+ $out .= $input_tzone->show();
$out .= $table->show();
// surround html output with a form tag
@@ -935,6 +1013,10 @@ class rcube_template extends rcube_html_page
if (empty($attrib['id'])) {
$attrib['id'] = 'rcmqsearchbox';
}
+ if ($attrib['type'] == 'search' && !$this->browser->khtml) {
+ unset($attrib['type'], $attrib['results']);
+ }
+
$input_q = new html_inputfield($attrib);
$out = $input_q->show();