This commit is contained in:
root
2019-08-30 19:30:19 +02:00
commit 6f2b105ca0
595 changed files with 78405 additions and 0 deletions

94
util/crayon_log.class.php Normal file
View File

@ -0,0 +1,94 @@
<?php
require_once (CRAYON_ROOT_PATH . 'crayon_settings.class.php');
/* Manages logging variable values to the log file. */
class CrayonLog {
private static $file = NULL;
// Logs a variable value to a log file
public static function log($var = NULL, $title = '', $trim_url = TRUE) {
if ($var === NULL) {
// Return log
if (($log = CrayonUtil::file(CRAYON_LOG_FILE)) !== FALSE) {
return $log;
} else {
return '';
}
} else {
try {
if (self::$file == NULL) {
self::$file = @fopen(CRAYON_LOG_FILE, 'a+');
if (self::$file) {
$header = /*CRAYON_DASH .*/ CRAYON_NL . '[Crayon Syntax Highlighter Log Entry - ' . date('g:i:s A - d M Y') . ']' . CRAYON_NL .
/*CRAYON_DASH .*/ CRAYON_NL;
fwrite(self::$file, $header);
} else {
return;
}
}
// Capture variable dump
$buffer = trim(strip_tags(var_export($var, true)));
$title = (!empty($title) ? " [$title]" : '');
// Remove absolute path to plugin directory from buffer
if ($trim_url) {
$buffer = CrayonUtil::path_rel($buffer);
}
$write = $title . ' ' . $buffer . CRAYON_NL /* . CRAYON_LINE . CRAYON_NL*/;
// If we exceed max file size, truncate file first
if (filesize(CRAYON_LOG_FILE) + strlen($write) > CRAYON_LOG_MAX_SIZE) {
ftruncate(self::$file, 0);
fwrite(self::$file, 'The log has been truncated since it exceeded ' . CRAYON_LOG_MAX_SIZE .
' bytes.' . CRAYON_NL . /*CRAYON_LINE .*/ CRAYON_NL);
}
clearstatcache();
fwrite(self::$file, $write, CRAYON_LOG_MAX_SIZE);
} catch (Exception $e) {
// Ignore fatal errors during logging
}
}
}
// Logs system-wide only if global settings permit
public static function syslog($var = NULL, $title = '', $trim_url = TRUE) {
if (CrayonGlobalSettings::val(CrayonSettings::ERROR_LOG_SYS)) {
$title = (empty($title)) ? 'SYSTEM LOG' : $title;
self::log($var, $title, $trim_url);
}
}
public static function debug($var = NULL, $title = '', $trim_url = TRUE) {
if (CRAYON_DEBUG) {
$title = (empty($title)) ? 'DEBUG' : $title;
self::log($var, $title, $trim_url);
}
}
public static function clear() {
if (!@unlink(CRAYON_LOG_FILE)) {
// Will result in nothing if we can't log
self::log('The log could not be cleared', 'Log Clear');
}
self::$file = NULL; // Remove file handle
}
public static function email($to, $from = NULL) {
if (($log_contents = CrayonUtil::file(CRAYON_LOG_FILE)) !== FALSE) {
$headers = $from ? 'From: ' . $from : '';
$result = @mail($to, 'Crayon Syntax Highlighter Log', $log_contents, $headers);
self::log('The log was emailed to the admin.', 'Log Email');
} else {
// Will result in nothing if we can't email
self::log("The log could not be emailed to $to.", 'Log Email');
}
}
}
?>

View File

@ -0,0 +1,24 @@
<?php
/* Used to measure execution time */
class CrayonTimer {
const NO_SET = -1;
private $start_time = self::NO_SET;
function __construct() {}
public function start() {
$this->start_time = microtime(true);
}
public function stop() {
if ($this->start_time != self::NO_SET) {
$end_time = microtime(true) - $this->start_time;
$this->start_time = self::NO_SET;
return $end_time;
} else {
return 0;
}
}
}
?>

858
util/crayon_util.class.php Normal file
View File

@ -0,0 +1,858 @@
<?php
/* Common utility functions mainly for formatting, parsing etc. */
class CrayonUtil {
// Used to detect touchscreen devices
private static $touchscreen = NULL;
/* Return the lines inside a file as an array, options:
l - lowercase
w - remove whitespace
r - escape regex chars
c - remove comments
s - return as string */
public static function lines($path, $opts = NULL) {
$path = self::pathf($path);
if (($str = self::file($path)) === FALSE) {
// Log failure, n = no log
if (strpos($opts, 'n') === FALSE) {
CrayonLog::syslog("Cannot read lines at '$path'.", "CrayonUtil::lines()");
}
return FALSE;
}
// Read the options
if (is_string($opts)) {
$lowercase = strpos($opts, 'l') !== FALSE;
$whitespace = strpos($opts, 'w') !== FALSE;
$escape_regex = strpos($opts, 'r') !== FALSE;
$clean_commments = strpos($opts, 'c') !== FALSE;
$return_string = strpos($opts, 's') !== FALSE;
// $escape_hash = strpos($opts, 'h') !== FALSE;
} else {
$lowercase = $whitespace = $escape_regex = $clean_commments = $return_string = /*$escape_hash =*/
FALSE;
}
// Remove comments
if ($clean_commments) {
$str = self::clean_comments($str);
}
// Convert to lowercase if needed
if ($lowercase) {
$str = strtolower($str);
}
/* Match all the content on non-empty lines, also remove any whitespace to the left and
right if needed */
if ($whitespace) {
$pattern = '[^\s]+(?:.*[^\s])?';
} else {
$pattern = '^(?:.*)?';
}
preg_match_all('|' . $pattern . '|m', $str, $matches);
$lines = $matches[0];
// Remove regex syntax and assume all characters are literal
if ($escape_regex) {
for ($i = 0; $i < count($lines); $i++) {
$lines[$i] = self::esc_regex($lines[$i]);
// if ($escape_hash || true) {
// If we have used \#, then we don't want it to become \\#
$lines[$i] = preg_replace('|\\\\\\\\#|', '\#', $lines[$i]);
// }
}
}
// Return as string if needed
if ($return_string) {
// Add line breaks if they were stripped
$delimiter = '';
if ($whitespace) {
$delimiter = CRAYON_NL;
}
$lines = implode($lines, $delimiter);
}
return $lines;
}
// Returns the contents of a file
public static function file($path) {
if (($str = @file_get_contents($path)) === FALSE) {
return FALSE;
} else {
return $str;
}
}
/**
* Zips a source file or directory.
*
* @param $src A directory or file
* @param $dest A directory or zip file. If a zip file is provided it must exist beforehand.
*/
public static function createZip($src, $dest, $removeExistingZip = FALSE) {
if ($src == $dest) {
throw new InvalidArgumentException("Source '$src' and '$dest' cannot be the same");
}
if (is_dir($src)) {
$src = CrayonUtil::path_slash($src);
$base = $src;
// Make sure the destination isn't in the files
$files = self::getFiles($src, array('recursive' => TRUE, 'ignore' => array($dest)));
} else if (is_file($src)) {
$files = array($src);
$base = dirname($src);
} else {
throw new InvalidArgumentException("Source '$src' is not a directory or file");
}
if (is_dir($dest)) {
$dest = CrayonUtil::path_slash($dest);
$zipFile = $dest . basename($src) . '.zip';
} else if (is_file($dest)) {
$zipFile = $dest;
} else {
throw new InvalidArgumentException("Destination '$dest' is not a directory or file");
}
if ($removeExistingZip) {
@unlink($zipFile);
}
$zip = new ZipArchive;
if ($zip->open($zipFile, ZIPARCHIVE::CREATE) === TRUE) {
foreach ($files as $file) {
$relFile = str_replace($base, '', $file);
$zip->addFile($file, $relFile);
}
$zip->close();
} else {
throw new Exception("Could not create zip file at '$zipFile'");
}
return $zipFile;
}
/**
* Sends an email in html and plain encodings with a file attachment.
*
* @param array $args Arguments associative array
* 'to' (string)
* 'from' (string)
* 'subject' (optional string)
* 'message' (HTML string)
* 'plain' (optional plain string)
* 'file' (optional file path of the attachment)
* @see http://webcheatsheet.com/php/send_email_text_html_attachment.php
*/
public static function emailFile($args) {
$to = self::set_default($args['to']);
$from = self::set_default($args['from']);
$subject = self::set_default($args['subject'], '');
$message = self::set_default($args['message'], '');
$plain = self::set_default($args['plain'], '');
$file = self::set_default($args['file']);
// MIME
$random_hash = md5(date('r', time()));
$boundaryMixed = 'PHP-mixed-' . $random_hash;
$boundaryAlt = 'PHP-alt-' . $random_hash;
$charset = 'UTF-8';
$bits = '8bit';
// Headers
$headers = "MIME-Version: 1.0";
$headers .= "Reply-To: $to\r\n";
if ($from !== NULL) {
$headers .= "From: $from\r\n";
}
$headers .= "Content-Type: multipart/mixed; boundary=$boundaryMixed";
if ($file !== NULL) {
$info = pathinfo($file);
$filename = $info['filename'];
$extension = $info['extension'];
$contents = @file_get_contents($file);
if ($contents === FALSE) {
throw new Exception("File contents of '$file' could not be read");
}
$chunks = chunk_split(base64_encode($contents));
$attachment = <<<EOT
--$boundaryMixed
Content-Type: application/$extension; name=$filename.$extension
Content-Transfer-Encoding: base64
Content-Disposition: attachment
$chunks
EOT;
} else {
$attachment = '';
}
$body = <<<EOT
--$boundaryMixed
Content-Type: multipart/alternative; boundary=$boundaryAlt
--$boundaryAlt
Content-Type: text/plain; charset="$charset"
Content-Transfer-Encoding: $bits
$plain
--$boundaryAlt
Content-Type: text/html; charset="$charset"
Content-Transfer-Encoding: $bits
$message
--$boundaryAlt--
$attachment
--$boundaryMixed--
EOT;
$result = @mail($to, $subject, $body, $headers);
return $result;
}
/**
* @param $path A directory
* @param array $args Argument array:
* hidden: If true, hidden files beginning with a dot will be included
* ignoreRef: If true, . and .. are ignored
* recursive: If true, this function is recursive
* ignore: An array of paths to ignore
* @return array Files in the directory
*/
public static function getFiles($path, $args = array()) {
$hidden = self::set_default($args['hidden'], TRUE);
$ignoreRef = self::set_default($args['ignoreRef'], TRUE);
$recursive = self::set_default($args['recursive'], FALSE);
$ignore = self::set_default($args['ignore'], NULL);
$ignore_map = array();
if ($ignore) {
foreach ($ignore as $i) {
if (is_dir($i)) {
$i = CrayonUtil::path_slash($i);
}
$ignore_map[$i] = TRUE;
}
}
$files = glob($path . '*', GLOB_MARK);
if ($hidden) {
$files = array_merge($files, glob($path . '.*', GLOB_MARK));
}
if ($ignoreRef || $ignore) {
$result = array();
for ($i = 0; $i < count($files); $i++) {
$file = $files[$i];
if (!isset($ignore_map[$file]) && (!$ignoreRef || (basename($file) != '.' && basename($file) != '..'))) {
$result[] = $file;
if ($recursive && is_dir($file)) {
$result = array_merge($result, self::getFiles($file, $args));
}
}
}
} else {
$result = $files;
}
return $result;
}
public static function deleteDir($path) {
if (!is_dir($path)) {
throw new InvalidArgumentException("deleteDir: $path is not a directory");
}
if (substr($path, strlen($path) - 1, 1) != '/') {
$path .= '/';
}
$files = self::getFiles($path);
foreach ($files as $file) {
if (is_dir($file)) {
self::deleteDir($file);
} else {
unlink($file);
}
}
rmdir($path);
}
public static function copyDir($src, $dst, $mkdir = NULL) {
// http://stackoverflow.com/questions/2050859
if (!is_dir($src)) {
throw new InvalidArgumentException("copyDir: $src is not a directory");
}
$dir = opendir($src);
if ($mkdir !== NULL) {
call_user_func($mkdir, $dst);
} else {
@mkdir($dst, 0777, TRUE);
}
while (false !== ($file = readdir($dir))) {
if (($file != '.') && ($file != '..')) {
if (is_dir($src . '/' . $file)) {
self::copyDir($src . '/' . $file, $dst . '/' . $file);
} else {
copy($src . '/' . $file, $dst . '/' . $file);
}
}
}
closedir($dir);
}
// Supports arrays in the values
public static function array_flip($array) {
$result = array();
foreach ($array as $k => $v) {
if (is_array($v)) {
foreach ($v as $u) {
self::_array_flip($result, $k, $u);
}
} else {
self::_array_flip($result, $k, $v);
}
}
return $result;
}
private static function _array_flip(&$array, $k, $v) {
if (is_string($v) || is_int($v)) {
$array[$v] = $k;
} else {
trigger_error("Values must be STRING or INTEGER", E_USER_WARNING);
}
}
// Detects if device is touchscreen or mobile
public static function is_touch() {
// Only detect once
if (self::$touchscreen !== NULL) {
return self::$touchscreen;
}
if (($devices = self::lines(CRAYON_TOUCH_FILE, 'lw')) !== FALSE) {
if (!isset($_SERVER['HTTP_USER_AGENT'])) {
return false;
}
// Create array of device strings from file
$user_agent = strtolower($_SERVER['HTTP_USER_AGENT']);
self::$touchscreen = (self::strposa($user_agent, $devices) !== FALSE);
return self::$touchscreen;
} else {
CrayonLog::syslog('Error occurred when trying to identify touchscreen devices');
}
}
// Removes duplicates in array, ensures they are all strings
public static function array_unique_str($array) {
if (!is_array($array) || empty($array)) {
return array();
}
for ($i = 0; $i < count($array); $i++) {
$array[$i] = strval($array[$i]);
}
return array_unique($array);
}
// Same as array_key_exists, but returns the key when exists, else FALSE;
public static function array_key_exists($key, $array) {
if (!is_array($array) || empty($array) || !is_string($key) || empty($key)) {
FALSE;
}
if (array_key_exists($key, $array)) {
return $array[$key];
}
}
// Performs explode() on a string with the given delimiter and trims all whitespace
public static function trim_e($str, $delimiter = ',') {
if (is_string($delimiter)) {
$str = trim(preg_replace('|\s*(?:' . preg_quote($delimiter) . ')\s*|', $delimiter, $str));
return explode($delimiter, $str);
}
return $str;
}
/* Creates an array of integers based on a given range string of format "int - int"
Eg. range_str('2 - 5'); */
public static function range_str($str) {
preg_match('#(\d+)\s*-\s*(\d+)#', $str, $matches);
if (count($matches) == 3) {
return range($matches[1], $matches[2]);
}
return FALSE;
}
// Creates an array out of a single range string (e.i "x-y")
public static function range_str_single($str) {
$match = preg_match('#(\d+)(?:\s*-\s*(\d+))?#', $str, $matches);
if ($match > 0) {
if (empty($matches[2])) {
$matches[2] = $matches[1];
}
if ($matches[1] <= $matches[2]) {
return array($matches[1], $matches[2]);
}
}
return FALSE;
}
// Sets a variable to a string if valid
public static function str(&$var, $str, $escape = TRUE) {
if (is_string($str)) {
$var = ($escape == TRUE ? self::htmlentities($str) : $str);
return TRUE;
}
return FALSE;
}
// Converts all special characters to entities
public static function htmlentities($str) {
return htmlentities($str, ENT_COMPAT, 'UTF-8');
}
public static function html_entity_decode($str) {
return html_entity_decode($str, ENT_QUOTES, 'UTF-8');
}
// Converts <, >, & into entities
public static function htmlspecialchars($str) {
return htmlspecialchars($str, ENT_NOQUOTES, 'UTF-8');
}
// Sets a variable to an int if valid
public static function num(&$var, $num) {
if (is_numeric($num)) {
$var = intval($num);
return TRUE;
}
return FALSE;
}
// Sets a variable to an array if valid
public static function arr(&$var, $array) {
if (is_array($array)) {
$var = $array;
return TRUE;
}
return FALSE;
}
// Sets a variable to an array if valid
public static function set_array($var, $array, $false = FALSE) {
return isset($array[$var]) ? $array[$var] : $false;
}
// Sets a variable to null if not set
public static function set_var(&$var, $false = NULL) {
$var = isset($var) ? $var : $false;
}
// Sets a variable to null if not set
public static function set_default(&$var, $default = NULL) {
return isset($var) ? $var : $default;
}
public static function set_default_null($var, $default = NULL) {
return $var !== NULL ? $var : $default;
}
// Thanks, http://www.php.net/manual/en/function.str-replace.php#102186
function str_replace_once($str_pattern, $str_replacement, $string) {
if (strpos($string, $str_pattern) !== FALSE) {
$occurrence = strpos($string, $str_pattern);
return substr_replace($string, $str_replacement, strpos($string, $str_pattern), strlen($str_pattern));
}
return $string;
}
// Removes non-numeric chars in string
public static function clean_int($str, $return_zero = TRUE) {
$str = preg_replace('#[^\d]#', '', $str);
if ($return_zero) {
// If '', then returns 0
return strval(intval($str));
} else {
// Might be ''
return $str;
}
}
// Replaces whitespace with hypthens
public static function space_to_hyphen($str) {
return preg_replace('#\s+#', '-', $str);
}
// Replaces hypthens with spaces
public static function hyphen_to_space($str) {
return preg_replace('#-#', ' ', $str);
}
// Remove comments with /* */, // or #, if they occur before any other char on a line
public static function clean_comments($str) {
$comment_pattern = '#(?:^\s*/\*.*?^\s*\*/)|(?:^(?!\s*$)[\s]*(?://|\#)[^\r\n]*)#ms';
$str = preg_replace($comment_pattern, '', $str);
return $str;
}
// Convert to title case and replace underscores with spaces
public static function ucwords($str) {
$str = strval($str);
$str = str_replace('_', ' ', $str);
return ucwords($str);
}
// Escapes regex characters as literals
public static function esc_regex($regex) {
return /*htmlspecialchars(*/
preg_quote($regex) /* , ENT_NOQUOTES)*/
;
}
// Escapes hash character as literals
public static function esc_hash($regex) {
if (is_string($regex)) {
return preg_replace('|(?<!\\\\)#|', '\#', $regex);
} else {
return FALSE;
}
}
// Ensure all parenthesis are atomic to avoid conflicting with element matches
public static function esc_atomic($regex) {
return preg_replace('#(?<!\\\\)\((?!\?)#', '(?:', $regex);
}
// Returns the current HTTP URL
public static function current_url() {
$p = self::isSecure() ? "https://" : "http://";
return $p . $_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI'];
}
// Removes crayon plugin path from absolute path
public static function path_rel($url) {
if (is_string($url)) {
return str_replace(CRAYON_ROOT_PATH, '/', $url);
}
return $url;
}
// Returns path according to detected use of forwardslash/backslash
// Deprecated from regular use after v.1.1.1
public static function path($path, $detect) {
$slash = self::detect_slash($detect);
return str_replace(array('\\', '/'), $slash, $path);
}
// Detect which kind of slash is being used in a path
public static function detect_slash($path) {
if (strpos($path, '\\')) {
// Windows
return $slash = '\\';
} else {
// UNIX
return $slash = '/';
}
}
// Returns path using forward slashes
public static function pathf($url) {
return str_replace('\\', '/', trim(strval($url)));
}
// Returns path using back slashes
public static function pathb($url) {
return str_replace('/', '\\', trim(strval($url)));
}
// returns 'true' or 'false' depending on whether this PHP file was served over HTTPS
public static function isSecure() {
// From https://core.trac.wordpress.org/browser/tags/4.0.1/src/wp-includes/functions.php
if ( isset($_SERVER['HTTPS']) ) {
if ( 'on' == strtolower($_SERVER['HTTPS']) )
return true;
if ( '1' == $_SERVER['HTTPS'] )
return true;
} elseif ( isset($_SERVER['SERVER_PORT']) && ( '443' == $_SERVER['SERVER_PORT'] ) ) {
return true;
}
return false;
}
public static function startsWith($haystack, $needle) {
return substr($haystack, 0, strlen($needle)) === $needle;
}
// Append either forward slash or backslash based on environment to paths
public static function path_slash($path) {
$path = self::pathf($path);
if (!empty($path) && !preg_match('#\/$#', $path)) {
$path .= '/';
}
if (self::startsWith($path, 'http://') && self::isSecure()) {
$path = str_replace('http://', 'https://', $path);
}
return $path;
}
public static function path_slash_remove($path) {
return preg_replace('#\/+$#', '', $path);
}
// Append a forward slash to a path if needed
public static function url_slash($url) {
$url = self::pathf($url);
if (!empty($url) && !preg_match('#\/$#', $url)) {
$url .= '/';
}
if (self::startsWith($url, 'http://') && self::isSecure()) {
$url = str_replace('http://', 'https://', $url);
}
return $url;
}
// Removes extension from file path
public static function path_rem_ext($path) {
$path = self::pathf($path);
return preg_replace('#\.\w+$#m', '', $path);
}
// Shorten a URL into a string of given length, used to identify a URL uniquely
public static function shorten_url_to_length($url, $length) {
if ($length < 1) {
return '';
}
$url = preg_replace('#(^\w+://)|([/\.])#si', '', $url);
if (strlen($url) > $length) {
$diff = strlen($url) - $length;
$rem = floor(strlen($url) / $diff);
$rem_count = 0;
for ($i = $rem - 1; $i < strlen($url) && $rem_count < $diff; $i = $i + $rem) {
$url[$i] = '.';
$rem_count++;
}
$url = preg_replace('#\.#s', '', $url);
}
return $url;
}
// Creates a unique ID from a string
public static function get_var_str() {
$get_vars = array();
foreach ($_GET as $get => $val) {
$get_vars[] = $get . '=' . $val;
}
return implode($get_vars, '&');
}
// Creates a unique ID from a string
public static function str_uid($str) {
$uid = 0;
for ($i = 1; $i < strlen($str); $i++) {
$uid += round(ord($str[$i]) * ($i / strlen($str)), 2) * 100;
}
return strval(dechex(strlen($str))) . strval(dechex($uid));
}
// Breaks up a version string into parts
public static function version_parts($version) {
preg_match('#[\d+\.]+#msi', $version, $match);
if (count($match[0])) {
return explode('.', $match[0]);
} else {
return array();
}
}
// Compares two version strings lexicographically
public static function version_compare($a, $b) {
$a_parts = self::version_parts($a);
$b_parts = self::version_parts($b);
return self::array_compare_lexi($a_parts, $b_parts);
}
// Compares two arrays lexicographically
// This could be extended with a compare function argument
public static function array_compare_lexi($a, $b) {
$short = count($a) < count($b) ? $a : $b;
for ($i = 0; $i < count($short); $i++) {
if ($a[$i] > $b[$i]) {
return 1;
} else if ($a[$i] < $b[$i]) {
return -1;
}
}
return 0;
}
// strpos with an array of $needles
public static function strposa($haystack, $needles, $insensitive = FALSE) {
if (is_array($needles)) {
foreach ($needles as $str) {
if (is_array($str)) {
$pos = self::strposa($haystack, $str, $insensitive);
} else {
$pos = $insensitive ? stripos($haystack, $str) : strpos($haystack, $str);
}
if ($pos !== FALSE) {
return $pos;
}
}
return FALSE;
} else {
return strpos($haystack, $needles);
}
}
// tests if $needle is equal to any strings in $haystack
public static function str_equal_array($needle, $haystack, $case_insensitive = TRUE) {
if (!is_string($needle) || !is_array($haystack)) {
return FALSE;
}
if ($case_insensitive) {
$needle = strtolower($needle);
}
foreach ($haystack as $hay) {
if (!is_string($hay)) {
continue;
}
if ($case_insensitive) {
$hay = strtolower($hay);
}
if ($needle == $hay) {
return TRUE;
}
}
return FALSE;
}
// Support for singular and plural string variations
public static function spnum($int, $singular, $plural = NULL) {
if (!is_int($int) || !is_string($singular)) {
$int = intval($int);
$singular = strval($singular);
}
if ($plural == NULL || !is_string($plural)) {
$plural = $singular . 's';
}
return $int . ' ' . (($int == 1) ? $singular : $plural);
}
// Turn boolean into Yes/No
public static function bool_yn($bool) {
return $bool ? 'Yes' : 'No';
}
// String to boolean, default decides what boolean value to return when not found
public static function str_to_bool($str, $default = TRUE) {
$str = self::tlower($str);
if ($default === FALSE) {
if ($str == 'true' || $str == 'yes' || $str == '1') {
return TRUE;
} else {
return FALSE;
}
} else {
if ($str == 'false' || $str == 'no' || $str == '0') {
return FALSE;
} else {
return TRUE;
}
}
}
public static function bool_to_str($bool, $strict = FALSE) {
if ($strict) {
return $bool === TRUE ? 'true' : 'false';
} else {
return $bool ? 'true' : 'false';
}
}
public static function tlower($str) {
return trim(strtolower($str));
}
// Escapes $ and \ from the replacement to avoid becoming a backreference
public static function preg_replace_escape_back($pattern, $replacement, $subject, $limit = -1, &$count = 0) {
return preg_replace($pattern, self::preg_escape_back($replacement), $subject, $limit, $count);
}
// Escape backreferences from string for use with regex
public static function preg_escape_back($string) {
// Replace $ with \$ and \ with \\
$string = preg_replace('#(\\$|\\\\)#', '\\\\$1', $string);
return $string;
}
// Detect if on a Mac or PC
public static function is_mac($default = FALSE) {
$user = $_SERVER['HTTP_USER_AGENT'];
if (stripos($user, 'macintosh') !== FALSE) {
return TRUE;
} else if (stripos($user, 'windows') !== FALSE || stripos($user, 'linux') !== FALSE) {
return FALSE;
} else {
return $default === TRUE;
}
}
// Decodes WP html entities
public static function html_entity_decode_wp($str) {
if (!is_string($str) || empty($str)) {
return $str;
}
// http://www.ascii.cl/htmlcodes.htm
$wp_entities = array('&#8216;', '&#8217;', '&#8218;', '&#8220;', '&#8221;');
$wp_replace = array('\'', '\'', ',', '"', '"');
$str = str_replace($wp_entities, $wp_replace, $str);
return $str;
}
// Constructs an html element
// If $content = FALSE, then element is closed
public static function html_element($name, $content = NULL, $attributes = array()) {
$atts = self::html_attributes($attributes);
$tag = "<$name $atts";
$tag .= $content === FALSE ? '/>' : ">$content</$name>";
return $tag;
}
public static function html_attributes($attributes, $assign = '=', $quote = '"', $glue = ' ') {
$atts = '';
foreach ($attributes as $k => $v) {
$atts .= $k . $assign . $quote . $v . $quote . $glue;
}
return $atts;
}
// Strips only the given tags in the given HTML string.
public static function strip_tags_blacklist($html, $tags) {
foreach ($tags as $tag) {
$regex = '#<\s*\b' . $tag . '\b[^>]*>.*?<\s*/\s*'. $tag . '\b[^>]*>?#msi';
$html = preg_replace($regex, '', $html);
}
return $html;
}
// Strips the given attributes found in the given HTML string.
public static function strip_attributes($html, $atts) {
foreach ($atts as $att) {
$regex = '#\b' . $att . '\b(\s*=\s*[\'"][^\'"]*[\'"])?(?=[^<]*>)#msi';
$html = preg_replace($regex, '', $html);
}
return $html;
}
// Strips all event attributes on DOM elements (prefixe with "on").
public static function strip_event_attributes($html) {
$regex = '#\bon\w+\b(\s*=\s*[\'"][^\'"]*[\'"])?(?=[^<]*>)#msi';
return preg_replace($regex, '', $html);
}
}
?>

57
util/external_use.php Normal file
View File

@ -0,0 +1,57 @@
<?php
require_once ('../global.php');
require_once (CRAYON_HIGHLIGHTER_PHP);
// These will depend on your framework
CrayonGlobalSettings::site_url('http://localhost/crayon/wp-content/plugins/crayon-syntax-highlighter/');
CrayonGlobalSettings::site_path(dirname(__FILE__));
CrayonGlobalSettings::plugin_path('http://localhost/crayon/wp-content/plugins/crayon-syntax-highlighter/');
// Should be in the header
crayon_resources();
$crayon = new CrayonHighlighter();
$crayon->code('some code');
$crayon->language('php');
$crayon->title('the title');
$crayon->marked('1-2');
$crayon->is_inline(FALSE);
// Settings
$settings = array(
// Just regular settings
CrayonSettings::NUMS => FALSE,
CrayonSettings::TOOLBAR => TRUE,
// Enqueue supported only for WP
CrayonSettings::ENQUEUE_THEMES => FALSE,
CrayonSettings::ENQUEUE_FONTS => FALSE);
$settings = CrayonSettings::smart_settings($settings);
$crayon->settings($settings);
// Print the Crayon
$crayon_formatted = $crayon->output(TRUE, FALSE);
echo $crayon_formatted;
// Utility Functions
function crayon_print_style($id, $url, $version) {
echo '<link id="',$id,'" href="',$url,'?v=',$version,'" type="text/css" rel="stylesheet" />',"\n";
}
function crayon_print_script($id, $url, $version) {
echo '<script id="',$id,'" src="',$url,'?v=',$version,'" type="text/javascript"></script>',"\n";
}
function crayon_resources() {
global $CRAYON_VERSION;
$plugin_url = CrayonGlobalSettings::plugin_path();
// jQuery only needed once! Don't have two jQuerys, so remove if you've already got one in your header :)
crayon_print_script('jquery', 'https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js', $CRAYON_VERSION);
crayon_print_style('crayon-style', $plugin_url.CRAYON_STYLE, $CRAYON_VERSION);
crayon_print_script('crayon_util_js', $plugin_url.CRAYON_JS_UTIL, $CRAYON_VERSION);
crayon_print_script('crayon-js', $plugin_url.CRAYON_JS, $CRAYON_VERSION);
crayon_print_script('crayon-jquery-popup', $plugin_url.CRAYON_JQUERY_POPUP, $CRAYON_VERSION);
}
?>

11
util/lines_to_array.rb Normal file
View File

@ -0,0 +1,11 @@
#!/usr/bin/env ruby
# Converts lines from a file into an array of strings.
if ARGV.size == 0
puts "lines_to_array.rb <file>"
else
lines = File.readlines(ARGV[0])
lines = lines.map do |line|
"'" + line.strip + "'"
end
puts '[' + lines.join(',') + ']'
end

11
util/lines_to_regex.rb Normal file
View File

@ -0,0 +1,11 @@
#!/usr/bin/env ruby
# Converts lines from a file into an alternation of regex.
if ARGV.size == 0
puts "lines_to_array.rb <file>"
else
lines = File.readlines(ARGV[0])
lines = lines.map do |line|
line.strip
end
puts '/\\b(' + lines.join('|') + ')\\b/'
end

17
util/minify.sh Normal file
View File

@ -0,0 +1,17 @@
#!/bin/bash
BASEDIR=$(dirname $0)
cd $BASEDIR
MINIFIER='/Users/Aram/Development/Tools/yuicompressor-2.4.7.jar'
INPUT_PATH='src'
OUTPUT_PATH='min'
TE_PATH='../util/tag-editor'
COLORBOX_PATH='../util/tag-editor/colorbox'
JS_PATH='../js'
function minify {
inputs=${@:0:$#}
output=${@:$#}
cat $inputs > $output
java -jar $MINIFIER $output -o $output
}

8
util/sample/abap.txt Normal file
View File

@ -0,0 +1,8 @@
* A sample function
CALL FUNCTION 'KD_GET_FILENAME_ON_F4'
EXPORTING
MASK = ',*.txt,*.*'
STATIC = 'X'
CHANGING
FILE_NAME = LV_FILE.

3
util/sample/apache.txt Normal file
View File

@ -0,0 +1,3 @@
RewriteEngine On
RewriteCond %{DOCUMENT_ROOT}/cache%{REQUEST_URI}.html -f
RewriteRule ^(.*)$ /cache/$1.html [QSA,L]

View File

@ -0,0 +1,10 @@
-- Dialog
set dialogReply to display dialog
"Dialog Text" default answer
"Text Answer" hidden answer false
buttons {"Skip", "Okay", "Cancel"}
default button
"Okay" cancel button
"Skip" with title
"Dialog Window Title" with icon note
giving up after 20

12
util/sample/arduino.txt Normal file
View File

@ -0,0 +1,12 @@
#define LED_PIN 13
void setup () {
pinMode (LED_PIN, OUTPUT); // enable pin 13 for digital output
}
void loop () {
digitalWrite (LED_PIN, HIGH); // turn on the LED
delay (1000); // wait one second (1000 milliseconds)
digitalWrite (LED_PIN, LOW); // turn off the LED
delay (1000); // wait one second
}

9
util/sample/as.txt Normal file
View File

@ -0,0 +1,9 @@
class com.example.Greeter extends MovieClip
{
public function Greeter() {}
public function onLoad():Void
{
var txtHello:TextField = this.createTextField("txtHello", 0, 0, 0, 100, 100);
txtHello.text = "Hello, world";
}
}

5
util/sample/asm.txt Normal file
View File

@ -0,0 +1,5 @@
mov eax, [ebx] ; Move the 4 bytes in memory at the address contained in EBX into EAX
mov [var], ebx ; Move the contents of EBX into the 4 bytes at memory address var. (Note, var is a 32-bit constant).
mov eax, [esi-4] ; Move 4 bytes at memory address ESI + (-4) into EAX
mov [esi+eax], cl ; Move the contents of CL into the byte at address ESI+EAX
mov edx, [esi+4*ebx] ; Move the 4 bytes of data at address ESI+4*EBX into EDX

7
util/sample/asp.txt Normal file
View File

@ -0,0 +1,7 @@
Set FS=Server.CreateObject("Scripting.FileSystemObject")
Set RS=FS.OpenTextFile(Server.MapPath("counter.txt"), 1, False)
fcount=RS.ReadLine
RS.Close
fcount=fcount+1
Set RS=Nothing
Set FS=Nothing

11
util/sample/autoit.txt Normal file
View File

@ -0,0 +1,11 @@
;Finds the average of numbers specified by a user.
;The numbers must be delimited by commas.
#NoTrayIcon
#include <GUIConstantsEx.au3>
#include <Array.au3>
;region---------------GUI-----------------------
$form = GUICreate("Average Finder", 300, 100)
$label = GUICtrlCreateLabel("Enter the numbers to be averaged separated by commas", 19, 0)
$textbox = GUICtrlCreateInput("", 20, 20, 220)
GUISetState()
;endregion---------------END GUI-----------------------

11
util/sample/batch.txt Normal file
View File

@ -0,0 +1,11 @@
if [%3]==[] (
goto :usage
)
if not exist %3 (
echo Creating %3 dir...
mkdir %3
)
echo Copying original files to %3 dir...
copy %2\* %3 >nul
echo Adding background...
mogrify -background #%1 -flatten %3\*

10
util/sample/c#.txt Normal file
View File

@ -0,0 +1,10 @@
using Functions;
class FunctionClient {
public static void Main(string[] args) {
Console.WriteLine("Function Client");
if ( args.Length == 0 ) {
Console.WriteLine("Usage: FunctionTest ... ");
return;
}
}
}

16
util/sample/c++.txt Normal file
View File

@ -0,0 +1,16 @@
#include <fstream.h>
void main () {
ifstream f1;
ofstream f2;
f1.open("scores.96");
f2.open("final.96");
int s1, s2, s3;
float w1, w2, w3;
f1 >> s1 >> w1;
f1 >> s2 >> w2;
f1 >> s3 >> w3;
f2 << (s1*w1+s2*w2+s3*w3);
}

9
util/sample/c.txt Normal file
View File

@ -0,0 +1,9 @@
#include <stdio.h>
int main(void) {
int x;
x = 0;
// Uses a pointer
set(&x, 42);
printf("%d %d", x);
return 0;
}

5
util/sample/clojure.txt Normal file
View File

@ -0,0 +1,5 @@
(defn keyword-params-request
"Converts string keys in :params map to keywords. See: wrap-keyword-params."
{:added "1.2"}
[request]
(update-in request [:params] keyify-params))

14
util/sample/coffee.txt Normal file
View File

@ -0,0 +1,14 @@
# Example Script
class Animal
constructor: (@name) ->
move: (meters) ->
alert @name + " moved #{meters}m."
alert @name.foo
alert this.name
class Snake extends Animal
move: ->
alert "Slithering..."
super 5

12
util/sample/css.txt Normal file
View File

@ -0,0 +1,12 @@
@import url('fonts/monaco/monaco.css');
/* General ========================= */
.crayon-syntax {
overflow: hidden !important;
position: relative !important;
}
.crayon-syntax .crayon-toolbar {
position: relative;
overflow: hidden;
}

8
util/sample/default.txt Normal file
View File

@ -0,0 +1,8 @@
// A sample class
class Human {
private int age = 0;
public void birthday() {
age++;
print('Happy Birthday!');
}
}

9
util/sample/delphi.txt Normal file
View File

@ -0,0 +1,9 @@
type
THelloWorld = class
procedure Put;
end;
procedure THelloWorld.Put;
begin
Writeln('Hello, World!');
end;

9
util/sample/diff.txt Normal file
View File

@ -0,0 +1,9 @@
*** testing ***
It is important to spell
--- testing ---
-check this dokument. On
+check this document. On
the other hand, a
! misspelled word isn't
the end of the world.
@@ -22,3 +22,7 @@

13
util/sample/dws.txt Normal file
View File

@ -0,0 +1,13 @@
type
THelloWorld = class
procedure Put; // you can also implement out of line
begin
PrintLn('Hello, World!');
end
end;
var HelloWorld := new THelloWorld; // strong typing, inferred
HelloWorld.Put;
// no need to release objects thanks to automatic memory management

12
util/sample/erlang.txt Normal file
View File

@ -0,0 +1,12 @@
%% qsort:qsort(List)
%% Sort a list of items
-module(qsort). % This is the file 'qsort.erl'
-export([qsort/1]). % A function 'qsort' with 1 parameter is exported (no type, no name)
qsort([]) -> []; % If the list [] is empty, return an empty list (nothing to sort)
qsort([Pivot|Rest]) ->
% Compose recursively a list with 'Front' for all elements that should be before 'Pivot'
% then 'Pivot' then 'Back' for all elements that should be after 'Pivot'
qsort([Front || Front <- Rest, Front < Pivot])
++ [Pivot] ++
qsort([Back || Back <- Rest, Back >= Pivot]).

11
util/sample/go.txt Normal file
View File

@ -0,0 +1,11 @@
package geometry
import "math"
// Test functions
func add(a, b int) int { return a + b }
func (self *Point) Scale(factor float64) {
self.setX(self.x * factor)
self.setY(self.y * factor)
}
type Writer interface {
Write(p []byte) (n int, err os.Error)
}

23
util/sample/haskell.txt Normal file
View File

@ -0,0 +1,23 @@
module Interpret(interpret) where
import Prog
import System.IO.Unsafe
import Control.Monad
import Char
-- In a call to this function such as "interpret prog vars entry debug":
-- prog is the ABCD program to be interpreted;
-- vars represents the initial values of the four variables;
-- entry is the name of the entry point function, "main" by default; and
-- debug specifies whether the user wants debugging output.
interpret :: Prog -> Vars -> String -> MaybeDebug -> IO ()
interpret prog vars entry debug = do
    let context = Context prog vars entry debug 0
    let newContext = runFunc entry context
    let output =
        case newContext of
            IError s -> "abcdi: " ++ s
            IOK c -> (strVal (getVar A (cVars c))) ++ "\n"
    putStrLn output

10
util/sample/ilogic.txt Normal file
View File

@ -0,0 +1,10 @@
Dim map As Inventor.NameValueMap = ThisApplication.TransientObjects.CreateNameValueMap()
map.Add("Arg1", "Arg1Value")
iLogicVb.RunRule("ruleName", map)
iLogicVb.RunRule("PartA:1", "ruleName")
InventorVb.RunMacro("projectName", "moduleName", "macroName")
AddVbRule "RuleName"
AddReference "fileName.dll"
AddVbFile "fileName.vb"
AddResources "fileName.resources"
arg1Value = RuleArguments("Arg1")

10
util/sample/ini.txt Normal file
View File

@ -0,0 +1,10 @@
; last modified 1 April 2001 by John Doe
[owner]
name=John Doe
organization=Acme Widgets Inc.
[database]
; use IP address in case network name resolution is not working
server=192.0.2.62
port=143
file="payroll.dat"

8
util/sample/java.txt Normal file
View File

@ -0,0 +1,8 @@
// A sample class
class Human extends Mammal implements Humanoid {
private int age = 0;
public void birthday() {
age++;
System.out.println('Happy Birthday!');
}
}

12
util/sample/js.txt Normal file
View File

@ -0,0 +1,12 @@
// Convert '-10px' to -10
function px_to_int(pixels) {
if (typeof pixels != 'string') {
return 0;
}
var result = pixels.replace(/[^-0-9]/g, '');
if (result.length == 0) {
return 0;
} else {
return parseInt(result);
}
}

18
util/sample/kl.txt Normal file
View File

@ -0,0 +1,18 @@
/*
* Swirley Movement OP KL Example
*/
require Math;
operator swirleyMovementOp(
Scalar seconds,
Index id,
Xfo baseXfo,
io Xfo xfo
) {
xfo.tr = baseXfo.tr + Vec3(sin((seconds * 2.3) + (id * 3.2)) * 3.0, cos(seconds * 4.30) * 3.0, 0.0);
// The following line will log a message to the console...
// report("swirleyMovementOp :" + xfo.tr);
}

13
util/sample/less.txt Normal file
View File

@ -0,0 +1,13 @@
@import "lib.css";
@the-border: 1px;
@base-color: #111;
@red: #842210;
#header {
color: (@base-color * 3);
border-left: @the-border;
border-right: (@the-border * 2);
}
#footer {
color: (@base-color + #003300);
border-color: desaturate(@red, 10%);
}

12
util/sample/lisp.txt Normal file
View File

@ -0,0 +1,12 @@
;Coding starts here
(defun c:lg ( / x_object x_length)
(vl-load-com)
(setq x_object (entsel))
(setq x_object (vlax-Ename->Vla-Object (car x_object)))
(setq x_length (vlax-curve-getdistatparam x_object
(vlax-curve-getendparam x_object )))
(alert (strcat "Length = " (rtos x_length)))
(princ)
);defun
(princ)
;Coding ends here

7
util/sample/lua.txt Normal file
View File

@ -0,0 +1,7 @@
fibs = { 1, 1 } -- Initial values for fibs[1] and fibs[2].
setmetatable(fibs, {
__index = function(name, n) -- Call this function if fibs[n] does not exist.
name[n] = name[n - 1] + name[n - 2] -- Calculate and memoize fibs[n].
return name[n]
end
})

9
util/sample/matlab.txt Normal file
View File

@ -0,0 +1,9 @@
clear
N = input('Give numerator: ');
D = input('Give denominator: ');
if D==0
'Sorry, cannot divide by zero'
else
ratio = N/D
end

24
util/sample/mel.txt Normal file
View File

@ -0,0 +1,24 @@
// Code starts here
global proc human(int $age){
string $ageExt;
$age++;
if($age == 0){
$ageExt = "th";
}else if($age == 1){
$ageExt = "st";
}else if($age == 2){
$ageExt = "nd";
}else{
$ageExt = "th";
}
print("Happy " + $age + $ageExt + " Birthday!\n");
}
int $i=0;
for($i=0;$i<=99;$i+=1){
human($i);
}

8
util/sample/monkey.txt Normal file
View File

@ -0,0 +1,8 @@
Class GameApp Extends App
Field player:Player
Method OnCreate:Int()
local img:Image = LoadImage("player.png")
player = New Player(img, 100, 100)
SetUpdateRate 60
End
End

8
util/sample/mysql.txt Normal file
View File

@ -0,0 +1,8 @@
CREATE TABLE shop (
article INT(4) UNSIGNED ZEROFILL DEFAULT '0000' NOT NULL,
dealer CHAR(20) DEFAULT '' NOT NULL,
price DOUBLE(16,2) DEFAULT '0.00' NOT NULL,
PRIMARY KEY(article, dealer));
INSERT INTO shop VALUES
(1,'A',3.45),(1,'B',3.99),(2,'A',10.99),(3,'B',1.45),
(3,'C',1.69),(3,'D',1.25),(4,'D',19.95);

8
util/sample/objc.txt Normal file
View File

@ -0,0 +1,8 @@
#import <objc/Object.h>
@interface Forwarder : Object {
id recipient; // The object we want to forward the message to.
}
// Accessor methods.
- (id) recipient;
- (id) setRecipient:(id)_recipient;
@end

14
util/sample/perl.txt Normal file
View File

@ -0,0 +1,14 @@
while (<STDIN>) {
$oldStr = $_;
foreach $k (keys %dic) {
s/$k/$dic{$k}/g;
}
$newStr = $_;
if ($oldStr ne $newStr) {
print STDERR "\n";
print STDERR "old>>$oldStr";
print STDERR "new>>$newStr";
}
print;
}

8
util/sample/pgsql.txt Normal file
View File

@ -0,0 +1,8 @@
CREATE TABLE arr(f1 int[], f2 int[]);
INSERT INTO arr VALUES (ARRAY[[1,2],[3,4]], ARRAY[[5,6],[7,8]]);
SELECT ARRAY[f1, f2, '{{9,10},{11,12}}'::int[]] FROM arr;
array_prepend(1, ARRAY[2,3])
SELECT ROW(table.*) IS NULL FROM table; -- detect all-null rows
SELECT getf1(CAST(ROW(11,'this is a test',2.5) AS myrowtype));
CHARACTER VARYING

10
util/sample/php.txt Normal file
View File

@ -0,0 +1,10 @@
<?php
// A sample class
class Human {
$age = 0;
function birthday() {
$age++;
echo 'Happy Birthday!';
}
}
?>

11
util/sample/plsql.txt Normal file
View File

@ -0,0 +1,11 @@
DECLARE
number1 NUMBER(2);
number2 number1%TYPE := 17; -- value default
text1 VARCHAR2(12) := 'Hello world';
text2 DATE := SYSDATE; -- current date and time
BEGIN
SELECT street_number
INTO number1
FROM address
WHERE name = 'INU';
END;

2
util/sample/ps.txt Normal file
View File

@ -0,0 +1,2 @@
# Find the processes that use more than 1000 MB of memory and kill them
Get-Process | Where-Object { $_.WS -gt 1000MB } | Stop-Process

9
util/sample/python.txt Normal file
View File

@ -0,0 +1,9 @@
# Merge example
def mergeWithoutOverlap(oneDict, otherDict):
newDict = oneDict.copy()
for key in otherDict.keys():
if key in oneDict.keys():
raise ValueError, "the two dictionaries are sharing keys!"
newDict[key] = otherDict[key]
return newDict

14
util/sample/r.txt Normal file
View File

@ -0,0 +1,14 @@
library(caTools) # external package providing write.gif function
jet.colors <- colorRampPalette(c("#00007F", "blue", "#007FFF", "cyan", "#7FFF7F",
"yellow", "#FF7F00", "red", "#7F0000"))
m <- 1200 # define size
C <- complex( real=rep(seq(-1.8,0.6, length.out=m), each=m ),
imag=rep(seq(-1.2,1.2, length.out=m), m ) )
C <- matrix(C,m,m) # reshape as square matrix of complex numbers
Z <- 0 # initialize Z to zero
X <- array(0, c(m,m,20)) # initialize output 3D array
for (k in 1:20) { # loop with 20 iterations
Z <- Z^2+C # the central difference equation
X[,,k] <- exp(-abs(Z)) # capture results
}
write.gif(X, "Mandelbrot.gif", col=jet.colors, delay=100)

7
util/sample/reg.txt Normal file
View File

@ -0,0 +1,7 @@
Windows Registry Editor Version 5.00
[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft]
"Value A"="<String value data>"
"Value B"=hex:<Binary data (as comma-delimited list of hexadecimal values)>
"Value C"=dword:<DWORD value integer>
"Value D"=hex(7):<Multi-string value data (as comma-delimited list of hexadecimal values)>
"Value E"=hex(2):<Expandable string value data (as comma-delimited list of hexadecimal values)>

9
util/sample/ruby.txt Normal file
View File

@ -0,0 +1,9 @@
# 'w' denotes "write mode".
File.open('file.txt', 'w') do |file|
file.puts 'Wrote some text.'
end # File is automatically closed here
File.readlines('file.txt').each do |line|
puts line
end
# => Wrote some text.

8
util/sample/rust.txt Normal file
View File

@ -0,0 +1,8 @@
/* The branches in this function exhibit Rust's optional implicit return
values, which can be utilized where a more "functional" style is preferred.
Unlike C++ and related languages, Rust's `if` construct is an expression
rather than a statement, and thus has a return value of its own. */
fn recursive_factorial(n: int) -> int {
if n <= 1 { 1 }
else { n * recursive_factorial(n-1) }
}

11
util/sample/sass.txt Normal file
View File

@ -0,0 +1,11 @@
@mixin adjust-location($x, $y) {
@if unitless($x) {
@warn "Assuming #{$x} to be in pixels";
$x: 1px * $x;
}
@if unitless($y) {
@warn "Assuming #{$y} to be in pixels";
$y: 1px * $y;
}
position: relative; left: $x; top: $y;
}

15
util/sample/scala.txt Normal file
View File

@ -0,0 +1,15 @@
// A sample class
object Newton extends App {
def EPS = 1e-5
def sqrt(x: Double): Double = {
def loop(y: Double): Double =
if (math.abs(y * y - x) > EPS) loop(((x / y) + y) / 2.0)
else y
loop(1.0)
}
println(sqrt(2.0)) // 1.41
}

6
util/sample/scheme.txt Normal file
View File

@ -0,0 +1,6 @@
(define var "goose")
;; Any reference to var here will be bound to "goose"
(let* ((var1 10)
(var2 (+ var1 12)))
;; But the definition of var1 could not refer to var2
)

12
util/sample/sh.txt Normal file
View File

@ -0,0 +1,12 @@
#!/bin/bash
for jpg in "$@" ; do
png="${jpg%.jpg}.png"
echo converting "$jpg" ...
if convert "$jpg" jpg.to.png ; then
mv jpg.to.png "$png"
else
echo 'error: failed output saved in "jpg.to.png".' 1>&2
exit 1
fi
done
echo all conversions successful

7
util/sample/swift.txt Normal file
View File

@ -0,0 +1,7 @@
class Human {
var age = 0
func birthday() {
age++;
println('Happy Birthday!');
}
}

5
util/sample/tex.txt Normal file
View File

@ -0,0 +1,5 @@
\begin{document}
\hello % Here a comment
% Here a comment from line beginning
10\% is not a comment.

4
util/sample/tsql.txt Normal file
View File

@ -0,0 +1,4 @@
IF DATEPART(dw, GETDATE()) = 7 OR DATEPART(dw, GETDATE()) = 1
PRINT 'It is the weekend.'
ELSE
PRINT 'It is a weekday.'

10
util/sample/vb.txt Normal file
View File

@ -0,0 +1,10 @@
Option Explicit
Dim Count As Integer
Private Sub Form_Load()
Count = 0
Timer1.Interval = 1000 ' units of milliseconds
End Sub
Private Sub Timer1_Timer()
Count = Count + 1
lblCount.Caption = Count
End Sub

8
util/sample/vbnet.txt Normal file
View File

@ -0,0 +1,8 @@
Imports System
Module Module1
'This program will display Hello World
Sub Main()
Console.WriteLine("Hello World")
Console.ReadKey()
End Sub
End Module

12
util/sample/vim.txt Normal file
View File

@ -0,0 +1,12 @@
"Toggle word checking on or off...
function! WordCheck ()
"Toggle the flag (or set it if it doesn't yet exist)...
let w:check_words = exists('w:check_words') ? !w:check_words : 1
"Turn match mechanism on/off, according to new state of flag...
if w:check_words
exec s:words_matcher
else
match none
endif
endfunction

12
util/sample/xhtml.txt Normal file
View File

@ -0,0 +1,12 @@
<body onload="loadpdf()">
<p>This is an example of an
<abbr title="Extensible HyperText Markup Language">XHTML</abbr> 1.0 Strict document.<br />
<img id="validation-icon" src="http://www.w3.org/Icons/valid-xhtml10" alt="Valid XHTML 1.0 Strict" /><br />
<object id="pdf-object"
name="pdf-object"
type="application/pdf"
data="http://www.w3.org/TR/xhtml1/xhtml1.pdf"
width="100%"
height="500">
</object>
</p>

7
util/sample/yaml.txt Normal file
View File

@ -0,0 +1,7 @@
---
receipt: Oz-Ware Purchase Invoice
date: 2007-08-06
customer:
given: "Dorothy"
family: Gale
...

20
util/sample/zsh.txt Normal file
View File

@ -0,0 +1,20 @@
parse_options()
{
o_port=(-p 9999)
o_root=(-r WWW)
o_log=(-d ZWS.log)
zparseopts -K -- p:=o_port r:=o_root l:=o_log h=o_help
if [[ $? != 0 || "$o_help" != "" ]]; then
echo Usage: $(basename "$0") "[-p PORT] [-r DIRECTORY]"
exit 1
fi
port=$o_port[2]
root=$o_root[2]
log=$o_log[2]
if [[ $root[1] != '/' ]]; then root="$PWD/$root"; fi
}
# now use the function:
parse_options $*

View File

@ -0,0 +1,21 @@
import sys
'''
Concatenates all arguments together, assuming they are files, into the last argument file.
'''
if len(sys.argv) < 4:
print "Usage: file_concat.py <inputfile1>, <inputfile2>, ... <outputfile>"
exit()
else:
ins = sys.argv[1:-1]
out = sys.argv[-1]
outfile = open(out, 'w')
all_lines = []
for i in ins:
f = open(i, 'r')
lines = [x.strip() for x in f.readlines()]
all_lines += lines
outfile.write('\n'.join(all_lines))

View File

@ -0,0 +1,26 @@
import sys
import keyword_scraper
'''
Invokes keyword_scraper to sort a file of keywords
Example:
$ python keyword_scraper_tool.py geshi_lang_file.php somedir
'''
if len(sys.argv) < 2:
print "Usage: keyword_scraper_tool <inputfile> <outputfile>"
exit()
else:
infile_ = sys.argv[1]
outfile_ = sys.argv[2] if len(sys.argv) >= 3 else None
infile = open(infile_, 'r')
keywords = [x.strip() for x in infile.readlines()]
keywords.sort(keyword_scraper.cmp_keywords)
if outfile_:
outfile = open(outfile_, 'w')
outfile.write('\n'.join(keywords))

View File

@ -0,0 +1,73 @@
import re
import os
def cmp_keywords(x,y):
'''
Sorts keywords by length, and then alphabetically
'''
if len(x) < len(y):
return 1
elif len(x) == len(y):
# Sort alphabetically
if x == y:
return 0
elif x < y:
return -1
else:
return 1
else:
return -1
def keywords(infile, outdir):
'''
Scrapes comma separated keywords out of a file and sorts them in descending order of length.
It is assumed a keyword is surrounded in quotes ('' or ""), are grouped by commas and separated by line breaks.
The output is then printed and each group is written in text files in the given directory
An example use case for this is scraping keywords out of GeSHi language files:
>>> keywords('geshi_lang_file.php', 'somedir')
'''
if outdir and not os.path.exists(outdir):
os.makedirs(outdir)
f = open(infile, 'r')
fs = f.read()
fs = re.sub(r"(//.*?[\r\n])|(/\*.*?\*/)", '', fs)
matches = re.findall(r"(?:(?:'[^']+'|\"[^\"]+\")(?:[ \t]*[\r\n]?[ \t]*,[ \t]*[\r\n]?[ \t]*)?(?!\s*=>)){2,}", fs, flags=re.I | re.M | re.S)
output = ''
group = 0
for i in matches:
match = re.findall(r"'([^']+)'", i, flags=re.I | re.M | re.S)
match.sort(cmp=cmp_keywords)
suboutput = ''
for m in match:
m = m.strip()
if len(m) > 0:
suboutput += m + '\n'
suboutput += '\n'
if outdir:
w = open(outdir + '/' + str(group) + '.txt' , 'w')
w.write(suboutput)
output += suboutput
group += 1;
print output
exit()
matches = re.findall(r"(['\"])(.*?)\1", fs, re.I | re.M | re.S)
output = ''
if len(matches):
for m in matches:
s = m[1].strip()
if len(s) > 0:
output += s + '\n'
f.close()
print output
if w:
w.write(output)
w.close()

View File

@ -0,0 +1,18 @@
import sys
import keyword_scraper
'''
Invokes keyword_scraper over command line
Example:
$ python keyword_scraper_tool.py geshi_lang_file.php somedir
'''
if len(sys.argv) < 2:
print "Usage: keyword_scraper_tool <inputfile> [directory]"
exit()
else:
infile = sys.argv[1]
outdir = sys.argv[2] if len(sys.argv) >= 3 else None
keyword_scraper.keywords(infile, outdir)

1
util/scraper/readme.txt Normal file
View File

@ -0,0 +1 @@
I created this to help scrape keywords out of text files. Mostly I use it to scrape GeSHi language files and remove the bits I need.

48
util/settings_list.txt Normal file
View File

@ -0,0 +1,48 @@
theme
font
font-size-enable
font-size
preview
height-set
height-mode
height
height-unit
width-set
width-mode
width
width-unit
top-set
top-margin
left-set
left-margin
bottom-set
bottom-margin
right-set
right-margin
h-align
float-enable
toolbar
toolbar-overlay
toolbar-hide
toolbar-delay
show-lang
show-title
striped
marking
nums
nums-toggle
trim-whitespace
tab-size
fallback-lang
local-path
scroll
plain
show-plain
runtime
exp-scroll
touchscreen
disable-anim
error-log
error-log-sys
error-msg-show
error-msg

View File

@ -0,0 +1,145 @@
/*
Colorbox Core Style:
The following CSS is consistent between example themes and should not be altered.
*/
#colorbox.crayon-colorbox, #cboxOverlay.crayon-colorbox, .crayon-colorbox #cboxWrapper {
position: absolute;
top: 0;
left: 0;
z-index: 9999;
overflow: hidden;
}
#cboxOverlay.crayon-colorbox {
position: fixed;
width: 100%;
height: 100%;
}
.crayon-colorbox #cboxMiddleLeft, .crayon-colorbox #cboxBottomLeft {
clear: left;
}
.crayon-colorbox #cboxContent {
position: relative;
}
.crayon-colorbox #cboxLoadedContent {
overflow: auto;
-webkit-overflow-scrolling: touch;
}
.crayon-colorbox #cboxTitle {
/* Fixes overlay issue preventing tag editor controls from being selected */
display: none !important;
}
.crayon-colorbox #cboxLoadingOverlay, .crayon-colorbox #cboxLoadingGraphic {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
.crayon-colorbox #cboxPrevious, .crayon-colorbox #cboxNext, .crayon-colorbox #cboxClose, .crayon-colorbox #cboxSlideshow {
cursor: pointer;
}
.crayon-colorbox .cboxPhoto {
float: left;
margin: auto;
border: 0;
display: block;
max-width: none;
-ms-interpolation-mode: bicubic;
}
.crayon-colorbox .cboxIframe {
width: 100%;
height: 100%;
display: block;
border: 0;
}
#colorbox.crayon-colorbox, .crayon-colorbox #cboxContent, .crayon-colorbox #cboxLoadedContent {
box-sizing: content-box;
-moz-box-sizing: content-box;
-webkit-box-sizing: content-box;
}
/*
User Style:
Change the following styles to modify the appearance of Colorbox. They are
ordered & tabbed in a way that represents the nesting of the generated HTML.
*/
#cboxOverlay.crayon-colorbox {
background: #000;
}
#colorbox.crayon-colorbox {
outline: 0;
}
.crayon-colorbox #cboxContent {
margin-top: 20px;
background: #000;
}
.crayon-colorbox .cboxIframe {
background: #fff;
}
.crayon-colorbox #cboxError {
padding: 50px;
border: 1px solid #ccc;
}
.crayon-colorbox #cboxLoadedContent {
border: 5px solid #000;
background: #fff;
}
.crayon-colorbox #cboxTitle {
position: absolute;
top: -20px;
left: 0;
color: #ccc;
}
.crayon-colorbox #cboxCurrent {
position: absolute;
top: -20px;
right: 0px;
color: #ccc;
}
/* these elements are buttons, and may need to have additional styles reset to avoid unwanted base styles */
.crayon-colorbox #cboxPrevious, .crayon-colorbox #cboxNext, .crayon-colorbox #cboxSlideshow, .crayon-colorbox #cboxClose {
border: 0;
padding: 0;
margin: 0;
overflow: visible;
width: auto;
background: none;
}
/* avoid outlines on :active (mouseclick), but preserve outlines on :focus (tabbed navigating) */
.crayon-colorbox #cboxPrevious:active, .crayon-colorbox #cboxNext:active, .crayon-colorbox #cboxSlideshow:active, .crayon-colorbox #cboxClose:active {
outline: 0;
}
.crayon-colorbox #cboxSlideshow {
position: absolute;
top: -20px;
right: 90px;
color: #fff;
}
.crayon-colorbox #cboxContent {
margin-top: 0
}
.crayon-colorbox #cboxLoadedContent {
border: 0
}

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1,51 @@
(function ($) {
var settings = CrayonTagEditorSettings;
window.CrayonQuickTags = new function () {
var base = this;
base.init = function () {
base.sel = '*[id*="crayon_quicktag"],*[class*="crayon_quicktag"]';
var buttonText = settings.quicktag_text;
buttonText = buttonText !== undefined ? buttonText : 'crayon';
QTags.addButton('crayon_quicktag', buttonText, function () {
CrayonTagEditor.showDialog({
insert: function (shortcode) {
QTags.insertContent(shortcode);
},
select: base.getSelectedText,
editor_str: 'html',
output: 'encode'
});
$(base.sel).removeClass('qt_crayon_highlight');
});
var qt_crayon;
var find_qt_crayon = setInterval(function () {
qt_crayon = $(base.sel).first();
if (typeof qt_crayon != 'undefined') {
CrayonTagEditor.bind(base.sel);
clearInterval(find_qt_crayon);
}
}, 100);
};
base.getSelectedText = function () {
if (QTags.instances.length == 0) {
return null;
} else {
var qt = QTags.instances[0];
var startPos = qt.canvas.selectionStart;
var endPos = qt.canvas.selectionEnd;
return qt.canvas.value.substring(startPos, endPos);
}
};
};
$(document).ready(function () {
CrayonQuickTags.init();
});
})(jQueryCrayon);

View File

@ -0,0 +1,631 @@
(function ($) {
window.CrayonTagEditor = new function () {
var base = this;
var isInit = false;
var loaded = false;
var editing = false;
var insertCallback, editCallback, showCallback, hideCallback, selectCallback;
// Used for encoding, decoding
var inputHTML, outputHTML, editor_name, ajax_class_timer;
var ajax_class_timer_count = 0;
var code_refresh, url_refresh;
// Current $ obj of pre node
var currCrayon = null;
// Classes from pre node, excl. settings
var currClasses = '';
// Whether to make span or pre
var is_inline = false;
// Generated in WP and contains the settings
var s, gs, util;
// CSS
var dialog, code, clear, submit, cancel;
var colorboxSettings = {
inline: true,
width: 690,
height: '90%',
closeButton: false,
fixed: true,
transition: 'none',
className: 'crayon-colorbox',
onOpen: function () {
$(this.outer).prepend($(s.bar_content));
},
onComplete: function () {
$(s.code_css).focus();
},
onCleanup: function () {
$(s.bar).prepend($(s.bar_content));
}
};
base.init = function () {
s = CrayonTagEditorSettings;
gs = CrayonSyntaxSettings;
util = CrayonUtil;
// This allows us to call $.colorbox and reload without needing a button click.
colorboxSettings.href = s.content_css;
};
base.bind = function (buttonCls) {
if (!isInit) {
isInit = true;
base.init();
}
var $buttons = $(buttonCls);
$buttons.each(function (i, button) {
var $button = $(button);
var $wrapper = $('<a class="crayon-tag-editor-button-wrapper"></a>').attr('href', s.content_css);
$button.after($wrapper);
$wrapper.append($button);
$wrapper.colorbox(colorboxSettings);
});
};
base.hide = function () {
$.colorbox.close();
return false;
};
// XXX Loads dialog contents
base.loadDialog = function (callback) {
// Loaded once url is given
if (!loaded) {
loaded = true;
} else {
callback && callback();
return;
}
// Load the editor content
CrayonUtil.getAJAX({action: 'crayon-tag-editor', is_admin: gs.is_admin}, function (data) {
dialog = $('<div id="' + s.css + '"></div>');
dialog.appendTo('body').hide();
dialog.html(data);
base.setOrigValues();
submit = dialog.find(s.submit_css);
cancel = dialog.find(s.cancel_css);
code = $(s.code_css);
clear = $('#crayon-te-clear');
code_refresh = function () {
var clear_visible = clear.is(":visible");
if (code.val().length > 0 && !clear_visible) {
clear.show();
code.removeClass(gs.selected);
} else if (code.val().length <= 0) {
clear.hide();
}
};
code.keyup(code_refresh);
code.change(code_refresh);
clear.click(function () {
code.val('');
code.removeClass(gs.selected);
code.focus();
});
var url = $(s.url_css);
var url_info = $(s.url_info_css);
var exts = CrayonTagEditorSettings.extensions;
url_refresh = function () {
if (url.val().length > 0 && !url_info.is(":visible")) {
url_info.show();
url.removeClass(gs.selected);
} else if (url.val().length <= 0) {
url_info.hide();
}
// Check for extensions and select language automatically
var ext = CrayonUtil.getExt(url.val());
if (ext) {
var lang = exts[ext];
// Otherwise use the extention as the lang
var lang_id = lang ? lang : ext;
var final_lang = CrayonTagEditorSettings.fallback_lang;
$(s.lang_css + ' option').each(function () {
if ($(this).val() == lang_id) {
final_lang = lang_id;
}
});
$(s.lang_css).val(final_lang);
}
};
url.keyup(url_refresh);
url.change(url_refresh);
var setting_change = function () {
var setting = $(this);
var orig_value = $(this).attr(gs.orig_value);
if (typeof orig_value == 'undefined') {
orig_value = '';
}
// Depends on type
var value = base.settingValue(setting);
CrayonUtil.log(setting.attr('id') + ' value: ' + value);
var highlight = null;
if (setting.is('input[type=checkbox]')) {
highlight = setting.next('span');
}
CrayonUtil.log(' >>> ' + setting.attr('id') + ' is ' + orig_value + ' = ' + value);
if (orig_value == value) {
// No change
setting.removeClass(gs.changed);
if (highlight) {
highlight.removeClass(gs.changed);
}
} else {
// Changed
setting.addClass(gs.changed);
if (highlight) {
highlight.addClass(gs.changed);
}
}
// Save standardized value for later
base.settingValue(setting, value);
};
$('.' + gs.setting + '[id]:not(.' + gs.special + ')').each(function () {
$(this).change(setting_change);
$(this).keyup(setting_change);
});
callback && callback();
});
};
// XXX Displays the dialog.
base.showDialog = function (args) {
var wasLoaded = loaded;
base.loadDialog(function () {
if (!wasLoaded) {
// Forcefully load the colorbox. Otherwise it populates the content after opening the window and
// never renders.
$.colorbox(colorboxSettings);
}
base._showDialog(args);
});
};
base._showDialog = function (args) {
args = $.extend({
insert: null,
edit: null,
show: null,
hide: base.hide,
select: null,
editor_str: null,
ed: null,
node: null,
input: null,
output: null
}, args);
// Need to reset all settings back to original, clear yellow highlighting
base.resetSettings();
// Save these for when we add a Crayon
insertCallback = args.insert;
editCallback = args.edit;
showCallback = args.show;
hideCallback = args.hide;
selectCallback = args.select;
inputHTML = args.input;
outputHTML = args.output;
editor_name = args.editor_str;
var currNode = args.node;
var currNode = args.node;
is_inline = false;
// Unbind submit
submit.unbind();
submit.click(function (e) {
base.submitButton();
e.preventDefault();
});
base.setSubmitText(s.submit_add);
cancel.unbind();
cancel.click(function (e) {
base.hide();
e.preventDefault();
});
if (base.isCrayon(currNode)) {
currCrayon = $(currNode);
if (currCrayon.length != 0) {
// Read back settings for editing
currClasses = currCrayon.attr('class');
var re = new RegExp('\\b([A-Za-z-]+)' + s.attr_sep + '(\\S+)', 'gim');
var matches = re.execAll(currClasses);
// Retain all other classes, remove settings
currClasses = $.trim(currClasses.replace(re, ''));
var atts = {};
for (var i in matches) {
var id = matches[i][1];
var value = matches[i][2];
atts[id] = value;
}
// Title
var title = currCrayon.attr('title');
if (title) {
atts['title'] = title;
}
// URL
var url = currCrayon.attr('data-url');
if (url) {
atts['url'] = url;
}
// Inverted settings
if (typeof atts['highlight'] != 'undefined') {
atts['highlight'] = '0' ? '1' : '0';
}
// Inline
is_inline = currCrayon.hasClass(s.inline_css);
atts['inline'] = is_inline ? '1' : '0';
// Ensure language goes to fallback if invalid
var avail_langs = [];
$(s.lang_css + ' option').each(function () {
var value = $(this).val();
if (value) {
avail_langs.push(value);
}
});
if ($.inArray(atts['lang'], avail_langs) == -1) {
atts['lang'] = s.fallback_lang;
}
// Validate the attributes
atts = base.validate(atts);
// Load in attributes, add prefix
for (var att in atts) {
var setting = $('#' + gs.prefix + att + '.' + gs.setting);
var value = atts[att];
base.settingValue(setting, value);
// Update highlights
setting.change();
// If global setting changes and we access settings, it should declare loaded settings as changed even if they equal the global value, just so they aren't lost on save
if (!setting.hasClass(gs.special)) {
setting.addClass(gs.changed);
if (setting.is('input[type=checkbox]')) {
highlight = setting.next('span');
highlight.addClass(gs.changed);
}
}
CrayonUtil.log('loaded: ' + att + ':' + value);
}
editing = true;
base.setSubmitText(s.submit_edit);
// Code
var content = currCrayon.html();
if (inputHTML == 'encode') {
content = CrayonUtil.encode_html(content);
} else if (inputHTML == 'decode') {
content = CrayonUtil.decode_html(content);
}
code.val(content);
} else {
CrayonUtil.log('cannot load currNode of type pre');
}
} else {
if (selectCallback) {
// Add selected content as code
code.val(selectCallback);
}
// We are creating a new Crayon, not editing
editing = false;
base.setSubmitText(s.submit_add);
currCrayon = null;
currClasses = '';
}
// Inline
var inline = $('#' + s.inline_css);
inline.change(function () {
is_inline = $(this).is(':checked');
var inline_hide = $('.' + s.inline_hide_css);
var inline_single = $('.' + s.inline_hide_only_css);
var disabled = [s.mark_css, s.range_css, s.title_css, s.url_css];
for (var i in disabled) {
var obj = $(disabled[i]);
obj.attr('disabled', is_inline);
}
if (is_inline) {
inline_hide.hide();
inline_single.hide();
inline_hide.closest('tr').hide();
for (var i in disabled) {
var obj = $(disabled[i]);
obj.addClass('crayon-disabled');
}
} else {
inline_hide.show();
inline_single.show();
inline_hide.closest('tr').show();
for (var i in disabled) {
var obj = $(disabled[i]);
obj.removeClass('crayon-disabled');
}
}
});
inline.change();
// Show the dialog
var dialog_title = editing ? s.edit_text : s.add_text;
$(s.dialog_title_css).html(dialog_title);
if (showCallback) {
showCallback();
}
code.focus();
code_refresh();
url_refresh();
if (ajax_class_timer) {
clearInterval(ajax_class_timer);
ajax_class_timer_count = 0;
}
var ajax_window = $('#TB_window');
ajax_window.hide();
var fallback = function () {
ajax_window.show();
// Prevent draw artifacts
var oldScroll = $(window).scrollTop();
$(window).scrollTop(oldScroll + 10);
$(window).scrollTop(oldScroll - 10);
};
ajax_class_timer = setInterval(function () {
if (typeof ajax_window != 'undefined' && !ajax_window.hasClass('crayon-te-ajax')) {
ajax_window.addClass('crayon-te-ajax');
clearInterval(ajax_class_timer);
fallback();
}
if (ajax_class_timer_count >= 100) {
// In case it never loads, terminate
clearInterval(ajax_class_timer);
fallback();
}
ajax_class_timer_count++;
}, 40);
};
// XXX Add Crayon to editor
base.addCrayon = function () {
var url = $(s.url_css);
if (url.val().length == 0 && code.val().length == 0) {
code.addClass(gs.selected);
code.focus();
return false;
}
code.removeClass(gs.selected);
// Add inline for matching with CSS
var inline = $('#' + s.inline_css);
is_inline = inline.length != 0 && inline.is(':checked');
// Spacing only for <pre>
var br_before = br_after = '';
if (!editing) {
// Don't add spaces if editing
if (!is_inline) {
if (editor_name == 'html') {
br_after = br_before = ' \n';
} else {
br_after = '<p>&nbsp;</p>';
}
} else {
// Add a space after
if (editor_name == 'html') {
br_after = br_before = ' ';
} else {
br_after = '&nbsp;';
}
}
}
var tag = (is_inline ? 'span' : 'pre');
var shortcode = br_before + '<' + tag + ' ';
var atts = {};
shortcode += 'class="';
var inline_re = new RegExp('\\b' + s.inline_css + '\\b', 'gim');
if (is_inline) {
// If don't have inline class, add it
if (inline_re.exec(currClasses) == null) {
currClasses += ' ' + s.inline_css + ' ';
}
} else {
// Remove inline css if it exists
currClasses = currClasses.replace(inline_re, '');
}
// Grab settings as attributes
$('.' + gs.changed + '[id],.' + gs.changed + '[' + s.data_value + ']').each(function () {
var id = $(this).attr('id');
var value = $(this).attr(s.data_value);
// Remove prefix
id = util.removePrefixFromID(id);
atts[id] = value;
});
// Settings
atts['lang'] = $(s.lang_css).val();
var mark = $(s.mark_css).val();
if (mark.length != 0 && !is_inline) {
atts['mark'] = mark;
}
var range = $(s.range_css).val();
if (range.length != 0 && !is_inline) {
atts['range'] = range;
}
// XXX Code highlighting, checked means 0!
if ($(s.hl_css).is(':checked')) {
atts['highlight'] = '0';
}
// XXX Very important when working with editor
atts['decode'] = 'true';
// Validate the attributes
atts = base.validate(atts);
for (var id in atts) {
// Remove prefix, if exists
var value = atts[id];
CrayonUtil.log('add ' + id + ':' + value);
shortcode += id + s.attr_sep + value + ' ';
}
// Add classes
shortcode += currClasses;
// Don't forget to close quote for class
shortcode += '" ';
if (!is_inline) {
// Title
var title = $(s.title_css).val();
if (title.length != 0) {
shortcode += 'title="' + title + '" ';
}
// URL
var url = $(s.url_css).val();
if (url.length != 0) {
shortcode += 'data-url="' + url + '" ';
}
}
var content = $(s.code_css).val();
if (outputHTML == 'encode') {
content = CrayonUtil.encode_html(content);
} else if (outputHTML == 'decode') {
content = CrayonUtil.decode_html(content);
}
content = typeof content != 'undefined' ? content : '';
shortcode += '>' + content + '</' + tag + '>' + br_after;
if (editing && editCallback) {
// Edit the current selected node
editCallback(shortcode);
} else if (insertCallback) {
// Insert the tag and hide dialog
insertCallback(shortcode);
}
return true;
};
base.submitButton = function () {
CrayonUtil.log('submit');
if (base.addCrayon() != false) {
base.hideDialog();
}
};
base.hideDialog = function () {
CrayonUtil.log('hide');
if (hideCallback) {
hideCallback();
}
};
// XXX Auxiliary methods
base.setOrigValues = function () {
$('.' + gs.setting + '[id]').each(function () {
var setting = $(this);
setting.attr(gs.orig_value, base.settingValue(setting));
});
};
base.resetSettings = function () {
CrayonUtil.log('reset');
$('.' + gs.setting).each(function () {
var setting = $(this);
base.settingValue(setting, setting.attr(gs.orig_value));
// Update highlights
setting.change();
});
code.val('');
};
base.settingValue = function (setting, value) {
if (typeof value == 'undefined') {
// getter
value = '';
if (setting.is('input[type=checkbox]')) {
// Boolean is stored as string
value = setting.is(':checked') ? 'true' : 'false';
} else {
value = setting.val();
}
return value;
} else {
// setter
if (setting.is('input[type=checkbox]')) {
if (typeof value == 'string') {
if (value == 'true' || value == '1') {
value = true;
} else if (value == 'false' || value == '0') {
value = false;
}
}
setting.prop('checked', value);
} else {
setting.val(value);
}
setting.attr(s.data_value, value);
}
};
base.validate = function (atts) {
var fields = ['range', 'mark'];
for (var i in fields) {
var field = fields[i];
if (typeof atts[field] != 'undefined') {
atts[field] = atts[field].replace(/\s/g, '');
}
}
return atts;
};
base.isCrayon = function (node) {
return node != null &&
(node.nodeName == 'PRE' || (node.nodeName == 'SPAN' && $(node).hasClass(s.inline_css)));
};
base.elemValue = function (obj) {
var value = null;
if (obj.is('input[type=checkbox]')) {
value = obj.is(':checked');
} else {
value = obj.val();
}
return value;
};
base.setSubmitText = function (text) {
submit.html(text);
};
};
})(jQueryCrayon);

View File

@ -0,0 +1,292 @@
<?php
require_once(CRAYON_ROOT_PATH . 'crayon_settings_wp.class.php');
class CrayonTagEditorWP {
public static $settings = null;
public static function init() {
// Hooks
if (CRAYON_TAG_EDITOR) {
CrayonSettingsWP::load_settings(TRUE);
if (is_admin()) {
// XXX Only runs in wp-admin
add_action('admin_print_scripts-post-new.php', 'CrayonTagEditorWP::enqueue_resources');
add_action('admin_print_scripts-post.php', 'CrayonTagEditorWP::enqueue_resources');
add_filter('tiny_mce_before_init', 'CrayonTagEditorWP::init_tinymce');
// Must come after
add_action("admin_print_scripts-post-new.php", 'CrayonSettingsWP::init_js_settings');
add_action("admin_print_scripts-post.php", 'CrayonSettingsWP::init_js_settings');
self::addbuttons();
} else if (CrayonGlobalSettings::val(CrayonSettings::TAG_EDITOR_FRONT)) {
// XXX This will always need to enqueue, but only runs on front end
add_action('wp', 'CrayonTagEditorWP::enqueue_resources');
add_filter('tiny_mce_before_init', 'CrayonTagEditorWP::init_tinymce');
self::addbuttons();
}
}
}
public static function init_settings() {
if (!self::$settings) {
// Add settings
self::$settings = array(
'home_url' => home_url(),
'css' => 'crayon-te',
'css_selected' => 'crayon-selected',
'code_css' => '#crayon-code',
'url_css' => '#crayon-url',
'url_info_css' => '#crayon-te-url-info',
'lang_css' => '#crayon-lang',
'title_css' => '#crayon-title',
'mark_css' => '#crayon-mark',
'range_css' => '#crayon-range',
'inline_css' => 'crayon-inline',
'inline_hide_css' => 'crayon-hide-inline',
'inline_hide_only_css' => 'crayon-hide-inline-only',
'hl_css' => '#crayon-highlight',
'switch_html' => '#content-html',
'switch_tmce' => '#content-tmce',
'tinymce_button_generic' => '.mce-btn',
'tinymce_button' => 'a.mce_crayon_tinymce,.mce-i-crayon_tinymce',
'tinymce_button_unique' => 'mce_crayon_tinymce',
'tinymce_highlight' => 'mce-active',
'submit_css' => '#crayon-te-ok',
'cancel_css' => '#crayon-te-cancel',
'content_css' => '#crayon-te-content',
'dialog_title_css' => '#crayon-te-title',
'submit_wrapper_css' => '#crayon-te-submit-wrapper',
'data_value' => 'data-value',
'attr_sep' => CrayonGlobalSettings::val_str(CrayonSettings::ATTR_SEP),
'css_sep' => '_',
'fallback_lang' => CrayonGlobalSettings::val(CrayonSettings::FALLBACK_LANG),
'add_text' => CrayonGlobalSettings::val(CrayonSettings::TAG_EDITOR_ADD_BUTTON_TEXT),
'edit_text' => CrayonGlobalSettings::val(CrayonSettings::TAG_EDITOR_EDIT_BUTTON_TEXT),
'quicktag_text' => CrayonGlobalSettings::val(CrayonSettings::TAG_EDITOR_QUICKTAG_BUTTON_TEXT),
'submit_add' => crayon__('Add'),
'submit_edit' => crayon__('Save'),
'bar' => '#crayon-te-bar',
'bar_content' => '#crayon-te-bar-content',
'extensions' => CrayonResources::langs()->extensions_inverted()
);
}
}
public static function enqueue_resources() {
global $CRAYON_VERSION;
self::init_settings();
if (CRAYON_MINIFY) {
wp_deregister_script('crayon_js');
wp_enqueue_script('crayon_js', plugins_url(CRAYON_JS_TE_MIN, dirname(dirname(__FILE__))), array('jquery', 'quicktags'), $CRAYON_VERSION);
CrayonSettingsWP::init_js_settings();
wp_localize_script('crayon_js', 'CrayonTagEditorSettings', self::$settings);
} else {
wp_enqueue_script('crayon_colorbox_js', plugins_url(CRAYON_COLORBOX_JS, __FILE__), array('jquery'), $CRAYON_VERSION);
wp_enqueue_style('crayon_colorbox_css', plugins_url(CRAYON_COLORBOX_CSS, __FILE__), array(), $CRAYON_VERSION);
wp_enqueue_script('crayon_te_js', plugins_url(CRAYON_TAG_EDITOR_JS, __FILE__), array('crayon_util_js', 'crayon_colorbox_js'), $CRAYON_VERSION);
wp_enqueue_script('crayon_qt_js', plugins_url(CRAYON_QUICKTAGS_JS, __FILE__), array('quicktags', 'crayon_te_js'), $CRAYON_VERSION, TRUE);
wp_localize_script('crayon_te_js', 'CrayonTagEditorSettings', self::$settings);
CrayonSettingsWP::other_scripts();
}
}
public static function init_tinymce($init) {
if (!array_key_exists('extended_valid_elements', $init)) {
$init['extended_valid_elements'] = '';
}
$init['extended_valid_elements'] .= ',pre[*],code[*],iframe[*]';
return $init;
}
public static function addbuttons() {
// Add only in Rich Editor mode
add_filter('mce_external_plugins', 'CrayonTagEditorWP::add_plugin');
add_filter('mce_buttons', 'CrayonTagEditorWP::register_buttons');
add_filter('bbp_before_get_the_content_parse_args', 'CrayonTagEditorWP::bbp_get_the_content_args');
}
public static function bbp_get_the_content_args($args) {
// Turn off "teeny" to allow the bbPress TinyMCE to display external plugins
return array_merge($args, array('teeny' => false));
}
public static function register_buttons($buttons) {
array_push($buttons, 'separator', 'crayon_tinymce');
return $buttons;
}
public static function add_plugin($plugin_array) {
$plugin_array['crayon_tinymce'] = plugins_url(CRAYON_TINYMCE_JS, __FILE__);
return $plugin_array;
}
// The remaining functions are for displayed output.
public static function select_resource($id, $resources, $current, $set_class = TRUE) {
$id = CrayonSettings::PREFIX . $id;
if (count($resources) > 0) {
$class = $set_class ? 'class="' . CrayonSettings::SETTING . ' ' . CrayonSettings::SETTING_SPECIAL . '"' : '';
echo '<select id="' . $id . '" name="' . $id . '" ' . $class . ' ' . CrayonSettings::SETTING_ORIG_VALUE . '="' . $current . '">';
foreach ($resources as $resource) {
$asterisk = $current == $resource->id() ? ' *' : '';
echo '<option value="' . $resource->id() . '" ' . selected($current, $resource->id()) . ' >' . $resource->name() . $asterisk . '</option>';
}
echo '</select>';
} else {
// None found, default to text box
echo '<input type="text" id="' . $id . '" name="' . $id . '" class="' . CrayonSettings::SETTING . ' ' . CrayonSettings::SETTING_SPECIAL . '" />';
}
}
public static function checkbox($id) {
$id = CrayonSettings::PREFIX . $id;
echo '<input type="checkbox" id="' . $id . '" name="' . $id . '" class="' . CrayonSettings::SETTING . ' ' . CrayonSettings::SETTING_SPECIAL . '" />';
}
public static function textbox($id, $atts = array(), $set_class = TRUE) {
$id = CrayonSettings::PREFIX . $id;
$atts_str = '';
$class = $set_class ? 'class="' . CrayonSettings::SETTING . ' ' . CrayonSettings::SETTING_SPECIAL . '"' : '';
foreach ($atts as $k => $v) {
$atts_str = $k . '="' . $v . '" ';
}
echo '<input type="text" id="' . $id . '" name="' . $id . '" ' . $class . ' ' . $atts_str . ' />';
}
public static function submit() {
?>
<input type="button"
class="button-primary <?php echo CrayonTagEditorWP::$settings['submit_css']; ?>"
value="<?php echo CrayonTagEditorWP::$settings['submit_add']; ?>"
name="submit"/>
<?php
}
public static function content() {
CrayonSettingsWP::load_settings();
$langs = CrayonLangs::sort_by_name(CrayonParser::parse_all());
$curr_lang = CrayonGlobalSettings::val(CrayonSettings::FALLBACK_LANG);
$themes = CrayonResources::themes()->get();
$curr_theme = CrayonGlobalSettings::val(CrayonSettings::THEME);
$fonts = CrayonResources::fonts()->get();
$curr_font = CrayonGlobalSettings::val(CrayonSettings::FONT);
CrayonTagEditorWP::init_settings();
?>
<div id="crayon-te-content" class="crayon-te">
<div id="crayon-te-bar">
<div id="crayon-te-bar-content">
<div id="crayon-te-title">Title</div>
<div id="crayon-te-controls">
<a id="crayon-te-ok" href="#"><?php crayon_e('OK'); ?></a> <span
class="crayon-te-seperator">|</span> <a id="crayon-te-cancel"
href="#"><?php crayon_e('Cancel'); ?></a>
</div>
</div>
</div>
<table id="crayon-te-table" class="describe">
<tr class="crayon-tr-center">
<th><?php crayon_e('Title'); ?>
</th>
<td class="crayon-nowrap"><?php self::textbox('title', array('placeholder' => crayon__('A short description'))); ?>
<span id="crayon-te-sub-section"> <?php self::checkbox('inline'); ?>
<span class="crayon-te-section"><?php crayon_e('Inline'); ?> </span>
</span> <span id="crayon-te-sub-section"> <?php self::checkbox('highlight'); ?>
<span class="crayon-te-section"><?php crayon_e("Don't Highlight"); ?>
</span>
</span></td>
</tr>
<tr class="crayon-tr-center">
<th><?php crayon_e('Language'); ?>
</th>
<td class="crayon-nowrap"><?php self::select_resource('lang', $langs, $curr_lang); ?>
<span class="crayon-te-section"><?php crayon_e('Line Range'); ?> </span>
<?php self::textbox('range', array('placeholder' => crayon__('(e.g. 3-5 or 3)'))); ?>
<span class="crayon-te-section"><?php crayon_e('Marked Lines'); ?> </span>
<?php self::textbox('mark', array('placeholder' => crayon__('(e.g. 1,2,3-5)'))); ?>
</td>
</tr>
<tr class="crayon-tr-center" style="text-align: center;">
<th>
<div>
<?php crayon_e('Code'); ?>
</div>
<input type="button" id="crayon-te-clear"
class="secondary-primary" value="<?php crayon_e('Clear'); ?>"
name="clear"/>
</th>
<td><textarea id="crayon-code" name="code"
placeholder="<?php crayon_e('Paste your code here, or type it in manually.'); ?>"></textarea>
</td>
</tr>
<tr class="crayon-tr-center">
<th id="crayon-url-th"><?php crayon_e('URL'); ?>
</th>
<td><?php self::textbox('url', array('placeholder' => crayon__('Relative local path or absolute URL'))); ?>
<div id="crayon-te-url-info" class="crayon-te-info">
<?php
crayon_e("If the URL fails to load, the code above will be shown instead. If no code exists, an error is shown.");
echo ' ';
printf(crayon__('If a relative local path is given it will be appended to %s - which is defined in %sCrayon &gt; Settings &gt; Files%s.'), '<span class="crayon-te-quote">' . get_home_url() . '/' . CrayonGlobalSettings::val(CrayonSettings::LOCAL_PATH) . '</span>', '<a href="options-general.php?page=crayon_settings" target="_blank">', '</a>');
?>
</div>
</td>
</tr>
<tr>
<td id="crayon-te-submit-wrapper" colspan="2"
style="text-align: center;"><?php self::submit(); ?></td>
</tr>
<!-- <tr>-->
<!-- <td colspan="2"><div id="crayon-te-warning" class="updated crayon-te-info"></div></td>-->
<!-- </tr>-->
<tr>
<td colspan="2"><?php
$admin = isset($_GET['is_admin']) ? intval($_GET['is_admin']) : is_admin();
if (!$admin && !CrayonGlobalSettings::val(CrayonSettings::TAG_EDITOR_SETTINGS)) {
exit();
}
?>
<hr/>
<div>
<h2 class="crayon-te-heading">
<?php crayon_e('Settings'); ?>
</h2>
</div>
<div id="crayon-te-settings-info" class="crayon-te-info">
<?php
crayon_e('Change the following settings to override their global values.');
echo ' <span class="', CrayonSettings::SETTING_CHANGED, '">';
crayon_e('Only changes (shown yellow) are applied.');
echo '</span><br/>';
echo sprintf(crayon__('Future changes to the global settings under %sCrayon &gt; Settings%s won\'t affect overridden settings.'), '<a href="options-general.php?page=crayon_settings" target="_blank">', '</a>');
?>
</div>
</td>
</tr>
<?php
$sections = array('Theme', 'Font', 'Metrics', 'Toolbar', 'Lines', 'Code');
foreach ($sections as $section) {
echo '<tr><th>', crayon__($section), '</th><td>';
call_user_func('CrayonSettingsWP::' . strtolower($section), TRUE);
echo '</td></tr>';
}
?>
</table>
</div>
<?php
exit();
}
}
if (defined('ABSPATH')) {
add_action('init', 'CrayonTagEditorWP::init');
}
?>

View File

@ -0,0 +1,32 @@
pre {
background: #F4F4F4 !important;
border: 1px solid #CCC !important;
margin-bottom: 1.5em !important;
padding: 0.3em 0.5em !important;
min-height: 1.5em;
}
pre.crayon-selected {
background: #cce4f5 !important;
border: 1px solid #9dc8e6 !important;
}
pre, span.crayon-inline {
font-family: "Courier 10 Pitch", Courier, monospace !important;
font-size: 80% !important;
}
span.crayon-inline {
background: #F4F4F4 !important;
border: 1px solid #CCC !important;
padding: 2px 3px;
/* font: 80% !important; */
/* margin-bottom: 1.5em !important; */
/* padding: 0.3em 0.5em !important; */
}
span.crayon-inline.crayon-selected {
background: #d2eeca !important;
border: 1px solid #b8dc9b !important;
}

View File

@ -0,0 +1,270 @@
(function ($) {
window.CrayonTinyMCE = new function () {
// TinyMCE specific
var name = 'crayon_tinymce';
var s, te = null;
var isHighlighted = false;
var currPre = null;
var isInit = false;
// Switch events
var switch_html_click = switch_tmce_click = null;
var base = this;
// var wasHighlighted = false;
base.setHighlight = function (highlight) {
$(s.tinymce_button).closest(s.tinymce_button_generic).toggleClass(s.tinymce_highlight, highlight);
isHighlighted = highlight;
};
base.selectPreCSS = function (selected) {
if (currPre) {
if (selected) {
$(currPre).addClass(s.css_selected);
} else {
$(currPre).removeClass(s.css_selected);
}
}
};
base.isPreSelectedCSS = function () {
if (currPre) {
return $(currPre).hasClass(s.css_selected);
}
return false;
};
base.loadTinyMCE = function () {
var version = parseInt(tinymce.majorVersion);
if (!isNaN(version) && version <= 3) {
return this._loadTinyMCEv3();
}
s = CrayonTagEditorSettings;
te = CrayonTagEditor;
// TODO(aramk) find the TinyMCE version 4 compliant command for this.
//tinymce.PluginManager.requireLangPack(name);
tinymce.PluginManager.add(name, function (ed, url) {
// TODO(aramk) This is called twice for some reason.
ed.on('init', function () {
ed.dom.loadCSS(url + '/crayon_te.css');
if (isInit) {
return;
}
$(s.tinymce_button).parent().addClass(s.tinymce_button_unique);
CrayonTagEditor.bind('.' + s.tinymce_button_unique);
// Remove all selected pre tags
$('.' + s.css_selected, ed.getContent()).removeClass(s.css_selected);
isInit = true;
});
// Prevent <p> on enter, turn into \n
ed.on('keyDown', function (e) {
var selection = ed.selection;
if (e.keyCode == 13) {
var node = selection.getNode();
if (node.nodeName == 'PRE') {
selection.setContent('\n', {format: 'raw'});
return tinymce.dom.Event.cancel(e);
} else if (te.isCrayon(node)) {
// Only triggers for inline <span>, ignore enter in inline
return tinymce.dom.Event.cancel(e);
}
}
});
// Remove onclick and call ourselves
var switch_html = $(s.switch_html);
switch_html.prop('onclick', null);
switch_html.click(function () {
// Remove selected pre class when switching to HTML editor
base.selectPreCSS(false);
switchEditors.go('content', 'html');
});
// Highlight selected
ed.on('nodeChange', function (event) {
var n = event.element;
if (n != currPre) {
// We only care if we select another same object
if (currPre) {
// If we have a previous pre, remove it
base.selectPreCSS(false);
currPre = null;
}
if (te.isCrayon(n)) {
// Add new pre
currPre = n;
base.selectPreCSS(true);
base.setHighlight(true);
} else {
// No pre selected
base.setHighlight(false);
}
}
});
ed.addButton(name, {
// TODO add translation
title: s.dialog_title_add,
onclick: function () {
te.showDialog({
insert: function (shortcode) {
ed.execCommand('mceInsertContent', 0, shortcode);
},
edit: function (shortcode) {
// This will change the currPre object
var newPre = $(shortcode);
$(currPre).replaceWith(newPre);
// XXX DOM element not jQuery
currPre = newPre[0];
},
select: function () {
return ed.selection.getContent({format: 'text'});
},
editor_str: 'tinymce',
ed: ed,
node: currPre,
input: 'decode',
output: 'encode'
});
}
});
});
};
// TinyMCE v3 - deprecated.
base._loadTinyMCEv3 = function () {
s = CrayonTagEditorSettings;
te = CrayonTagEditor;
tinymce.PluginManager.requireLangPack(name);
tinymce.create('tinymce.plugins.Crayon', {
init: function (ed, url) {
ed.onInit.add(function (ed) {
ed.dom.loadCSS(url + '/crayon_te.css');
});
// Prevent <p> on enter, turn into \n
ed.onKeyDown.add(function (ed, e) {
var selection = ed.selection;
if (e.keyCode == 13) {
var node = selection.getNode();
if (node.nodeName == 'PRE') {
selection.setContent('\n', {format: 'raw'});
return tinymce.dom.Event.cancel(e);
} else if (te.isCrayon(node)) {
// Only triggers for inline <span>, ignore enter in inline
return tinymce.dom.Event.cancel(e);
}
}
});
ed.onInit.add(function (ed) {
CrayonTagEditor.bind(s.tinymce_button);
});
ed.addCommand('showCrayon', function () {
te.showDialog({
insert: function (shortcode) {
ed.execCommand('mceInsertContent', 0, shortcode);
},
edit: function (shortcode) {
// This will change the currPre object
var newPre = $(shortcode);
$(currPre).replaceWith(newPre);
// XXX DOM element not jQuery
currPre = newPre[0];
},
select: function () {
return ed.selection.getContent({format: 'text'});
},
editor_str: 'tinymce',
ed: ed,
node: currPre,
input: 'decode',
output: 'encode'
});
});
// Remove onclick and call ourselves
var switch_html = $(s.switch_html);
switch_html.prop('onclick', null);
switch_html.click(function () {
// Remove selected pre class when switching to HTML editor
base.selectPreCSS(false);
switchEditors.go('content', 'html');
});
// Highlight selected
ed.onNodeChange.add(function (ed, cm, n, co) {
if (n != currPre) {
// We only care if we select another same object
if (currPre) {
// If we have a previous pre, remove it
base.selectPreCSS(false);
currPre = null;
}
if (te.isCrayon(n)) {
// Add new pre
currPre = n;
base.selectPreCSS(true);
base.setHighlight(true);
} else {
// No pre selected
base.setHighlight(false);
}
// var tooltip = currPre ? s.dialog_title_edit : s.dialog_title_add;
// $(s.tinymce_button).attr('title', tooltip);
}
});
ed.onBeforeSetContent.add(function (ed, o) {
// Remove all selected pre tags
var content = $(o.content);
var wrapper = $('<div>');
content.each(function () {
$(this).removeClass(s.css_selected);
wrapper.append($(this).clone());
});
o.content = wrapper.html();
});
ed.addButton(name, {
// TODO add translation
title: s.dialog_title,
cmd: 'showCrayon'
});
},
createControl: function (n, cm) {
return null;
},
getInfo: function () {
return {
longname: 'Crayon Syntax Highlighter',
author: 'Aram Kocharyan',
authorurl: 'http://aramk.com/',
infourl: 'https://github.com/aramk/crayon-syntax-highlighter',
version: "1.0"
};
}
});
tinymce.PluginManager.add(name, tinymce.plugins.Crayon);
};
};
$(document).ready(function () {
// Load TinyMCE
CrayonTinyMCE.loadTinyMCE();
});
})(jQueryCrayon);

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

@ -0,0 +1,317 @@
#crayon-theme-editor-button {
margin-left: 10px;
}
#crayon-editor-controls {
}
#crayon-editor-preview .crayon-syntax {
margin: 0 !important;
padding: 0 !important;
}
#crayon-editor-control-wrapper {
padding-left: 20px;
}
#crayon-editor-control-wrapper,
#crayon-editor-controls {
width: 422px;
overflow: hidden;
}
#crayon-editor-save {
margin: 0 5px;
}
#crayon-editor-controls label {
margin-right: 10px;
width: 70px;
float: left;
}
#crayon-editor-controls .crayon-theme-editor-form .separator .content {
font-weight: bold;
color: #999;
padding-top: 8px;
border-bottom: 1px solid #ccc;
text-shadow: 0 1px 0px #fff;
text-align: center;
padding-bottom: 2px;
margin-bottom: 5px;
}
#crayon-editor-controls .crayon-theme-editor-form .separator.first .content {
padding-top: 0;
}
#crayon-editor-controls .crayon-theme-editor-form .separator.title .content {
line-height: 24px;
height: 22px;
padding-top: 0;
background: #dedede url(images/title.png) center bottom repeat-x;
border-color: #999;
}
#crayon-editor-controls .crayon-theme-editor-form .separator.title .content {
color: #333;
text-shadow: 0 1px 2px #eee;
}
#crayon-editor-controls .crayon-theme-editor-form .separator.title td {
color: #333;
padding: 0;
}
#crayon-editor-controls .crayon-theme-editor-form .field {
border: 0px;
padding-right: 5px;
vertical-align: middle;
}
#crayon-editor-controls .crayon-theme-editor-form .split-field td {
padding-right: 5px;
}
#crayon-editor-controls .crayon-theme-editor-form .split-field td.last {
padding-right: 0;
}
#crayon-editor-controls .split-field input,
#crayon-editor-controls .split-field select {
width: 100%;
}
#crayon-editor-controls .crayon-theme-editor-form table td.value.split {
padding-left: 0;
}
#crayon-editor-controls .crayon-theme-editor-form table td.field.split {
padding-right: 0;
}
#crayon-editor-controls input {
line-height: 23px;
height: 23px;
border: 1px solid #ccc;
padding: 0 5px;
margin: 2px 0;
}
#crayon-editor-controls input:focus {
border: 1px solid #999;
}
#crayon-editor-controls .ui-tabs-panel {
padding: 5px;
}
.crayon-theme-editor-form table {
width: 100%;
}
#crayon-editor-controls .crayon-theme-editor-form table,
#crayon-editor-controls .crayon-theme-editor-form tr,
#crayon-editor-controls .crayon-theme-editor-form td {
padding: 0;
margin: 0;
border-spacing: 0 !important;
}
#crayon-editor-controls .crayon-theme-editor-form table tr:first-child td,
#crayon-editor-controls .crayon-theme-editor-form table tr:last-child td {
padding: 4px;
}
#crayon-editor-controls .crayon-theme-editor-form table td {
padding: 1px 4px;
}
.crayon-theme-editor-form table .value input {
width: 100%;
}
#crayon-editor-controls .ui-tabs-nav li {
padding: 0;
margin: 0;
border-top: 0;
border-left: 0;
}
#crayon-editor-controls .ui-tabs-nav * {
border-radius: 0px;
}
#crayon-editor-controls .ui-tabs-nav {
padding: 0;
margin: 0;
}
#crayon-editor-controls .ui-tabs-nav,
#crayon-editor-controls .ui-tabs-nav li,
#crayon-editor-controls .ui-tabs-nav li a {
height: 33px;
line-height: 33px;
padding: 0;
}
#crayon-editor-controls .ui-tabs-nav li a,
#crayon-editor-controls .ui-tabs-nav li {
float: left;
width: 70px;
}
#crayon-editor-controls.ui-tabs {
padding: 0;
margin: 0;
}
#crayon-editor-controls .ui-widget-header {
width: 1000px;
overflow: hidden;
border-bottom-left-radius: 0;
border-bottom-right-radius: 0;
}
#crayon-editor-controls .ui-widget-header li:last-child {
border-right: none !important;
}
#crayon-editor-control-wrapper .ui-widget-content {
border: 0;
background: none;
}
#crayon-editor-controls .ui-widget-content {
border: 1px solid #bbb;
border-top-style: none;
background: #f5f5f5 50% top repeat-x;
color: #333333;
padding: 0;
}
.ui-colorpicker-preview-container .ui-colorpicker-border,
.ui-colorpicker-preview-initial,
.ui-colorpicker-preview-current {
height: 20px;
}
.ui-colorpicker .ui-colorpicker-mode {
margin-right: 5px;
}
.ui-colorpicker-swatches {
height: auto;
}
.ui-colorpicker {
z-index: 100 !important;
}
.crayon-tab-information {
background: url(images/information.png) no-repeat top center;
}
.crayon-tab-highlighting {
background: url(images/highlighting.png) no-repeat top center;
}
.crayon-tab-frame {
background: url(images/frame.png) no-repeat top center;
}
.crayon-tab-lines {
background: url(images/lines.png) no-repeat top center;
}
.crayon-tab-numbers {
background: url(images/numbers.png) no-repeat top center;
}
.crayon-tab-toolbar {
background: url(images/toolbar.png) no-repeat top center;
}
#crayon-editor-controls .ui-widget-header {
border: 1px solid #b3b3b3;
border-bottom: 1px solid #666;
background: #929292 url(images/button.png) center bottom repeat-x;
color: #474747;
font-weight: bold;
}
#crayon-editor-controls .ui-state-default,
#crayon-editor-controls .ui-widget-content .ui-state-default,
#crayon-editor-controls .ui-widget-header .ui-state-default {
border: none;
background: #929292 url(images/button.png) center bottom repeat-x;
font-weight: bold;
color: #545454;
border-top: 1px solid #ccc !important;
}
#crayon-editor-controls .ui-state-hover,
#crayon-editor-controls .ui-widget-content .ui-state-hover,
#crayon-editor-controls .ui-widget-header .ui-state-hover,
#crayon-editor-controls .ui-state-focus,
#crayon-editor-controls .ui-widget-content .ui-state-focus,
#crayon-editor-controls .ui-widget-header .ui-state-focus {
border: none;
background: #b3b3b3 url(images/button-pressed.png) center bottom repeat-x;
border-top: 1px solid #eee !important;
font-weight: bold;
color: #00467a;
}
#crayon-editor-controls .ui-state-active,
#crayon-editor-controls .ui-widget-content .ui-state-active,
#crayon-editor-controls .ui-widget-header .ui-state-active {
border: none;
background: #b3b3b3 url(images/button-pressed.png) center bottom repeat-x;
font-weight: bold;
color: #4f4f4f;
border-top: 1px solid #eee !important;
}
.wp-dialog {
min-width: 300px;
}
.wp-dialog .ui-dialog-content {
padding: 10px;
min-height: 10px !important;
}
.wp-dialog .ui-dialog-content td {
padding: 5px 0;
}
.wp-dialog .ui-dialog-content .field-table td input,
.wp-dialog .ui-dialog-content .field-table {
width: 100%;
}
.ui-colorpicker-dialog {
width: 575px !important;
height: 350px !important;
/*position: fixed;*/
/*left: auto;*/
/*right: 450px;*/
bottom: 0;
}
.ui-colorpicker-dialog .ui-colorpicker-bar-container {
padding-right: 5px !important;
}
.ui-colorpicker-dialog .ui-dialog-buttonpane {
margin-top: 0;
padding-top: 0;
}
.ui-colorpicker-dialog .ui-dialog-content {
padding-bottom: 0;
}
/* {*/
/*height: auto !important;*/
/*}*/

View File

@ -0,0 +1,655 @@
// Crayon Syntax Highlighter Theme Editor JavaScript
(function ($) {
CrayonSyntaxThemeEditor = new function () {
var base = this;
var crayonSettings = CrayonSyntaxSettings;
var adminSettings = CrayonAdminSettings;
var settings = CrayonThemeEditorSettings;
var strings = CrayonThemeEditorStrings;
var adminStrings = CrayonAdminStrings;
var admin = CrayonSyntaxAdmin;
var preview, previewCrayon, previewCSS, status, title, info;
var colorPickerPos;
var changed, loaded;
var themeID, themeJSON, themeCSS, themeStr, themeInfo;
var reImportant = /\s+!important$/gmi;
var reSize = /^[0-9-]+px$/;
var reCopy = /-copy(-\d+)?$/;
var changedAttr = 'data-value';
var borderCSS = {'border': true, 'border-left': true, 'border-right': true, 'border-top': true, 'border-bottom': true};
base.init = function (callback) {
// Called only once
CrayonUtil.log('editor init');
base.initUI();
if (callback) {
callback();
}
};
base.show = function (callback, crayon) {
// Called each time editor is shown
previewCrayon = crayon.find('.crayon-syntax');
preview.append(crayon)
base.load();
if (callback) {
callback();
}
};
base.load = function () {
loaded = false;
themeStr = adminSettings.currThemeCSS;
themeID = adminSettings.currTheme;
changed = false;
themeJSON = CSSJSON.toJSON(themeStr, {
stripComments: true,
split: true
});
themeJSON = base.filterCSS(themeJSON);
CrayonUtil.log(themeJSON);
themeInfo = base.readCSSInfo(themeStr);
base.removeExistingCSS();
base.initInfoUI();
base.updateTitle();
base.updateInfo();
base.setFieldValues(themeInfo);
base.populateAttributes();
base.updateLiveCSS();
base.updateUI();
loaded = true;
};
base.save = function () {
// Update info from form fields
themeInfo = base.getFieldValues($.keys(themeInfo));
// Get the names of the fields and map them to their values
var names = base.getFieldNames(themeInfo);
var info = {};
for (var id in themeInfo) {
info[names[id]] = themeInfo[id];
}
// Update attributes
base.persistAttributes();
// Save
themeCSS = CSSJSON.toCSS(themeJSON);
var newThemeStr = base.writeCSSInfo(info) + themeCSS;
CrayonUtil.postAJAX({
action: 'crayon-theme-editor-save',
id: themeID,
name: base.getName(),
css: newThemeStr
}, function (result) {
status.show();
result = parseInt(result);
if (result > 0) {
status.html(strings.success);
if (result === 2) {
window.GET['theme-editor'] = 1;
CrayonUtil.reload();
}
} else {
status.html(strings.fail);
}
changed = false;
setTimeout(function () {
status.fadeOut();
}, 1000);
});
};
base.del = function (id, name) {
admin.createDialog({
title: strings.del,
html: strings.deleteThemeConfirm.replace('%s', name),
yes: function () {
CrayonUtil.postAJAX({
action: 'crayon-theme-editor-delete',
id: id
}, function (result) {
if (result > 0) {
CrayonUtil.reload();
} else {
admin.createAlert({
html: strings.deleteFail + ' ' + strings.checkLog
});
}
});
},
options: {
selectedButtonIndex: 2
}
});
};
base.duplicate = function (id, name) {
base.createPrompt({
//html: "Are you sure you want to duplicate the '" + name + "' theme?",
title: strings.duplicate,
text: strings.newName,
value: base.getNextAvailableName(id),
ok: function (val) {
CrayonUtil.postAJAX({
action: 'crayon-theme-editor-duplicate',
id: id,
name: val
}, function (result) {
if (result > 0) {
CrayonUtil.reload();
} else {
admin.createAlert({
html: strings.duplicateFail + ' ' + strings.checkLog
});
}
});
}
});
};
base.submit = function (id, name) {
base.createPrompt({
title: strings.submit,
desc: strings.submitText,
text: strings.message,
value: strings.submitMessage,
ok: function (val) {
CrayonUtil.postAJAX({
action: 'crayon-theme-editor-submit',
id: id,
message: val
}, function (result) {
var msg = result > 0 ? strings.submitSucceed : strings.submitFail + ' ' + strings.checkLog;
admin.createAlert({
html: msg
});
});
}
});
};
base.getNextAvailableName = function (id) {
var next = base.getNextAvailableID(id);
return base.idToName(next[1]);
};
base.getNextAvailableID = function (id) {
var themes = adminSettings.themes;
var count = 0;
if (reCopy.test(id)) {
// Remove the "copy" if it already exists
var newID = id.replace(reCopy, '');
if (newID.length > 0) {
id = newID;
}
}
var nextID = id;
while (nextID in themes) {
count++;
if (count == 1) {
nextID = id + '-copy';
} else {
nextID = id + '-copy-' + count.toString();
}
}
return [count, nextID];
};
base.readCSSInfo = function (cssStr) {
var infoStr = /^\s*\/\*[\s\S]*?\*\//gmi.exec(cssStr);
var themeInfo = {};
var match = null;
var infoRegex = /([^\r\n:]*[^\r\n\s:])\s*:\s*([^\r\n]+)/gmi;
while ((match = infoRegex.exec(infoStr)) != null) {
themeInfo[base.nameToID(match[1])] = CrayonUtil.encode_html(match[2]);
}
// Force title case on the name
if (themeInfo.name) {
themeInfo.name = base.idToName(themeInfo.name);
}
return themeInfo;
};
base.getFieldName = function (id) {
var name = '';
if (id in settings.fields) {
name = settings.fields[id];
} else {
name = base.idToName(id);
}
return name;
};
base.getFieldNames = function (fields) {
var names = {};
for (var id in fields) {
names[id] = base.getFieldName(id);
}
return names;
};
base.removeExistingCSS = function () {
// Remove the old <style> tag to prevent clashes
preview.find('link[rel="stylesheet"][href*="' + adminSettings.currThemeURL + '"]').remove()
};
base.initInfoUI = function () {
CrayonUtil.log(themeInfo);
// TODO abstract
var names = base.getFieldNames(themeInfo);
var fields = {};
for (var id in names) {
var name = names[id];
var value = themeInfo[id];
fields[name] = base.createInput(id, value);
}
$('#tabs-1-contents').html(base.createForm(fields));
base.getField('name').bind('change keydown keyup', function () {
themeInfo.name = base.getFieldValue('name');
base.updateTitle();
});
};
base.nameToID = function (name) {
return name.toLowerCase().replace(/\s+/gmi, '-');
};
base.idToName = function (id) {
id = id.replace(/-/gmi, ' ');
return id.toTitleCase();
};
base.getName = function () {
var name = themeInfo.name;
if (!name) {
name = base.idToName(themeID);
}
return name;
};
base.getField = function (id) {
return $('#' + settings.cssInputPrefix + id);
};
base.getFieldValue = function (id) {
return base.getElemValue(base.getField(id));
};
base.getElemValue = function (elem) {
if (elem) {
// TODO add support for checkboxes etc.
return elem.val();
} else {
return null;
}
};
base.getFieldValues = function (fields) {
var info = {};
$(fields).each(function (i, id) {
info[id] = base.getFieldValue(id);
});
return info;
};
base.setFieldValue = function (id, value) {
base.setElemValue(base.getField(id), value);
};
base.setFieldValues = function (obj) {
for (var i in obj) {
base.setFieldValue(i, obj[i]);
}
};
base.setElemValue = function (elem, val) {
if (elem) {
// TODO add support for checkboxes etc.
return elem.val(val);
} else {
return false;
}
};
base.getAttribute = function (element, attribute) {
return base.getField(element + '_' + attribute);
};
base.getAttributes = function () {
return $('.' + settings.cssInputPrefix + settings.attribute);
};
base.visitAttribute = function (attr, callback) {
var elems = themeJSON.children;
var root = settings.cssThemePrefix + base.nameToID(themeInfo.name);
var dataElem = attr.attr('data-element');
var dataAttr = attr.attr('data-attribute');
var elem = elems[root + dataElem];
callback(attr, elem, dataElem, dataAttr, root, elems);
};
base.persistAttributes = function (remove_default) {
remove_default = CrayonUtil.setDefault(remove_default, true);
base.getAttributes().each(function () {
base.persistAttribute($(this), remove_default);
});
};
base.persistAttribute = function (attr, remove_default) {
remove_default = CrayonUtil.setDefault(remove_default, true);
base.visitAttribute(attr, function (attr, elem, dataElem, dataAttr, root, elems) {
if (remove_default && attr.prop('tagName') == 'SELECT' && attr.val() == attr.attr('data-default')) {
if (elem) {
// If default is selected in a dropdown, then remove
delete elem.attributes[dataAttr];
}
return;
}
var val = base.getElemValue(attr);
if ((val == null || val == '')) {
// No value given
if (remove_default && elem) {
delete elem.attributes[dataAttr];
return;
}
} else {
val = base.addImportant(val);
if (!elem) {
elem = elems[root + dataElem] = {
attributes: {},
children: {}
};
}
elem.attributes[dataAttr] = val;
}
CrayonUtil.log(dataElem + ' ' + dataAttr);
});
};
base.populateAttributes = function ($change) {
var elems = themeJSON.children;
var root = settings.cssThemePrefix + base.nameToID(themeInfo.name);
CrayonUtil.log(elems, root);
base.getAttributes().each(function () {
base.visitAttribute($(this), function (attr, elem, dataElem, dataAttr, root, elems) {
if (elem) {
if (dataAttr in elem.attributes) {
var val = base.removeImportant(elem.attributes[dataAttr]);
base.setElemValue(attr, val);
attr.trigger('change');
}
}
});
});
};
base.addImportant = function (attr) {
if (!reImportant.test(attr)) {
attr = attr + ' !important';
}
return attr;
};
base.removeImportant = function (attr) {
return attr.replace(reImportant, '');
};
base.isImportant = function (attr) {
return reImportant.exec(attr) != null;
};
base.appendStyle = function (css) {
previewCSS.html('<style>' + css + '</style>');
};
base.removeStyle = function () {
previewCSS.html('');
};
base.writeCSSInfo = function (info) {
var infoStr = '/*\n';
for (var field in info) {
infoStr += field + ': ' + info[field] + '\n';
}
return infoStr + '*/\n';
};
base.filterCSS = function (css) {
// Split all border CSS attributes into individual attributes
for (var child in css.children) {
var atts = css.children[child].attributes;
for (var att in atts) {
if (att in borderCSS) {
var rules = base.getBorderCSS(atts[att]);
for (var rule in rules) {
atts[att + '-' + rule] = rules[rule];
}
delete atts[att];
}
}
}
return css;
},
base.getBorderCSS = function (css) {
var result = {};
var important = base.isImportant(css);
$.each(strings.borderStyles, function (i, style) {
if (css.indexOf(style) >= 0) {
result.style = style;
}
});
var width = /\d+\s*(px|%|em|rem)/gi.exec(css);
if (width) {
result.width = width[0];
}
var color = /#\w+/gi.exec(css);
if (color) {
result.color = color[0];
}
if (important) {
for (var rule in result) {
result[rule] = base.addImportant(result[rule]);
}
}
return result;
},
base.createPrompt = function (args) {
args = $.extend({
title: adminStrings.prompt,
text: adminStrings.value,
desc: null,
value: '',
options: {
buttons: {
"OK": function () {
if (args.ok) {
args.ok(base.getFieldValue('prompt-text'));
}
$(this).crayonDialog('close');
},
"Cancel": function () {
$(this).crayonDialog('close');
}
},
open: function () {
base.getField('prompt-text').val(args.value).focus();
}
}
}, args);
args.html = '<table class="field-table crayon-prompt-' + base.nameToID(args.title) + '">';
if (args.desc) {
args.html += '<tr><td colspan="2">' + args.desc + '</td></tr>';
}
args.html += '<tr><td>' + args.text + ':</td><td>' + base.createInput('prompt-text') + '</td></tr>';
args.html += '</table>';
var options = {width: '400px'};
admin.createDialog(args, options);
};
base.initUI = function () {
// Bind events
preview = $('#crayon-editor-preview');
previewCSS = $('#crayon-editor-preview-css');
status = $('#crayon-editor-status');
title = $('#crayon-theme-editor-name');
info = $('#crayon-theme-editor-info');
$('#crayon-editor-controls').tabs();
$('#crayon-editor-back').click(function () {
if (changed) {
admin.createDialog({
html: strings.discardConfirm,
title: adminStrings.confirm,
yes: function () {
showMain();
}
});
} else {
showMain();
}
});
$('#crayon-editor-save').click(base.save);
// Set up jQuery UI
base.getAttributes().each(function () {
var attr = $(this);
var type = attr.attr('data-group');
if (type == 'color') {
var args = {
parts: 'full',
showNoneButton: true,
colorFormat: '#HEX'
};
args.open = function (e, color) {
$('.ui-colorpicker-dialog .ui-button').addClass('button-primary');
if (colorPickerPos) {
var picker = $('.ui-colorpicker-dialog:visible');
picker.css('left', colorPickerPos.left);
// picker.css('top', colorPickerPos.top);
}
};
args.select = function (e, color) {
attr.trigger('change');
};
args.close = function (e, color) {
attr.trigger('change');
};
attr.colorpicker(args);
attr.bind('change', function () {
var hex = attr.val();
attr.css('background-color', hex);
attr.css('color', CrayonUtil.getReadableColor(hex));
});
} else if (type == 'size') {
attr.bind('change', function () {
var val = attr.val();
if (!reSize.test(val)) {
val = CrayonUtil.removeChars('^0-9-', val);
if (val != '') {
attr.val(val + 'px');
}
}
});
}
if (type != 'color') {
// For regular text boxes, capture changes on keys
attr.bind('keydown keyup', function () {
if (attr.attr(changedAttr) != attr.val()) {
CrayonUtil.log('triggering', attr.attr(changedAttr), attr.val());
attr.trigger('change');
}
});
}
// Update CSS changes to the live instance
attr.bind('change', function () {
if (attr.attr(changedAttr) == attr.val()) {
return;
} else {
attr.attr(changedAttr, attr.val());
}
if (loaded) {
base.persistAttribute(attr);
base.updateLiveCSS();
}
});
});
$('.ui-colorpicker-dialog').addClass('wp-dialog');
$('.ui-colorpicker-dialog').mouseup(function () {
base.colorPickerMove($(this));
});
};
base.colorPickerMove = function (picker) {
if (picker) {
colorPickerPos = {left: picker.css('left'), top: picker.css('top')};
}
};
base.updateLiveCSS = function (clone) {
clone = CrayonUtil.setDefault(clone, false);
if (previewCrayon) {
var json;
if (clone) {
var id = previewCrayon.attr('id');
json = $.extend(true, {}, themeJSON);
$.each(json.children, function (child) {
json.children['#' + id + child] = json.children[child];
delete json.children[child];
});
} else {
json = themeJSON;
}
base.appendStyle(CSSJSON.toCSS(json));
}
};
base.updateUI = function () {
$('#crayon-editor-controls input, #crayon-editor-controls select').bind('change', function () {
changed = true;
});
};
base.createInput = function (id, value, type) {
value = CrayonUtil.setDefault(value, '');
type = CrayonUtil.setDefault(type, 'text');
return '<input id="' + settings.cssInputPrefix + id + '" class="' + settings.cssInputPrefix + type + '" type="' + type + '" value="' + value + '" />';
};
base.createForm = function (inputs) {
var str = '<form class="' + settings.prefix + '-form"><table>';
$.each(inputs, function (input) {
str += '<tr><td class="field">' + input + '</td><td class="value">' + inputs[input] + '</td></tr>';
});
str += '</table></form>';
return str;
};
var showMain = function () {
admin.resetPreview();
admin.preview_update();
admin.show_theme_info();
admin.show_main();
//preview.html('');
};
base.updateTitle = function () {
var name = base.getName();
if (adminSettings.editing_theme) {
title.html(strings.editingTheme.replace('%s', name));
} else {
title.html(strings.creatingTheme.replace('%s', name));
}
};
base.updateInfo = function () {
info.html('<a target="_blank" href="' + adminSettings.currThemeURL + '">' + adminSettings.currThemeURL + '</a>');
};
};
})(jQueryCrayon);

View File

@ -0,0 +1,879 @@
<?php
class CrayonHTMLElement {
public $id;
public $class = '';
public $tag = 'div';
public $closed = FALSE;
public $contents = '';
public $attributes = array();
const CSS_INPUT_PREFIX = "crayon-theme-input-";
public static $borderStyles = array(
'none',
'hidden',
'dotted',
'dashed',
'solid',
'double',
'groove',
'ridge',
'inset',
'outset',
'inherit'
);
public function __construct($id) {
$this->id = $id;
}
public function addClass($class) {
$this->class .= ' ' . self::CSS_INPUT_PREFIX . $class;
}
public function addAttributes($atts) {
$this->attributes = array_merge($this->attributes, $atts);
}
public function attributeString() {
$str = '';
foreach ($this->attributes as $k => $v) {
$str .= "$k=\"$v\" ";
}
return $str;
}
public function __toString() {
return '<' . $this->tag . ' id="' . self::CSS_INPUT_PREFIX . $this->id . '" class="' . self::CSS_INPUT_PREFIX . $this->class . '" ' . $this->attributeString() . ($this->closed ? ' />' : ' >' . $this->contents . "</$this->tag>");
}
}
class CrayonHTMLInput extends CrayonHTMLElement {
public $name;
public $type;
public function __construct($id, $name = NULL, $value = '', $type = 'text') {
parent::__construct($id);
$this->tag = 'input';
$this->closed = TRUE;
if ($name === NULL) {
$name = CrayonUserResource::clean_name($id);
}
$this->name = $name;
$this->class .= $type;
$this->addAttributes(array(
'type' => $type,
'value' => $value
));
}
}
class CrayonHTMLSelect extends CrayonHTMLInput {
public $options;
public $selected = NULL;
public function __construct($id, $name = NULL, $value = '', $options = array()) {
parent::__construct($id, $name, 'select');
$this->tag = 'select';
$this->closed = FALSE;
$this->addOptions($options);
}
public function addOptions($options, $default = NULL) {
for ($i = 0; $i < count($options); $i++) {
$key = $options[$i];
$value = isset($options[$key]) ? $options[$key] : $key;
$this->options[$key] = $value;
}
if ($default === NULL && count($options) > 1) {
$this->attributes['data-default'] = $options[0];
} else {
$this->attributes['data-default'] = $default;
}
}
public function getOptionsString() {
$str = '';
foreach ($this->options as $k => $v) {
$selected = $this->selected == $k ? 'selected="selected"' : '';
$str .= "<option value=\"$k\" $selected>$v</option>";
}
return $str;
}
public function __toString() {
$this->contents = $this->getOptionsString();
return parent::__toString();
}
}
class CrayonHTMLSeparator extends CrayonHTMLElement {
public $name = '';
public function __construct($name) {
parent::__construct($name);
$this->name = $name;
}
}
class CrayonHTMLTitle extends CrayonHTMLSeparator {
}
class CrayonThemeEditorWP {
public static $attributes = NULL;
public static $attributeGroups = NULL;
public static $attributeGroupsInverse = NULL;
public static $attributeTypes = NULL;
public static $attributeTypesInverse = NULL;
public static $infoFields = NULL;
public static $infoFieldsInverse = NULL;
public static $settings = NULL;
public static $strings = NULL;
const ATTRIBUTE = 'attribute';
const RE_COMMENT = '#^\s*\/\*[\s\S]*?\*\/#msi';
public static function initFields() {
if (self::$infoFields === NULL) {
self::$infoFields = array(
// These are canonical and can't be translated, since they appear in the comments of the CSS
'name' => 'Name',
'description' => 'Description',
'version' => 'Version',
'author' => 'Author',
'url' => 'URL',
'original-author' => 'Original Author',
'notes' => 'Notes',
'maintainer' => 'Maintainer',
'maintainer-url' => 'Maintainer URL'
);
self::$infoFieldsInverse = CrayonUtil::array_flip(self::$infoFields);
// A map of CSS element name and property to name
self::$attributes = array();
// A map of CSS attribute to input type
self::$attributeGroups = array(
'color' => array('background', 'background-color', 'border-color', 'color', 'border-top-color', 'border-bottom-color', 'border-left-color', 'border-right-color'),
'size' => array('border-width'),
'border-style' => array('border-style', 'border-bottom-style', 'border-top-style', 'border-left-style', 'border-right-style')
);
self::$attributeGroupsInverse = CrayonUtil::array_flip(self::$attributeGroups);
// Mapping of input type to attribute group
self::$attributeTypes = array(
'select' => array('border-style', 'font-style', 'font-weight', 'text-decoration')
);
self::$attributeTypesInverse = CrayonUtil::array_flip(self::$attributeTypes);
}
}
public static function initSettings() {
CrayonSettingsWP::load_settings();
self::initFields();
self::initStrings();
if (self::$settings === NULL) {
self::$settings = array(
// Only things the theme editor needs
'cssThemePrefix' => CrayonThemes::CSS_PREFIX,
'cssInputPrefix' => CrayonHTMLElement::CSS_INPUT_PREFIX,
'attribute' => self::ATTRIBUTE,
'fields' => self::$infoFields,
'fieldsInverse' => self::$infoFieldsInverse,
'prefix' => 'crayon-theme-editor'
);
}
}
public static function initStrings() {
if (self::$strings === NULL) {
self::$strings = array(
// These appear only in the UI and can be translated
'userTheme' => crayon__("User-Defined Theme"),
'stockTheme' => crayon__("Stock Theme"),
'success' => crayon__("Success!"),
'fail' => crayon__("Failed!"),
'delete' => crayon__("Delete"),
'deleteThemeConfirm' => crayon__("Are you sure you want to delete the \"%s\" theme?"),
'deleteFail' => crayon__("Delete failed!"),
'duplicate' => crayon__("Duplicate"),
'newName' => crayon__("New Name"),
'duplicateFail' => crayon__("Duplicate failed!"),
'checkLog' => crayon__("Please check the log for details."),
'discardConfirm' => crayon__("Are you sure you want to discard all changes?"),
'editingTheme' => crayon__("Editing Theme: %s"),
'creatingTheme' => crayon__("Creating Theme: %s"),
'submit' => crayon__("Submit Your Theme"),
'submitText' => crayon__("Submit your User Theme for inclusion as a Stock Theme in Crayon! This will email me your theme - make sure it's considerably different from the stock themes :)"),
'message' => crayon__("Message"),
'submitMessage' => crayon__("Please include this theme in Crayon!"),
'submitSucceed' => crayon__("Submit was successful."),
'submitFail' => crayon__("Submit failed!"),
'borderStyles' => CrayonHTMLElement::$borderStyles
);
}
}
public static function admin_resources() {
global $CRAYON_VERSION;
self::initSettings();
$path = dirname(dirname(__FILE__));
wp_enqueue_script('cssjson_js', plugins_url(CRAYON_CSSJSON_JS, $path), $CRAYON_VERSION);
wp_enqueue_script('jquery_colorpicker_js', plugins_url(CRAYON_JS_JQUERY_COLORPICKER, $path), array('jquery', 'jquery-ui-core', 'jquery-ui-widget', 'jquery-ui-tabs', 'jquery-ui-draggable', 'jquery-ui-dialog', 'jquery-ui-position', 'jquery-ui-mouse', 'jquery-ui-slider', 'jquery-ui-droppable', 'jquery-ui-selectable', 'jquery-ui-resizable'), $CRAYON_VERSION);
wp_enqueue_script('jquery_tinycolor_js', plugins_url(CRAYON_JS_TINYCOLOR, $path), array(), $CRAYON_VERSION);
if (CRAYON_MINIFY) {
wp_enqueue_script('crayon_theme_editor', plugins_url(CRAYON_THEME_EDITOR_JS, $path), array('jquery', 'crayon_js', 'crayon_admin_js', 'cssjson_js', 'jquery_colorpicker_js', 'jquery_tinycolor_js'), $CRAYON_VERSION);
} else {
wp_enqueue_script('crayon_theme_editor', plugins_url(CRAYON_THEME_EDITOR_JS, $path), array('jquery', 'crayon_util_js', 'crayon_admin_js', 'cssjson_js', 'jquery_colorpicker_js', 'jquery_tinycolor_js'), $CRAYON_VERSION);
}
wp_localize_script('crayon_theme_editor', 'CrayonThemeEditorSettings', self::$settings);
wp_localize_script('crayon_theme_editor', 'CrayonThemeEditorStrings', self::$strings);
wp_enqueue_style('crayon_theme_editor', plugins_url(CRAYON_THEME_EDITOR_STYLE, $path), array('wp-jquery-ui-dialog'), $CRAYON_VERSION);
wp_enqueue_style('jquery_colorpicker', plugins_url(CRAYON_CSS_JQUERY_COLORPICKER, $path), array(), $CRAYON_VERSION);
}
public static function form($inputs) {
$str = '<form class="' . self::$settings['prefix'] . '-form"><table>';
$sepCount = 0;
foreach ($inputs as $input) {
if ($input instanceof CrayonHTMLInput) {
$str .= self::formField($input->name, $input);
} else if ($input instanceof CrayonHTMLSeparator) {
$sepClass = '';
if ($input instanceof CrayonHTMLTitle) {
$sepClass .= ' title';
}
if ($sepCount == 0) {
$sepClass .= ' first';
}
$str .= '<tr class="separator' . $sepClass . '"><td colspan="2"><div class="content">' . $input->name . '</div></td></tr>';
$sepCount++;
} else if (is_array($input) && count($input) > 1) {
$name = $input[0];
$fields = '<table class="split-field"><tr>';
$percent = 100 / count($input);
for ($i = 1; $i < count($input); $i++) {
$class = $i == count($input) - 1 ? 'class="last"' : '';
$fields .= '<td ' . $class . ' style="width: ' . $percent . '%">' . $input[$i] . '</td>';
}
$fields .= '</tr></table>';
$str .= self::formField($name, $fields, 'split');
}
}
$str .= '</table></form>';
return $str;
}
public static function formField($name, $field, $class = '') {
return '<tr><td class="field ' . $class . '">' . $name . '</td><td class="value ' . $class . '">' . $field . '</td></tr>';
}
public static function content() {
self::initSettings();
$theme = CrayonResources::themes()->get_default();
$editing = false;
if (isset($_GET['curr_theme'])) {
$currTheme = CrayonResources::themes()->get($_GET['curr_theme']);
if ($currTheme) {
$theme = $currTheme;
}
}
if (isset($_GET['editing'])) {
$editing = CrayonUtil::str_to_bool($_GET['editing'], FALSE);
}
$tInformation = crayon__("Information");
$tHighlighting = crayon__("Highlighting");
$tFrame = crayon__("Frame");
$tLines = crayon__("Lines");
$tNumbers = crayon__("Line Numbers");
$tToolbar = crayon__("Toolbar");
$tBackground = crayon__("Background");
$tText = crayon__("Text");
$tBorder = crayon__("Border");
$tTopBorder = crayon__("Top Border");
$tBottomBorder = crayon__("Bottom Border");
$tBorderRight = crayon__("Right Border");
$tHover = crayon__("Hover");
$tActive = crayon__("Active");
$tPressed = crayon__("Pressed");
$tHoverPressed = crayon__("Pressed & Hover");
$tActivePressed = crayon__("Pressed & Active");
$tTitle = crayon__("Title");
$tButtons = crayon__("Buttons");
$tNormal = crayon__("Normal");
$tInline = crayon__("Inline");
$tStriped = crayon__("Striped");
$tMarked = crayon__("Marked");
$tStripedMarked = crayon__("Striped & Marked");
$tLanguage = crayon__("Language");
$top = '.crayon-top';
$bottom = '.crayon-bottom';
$hover = ':hover';
$active = ':active';
$pressed = '.crayon-pressed';
?>
<div
id="icon-options-general" class="icon32"></div>
<h2>
Crayon Syntax Highlighter
<?php crayon_e('Theme Editor'); ?>
</h2>
<h3 id="<?php echo self::$settings['prefix'] ?>-name">
<?php
// if ($editing) {
// echo sprintf(crayon__('Editing "%s" Theme'), $theme->name());
// } else {
// echo sprintf(crayon__('Creating Theme From "%s"'), $theme->name());
// }
?>
</h3>
<div id="<?php echo self::$settings['prefix'] ?>-info"></div>
<p>
<a id="crayon-editor-back" class="button-primary"><?php crayon_e("Back To Settings"); ?></a>
<a id="crayon-editor-save" class="button-primary"><?php crayon_e("Save"); ?></a>
<span id="crayon-editor-status"></span>
</p>
<?php //crayon_e('Use the Sidebar on the right to change the Theme of the Preview window.') ?>
<div id="crayon-editor-top-controls"></div>
<table id="crayon-editor-table" style="width: 100%;" cellspacing="5"
cellpadding="0">
<tr>
<td id="crayon-editor-preview-wrapper">
<div id="crayon-editor-preview"></div>
</td>
<div id="crayon-editor-preview-css"></div>
<td id="crayon-editor-control-wrapper">
<div id="crayon-editor-controls">
<ul>
<li title="<?php echo $tInformation ?>"><a class="crayon-tab-information" href="#tabs-1"></a></li>
<li title="<?php echo $tHighlighting ?>"><a class="crayon-tab-highlighting" href="#tabs-2"></a></li>
<li title="<?php echo $tFrame ?>"><a class="crayon-tab-frame" href="#tabs-3"></a></li>
<li title="<?php echo $tLines ?>"><a class="crayon-tab-lines" href="#tabs-4"></a></li>
<li title="<?php echo $tNumbers ?>"><a class="crayon-tab-numbers" href="#tabs-5"></a></li>
<li title="<?php echo $tToolbar ?>"><a class="crayon-tab-toolbar" href="#tabs-6"></a></li>
</ul>
<div id="tabs-1">
<?php
self::createAttributesForm(array(
new CrayonHTMLTitle($tInformation)
));
?>
<div id="tabs-1-contents"></div>
<!-- Auto-filled by theme_editor.js -->
</div>
<div id="tabs-2">
<?php
$highlight = ' .crayon-pre';
$elems = array(
'c' => crayon__("Comment"),
's' => crayon__("String"),
'p' => crayon__("Preprocessor"),
'ta' => crayon__("Tag"),
'k' => crayon__("Keyword"),
'st' => crayon__("Statement"),
'r' => crayon__("Reserved"),
't' => crayon__("Type"),
'm' => crayon__("Modifier"),
'i' => crayon__("Identifier"),
'e' => crayon__("Entity"),
'v' => crayon__("Variable"),
'cn' => crayon__("Constant"),
'o' => crayon__("Operator"),
'sy' => crayon__("Symbol"),
'n' => crayon__("Notation"),
'f' => crayon__("Faded"),
'h' => crayon__("HTML"),
'' => crayon__("Unhighlighted")
);
$atts = array(new CrayonHTMLTitle($tHighlighting));
foreach ($elems as $class => $name) {
$fullClass = $class != '' ? $highlight . ' .crayon-' . $class : $highlight;
$atts[] = array(
$name,
self::createAttribute($fullClass, 'color'),
self::createAttribute($fullClass, 'font-weight'),
self::createAttribute($fullClass, 'font-style'),
self::createAttribute($fullClass, 'text-decoration')
);
}
self::createAttributesForm($atts);
?>
</div>
<div id="tabs-3">
<?php
$inline = '-inline';
self::createAttributesForm(array(
new CrayonHTMLTitle($tFrame),
new CrayonHTMLSeparator($tNormal),
// self::createAttribute('', 'background', $tBackground),
array(
$tBorder,
self::createAttribute('', 'border-width'),
self::createAttribute('', 'border-color'),
self::createAttribute('', 'border-style')
),
new CrayonHTMLSeparator($tInline),
self::createAttribute($inline, 'background', $tBackground),
array(
$tBorder,
self::createAttribute($inline, 'border-width'),
self::createAttribute($inline, 'border-color'),
self::createAttribute($inline, 'border-style')
),
));
?>
</div>
<div id="tabs-4">
<?php
$stripedLine = ' .crayon-striped-line';
$markedLine = ' .crayon-marked-line';
$stripedMarkedLine = ' .crayon-marked-line.crayon-striped-line';
self::createAttributesForm(array(
new CrayonHTMLTitle($tLines),
new CrayonHTMLSeparator($tNormal),
self::createAttribute('', 'background', $tBackground),
new CrayonHTMLSeparator($tStriped),
self::createAttribute($stripedLine, 'background', $tBackground),
new CrayonHTMLSeparator($tMarked),
self::createAttribute($markedLine, 'background', $tBackground),
array(
$tBorder,
self::createAttribute($markedLine, 'border-width'),
self::createAttribute($markedLine, 'border-color'),
self::createAttribute($markedLine, 'border-style'),
),
self::createAttribute($markedLine . $top, 'border-top-style', $tTopBorder),
self::createAttribute($markedLine . $bottom, 'border-bottom-style', $tBottomBorder),
new CrayonHTMLSeparator($tStripedMarked),
self::createAttribute($stripedMarkedLine, 'background', $tBackground),
));
?>
</div>
<div id="tabs-5">
<?php
$nums = ' .crayon-table .crayon-nums';
$stripedNum = ' .crayon-striped-num';
$markedNum = ' .crayon-marked-num';
$stripedMarkedNum = ' .crayon-marked-num.crayon-striped-num';
self::createAttributesForm(array(
new CrayonHTMLTitle($tNumbers),
array(
$tBorderRight,
self::createAttribute($nums, 'border-right-width'),
self::createAttribute($nums, 'border-right-color'),
self::createAttribute($nums, 'border-right-style'),
),
new CrayonHTMLSeparator($tNormal),
self::createAttribute($nums, 'background', $tBackground),
self::createAttribute($nums, 'color', $tText),
new CrayonHTMLSeparator($tStriped),
self::createAttribute($stripedNum, 'background', $tBackground),
self::createAttribute($stripedNum, 'color', $tText),
new CrayonHTMLSeparator($tMarked),
self::createAttribute($markedNum, 'background', $tBackground),
self::createAttribute($markedNum, 'color', $tText),
array(
$tBorder,
self::createAttribute($markedNum, 'border-width'),
self::createAttribute($markedNum, 'border-color'),
self::createAttribute($markedNum, 'border-style'),
),
self::createAttribute($markedNum.$top, 'border-top-style', $tTopBorder),
self::createAttribute($markedNum.$bottom, 'border-bottom-style', $tBottomBorder),
new CrayonHTMLSeparator($tStripedMarked),
self::createAttribute($stripedMarkedNum, 'background', $tBackground),
self::createAttribute($stripedMarkedNum, 'color', $tText),
));
?>
</div>
<div id="tabs-6">
<?php
$toolbar = ' .crayon-toolbar';
$title = ' .crayon-title';
$button = ' .crayon-button';
$info = ' .crayon-info';
$language = ' .crayon-language';
self::createAttributesForm(array(
new CrayonHTMLTitle($tToolbar),
new CrayonHTMLSeparator($tFrame),
self::createAttribute($toolbar, 'background', $tBackground),
array(
$tBottomBorder,
self::createAttribute($toolbar, 'border-bottom-width'),
self::createAttribute($toolbar, 'border-bottom-color'),
self::createAttribute($toolbar, 'border-bottom-style'),
),
array(
$tTitle,
self::createAttribute($title, 'color'),
self::createAttribute($title, 'font-weight'),
self::createAttribute($title, 'font-style'),
self::createAttribute($title, 'text-decoration')
),
new CrayonHTMLSeparator($tButtons),
self::createAttribute($button, 'background-color', $tBackground),
self::createAttribute($button.$hover, 'background-color', $tHover),
self::createAttribute($button.$active, 'background-color', $tActive),
self::createAttribute($button.$pressed, 'background-color', $tPressed),
self::createAttribute($button.$pressed.$hover, 'background-color', $tHoverPressed),
self::createAttribute($button.$pressed.$active, 'background-color', $tActivePressed),
new CrayonHTMLSeparator($tInformation . ' ' . crayon__("(Used for Copy/Paste)")),
self::createAttribute($info, 'background', $tBackground),
array(
$tText,
self::createAttribute($info, 'color'),
self::createAttribute($info, 'font-weight'),
self::createAttribute($info, 'font-style'),
self::createAttribute($info, 'text-decoration')
),
array(
$tBottomBorder,
self::createAttribute($info, 'border-bottom-width'),
self::createAttribute($info, 'border-bottom-color'),
self::createAttribute($info, 'border-bottom-style'),
),
new CrayonHTMLSeparator($tLanguage),
array(
$tText,
self::createAttribute($language, 'color'),
self::createAttribute($language, 'font-weight'),
self::createAttribute($language, 'font-style'),
self::createAttribute($language, 'text-decoration')
),
self::createAttribute($language, 'background-color', $tBackground)
));
?>
</div>
</div>
</td>
</tr>
</table>
<?php
exit();
}
public static function createAttribute($element, $attribute, $name = NULL) {
$group = self::getAttributeGroup($attribute);
$type = self::getAttributeType($group);
if ($type == 'select') {
$input = new CrayonHTMLSelect($element . '_' . $attribute, $name);
if ($group == 'border-style') {
$input->addOptions(CrayonHTMLElement::$borderStyles);
} else if ($group == 'float') {
$input->addOptions(array(
'left',
'right',
'both',
'none',
'inherit'
));
} else if ($group == 'font-style') {
$input->addOptions(array(
'normal',
'italic',
'oblique',
'inherit'
));
} else if ($group == 'font-weight') {
$input->addOptions(array(
'normal',
'bold',
'bolder',
'lighter',
'100',
'200',
'300',
'400',
'500',
'600',
'700',
'800',
'900',
'inherit'
));
} else if ($group == 'text-decoration') {
$input->addOptions(array(
'none',
'underline',
'overline',
'line-through',
'blink',
'inherit'
));
}
} else {
$input = new CrayonHTMLInput($element . '_' . $attribute, $name);
}
$input->addClass(self::ATTRIBUTE);
$input->addAttributes(array(
'data-element' => $element,
'data-attribute' => $attribute,
'data-group' => $group
));
return $input;
}
public static function createAttributesForm($atts) {
echo self::form($atts);
}
/**
* Saves the given theme id and css, making any necessary path and id changes to ensure the new theme is valid.
* Echos 0 on failure, 1 on success and 2 on success and if paths have changed.
*/
public static function save() {
CrayonSettingsWP::load_settings();
$oldID = stripslashes($_POST['id']);
$name = stripslashes($_POST['name']);
$css = stripslashes($_POST['css']);
$change_settings = CrayonUtil::set_default($_POST['change_settings'], TRUE);
$allow_edit = CrayonUtil::set_default($_POST['allow_edit'], TRUE);
$allow_edit_stock_theme = CrayonUtil::set_default($_POST['allow_edit_stock_theme'], CRAYON_DEBUG);
$delete = CrayonUtil::set_default($_POST['delete'], TRUE);
$oldTheme = CrayonResources::themes()->get($oldID);
if (!empty($oldID) && !empty($css) && !empty($name)) {
// By default, expect a user theme to be saved - prevents editing stock themes
// If in DEBUG mode, then allow editing stock themes.
$user = $oldTheme !== NULL && $allow_edit_stock_theme ? $oldTheme->user() : TRUE;
$oldPath = CrayonResources::themes()->path($oldID);
$oldDir = CrayonResources::themes()->dirpath_for_id($oldID);
// Create an instance to use functions, since late static binding is only available in 5.3 (PHP kinda sucks)
$theme = CrayonResources::themes()->resource_instance('');
$newID = $theme->clean_id($name);
$name = CrayonResource::clean_name($newID);
$newPath = CrayonResources::themes()->path($newID, $user);
$newDir = CrayonResources::themes()->dirpath_for_id($newID, $user);
$exists = CrayonResources::themes()->is_loaded($newID) || (is_file($newPath) && is_file($oldPath));
if ($exists && $oldPath != $newPath) {
// Never allow overwriting a theme with a different id!
echo -3;
exit();
}
if ($oldPath == $newPath && $allow_edit === FALSE) {
// Don't allow editing
echo -4;
exit();
}
// Create the new path if needed
if (!is_dir($newDir)) {
wp_mkdir_p($newDir);
$imageSrc = $oldDir . 'images';
if (is_dir($imageSrc)) {
try {
// Copy image folder
CrayonUtil::copyDir($imageSrc, $newDir . 'images', 'wp_mkdir_p');
} catch (Exception $e) {
CrayonLog::syslog($e->getMessage(), "THEME SAVE");
}
}
}
$refresh = FALSE;
$replaceID = $oldID;
// Replace ids in the CSS
if (!is_file($oldPath) || strpos($css, CrayonThemes::CSS_PREFIX . $oldID) === FALSE) {
// The old path/id is no longer valid - something has gone wrong - we should refresh afterwards
$refresh = TRUE;
}
// XXX This is case sensitive to avoid modifying text, but it means that CSS must be in lowercase
$css = preg_replace('#(?<=' . CrayonThemes::CSS_PREFIX . ')' . $replaceID . '\b#ms', $newID, $css);
// Replace the name with the new one
$info = self::getCSSInfo($css);
$info['name'] = $name;
$css = self::setCSSInfo($css, $info);
$result = @file_put_contents($newPath, $css);
$success = $result !== FALSE;
if ($success && $oldPath !== $newPath) {
if ($oldID !== CrayonThemes::DEFAULT_THEME && $delete) {
// Only delete the old path if it isn't the default theme
try {
// Delete the old path
CrayonUtil::deleteDir($oldDir);
} catch (Exception $e) {
CrayonLog::syslog($e->getMessage(), "THEME SAVE");
}
}
// Refresh
echo 2;
} else {
if ($refresh) {
echo 2;
} else {
if ($success) {
echo 1;
} else {
echo -2;
}
}
}
// Set the new theme in settings
if ($change_settings) {
CrayonGlobalSettings::set(CrayonSettings::THEME, $newID);
CrayonSettingsWP::save_settings();
}
} else {
CrayonLog::syslog("$oldID=$oldID\n\n$name=$name", "THEME SAVE");
echo -1;
}
exit();
}
public static function duplicate() {
CrayonSettingsWP::load_settings();
$oldID = $_POST['id'];
$oldPath = CrayonResources::themes()->path($oldID);
$_POST['css'] = file_get_contents($oldPath);
$_POST['delete'] = FALSE;
$_POST['allow_edit'] = FALSE;
$_POST['allow_edit_stock_theme'] = FALSE;
self::save();
}
public static function delete() {
CrayonSettingsWP::load_settings();
$id = $_POST['id'];
$dir = CrayonResources::themes()->dirpath_for_id($id);
if (is_dir($dir) && CrayonResources::themes()->exists($id)) {
try {
CrayonUtil::deleteDir($dir);
CrayonGlobalSettings::set(CrayonSettings::THEME, CrayonThemes::DEFAULT_THEME);
CrayonSettingsWP::save_settings();
echo 1;
} catch (Exception $e) {
CrayonLog::syslog($e->getMessage(), "THEME SAVE");
echo -2;
}
} else {
echo -1;
}
exit();
}
public static function submit() {
global $CRAYON_EMAIL;
CrayonSettingsWP::load_settings();
$id = $_POST['id'];
$message = $_POST['message'];
$dir = CrayonResources::themes()->dirpath_for_id($id);
$dest = $dir . 'tmp';
wp_mkdir_p($dest);
if (is_dir($dir) && CrayonResources::themes()->exists($id)) {
try {
$zipFile = CrayonUtil::createZip($dir, $dest, TRUE);
$result = CrayonUtil::emailFile(array(
'to' => $CRAYON_EMAIL,
'from' => get_bloginfo('admin_email'),
'subject' => 'Theme Editor Submission',
'message' => $message,
'file' => $zipFile
));
CrayonUtil::deleteDir($dest);
if ($result) {
echo 1;
} else {
echo -3;
}
} catch (Exception $e) {
CrayonLog::syslog($e->getMessage(), "THEME SUBMIT");
echo -2;
}
} else {
echo -1;
}
exit();
}
public static function getCSSInfo($css) {
$info = array();
preg_match(self::RE_COMMENT, $css, $matches);
if (count($matches)) {
$comment = $matches[0];
preg_match_all('#([^\r\n:]*[^\r\n\s:])\s*:\s*([^\r\n]+)#msi', $comment, $matches);
if (count($matches)) {
for ($i = 0; $i < count($matches[1]); $i++) {
$name = $matches[1][$i];
$value = $matches[2][$i];
$info[self::getFieldID($name)] = $value;
}
}
}
return $info;
}
public static function cssInfoToString($info) {
$str = "/*\n";
foreach ($info as $id => $value) {
$str .= self::getFieldName($id) . ': ' . $value . "\n";
}
$str .= "*/";
return $str;
}
public static function setCSSInfo($css, $info) {
return preg_replace(self::RE_COMMENT, self::cssInfoToString($info), $css);
}
public static function getFieldID($name) {
if (isset(self::$infoFieldsInverse[$name])) {
return self::$infoFieldsInverse[$name];
} else {
return CrayonUserResource::clean_id($name);
}
}
public static function getFieldName($id) {
self::initFields();
if (isset(self::$infoFields[$id])) {
return self::$infoFields[$id];
} else {
return CrayonUserResource::clean_name($id);
}
}
public static function getAttributeGroup($attribute) {
if (isset(self::$attributeGroupsInverse[$attribute])) {
return self::$attributeGroupsInverse[$attribute];
} else {
return $attribute;
}
}
public static function getAttributeType($group) {
if (isset(self::$attributeTypesInverse[$group])) {
return self::$attributeTypesInverse[$group];
} else {
return 'text';
}
}
}
?>

18
util/touch.txt Normal file
View File

@ -0,0 +1,18 @@
// List of mobile device strings to look for inside the user agent of browsers.
// This is used to disable mouseover triggered events and just show the content if possible.
Android
Mobile
Touch
Phone
Nokia
Motorola
HTC
Blackberry
Samsung
Ericsson
LGE
Palm
Kindle
iPhone
iPad
iPod