Hello, I'm Aaron Harun, a New York based
Traveler, Developer and Web Consultant.
You're about to have an "AaHa!" moment.

PHP Syntax Highlighting For Prism.js

I wanted to test the newly-released Prism.js since it promised clean markup and easy plugin development, but I found it was lacking a major feature for my own use: PHP Syntax Highlighting.

So, letting the code be my guide, I present an add-on to Prism.js less than 10 hours after it was released into the wild publicly.

Update: Instead of using the below code-blocks, you can just grab it from my forked repository. The repository has a few other updates and fixes.

Prism

The following code snippets can be added into an external .js file or the main prism.js file. The modifications are mainly for testing (read: kinda buggy) and released under the same license Prism itself is.

Add PHP Syntax Highlighting

Prism.languages.php = {
	'comment': {
		pattern: /(^|[^\\])(\/\*[\w\W]*?\*\/|\/\/.*?(\r?\n|$))/g,
		lookbehind: true
	},
	'deliminator': /(\?>|\?&gt;|&lt;\?php|<\?php)/ig,
	'variable': /(\$\w+)\b/ig,
	'string': /("|')(\\?.)*?\1/g,
	'regex': {
		pattern: /(^|[^/])\/(?!\/)(\[.+?]|\\.|[^/\r\n])+\/[gim]{0,3}(?=\s*($|[\r\n,.;})]))/g,
		lookbehind: true
	},
	'keyword': /\b(and|or|xor|array|as|break|case|cfunction|class|const|continue|declare|default|die|do|else|elseif|enddeclare|endfor|endforeach|endif|endswitch|endwhile|extends|for|foreach|function|include|include_once|global|if|new|return|static|switch|use|require|require_once|var|while|abstract|interface|public|implements|extends|private|protected|throw)\b/g,
	'function': /\b(abs|acos|acosh|addcslashes|addslashes|array_change_key_case|array_chunk|array_combine|array_count_values|array_diff|array_diff_assoc|array_diff_key|array_diff_uassoc|array_diff_ukey|array_fill|array_filter|array_flip|array_intersect|array_intersect_assoc|array_intersect_key|array_intersect_uassoc|array_intersect_ukey|array_key_exists|array_keys|array_map|array_merge|array_merge_recursive|array_multisort|array_pad|array_pop|array_product|array_push|array_rand|array_reduce|array_reverse|array_search|array_shift|array_slice|array_splice|array_sum|array_udiff|array_udiff_assoc|array_udiff_uassoc|array_uintersect|array_uintersect_assoc|array_uintersect_uassoc|array_unique|array_unshift|array_values|array_walk|array_walk_recursive|atan|atan2|atanh|base64_decode|base64_encode|base_convert|basename|bcadd|bccomp|bcdiv|bcmod|bcmul|bindec|bindtextdomain|bzclose|bzcompress|bzdecompress|bzerrno|bzerror|bzerrstr|bzflush|bzopen|bzread|bzwrite|ceil|chdir|checkdate|checkdnsrr|chgrp|chmod|chop|chown|chr|chroot|chunk_split|class_exists|closedir|closelog|copy|cos|cosh|count|count_chars|date|decbin|dechex|decoct|deg2rad|delete|ebcdic2ascii|echo|empty|end|ereg|ereg_replace|eregi|eregi_replace|error_log|error_reporting|escapeshellarg|escapeshellcmd|eval|exec|exit|exp|explode|extension_loaded|feof|fflush|fgetc|fgetcsv|fgets|fgetss|file_exists|file_get_contents|file_put_contents|fileatime|filectime|filegroup|fileinode|filemtime|fileowner|fileperms|filesize|filetype|floatval|flock|floor|flush|fmod|fnmatch|fopen|fpassthru|fprintf|fputcsv|fputs|fread|fscanf|fseek|fsockopen|fstat|ftell|ftok|getallheaders|getcwd|getdate|getenv|gethostbyaddr|gethostbyname|gethostbynamel|getimagesize|getlastmod|getmxrr|getmygid|getmyinode|getmypid|getmyuid|getopt|getprotobyname|getprotobynumber|getrandmax|getrusage|getservbyname|getservbyport|gettext|gettimeofday|gettype|glob|gmdate|gmmktime|ini_alter|ini_get|ini_get_all|ini_restore|ini_set|interface_exists|intval|ip2long|is_a|is_array|is_bool|is_callable|is_dir|is_double|is_executable|is_file|is_finite|is_float|is_infinite|is_int|is_integer|is_link|is_long|is_nan|is_null|is_numeric|is_object|is_readable|is_real|is_resource|is_scalar|is_soap_fault|is_string|is_subclass_of|is_uploaded_file|is_writable|is_writeable|mkdir|mktime|nl2br|parse_ini_file|parse_str|parse_url|passthru|pathinfo|readlink|realpath|rewind|rewinddir|rmdir|round|str_ireplace|str_pad|str_repeat|str_replace|str_rot13|str_shuffle|str_split|str_word_count|strcasecmp|strchr|strcmp|strcoll|strcspn|strftime|strip_tags|stripcslashes|stripos|stripslashes|stristr|strlen|strnatcasecmp|strnatcmp|strncasecmp|strncmp|strpbrk|strpos|strptime|strrchr|strrev|strripos|strrpos|strspn|strstr|strtok|strtolower|strtotime|strtoupper|strtr|strval|substr|substr_compare)\b/g,
	'constant': /\b(__FILE__|__LINE__|__METHOD__|__FUNCTION__|__CLASS__)\b/g,
	'boolean': /\b(true|false)\b/g,
	'number': /\b-?(0x)?\d*\.?\d+\b/g,
	'operator': /[-+]{1,2}|!|=?\<|=?\>;|={1,2}(?!>)|(\&){1,2}|\|?\||\?|\*|\//g,
	'punctuation': /[{}[\];(),.:]/g
};

Allow embedded HTML in PHP

if (Prism.languages.markup) {
	Prism.languages.insertBefore('php', 'comment', {
		'markup': {
			pattern: /(\?>|\?&gt;)[\w\W]*?(?=(&lt;\?php|<\?php))/ig,
			lookbehind : true,
			inside: {
				'markup': {
					pattern: /&lt;\/?[\w:-]+\s*[\w\W]*?&gt;/gi,
					inside: Prism.languages.markup.tag.inside
				},
				rest: Prism.languages.php
			}
		}
	});
}

NOTES / Warnings

This code adds several new language elements named: function, keyword, variable and constant that have no CSS attributed to them, so use this CSS somewhere.

.token.function, .token.constant {
	color: #07a;
}
.token.variable {
	color: #e90;
}

.token.deliminator {
	font-weight:bold;
}

This code has NOT been heavily tested, but has been run successfully against the following block of code:

/**
			Sample Block. 
			Author: Aaron Harun
			URL: http://aaron.md, http://aahacreative.com
		**/
    if(__FILE__){
        $explicitive = ($happyandyouknowit == false) ? ':(' : '! =D';
        // Stick in some HTML. 
        ?&gt;
        	&ltstrong>Why,&lt/strong>
        &lt?php
        echo 'hello ' . "world" . addslashes($explicitive);
    }

It doesn’t cover PHP embedded in HTML yet, but it seems very easy to do. The Repository version has it.

And finally, Prism.js is not running on this site, yet. I’ll have to integrate it into WP before that’s possible. Integrated with WP. Booyah.

Tagged with: , , ,
Posted in JavaScript
8 comments on “PHP Syntax Highlighting For Prism.js
  1. Alec Ritson says:

    Copied the code above and it worked perfectly. Awesome! thanks for this!

  2. Jason Davis says:

    Thanks for the contribution. I have a couple suggestion/request if someone could add it. Would really like to add something to make vriable/names in DocComments get wrapped with a CSS class. Also would like to be able to highlight custom Function names with a CSS class

  3. Greg says:

    Hello.

    I have a little problem with “=>”, try this:

    $var = array( 'bar' =&gt; 'foo' );

  4. Tem says:

    Your escaping is broken. In the last section the HTML after “// Stick in some HTML. ” is double escaped, making it unreadable.

    Also, the comments are colored brown which doesn’t go very well against the dark brown background of the code sections on this blog.

    (Feel free to remove once taken care of).

    • aaron says:

      It isn’t broken. If you download the github, you’ll see that code needs to be formatted in that way in the examples file.

  5. ejn says:

    One minor bug too:

    add this

    Prism.languages.php = { ‘ignore’: /&(lt|gt|amp);/gi,

    and change operator ={1,2} to ={1,2}(?!>)

    • Jake says:

      I second this – otherwise any code with logical AND “&&” is rewritten as “&&”.

      Adding the ‘ignore’ line fixes it.

  6. Danny says:

    Nice; I just started using this. One minor bug: on line 18, your operator reg exp uses literal ‘<’ and ‘>’ characters rather than the &lt; and &gt; entities (and prism.js on line 93 replaces the characters automatically).

    (and I’m still trying to figure out how how coded the cool spinning gears!)

2 Pings/Trackbacks for "PHP Syntax Highlighting For Prism.js"
  1. [...] und kann die Syntax von HTML, CSS und JavaScript hervorheben. Die Erweiterung für PHP habe ich von hier. Der Bugfix aus einer der Kommentare wird allerdings auch noch [...]

  2. [...] PHP, based almost completely on Aaron Harun's code [...]

Leave a Reply

Standard Rules Apply: Use <code> tags for code snippets. Keep it relevant. Other than that, be your awesome self.

*(required)

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

The Archive (Sounds ominous, right?)
Categories (Oh! Look at them all)
`