<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Artful Code &#187; html</title>
	<atom:link href="http://www.artfulcode.net/tags/html/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.artfulcode.net</link>
	<description>Resources and tips for dynamic, interactive languages.</description>
	<lastBuildDate>Fri, 09 Sep 2011 02:15:45 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<item>
		<title>PHP is a framework</title>
		<link>http://www.artfulcode.net/articles/php-is-a-framework/</link>
		<comments>http://www.artfulcode.net/articles/php-is-a-framework/#comments</comments>
		<pubDate>Fri, 15 May 2009 18:12:26 +0000</pubDate>
		<dc:creator>Jeff</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Soap box]]></category>
		<category><![CDATA[framework]]></category>
		<category><![CDATA[html]]></category>
		<category><![CDATA[php]]></category>
		<category><![CDATA[web design]]></category>

		<guid isPermaLink="false">http://www.artfulcode.net/?p=624</guid>
		<description><![CDATA[Rails, Django, Spring &#8211; application frameworks like these are now ubiquitous in the development of web-based applications. This is part of a trend in many general purpose languages of building toward the web. For these, the application framework is not just a buzzword; it is the abstraction used to build the language up to the [...]]]></description>
			<content:encoded><![CDATA[<p>Rails, Django, Spring &#8211; application frameworks like these are now ubiquitous in the development of web-based applications. This is part of a trend in many general purpose languages of building toward the web. For these, the application framework is not just a buzzword; it is the abstraction used to build the language up to the browser.<span id="more-624"></span></p>
<p>PHP was designed with the reverse in mind. In its first release, it could have been considered to be a DSL for web-based applications. It was written to specifically address the needs to writing web applications, and is now building toward a more general purpose language. In all likelihood, this is the wrong way around. It certainly does not fall into the bottom-up design Shangri-La of which Paul Graham is such a proponent.</p>
<p>In reality, though, web-based applications are driving the industry. PHP is still very relevant in that domain. From very early on, PHP was centered on functionality that is considered basic to any web-based framework. Functionality without which each library is simply a thin wrapper over CGI. Features like easy access to GET and POST variables, session handling, header control, and database access have been built into PHP from, if not the beginning, then close enough that dinosaurs like myself don&#8217;t remember it ever being otherwise.</p>
<p>PHP has its own share of frameworks, too, which allow the programmer to painstakingly map SQL schema to XML or vice versa. They carefully abstract the logic out of the view and force the programmer to jump through hoops to write a simple application (although, for complex applications, this often makes the programmer&#8217;s life *much* easier.)</p>
<p>PHP does not need any of this. In fact, the most pragmatic framework I have used to date for PHP is the <a href="http://clickontyler.com/simple-php-framework/">Simple PHP Framework</a>, which is just a set of useful classes to automate some of the more tedious areas of web development. What it does not do is get in the programmer&#8217;s way. It is <a href="http://en.wikipedia.org/wiki/Occam's_razor">Occam&#8217;s razor</a> at work in the world of web development. From the SPF website, quoting a non-existent link:</p>
<blockquote><p>&#8220;All the web frameworks in the world won’t turn a shitty programmer into a good one.&#8221;</p></blockquote>
<p>What PHP is not is elegant. It does not have beauty of prose, nor those features that make languages like ML and Lisp so exciting, such as closures, functions-as-objects, or lazy evaluation. Instead, PHP is, above all, a practical language. Instead, it has less sexy features, such as built-in support for XML, XSLT, and Xpath, support most databases, and the built-in ability to serialize to and from JSON and cookie strings.</p>
<p>It is easy to overlook how simple PHP makes many tasks that are complex in other frameworks. For example, Django&#8217;s form library is large and complex. I&#8217;ve no doubt that most other frameworks have equally Byzantine systems for developing reusable forms. In PHP, one might just write:</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;">function input($type, $name, $display, $value)
{
    &lt; ?
        &lt;label&gt;&lt; ?= $display ?&gt;
        &lt;input type=&quot;<span style="color: #000000; font-weight: bold;">&lt;?=</span> <span style="color: #000088;">$type</span> ?<span style="color: #339933;">/&gt;</span><span style="color: #0000ff;">&quot; value=&quot;</span><span style="color: #339933;">&lt;</span> ?<span style="color: #339933;">=</span> <span style="color: #000088;">$value</span> <span style="color: #000000; font-weight: bold;">?&gt;</span>&quot; /&gt;
    ?&gt;
}</pre></div></div>

<p>The function could be refined to separate the template and the code by putting the HTML into a separate include:</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000000; font-weight: bold;">function</span> input<span style="color: #009900;">&#40;</span><span style="color: #000088;">$type</span><span style="color: #339933;">,</span> <span style="color: #000088;">$name</span><span style="color: #339933;">,</span> <span style="color: #000088;">$dispaly</span><span style="color: #339933;">,</span> <span style="color: #000088;">$value</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #b1b100;">include</span> <span style="color: #0000ff;">'templates/input.inc.php'</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Simple, right? Which is not to say that PHP&#8217;s faults are not legion. That said, I think that PHP sometimes does a better job of building toward general purpose programming than many other languages do of building toward web development.</p>
<!-- Social Bookmarks BEGIN -->
<div class="social_bookmark">
<a><strong><em>Submit article</em></strong></a>
<br />
<div class="d">
<br />
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://del.icio.us/post?url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Fphp-is-a-framework%2F&amp;title=PHP+is+a+framework" rel="nofollow" title="Add to&nbsp;Del.icio.us"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/delicious.png" title="Add to&nbsp;Del.icio.us" alt="Add to&nbsp;Del.icio.us" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://digg.com/submit?phase=2&amp;url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Fphp-is-a-framework%2F&amp;title=PHP+is+a+framework" rel="nofollow" title="Add to&nbsp;digg"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/digg.png" title="Add to&nbsp;digg" alt="Add to&nbsp;digg" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://www.dzone.com/links/add.html?description=PHP+is+a+framework&amp;url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Fphp-is-a-framework%2F&amp;title=PHP+is+a+framework" rel="nofollow" title="Add to&nbsp;DZone"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/dzone.png" title="Add to&nbsp;DZone" alt="Add to&nbsp;DZone" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://www.facebook.com/sharer.php?u=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Fphp-is-a-framework%2F" rel="nofollow" title="Add to&nbsp;Facebook"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/facebook.png" title="Add to&nbsp;Facebook" alt="Add to&nbsp;Facebook" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://reddit.com/submit?url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Fphp-is-a-framework%2F&amp;title=PHP+is+a+framework" rel="nofollow" title="Add to&nbsp;reddit"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/reddit.png" title="Add to&nbsp;reddit" alt="Add to&nbsp;reddit" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://www.stumbleupon.com/submit?url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Fphp-is-a-framework%2F&amp;title=PHP+is+a+framework" rel="nofollow" title="Add to&nbsp;Stumble Upon"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/stumbleupon.png" title="Add to&nbsp;Stumble Upon" alt="Add to&nbsp;Stumble Upon" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://www.technorati.com/faves?add=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Fphp-is-a-framework%2F" rel="nofollow" title="Add to&nbsp;Technorati"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/technorati.png" title="Add to&nbsp;Technorati" alt="Add to&nbsp;Technorati" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://twitter.com/home/?status=Check+out+PHP+is+a+framework+@+http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Fphp-is-a-framework%2F" rel="nofollow" title="Add to&nbsp;Twitter"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/twitter.png" title="Add to&nbsp;Twitter" alt="Add to&nbsp;Twitter" /></a>
<br />
</div>
</div>
<!-- Social Bookmarks END -->
]]></content:encoded>
			<wfw:commentRss>http://www.artfulcode.net/articles/php-is-a-framework/feed/</wfw:commentRss>
		<slash:comments>9</slash:comments>
		</item>
		<item>
		<title>An alternative to large multi-selects</title>
		<link>http://www.artfulcode.net/articles/alternative-large-multi-selects/</link>
		<comments>http://www.artfulcode.net/articles/alternative-large-multi-selects/#comments</comments>
		<pubDate>Fri, 12 Sep 2008 15:15:59 +0000</pubDate>
		<dc:creator>Jeff</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[html]]></category>
		<category><![CDATA[javascript]]></category>
		<category><![CDATA[jquery]]></category>
		<category><![CDATA[releases]]></category>

		<guid isPermaLink="false">http://www.artfulcode.net/articles/alternative-large-multi-selects/</guid>
		<description><![CDATA[HTML has no useful, built-in form widget for selecting from a large number of options. Some libraries offer Javascript-powered alternatives, but few of these are built to deal with more than a few hundred options. The problem I recently worked on a project with a backend using the Django admin library. It is a wonderful [...]]]></description>
			<content:encoded><![CDATA[<p>HTML has no useful, built-in form widget for selecting from a large number of options.  Some libraries offer Javascript-powered alternatives, but few of these are built to deal with more than a few hundred options.<span id="more-12"></span></p>
<h4>The problem</h4>
<p>I recently worked on a project with a backend using the Django admin library.  It is a wonderful tool, but the <a href="http://docs.djangoproject.com/en/dev/ref/contrib/admin/#filter-horizontal">filter interface</a> is not equipped to deal with the thousands of options that were being populated in this particular form entry (a necessary parameter of the project.)</p>
<p>The Django filter interface would take 30 seconds or more to load the multi-select&#8217;s data on each form load, even on speedy computers.  Moreover, the search filter breaks up queries at spaces, then performs a substring search for each token for every option in the select.  Suffice it to say that this locked up more than a few browsers in our testing.</p>
<h4>The solution</h4>
<p>My first thought was to create my own search using a ternary tree or trie to index the data, but building these structures turned out to be <em>extremely</em> slow implemented in Javascript, taking even more time than the Django filter to initialize.</p>
<p>I ended up trying what seemed like a foolish idea.  Create one large string to search by joining all of the options&#8217; labels together (and delimiting with pipes).  I assumed this would take a huge amount of memory, but in fact it took less than Javascript trees and was <em>much</em> faster than operating directly on DOM nodes.  By delimiting the strings, a bounded regular expression could be used to perform reasonably fast searches of the data.  There would be the need to identify the options to which the strings originated, for which I created a simple hash mapping option label to value.</p>
<p>This solution has two main problems &#8211; it assumes that all entries in the select box have <em>both</em> a unique label and a unique value, and no label can have a pipe in it.  However, assuming that these conditions are met, this solution seems to work pretty speedily, and without overtaxing the browser.</p>
<h4>The code</h4>
<p>This code is implemented as a <a href="http://www.jquery.com">jQuery</a> plugin.  It hides the select and changes made to the widget automatically update the select.  A search box and two lists are inserted into the document; the user enters a partial match in the search box and hits return.  The first list is populated with the search results.  Double-clicking on a result copies it into the second list.</p>
<p>Items that are already selected are automatically put into the second list.  Regular expressions are permitted, and must be surrounded by forward slashes.</p>
<p>This module has been lightly tested in Firefox 2 and 3, Safari (latest), Opera (latest), and IE 7.  A few concessions in favor of efficiency have been made at the expense of clarity (mainly for IE, which seems to have the slowest Javascript engine), primarily in the SelectMap constructor.  jQuery&#8217;s each method and string concatenation proved to be too much for IE, so they were replaced with a for loop over the select node&#8217;s legacy <code>options</code> array.  Iterative string building was replaced with <code>Array.join</code>, which is faster (but more expensive in memory) in IE.</p>
<p>To use it:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">$<span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> select <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">new</span> BigSelect<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'target_id'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #006600; font-style: italic;">// or...</span>
    $<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'#target_id'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">bigSelect</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>The code is available <a title="Artful Code Projects" href="http://www.artfulcode.net/projects/">here</a>.  <span style="text-decoration: line-through;">You can see a live example here.</span></p>
<!-- Social Bookmarks BEGIN -->
<div class="social_bookmark">
<a><strong><em>Submit article</em></strong></a>
<br />
<div class="d">
<br />
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://del.icio.us/post?url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Falternative-large-multi-selects%2F&amp;title=An+alternative+to+large+multi-selects" rel="nofollow" title="Add to&nbsp;Del.icio.us"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/delicious.png" title="Add to&nbsp;Del.icio.us" alt="Add to&nbsp;Del.icio.us" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://digg.com/submit?phase=2&amp;url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Falternative-large-multi-selects%2F&amp;title=An+alternative+to+large+multi-selects" rel="nofollow" title="Add to&nbsp;digg"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/digg.png" title="Add to&nbsp;digg" alt="Add to&nbsp;digg" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://www.dzone.com/links/add.html?description=An+alternative+to+large+multi-selects&amp;url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Falternative-large-multi-selects%2F&amp;title=An+alternative+to+large+multi-selects" rel="nofollow" title="Add to&nbsp;DZone"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/dzone.png" title="Add to&nbsp;DZone" alt="Add to&nbsp;DZone" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://www.facebook.com/sharer.php?u=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Falternative-large-multi-selects%2F" rel="nofollow" title="Add to&nbsp;Facebook"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/facebook.png" title="Add to&nbsp;Facebook" alt="Add to&nbsp;Facebook" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://reddit.com/submit?url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Falternative-large-multi-selects%2F&amp;title=An+alternative+to+large+multi-selects" rel="nofollow" title="Add to&nbsp;reddit"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/reddit.png" title="Add to&nbsp;reddit" alt="Add to&nbsp;reddit" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://www.stumbleupon.com/submit?url=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Falternative-large-multi-selects%2F&amp;title=An+alternative+to+large+multi-selects" rel="nofollow" title="Add to&nbsp;Stumble Upon"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/stumbleupon.png" title="Add to&nbsp;Stumble Upon" alt="Add to&nbsp;Stumble Upon" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://www.technorati.com/faves?add=http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Falternative-large-multi-selects%2F" rel="nofollow" title="Add to&nbsp;Technorati"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/technorati.png" title="Add to&nbsp;Technorati" alt="Add to&nbsp;Technorati" /></a>
<a onclick="window.open(this.href, '_blank', 'scrollbars=yes,menubar=no,height=600,width=750,resizable=yes,toolbar=no,location=no,status=no'); return false;" href="http://twitter.com/home/?status=Check+out+An+alternative+to+large+multi-selects+@+http%3A%2F%2Fwww.artfulcode.net%2Farticles%2Falternative-large-multi-selects%2F" rel="nofollow" title="Add to&nbsp;Twitter"><img class="social_img" src="http://www.artfulcode.net/wp-content/plugins/social-bookmarks/images/twitter.png" title="Add to&nbsp;Twitter" alt="Add to&nbsp;Twitter" /></a>
<br />
</div>
</div>
<!-- Social Bookmarks END -->
]]></content:encoded>
			<wfw:commentRss>http://www.artfulcode.net/articles/alternative-large-multi-selects/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

