Source for file Html.php
Documentation is available at Html.php
* A Framework for Creating and Using Complex Web Elements
* The purpose of this framework is to provide a library of high-level objects
* to facilitate common HTML coding tasks, such as menus, tables, and forms.
* The intent is to reduce repetitive HTML coding as much as possible, replacing
* it with a combination of configuration files and style sheets with
* standardized naming conventions.
* This framework is built on and requires the
* {@link http://framework.zend.com/ Zend Framework}.
* @author Lyle Frost <lfrost@cnz.com>
* @copyright Copyright (c) 2006-2007 Citadel Network <{@link http://www.citadelnetwork.com/}>
* @license http://www.citadelnetwork.com/license/cnzframework New BSD License
* @version $Id: Html.php 27 2007-07-19 18:47:54Z lfrost $
Zend_Loader::loadClass('Zend_Config');
Zend_Loader::loadClass('Zend_Config_Ini');
Zend_Loader::loadClass('Zend_Log');
Zend_Loader::loadClass('Zend_Log_Filter_Priority');
Zend_Loader::loadClass('Zend_Log_Writer_Stream');
* This utility class provides general HTML support methods.
* To use this class, load the class <kbd>Cnz_Html</kbd> and then call the
* static method <kbd>init()</kbd> prior to any output on the web page. The
* class is controlled by a configuration file.
* Example INI (defaults shown as comments):
* domain = www.example.com
* sslDomain = www.example.com
* ;brickDir = /slib/image/brick/
* ;buttonDir = /slib/image/button/
* <var>brickDir</var> is for link bricks such as the W3C validation bricks.
* <var>buttonDir</var> is for control buttons such as table next/prev.
* <var>indent</var> defines the string used for a single level of HTML
* <var>tmpDir</var> and <var>logDir</var> are relative to the application root
* directory, which is defined to be the parent of the web document root
* <var>logLevel</var> can be any of the log levels defined by Zend_Log (debug,
* info, notice, warn, err, crit, alert, or severe).
* Zend_Loader::loadClass('Cnz_Html');
* The <kbd>init()</kbd> method will detect the capabilities of the client web
* browser and send the appropriate HTTP headers. XHTML 1.1 will be chosen as
* the content type if the browser prefers XHTML, else the content type will be
* set to HTML 4.01 Strict. If transitional is true, these will instead be
* XHTML 1.0 Transitional and HTML 4.01 Transitional, respectively.
* <kbd>init()</kbd> also compares the list of languages in the configuration
* file to those in the <kbd>Accept-Language</kbd> header to find the best
* match. If there is no match, the language defaults to the first in the
* configuration list. The match can be retrieved using
* <kbd>getLanguage()</kbd>.
* <kbd>init()</kbd> processes the <kbd>Accept-Charset</kbd> header in the same
* way. Use <kbd>getCharSet()</kbd> to retrieve the selected character set.
* Based on the detections above, the appropriate HTTP response headers are
* generated, and all prolog information up to and including the <kbd>html</kbd>
* Given that the most common scenario for a database-driven site is to have a
* single database, <kbd>init()</kbd> has an option of connecting to that
* database. This connection is defined by passing a second argument to
* <kbd>init()</kbd> which is the name of the database configuration file. This
* is allowed to be in a separate file because it contains security information.
* The connection is a <kbd>Zend_Db_Adapter</kbd>.
* A third boolean parameter specifies whether the connection will be made
* immediately, or postponed until it is accessed.
* username = database_user
* password = database_password
* The valid database type values are: <kbd>dblib</kbd>, <kbd>firebird</kbd>,
* <kbd>informix</kbd>, <kbd>mysql</kbd>, <kbd>oci</kbd>, <kbd>odbc</kbd>,
* <kbd>pgsql</kbd>, <kbd>sqlite</kbd>. See <kbd>PDO_*</kbd> at
* {@link http://www.php.net/manual/en/ref.pdo.php}. Additionally, the non-PDO
* database types <kbd>db2</kbd> and <kbd>oracle</kbd> may be used.
* Leave the host undefined for socket connections.
* Pages using this class must be written with XHTML syntax. If the end-tag
* shorthand sequence "<kbd>/></kbd>" occurs anywhere else in the text, it must
* be replaced with "<kbd>/></kbd>" or else the "<kbd>/</kbd>" (and any
* preceding whitespace) will be stripped when the page is served as HTML.
* When using JavaScript, the value of the <kbd>type</kbd> attribute of the
* script tag should be set as follows.
* type = "<?php echo Cnz_Html::getJavascriptType(); ?>"
* There are also getter methods for several other settings.
* The following directory structure is recommended. The recommended * BASE is
* $BASE --- app Application code
* | |- form Form configurations
* | |- table Table configurations
* |- upload Temporary upload directory
* |- www Web document root
* |- image Images (local to current directory)
* | |- script Client-side Scripts
* | |- style Style Sheets
* |- script Client-side Scripts (local to current directory)
* |- style Style sheets (local to current directory)
* --- slib Server library (Apache alias)
* | |- button Control buttons
* |- script Client-side Scripts
const CONFIG_SEC_HTML = 'Html';
const CONFIG_SEC_DATABASE = 'Database';
const CONTENT_TYPE_XHTML = 'application/xhtml+xml';
const CONTENT_TYPE_HTML = 'text/html';
const JAVASCRIPT_TYPE_XHTML = 'application/javascript';
const JAVASCRIPT_TYPE_HTML = 'text/javascript';
const STYLE_TYPE = 'text/css';
const DEFAULT_BRICK_DIR = '/slib/image/brick/';
const DEFAULT_BUTTON_DIR = '/slib/image/button/';
const DEFAULT_CFG_FILE = '../cfg/html.ini';
const DEFAULT_DBCFG_FILE = '../cfg/database.ini';
const DEFAULT_CHARSET = 'utf-8';
const DEFAULT_LANGUAGE = 'en-us';
const DEFAULT_FIELD_DELIMITER = ':';
const DEFAULT_LIST_DELIMITER = ',';
const DEFAULT_LOG_DIR = 'log';
const DEFAULT_LOG_FILE = 'html.log';
const DEFAULT_LOG_LEVEL = Zend_Log::INFO;
const DEFAULT_TMP_DIR = 'tmp';
const DEFAULT_UPLOAD_DIR = 'upload';
const SCRIPT_FILE_EXT = 'js';
const STYLE_FILE_EXT = 'css';
private static $charSetArray = array(self::DEFAULT_CHARSET);
private static $languageArray = array(self::DEFAULT_LANGUAGE);
private static $transitionalFlag = false;
private static $logLevel = self::DEFAULT_LOG_LEVEL;
private static $indentLevel = 0;
private static $phpLogLevel = NULL;
private static $brickDir = self::DEFAULT_BRICK_DIR;
private static $buttonDir = self::DEFAULT_BUTTON_DIR;
private static $logDir = self::DEFAULT_LOG_DIR;
private static $logFile = self::DEFAULT_LOG_FILE;
private static $phpLogFile = NULL;
private static $tmpDir = self::DEFAULT_TMP_DIR;
private static $uploadDir = self::DEFAULT_UPLOAD_DIR;
private static $charSet = self::DEFAULT_CHARSET;
private static $contentType = self::CONTENT_TYPE_HTML;
private static $indentString = "\t";
private static $javascriptType = self::JAVASCRIPT_TYPE_HTML;
private static $language = self::DEFAULT_LANGUAGE;
private static $htmlConfigFile = NULL;
private static $dbConfigFile = NULL;
private static $domain = NULL;
private static $sslDomain = NULL;
/** For config values with multiple parts */
private static $fieldDelimiter = self::DEFAULT_FIELD_DELIMITER;
/** For config entries with list values */
private static $listDelimiter = self::DEFAULT_LIST_DELIMITER;
private static $wcagLevel = '';
/** @var Zend_Db_Adapter_Abstract */
private static $db = NULL;
private static $logger = NULL;
/* Getters/Setters ===================================================*/
/** @return string Brick directory */
/** @return string Button directory */
/** @return string Content type */
return self::$contentType;
/** @return Zend_Db Database connection */
public static function getDb()
/** @return string Domain */
/** @return string Config file field delimiter */
return self::$fieldDelimiter;
* @param string $fieldDelimiter New config file field delimiter
public static function setFieldDelimiter($fieldDelimiter = self::DEFAULT_FIELD_DELIMITER)
self::$fieldDelimiter = $fieldDelimiter;
/** @return string HTML configuration file */
return self::$htmlConfigFile;
/** @return int Indent level */
return (int) self::$indentLevel;
* @param int $indentLevel New indentation level
/** @return string Indent string */
return self::$indentString;
/** @return string Type attribute for HTML script tag */
return self::$javascriptType;
/** @return string Language code */
/** @return string Config file list delimiter */
return self::$listDelimiter;
* @param string $listDelimiter New config file list delimiter
public static function setListDelimiter($listDelimiter = self::DEFAULT_LIST_DELIMITER)
self::$listDelimiter = $listDelimiter;
/** @return Zend_Log Logger */
/** @return string SSL domain */
/** @return string Tmp directory */
/** @return string Upload directory */
/* Testers ===========================================================*/
/** @return boolean True if SSL */
public static function isSsl()
return isset ($_SERVER['HTTPS']);
/** @return boolean True if content type is XHTML */
return self::$contentType == self::CONTENT_TYPE_XHTML;
/* Static Methods ====================================================*/
* Convert an associative array to a list of the form key:val,key:val.
* If any value is itself an array, it will be expanded as
* @param string $fieldDelimiter
* @param string $listDelimiter
public static function arrayToList($array, $fieldDelimiter = NULL, $listDelimiter = NULL)
if (empty($fieldDelimiter)) $fieldDelimiter = self::$fieldDelimiter;
if (empty($listDelimiter)) $listDelimiter = self::$listDelimiter;
foreach ($array as $key => $value)
$result .= $fieldDelimiter . $v;
$result .= $fieldDelimiter . $value;
if ($i++ < $n - 1) $result .= $listDelimiter;
* Convert a configuration file string value to boolean.
* @param $value Value from configuration file
* @return boolean $value converted to boolean
* Create a database connection using the configuration information
* provided to <kbd>init()</kbd>. The default Zend_Db_Table_Abstract
* adapter is set to this connection. The connection is actually
* established if nowFlag is true.
* @param boolean $nowFlag Connect to database now
* @return boolean Success
public static function dbConnect($nowFlag = false)
Zend_Loader::loadClass('Zend_Db');
Zend_Loader::loadClass('Zend_Db_Table');
// Process configuration file.
$config = new Zend_Config_Ini(self::$dbConfigFile, self::CONFIG_SEC_DATABASE);
if (!isset ($config->type)) return false;
if (isset ($config->host)) $options['host'] = $config->host;
if (isset ($config->port)) $options['port'] = $config->port;
if (!isset ($config->dbname)) return false;
$options['dbname'] = $config->dbname;
if (isset ($config->username)) $options['username'] = $config->username;
if (isset ($config->password)) $options['password'] = $config->password;
self::$db = Zend_Db::factory($type, $options);
if ($nowFlag) self::$db->getConnection();
Zend_Db_Table::setDefaultAdapter(self::$db);
catch (Zend_Exception $e)
self::$logger->err(__METHOD__ . '[' . __LINE__ . '] ' . 'Exception from ' . get_class($e) . ': ' . $e->getMessage() . '.');
* @param string $filename
* @return mixed Filename without extension, or false if wrong file extension
if ($dotPos === false) return '';
$fileExt = substr($filename, $dotPos + 1);
if ($fileExt != $ext) return false;
return substr($filename, 0, $dotPos);
* Display W3C bricks for valid X/HTML, CSS, and WCAG.
* The files valid-xhtml11.png, valid-html401.png, and vcss.png (all
* available from w3.org) must be in brickDir.
* @param boolean $link Link to validator pages (unless SSL)
// If SSL, disable links because there will be no referrer.
if (isset ($_SERVER['HTTPS'])) $link = false;
if ($link) echo '<a href = "http://www.citadelnetwork.com/open/php/cnzframework/">';
echo '<img alt = "[CNZ Framework]" src = "' . self::$brickDir . 'cnzframework.png" style = "border-style:none; height:31px; margin-right:5px; width:88px;"/>';
if (self::$contentType == self::CONTENT_TYPE_XHTML)
if ($link) echo '<a href = "http://validator.w3.org/check?uri=referer">';
if (self::$transitionalFlag) echo '<img alt = "[Valid XHTML 1.0]" src = "' . self::$brickDir . 'valid-xhtml10.png" style = "border-style:none; height:31px; width:88px;"/>';
else echo '<img alt = "[Valid XHTML 1.1]" src = "' . self::$brickDir . 'valid-xhtml11.png" style = "border-style:none; height:31px; width:88px;"/>';
if ($link) echo '<a href = "http://validator.w3.org/check?uri=referer">';
echo '<img alt = "[Valid HTML 4.01 Strict]" src = "' . self::$brickDir . 'valid-html401.png" style = "border-style:none; height:31px; width:88px;"/>';
if ($link) echo '<a href = "http://jigsaw.w3.org/css-validator/check/referer">';
echo '<img alt = "[Valid CSS]" src = "' . self::$brickDir . 'vcss.png" style = "border-style:none; height:31px; width:88px;"/>';
if (!empty(self::$wcagLevel))
if ($link) echo '<a href = "http://www.w3.org/WAI/WCAG1', self::$wcagLevel, '-Conformance">';
echo '<img alt = "[WCAG Level ', self::$wcagLevel, ' Conformance]" src = "' . self::$brickDir . 'wcag1', self::$wcagLevel, '.gif" style = "border-style:none; height:31px; width:88px;"/>';
* Determine the current document directory. This is necessary for use
* with mod_rewrite, when the script directory cannot be relied on.
* @param relative Relative (to web doc root) flag
* @return string Root URL
|