Contact Neil Pie

x Cancel
posted 4 years ago

Overriding the siteURL setting in Wordpress


Only a little one this. It's documented quite well in the WP Codex, but I thought it might be useful to share a use case.

When developing for Wordpress I often use a development and a staging environment alongside production. When staging, it's nice to hook into the production database to ensure that nothing is going to go awry when switching live. Unfortunately, Wordpress defines the URL used for generating all its links from an entry in the database, and placing the above declarations into wp-config.php (obviously changing '' to your actual staging url... ) works around this problem.

I know there are 'theme preview' plugins available, but this solution seemed a little cleaner to me.

posted 4 years ago

Removing Parent Links from WP Navigation


 * A function to strip parent links from WP generated navigation menus
 * This function is intended to be used to strip the <a> tags from any links in
 * a list that contain children. While it is intended to be used with the WP
 * wp_list_pages() function, it should also work with any list of <a> elements.
 * @author neil_pie <>
 * @version 0.2
 * @package Wordpress
 * @param string $pages - the HTML <li> elements from which to remove the parent
 *  links
 * @param boolean $echo - whether to return or echo the resulting HTML
 * @return string - the function always returns the resulting HTML as a string

function removeParentLinks($pages = FALSE, $echo = FALSE) {

    if (!$pages) $pages = wp_list_pages('echo=0&title_li=');
    $pages = explode("</li>", $pages);
    $count = 0;
    foreach($pages as $page) {
        if(strstr($page,"<ul>")) {
            $page = explode('<ul>', $page);
            $page[0] = str_replace('</a>','',$page[0]);
            $page[0] = preg_replace('/\<a(.*)\>/','',$page[0]);
            if(count($page) == 3) {
                $page[1] = str_replace('</a>','',$page[1]);
                $page[1] = preg_replace('/\<a(.*)\>/','',$page[1]);
            $page = implode('<ul>', $page);
        $pages[$count] = $page;
    $pages = implode('</li>',$pages);
    if ($echo) echo $pages;
    return $pages;

This function uses regular expression matching to remove the tags from list items that contain child lists.

I built it on request from client that had wanted some elements of his main navigation bar to contain drop-down menus, and on those elements only he did not want the parent element to be a 'clickable' link. There is currently no way perform this via wp_list_pages() or wp_nav_menu()

It seems to work fine but I'd imagine that it could be improved upon, particularly in the regex matching, but also that there must be a way to make these 'holding pages' non directly-navigable.

posted 4 years ago

Alternative HTML Form CAPTCHA

if (isset($_POST['submit'])){
    if(isset($_POST['mail']) && !empty($_POST['mail'])){
        $message = 'Whoopsie! You have entered something that you shouldn\'t have.';
    // Send your message
<!DOCTYPE html>
        <title>Invisible Captcha Mailing Form</title>
    <form  id="contact_form" action="/" method="post"  >
            <legend>Message Me Direct</legend>
            <?php if (isset($message)) echo "<p class=\"message $class\">$message</p>"; ?>
            <label for="name" >Name</label><input  placeholder="What is your name?" name="name" id="name" type="text"  />
            <label for="address" >Email</label><input placeholder="What is your email address?" id="address"  name="address" type="email"  />
            <label for="message" >Message</label><textarea placeholder="What have you got to say?"  id="message" name="message"   ></textarea>
            <label for="submit" >Submit</label><input type="submit" value="Send" id="submit" name="submit"   />
            <label for="cap" style="display:none" >Please leave blank</label><input type="email" id="cap" name="cap" style="display:none" />

I've been using this technique as a CAPTCHA on my personal site for a couple of years to great success, and have implemented into various client projects as well. I doubt it's a very new idea, or even particularly clever but I thought I'd share it anyway as an alternative to many of the other CAPTCHA methods out there.

Essentially you add an extra field to your form with the label 'Please leave blank', which you then hide with CSS. On submission, if there is any text in this field then the server just kicks the form back out again.

Like I said, I've been using it on my personal site for some time and it's quite effective. I can't admit to ever logging how much spam it catches, however, so it's possible that I'm just fortunate...

posted 4 years ago

Cachebusting Scripts & Styles in Wordpress

                function pie_enqueue_style($handle = 'None',$src = false,$deps = array(),$ver = false, $media = false ){
    $ver = $ver === false ? pie_cb_version($src) : $ver;

function pie_enqueue_script($handle = 'None',$src = false, $deps = array(),$ver = false, $in_footer = false){
    $ver = $ver === false ? pie_cb_version($src) : $ver;

function pie_cb_version($src){  
 $src = parse_url($src) ? $src : $_SERVER["DOCUMENT_ROOT"].$src;
return file_exists($file) ? filemtime($file) : 1;

These are three functions to overwrite the default version parameter that Wordpress appends to script & style URLs when using wp_enqueue_script() and wp_enqueue_style(). The WP version parameter is replaced with Cachebusting parameters based on the last time a local file was modified.

For example...

      `<script type='text/javascript' src='/wp-content/themes/mytheme/js/modernizr-1.5.min.js?ver=3.1.1'></script> `


     ` <script type='text/javascript' src='/wp-content/themes/mytheme/js/modernizr-1.5.min.js?ver=1300881484'></script> `

The effect is that if a file has been changed since it was last cached by a users browser, then the browser will be forced to reload the file, otherwise it will use the cached version. At the moment, it is only set up to work with absolute URLs or URLs relative to the site root (starting with a '/'). Worth noting is that if a file is not found, the function return '1' as the version parameter, thus keeping the WP version hidden.

I'm very interested in people's thoughts on these functions and possible ways to improve them, or if there's a better way of going about achieving this altogether.

EDIT: I've changed the pie_cb_version() to detect any valid URL versus a relative path (formerly it only looked for strings starting with 'http://') - credit for spotting this flaw to @mattwiebe

posted 4 years ago

Expanding Search Box from Search Icon (pure CSS)


/* Set up the background styles on the form element */
form {
border-bottom:4px solid #f0f6fb;

-webkit-appearance: none;  /*removes the default webkit styling of 'search' input elements */
 -webkit-transition: all .4s ease-in-out; /* animates the width change - adjusted by @jenius */
position:relative; /* required for the 'handle' of the spyglass */ 
border:4px solid #abc8df; 

::-webkit-input-placeholder {
color:transparent; /* prevents the placeholder text from displaying before we expand the input */
font-style:italic;font-size:13px; /* some basic styling */
 input[type="search"]::-webkit-search-cancel-button { 
display: none; /* prevents the default webkit 'x' from appearing in the search input element */ 
#expand:hover, #expand:focus{
input:hover::-webkit-input-placeholder {
color:#cae0ef; /*make the placeholder visible on hover */
/* some crazy CSS to create the 'handle' of the spyglass. It's placed on the form element because 'input' elements won't take an :after property, but could be tagged onto any other element and positioned accordingly */
border:4px solid #abc8df; 
-webkit-transform: rotate(-45deg);
    <input id="expand" type="search" placeholder="Search" /> 

This code is based on a design idea for a Spyglass icon that expands into a search input field on hover by @yassinebentaieb that was put forward in his post Search within icon

I really liked the idea and threw together this implementation. It's Webkit-centric CSS only at the moment, could probably use a tidy, and can be seen in place at

It would have been nice to be able to use the HTML5 'search' input element for the search field, but Webkit hijacks the styling on that element - so for this design it has to be a 'text' element. EDIT: thanks to @jesseweed for providing a solution to this problem.

Again much prop to @yassinebentaieb for the design and idea that I have hijacked!

posted 4 years ago

Clean up wp_head() in Wordpress

                remove_action('wp_head', 'feed_links_extra', 3); // Displays the links to the extra feeds such as category feeds
remove_action('wp_head', 'feed_links', 2); // Displays the links to the general feeds: Post and Comment Feed
remove_action('wp_head', 'rsd_link'); // Displays the link to the Really Simple Discovery service endpoint, EditURI link
remove_action('wp_head', 'wlwmanifest_link'); // Displays the link to the Windows Live Writer manifest file.
remove_action('wp_head', 'index_rel_link'); // index link
remove_action('wp_head', 'parent_post_rel_link'); // prev link
remove_action('wp_head', 'start_post_rel_link'); // start link
remove_action('wp_head', 'adjacent_posts_rel_link_wp_head'); // Displays relational links for the posts adjacent to the current post.
remove_action('wp_head', 'wp_generator'); // Displays the XHTML generator that is generated on the wp_head hook, WP version


This is just a collection of the various actions that you need to remove to clean out some of the default meta-data generated by the wp_head() function. Include them in your theme or plugin setup at your whim.

Recording this here because when I was looking for it I found 'adjacent_posts_rel_link_wp_head' was changed from 'adjacent_posts_rel_link' to this at WP3.0, but only chanced upon the change outside of the official docs. Thus, if you're still running WP2.x you may need to tweak it slightly.