Tuesday, October 5, 2010

Inline scripts in a WordPress plugin

I wanted to include some inline JavaScript code in WordPress pages for performance reasons (a second HTTP request for 200 bytes is silly). I found the wp_enqueue_script API call, but it's only for external scripts. Looking through the entire API, I found the wp_print_scripts hook. It's not elegant, but it works:

function my_script() {
echo '' . "\n";
}

// Register the processing functions with WordPress
add_action('wp_print_scripts', 'my_script');

Tuesday, July 6, 2010

How to truncate an HTML/XHTML/XML snippet in PHP

<?php
function xmlentities($xml) {
return str_replace ( array ( '&', '"', "'", '<', '>' ), array ( '&amp;' , '&quot;', '&apos;' , '&lt;' , '&gt;' ), $xml);
}

function char_limit($text, $char_limit, $append = '...') {
$tok = strtok($text, " \n\t");
$result = '';

while ($tok !== false) {
if (strlen($tok) + strlen($result) + 1 <= $char_limit) {
$result = $result . ' ' . $tok;
} else {
$result .= $append;
break;
}
$tok = strtok(" \n\t");
}

return $result;
}

class TruncatingParser {
var $tagStack = array();

var $bufferedCdata = NULL;
var $out = '';
var $append = '';

var $maxChars = -1;
var $currentChars = 0;

function startElement($parser, $tagName, $attrs) {
$this->flushCharacterData();

if ($this->currentChars < $this->maxChars) {
$this->out .= '<' . $tagName;

foreach ($attrs as $key => $value) {
$this->out .= ' ' . $key . '="' . xmlentities($value) . '"';
}

$this->out .= '>';

$this->tagStack[count($this->tagStack)] = $tagName;
}
}

function endElement($parser, $tagName) {
$this->flushCharacterData();
if ($this->currentChars < $this->maxChars) {
$this->out .= '</' . $tagName . '>';
array_pop($this->tagStack);
}
}

function characterData($parser, $data) {
if ($this->currentChars < $this->maxChars) {
if ($this->bufferedCdata == NULL) {
$this->bufferedCdata = $data;
} else {
$this->bufferedCdata .= $data;
}
}
}

function flushCharacterData() {
if ($this->bufferedCdata != NULL && $this->currentChars < $this->maxChars) {
if ($this->currentChars + strlen($this->bufferedCdata) >= $this->maxChars) {
$charLimit = $this->maxChars - $this->currentChars;
$this->out .= xmlentities(char_limit($this->bufferedCdata, $charLimit, ''));
$this->out .= $this->append;

$this->currentChars = $this->maxChars;

while ($tag = array_pop($this->tagStack)) {
$this->out .= '</' . $tag . '>';
}
} else {
$this->out .= $this->bufferedCdata;
$this->currentChars += strlen($this->bufferedCdata);
}
}
$this->bufferedCdata = NULL;
}
}

function xml_char_limit($text, $char_limit, $append_text = '') {
$parser = new TruncatingParser();
$parser->maxChars = $char_limit;
$parser->append = $append_text;

$xml_parser = xml_parser_create();
xml_parser_set_option($xml_parser, XML_OPTION_CASE_FOLDING, 0);

xml_set_object($xml_parser, &$parser);

xml_set_element_handler($xml_parser, "startElement", "endElement");
xml_set_character_data_handler($xml_parser, "characterData");

$text = '<div>' . $text . '</div>';

if (!xml_parse($xml_parser, $text, TRUE)) {
return '';
}

xml_parser_free($xml_parser);

$out = $parser->out;

// Strip out the temporary root tag that was added
$out = substr($out, 5, strlen($out) - 11);

return $out;
}
?>

Thursday, June 10, 2010

One-jar

If you're getting this error from one-jar, make sure you declared your main method as static.

Exception in thread "main" java.lang.NullPointerException
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at com.simontuffs.onejar.Boot.run(Boot.java:306)
at com.simontuffs.onejar.Boot.main(Boot.java:159)

Monday, June 7, 2010

Hack for generating a random number in a script without $RANDOM

let "rand = 0x`dd if=/dev/urandom bs=4 count=1 2> /dev/null| md5sum | sed 's/................ .*//'`"

Thursday, May 27, 2010

Inserting CSS in HEAD with ModX

One of the neat things about ModX (or any CMS, really) is that you divide your HTML into chunks and reuse them across pages. Great as this is, it makes managing CSS a little annoying since you don't have any direct access to <head>.

Here's a quick snippet that solves that problem. Just insert [[register_css?file=`/assets/css/foo.css`]] in your template, page, or chunk, and create a snippet with this code:

if ($file) {
$modx->regClientCSS("<link rel='stylesheet' type='text/css' href='$file'></link>");
}
?>