Archive

Archive for the ‘Web Coding’ Category

WordPress – 301 location to sub page

August 10th, 2010

WordPress is great for blogging but still has a way to go to be a CMS. One thing I find odd is that you can create Categories for Posts but not for Pages. Usually a client will want pages categorized for navigation. So this becomes a problem. Sure you can nest Pages (parents and children) but that means you must have content in every menu item.

After a quick google search I came across some code that allows WP’s Pages to have empty menu items for categorization. Or at least that’s the visual effect. The fix is to create a Template in your theme with some PHP code. It redirects the browser to the first Child Page:

<?php
/*
Template Name: Redirect To First Child
*/
if (have_posts()) {
  while (have_posts()) {
  the_post();
  $pagekids = get_pages("child_of=".$post->ID."&sort_column=menu_order");
  $firstchild = $pagekids[0];
  wp_redirect(get_permalink($firstchild->ID));
 }
}
?>

This works but I’m not too fond of it. It uses a refresh. I tweaked it a bit. Changed the wp_redirect to a Location header and added a 301 status code:

<?php
/*
Template Name: 301 Redirect To First Child
*/
if (have_posts()) {
 while (have_posts()) {
  the_post();
  $pagekids = get_pages("child_of=".$post->ID."&sort_column=menu_order");
  $firstchild = $pagekids[0];
  header("HTTP/1.1 301 Moved Permanently");
  header("Location: ".get_permalink($firstchild->ID));
  exit();
 }
}
?>

This is much faster on the front end. It also tells search engines not to index those blank categorization pages.

<?php/*Template Name: 301 Redirect To First Child*/if (have_posts()) {  while (have_posts()) {    the_post();    $pagekids = get_pages(“child_of=”.$post->ID.”&sort_column=menu_order”);    $firstchild = $pagekids[0];   header(“HTTP/1.1 301 Moved Permanently”);   header(“Location: “.get_permalink($firstchild->ID));   exit();  }}?>

PHP , , , , ,

Updated compressed scripty 1.8.3 for LightView, PHP

April 8th, 2010

I ran across a problem with LightView which is stated as requiring Prototype 1.6.1 and Scriptaculous 1.8.2. Yet it was failing even when I had scriptaculous 1.8.3 loaded.

Apparently LightView looks for the loader scriptaculous.js rather than the actual components (effect, builder, etc).

My previous compressed Prototype 1.6.1 and Scriptaculous 1.8.3 did not have the loader/stub scriptaculous.js file. Ideally, that’s never needed as long as you load the other scriptaculous js files.

So here is an updated package. Also in this archive is the PHP version of the ColdFusion file to server the jgz.

The combined file is now 273KB. The load order is as follows:

  • prototype
  • scriptaculous
  • builder
  • effects
  • dragdrop
  • controls
  • slider
  • sound

It includes all comments and credits. I gzipped it down to 62KB.

You’d load it like so:

<script type="text/javascript" charset="ISO-8859-1" src="/includes/js/scriptaculous/scriptaculous.cfm"></script>

Download it: wv-scripty-183.zip

ColdFusion, PHP, Scriptaculous

Custom scrollbars in Adium – ‘Elegant Simple’ Message Style

March 11th, 2010

Visually based on the “Pretty Simple” Message Style by Piotrek Marciniak, I’ve created a new breed of Adium Message Style – which boasts a completely custom scrollbar.

This message style is a working proof of concept. It is a prototype for the talented folks that create  wonderful message styles. I’m a developer, not an artist. I hope that others will use it as a spring board for rapid development of a whole new breed of message styles with custom scrollbars.

Since Adium Message Styles are really web pages, it only seemed right to mash up Prototype JS, LivePipe UI and Scriptaculous!

Features

  • Fade-in of messages
  • Auto smooth scrolling when new message is received
  • Custom styled scrollbar
  • Dynamic height scrollbar handle
  • Header and Footer objects of scrollbar handle
  • Auto-hiding and fading scrollbar (mouse in/out of window)
  • Mouse wheel support

Get the Flash Player to see the wordTube Media Player.

( View full size 800×600 MP4 3.7MB )

Go and get it!

Adium, JavaScript, Mac OS X, Scriptaculous , , ,

Compressed Prototype 1.6.1 and Scriptaculous 1.8.3

February 3rd, 2010

I created a new compressed file for Prototype 1.6.1 and Scriptaculous 1.8.3. Included is my modified sound.js.

The combined file is 268KB. The load order is as follows:

  • prototype
  • builder
  • effects
  • dragdrop
  • controls
  • slider
  • sound

It includes all comments and credits. I gzipped it down to 60KB.

For your convenience in the attached zip contains both versions and a ColdFusion file to serve the correct one. You’d load it like so:

<script type="text/javascript" charset="ISO-8859-1" src="/includes/js/scriptaculous/scriptaculous.cfm"></script>

Well, what are you waiting for? :) wv-scripty-183.zip

JavaScript, Scriptaculous

Speeding up cffm v1.1x

January 7th, 2010

I manage a site with nearly 50GB of small PDFs. Thousands of directories and files. This makes CFFM super duper slow. I know it sounds silly, but when staring at a blank window, 15 seconds feels like 15 minutes. The problem is that with every page load, the entire directory tree below your initial directory is read. Crazy. Here is the fix…

At around line 648 of cffm.cfm, only turn on recursion if this particular action requires it:

<cfset variables.listAllFiles = cffm.directoryList(cffm.includeDir, (isdefined("url.action") and url.action eq 'copymoveForm'))>

… which is, when moving or copying. In my application, speed increased 10x.
And to get a little more speed when listing a directory with images…

At around line 67 of cffm.cfm, turn off image sizes:

<cfinvokeargument name="enableImageDimensionsInDirList" value="true">

ColdFusion , , ,

CFSelect with multiple query columns

December 16th, 2009

CFSelect is nice because it can help you write out some code quicker. Just like the rest of ColdFusion. But I never used it because so many times I needed to display two columns in the <option>, such as “#lastName#, #firstName#”.

While working on a site I fell into the same routine. I start typing out CFSelect then grit my teeth when I get to the Display attribute. Being stubborn about it I stumbled upon a nice MySQL function called CONCAT(). Using that one can merge two columns in the query to be output as a single column name. Like so:

<cfquery name="emps" datasource="#application.datasource#">
SELECT
 id, CONCAT(lastname, ', ', firstname) AS fullName
FROM
 employees
ORDER BY
 lastname, firstname
</cfquery>

Then simply use that column name for the display (or elsewhere needed):

<cfselect name="employeeid" query="emps" selected="" value="id" display="fullName"/>

ColdFusion, MySQL, Web Coding , , , , , , ,

MySQL: counts of multiple sub-items of each parent

October 27th, 2009

Sometimes it is useful to show in a list the numbers of children each object has. For instance how many Products are in each Category.

That’s simple enough to do when only one child type is used:

SELECT
 categories.title, categories.id,
 count(products.id) as productCount
FROM
 categories
   INNER JOIN products ON categories.id = products.categoryid

However, if you wanted to count two separate children types, the same method of querying will give you very odd results:

SELECT
 categories.title, categories.id,
 count(products.id) as productCount, count(images.id) as imagesCount
FROM
 categories
   INNER JOIN products ON categories.id = products.categoryid
   INNER JOIN images ON categories.id = images.categoryid

The lazy programmer would get around this by using the server language – looping through a simple query of the category, and with each row run another query to count the products (and another for the images). Yuck.

Instead, I found this method to work quite well:

SELECT
 cats.title AS title, cats.ID AS id,
 COALESCE(prods.howmany,0) AS productCount,
 COALESCE(imgs.howmany,0) AS imageCount
FROM (
 SELECT title, ID
 FROM categories
) AS cats
LEFT JOIN (
 SELECT
   count(products.id) as howmany,
   products.categoryid as categoryid
 FROM products
   LEFT JOIN categories ON products.categoryid = categories.id
 GROUP BY products.categoryid
) AS prods ON cats.id=prods.categoryid
LEFT JOIN (
 SELECT
   count(images.id) as howmany,
   images.categoryid as categoryid
 FROM images
   LEFT JOIN categories ON images.categoryid = categories.id
 GROUP BY images.categoryid
) AS imgs ON cats.id=imgs.categoryid

Note the use of the ‘COALESCE()’ function so that nulls are returned as a 0 (zero).
As you can see the database is still running three queries. But they are all within one connection, and the server language didn’t do any work.  Then MySQL joins those queries together into one result, easily parsed by your server language of choice. Here, ColdFusion:

<table>
 <tr>
   <td>Category</td>
   <td>Products</td>
   <td>Images</td>
 </tr>
 <cfoutput query="read">
 <tr>
   <td>#title#</td>
   <td>#productCount#</td>
   <td>#imageCount#</td>
 </tr>
 </cfoutput>
</table>

MySQL, Web Coding , , ,

CF TinyMCE 090616 – Vscope no longer required for automatic multiple instance tracking

June 17th, 2009

A big thank to Mr. Camden for giving me a few minutes of his time! With his insight I was able to remove the required Vscope argument. Instead, multiple instances per page are tracked through Request. No more required argument, and it’s backwards compatible again.

Grab the update here: http://github.com/WebVeteran/cf-tinymce/

CF TinyMCE, ColdFusion, TinyMCE , ,

ColdFusion clips for Coda

June 16th, 2009

I have made quite a few Clips in Coda to make development a little speedier. Hopefully you can get some use out of them too.

Coda Clips

Preview of Coda Clips - keep in mind the clips window only shows the first line of each clip.

Download the Clips here:
ColdFusion Coda Clips

Coda, ColdFusion

CF TinyMCE 090612 – automatically handles multiple instance per page

June 16th, 2009

I updated CF tinyMCE with a small nicety. It now automatically handles multiple instance per page. Previously, it would have to be invoked like so:

<cfoutput>
<tr>
	<td>
		#application.includes.tinymce(
			content=read.en,
			element="en",
			csswidth="444px",
			resizing=true,
			theme='advanced',
			theme_advanced_buttons1 = "bold,italic,underline,|,justifyleft,justifycenter,justifyright,justifyfull,|,formatselect,|,bullist,numlist,|,undo,redo,|,code,cleanup",
			theme_advanced_buttons2 = "",
			theme_advanced_buttons3 = ""

		)#
	</td>
	<td>
		#application.includes.tinymce(
			content=read.es,
			element="es",
			csswidth="444px",
			resizing=true,
			theme='advanced',
			loadbase='0',
			language='es',
			theme_advanced_buttons1 = "bold,italic,underline,|,justifyleft,justifycenter,justifyright,justifyfull,|,formatselect,|,bullist,numlist,|,undo,redo,|,code,cleanup",
			theme_advanced_buttons2 = "",
			theme_advanced_buttons3 = "",
			gecko_spellcheck = "false"
		)#
	</td>
</tr>
</cfoutput>

Notice the ‘loadbase=0′ argument on the second invocation. That told the previous version of CF TinyMCE to not all of TinyMCE again – just load the settings instead.

The new version automatically handles multiple instances and not loading TinyMCE all over again for subsequent invocations on the same page. Therefore, the new syntax example is:

<cfoutput>
<tr>
	<td>
		#application.includes.tinymce(
			VScope=Variables,
			content=read.en,
			element="en",
			csswidth="444px",
			resizing=true,
			theme='advanced',
			theme_advanced_buttons1 = "bold,italic,underline,|,justifyleft,justifycenter,justifyright,justifyfull,|,formatselect,|,bullist,numlist,|,undo,redo,|,code,cleanup",
			theme_advanced_buttons2 = "",
			theme_advanced_buttons3 = ""

		)#
	</td>
	<td>
		#application.includes.tinymce(
			VScope=Variables,
			content=read.es,
			element="es",
			csswidth="444px",
			resizing=true,
			theme='advanced',
			language='es',
			theme_advanced_buttons1 = "bold,italic,underline,|,justifyleft,justifycenter,justifyright,justifyfull,|,formatselect,|,bullist,numlist,|,undo,redo,|,code,cleanup",
			theme_advanced_buttons2 = "",
			theme_advanced_buttons3 = "",
			gecko_spellcheck = "false"
		)#
	</td>
</tr>
</cfoutput>

No more loadbase! The key is the argument “Vscope=Variables”. That lets CF pass the Variables scope back and forth between a page and a function. It is a required argument which I am not happy about. But since it’s value never changes it’s not so bad.

Because of this fundamental change, CF TinyMCE 090612 is not backwards compatible. If anyone knows how to pass the Variables scope back and forth between a page and a function, without an argument like I am here – please let me know!

You can download CF TinyMCE at github: http://github.com/WebVeteran/cf-tinymce/

CF TinyMCE, ColdFusion, TinyMCE , ,