Skip to content

Instantly share code, notes, and snippets.

@stevepiercy
Forked from paulherron/readme.txt
Created November 20, 2011 03:09
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save stevepiercy/1379753 to your computer and use it in GitHub Desktop.
Save stevepiercy/1379753 to your computer and use it in GitHub Desktop.
jQuery script to populate a specified input with a suggested slug. For example, if I write 'My Title' in a title field, it can populate the slug field with a suggestion of 'my_title'.
Video demo at http://screencast.com/t/WcjpL2lc.
By default it uses a title field ending in [title] or [name] as the source field, and a field ending in [slug] as the destination. This matches the naming conventions for a framework like CakePHP, i.e. <?php echo $form->input('title'); ?> outputs an input with a name of data[Model][title].
You can override the default source and destination fields by setting document.slugField and document.titleField in JavaScript beforehand:
<script>
document.titleField = "input[name$='[heading]']";
document.slugField = "input[name$='[url_safe_heading]']";
</script>
You can specify multiple source fields, which the script will concatenate together into one slug:
<script>
document.titleField = "input[name$='[first_name]'], input[name$='[last_name]']";
</script>
If the slug is manually overridden, no further suggestions are given.
$(document).ready(function() {
// Set some defaults.
if(typeof document.titleField == 'undefined') {
document.titleField = "input[name$='[title]'],input[name$='[name]']";
}
if(typeof document.slugField == 'undefined') {
document.slugField = "input[name*='slug']";
}
var hasEdited = false;
// If there's a slug already present, and it looks different to what would have been generated from the current title, deduced that the slug has already been manually edited.
if($(document.slugField).attr('value') != '' && slugify(getTitle()) != $(document.slugField).attr('value')) {
hasEdited = true;
$(document.slugField).css('color', '#000');
}
// Colour the slug field grey to imply that magic is happening.
$(document.slugField).css('color', '#666');
// Generate the slug automatically as soon as the script loads, as the 'title' field may have been prepopulated with a value.
populateSlugField($(document.titleField));
// Generate a new slug each time the title has been edited.
$(document.titleField).keyup(function() {
populateSlugField();
});
// Check for a manual override of the generated slug. Once the slug has been manually overridden, automatic slug generation should stop.
$(document.slugField).change(function() {
console.log('slug field has been edited');
hasEdited = true;
$(this).css('color', '#000');
});
/**
* Populates the 'slug' field with a URL-safe version of the 'title' field.
*/
function populateSlugField() {
if(!hasEdited && $(document.titleField).length > 0) {
slug = slugify(getTitle());
$(document.slugField).val(slug);
}
}
/**
* Converts text to a URL-safe form. For example, 'My Title' would become 'my_title'.
*
* @param string text The text to be slugified.
* @return string Slugified text
*/
function slugify(text) {
text = text.toLowerCase();
// Remove any characters that aren't URL-safe.
slug = text
// Replace spaces.
.replace(/\s+/g, '_')
// Replace special characters.
.replace(/[àáâãäå]/g, 'a')
.replace(/æ/g, 'ae')
.replace(/ç/g, 'c')
.replace(/[èéêë]/g, 'e')
.replace(/[ìíîï]/g, 'i')
.replace(/ñ/g, 'n')
.replace(/[òóôõöø]/g, 'o')
.replace(/œ/g, 'oe')
.replace(/[ùúûü]/g, 'u')
.replace(/[ýÿ]/g, 'y')
// In what's left, remove anything that isn't URL-safe.
.replace(/[^a-z0-9_-]/g, '');
return slug;
}
/**
* Fetches source text to be slugified. This might come from just one field, or be concatenated from multiple fields.
*
* @return string Title text
*/
function getTitle() {
if($(document.titleField).size() > 1) {
// As multiple title fields have been defined, concatenate them.
title = '';
i = 0;
$(document.titleField).each(function() {
if(i > 0 && title.length > 0 && this.value.length > 0) {
title += '_';
}
title += this.value;
i++;
});
} else {
title = $(document.titleField).val();
}
return title;
}
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment