Skip to content

Instantly share code, notes, and snippets.

@cfg
Created July 27, 2011 19:24
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 cfg/1110161 to your computer and use it in GitHub Desktop.
Save cfg/1110161 to your computer and use it in GitHub Desktop.
Generic Paging Links with ColdFusion
<!---
See: http://coreygilmore.com/blog/2008/05/29/generic-paging-links-with-coldfusion/
--->
<cffunction name="paginate_links" access="public" output="false" returntype="any" hint="Return links to paginated results, heavily based on paginate_links() <http://trac.wordpress.org/ticket/3159> from WordPress <http://wordpress.org/> by Michael D Adams <http://blogwaffe.com/>">
<cfargument name="link_format" required="YES" type="string" default="" hint="Link format. Use %PAGE% for the page number placeholder (required), %SHOW% for the paging size (optional)" />
<cfargument name="prev_next" required="YES" type="boolean" default="true" hint="Show previous/next links" />
<cfargument name="prev_text" required="YES" type="string" default="&laquo;&nbsp;Previous" hint="Text for 'Previous Page' link" />
<cfargument name="next_text" required="YES" type="string" default="Next&nbsp;&raquo;" hint="Text for 'Next Page' link" />
<cfargument name="end_size" required="YES" type="numeric" default="1" hint="How many numbers on either end including the end" />
<cfargument name="mid_size" required="YES" type="numeric" default="2" hint="How many numbers to either side of current not including current" />
<cfargument name="current" required="YES" type="numeric" default="" hint="Currently active page" />
<cfargument name="total" required="YES" type="numeric" default="1" hint="Total number of results. Number of pages will be calculated by total/page_size" />
<cfargument name="page_size" required="YES" type="numeric" default="20" hint="Number of results to show per page" />
<cfargument name="max_page_size" required="YES" type="numeric" default="50" hint="Maximum number of results to show per page, to prevent abuse." />
<cfargument name="show_all" required="YES" type="boolean" default="false" hint="Show all page numbers (ignore end_size, mid_size)" />
<cfargument name="show_all_threshold" required="YES" type="numeric" default="0" hint="Show all page numbers ONLY if the total number of pages is <= this value. 0 to ignore." />
<cfargument name="prev_class" required="YES" type="string" default="page-numbers pn-prev" hint="Class(es) to use for Previous Page link" />
<cfargument name="next_class" required="YES" type="string" default="page-numbers pn-next" hint="Class(es) to use for Next Page link" />
<cfargument name="current_class" required="YES" type="string" default="page-numbers pn-current" hint="Class(es) to use for Next Page link" />
<cfargument name="dots_class" required="YES" type="string" default="page-numbers pn-dots" hint="Class(es) to use for dots span" />
<cfargument name="page_numbers_class" required="YES" type="string" default="page-numbers" hint="Class(es) to use for page numbers" />
<cfargument name="return_type" required="YES" type="string" default="text" hint="Valid types are array, text" />
<cfscript>
var page_links = ArrayNew(1);
var link = '';
var n = 0;
var dots = false;
var num_pages = Ceiling( arguments.total / arguments.page_size ); // Total number of pages
// Sanity checks
if( arguments.end_size LT 0 ) {
arguments.end_size = 1;
}
if( arguments.mid_size LTE 0 ) {
arguments.mid_size = 2;
}
if( arguments.max_page_size ) {
arguments.page_size = Min( arguments.page_size, arguments.max_page_size );
}
// If we are within our show all threshold, enable the display of all pages
if( arguments.show_all_threshold GTE num_pages ) {
arguments.show_all = true;
}
// Add Previous Page link if current page is 2+, and we want to show next/prev links
if( arguments.prev_next AND arguments.current AND arguments.current GT 1 ) {
link = ReplaceNoCase( arguments.link_format, '%PAGE%', arguments.current - 1 );
link = ReplaceNoCase( link, '%SHOW%', arguments.page_size );
ArrayAppend(page_links, '<a class="#arguments.prev_class#" href="#link#">#arguments.prev_text#</a>' );
}
// Build internal page number links
for( n = 1; n LTE num_pages; n=n+1 ) {
if( n EQ arguments.current ) {
ArrayAppend( page_links, '<span class="#arguments.current_class#">#n#</span>' );
dots = true;
} else {
if( arguments.show_all OR ( n LTE arguments.end_size OR ( arguments.current AND n GTE arguments.current - arguments.mid_size AND n LTE arguments.current + arguments.mid_size ) OR n GT num_pages - arguments.end_size ) ) {
link = ReplaceNoCase( arguments.link_format, '%PAGE%', n );
link = ReplaceNoCase( link, '%SHOW%', arguments.page_size );
ArrayAppend( page_links, '<a class="#arguments.page_numbers_class#" href="#link#">#n#</a>' );
dots = true;
} else if( dots AND NOT arguments.show_all ) {
ArrayAppend( page_links, '<span class="#arguments.dots_class#">...</span>' );
dots = false;
}
}
}
// Add Next Page link if current page LT total, and we want to show next/prev links
if( arguments.prev_next AND arguments.current AND arguments.current LT num_pages ) {
link = ReplaceNoCase( arguments.link_format, '%PAGE%', arguments.current + 1 );
link = ReplaceNoCase( link, '%SHOW%', arguments.page_size );
ArrayAppend(page_links, '<a class="#arguments.next_class#" href="#link#">#arguments.next_text#</a>' );
}
if( arguments.return_type EQ "array" ) {
return page_links;
} else {
return ArrayToList(page_links, "");
}
</cfscript>
</cffunction>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment