<?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>Jorge Iván Meza Martínez &#187; JavaScript</title>
	<atom:link href="http://blog.jorgeivanmeza.com/tag/javascript/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.jorgeivanmeza.com</link>
	<description>The Fire Within Me: &#34;knowledge will set you free&#34;</description>
	<lastBuildDate>Thu, 09 Sep 2010 02:16:50 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>Redefinir una función en Javascript</title>
		<link>http://blog.jorgeivanmeza.com/2009/12/redefinir-una-funcion-en-javascript/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=redefinir-una-funcion-en-javascript</link>
		<comments>http://blog.jorgeivanmeza.com/2009/12/redefinir-una-funcion-en-javascript/#comments</comments>
		<pubDate>Fri, 11 Dec 2009 18:14:45 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de software]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[Hipergalaxia]]></category>
		<category><![CDATA[JavaScript]]></category>
		<guid isPermaLink="false">http://blog.jorgeivanmeza.com/?p=2190</guid>
		<description><![CDATA[Introducción. Estaba reutilizando un formulario complejo en un nuevo módulo de mi aplicación.  Todo iba bien hasta que descubrí que uno de los códigos Javascript que actualiza parte del formulario a través de AJAX no me era útil ya que debía mostrar una vista diferente a la estándar.   Como el código estaba escrito en funciones [...]]]></description>
			<content:encoded><![CDATA[<h2>Introducción.</h2>
<p>Estaba <em>reutilizando</em> un formulario complejo en un nuevo módulo de mi aplicación.  Todo iba bien hasta que descubrí que uno de los códigos Javascript que actualiza parte del formulario a través de AJAX no me era útil ya que debía mostrar una vista diferente a la <em>estándar</em>.   Como el código estaba escrito en funciones procedimentales no podía acceder a la sobreescritura de la orientación a objetos, sin embargo encontré un par de detalles interesantes de Javascript que me permitieron hacer algo similar.</p>
<h2>Determinar existencia de funciones.</h2>
<pre class="javascript">if(typeof miFuncion == 'function')
    // Si existe la función
else
    // No existe la función</pre>
<p>El código anterior determina si la función <span style="font-family: courier new,courier;">miFuncion</span> ha sido definida o no en el espacio de ejecución de la aplicación Javascript.</p>
<h2>Redefinir una función.</h2>
<pre class="javascript">window['miFuncion'] = function()
{
    // Nueva implementación de la función
};</pre>
<p>El código anterior permite redefinir la implementación de la función <span style="font-family: courier new,courier;">miFuncion</span> la cual obviamente fue especificada anteriormente.  Lo interesante de esta sintáxis de Javascript es que esta redefinición puede realizarse de manera dinámica, es decir, en un segundo archivo <span style="font-family: courier new,courier;">*.js</span> que se cargue después del original o inclusive dentro de un condicional.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/12/redefinir-una-funcion-en-javascript/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Hacer algo cuando inicia o termina el evento AJAX con Prototype</title>
		<link>http://blog.jorgeivanmeza.com/2009/11/hacer-algo-cuando-inicia-o-termina-el-evento-ajax-con-prototype/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=hacer-algo-cuando-inicia-o-termina-el-evento-ajax-con-prototype</link>
		<comments>http://blog.jorgeivanmeza.com/2009/11/hacer-algo-cuando-inicia-o-termina-el-evento-ajax-con-prototype/#comments</comments>
		<pubDate>Wed, 25 Nov 2009 13:46:15 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de software]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[AJAX]]></category>
		<category><![CDATA[Hipergalaxia]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Prototype]]></category>
		<guid isPermaLink="false">http://blog.jorgeivanmeza.com/?p=2152</guid>
		<description><![CDATA[Introducción. De manera análoga a como hace poco había mostrado como manejar el evento de inicio y terminación de AJAX con jQuery para realizar algún tipo de acción específica como el mostrar un indicador de carga, ahora experimentaremos como hacerlo con el framework de Prototype el cual nuevamente estaré utilizando en el proyecto de los [...]]]></description>
			<content:encoded><![CDATA[<h2>Introducción.</h2>
<p>De manera análoga a como hace poco había mostrado como <a href="http://blog.jorgeivanmeza.com/2009/10/hacer-algo-cuando-inicia-o-termina-el-evento-ajax-con-jquery/" target="_blank">manejar el evento de inicio y terminación de AJAX con jQuery</a> para realizar algún tipo de acción específica como el mostrar un indicador de carga, ahora experimentaremos como hacerlo con el framework de Prototype el cual nuevamente estaré utilizando en el proyecto de los próximos meses.</p>
<h2>Procedimiento.</h2>
<pre class="javascript">Ajax.Responders.register({
    onCreate: function()
    {
        // An AJAX request has been initialized!
    },
    onComplete: function()
    {
        // An AJAX request has been completed!
    }
});</pre>
<p>Adicionalmente hay otros eventos que pueden manejarse de igual manera <span style="font-family: courier new,courier;">onUninitialized</span>, <span style="font-family: courier new,courier;">onLoading</span>, <span style="font-family: courier new,courier;">onLoaded</span>, <span style="font-family: courier new,courier;">onInteractive</span> y <span style="font-family: courier new,courier;">onException</span>, además de los ya mencionados <span style="font-family: courier new,courier;">onCreate</span> y <span style="font-family: courier new,courier;">onComplete</span>.</p>
<h2>Enlaces.</h2>
<ul>
<li>Prototype API - Ajax Responders.<br />
<a href="http://api.prototypejs.org/ajax/ajax/responders.html" target="_blank">http://api.prototypejs.org/ajax/ajax/responders.html</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/11/hacer-algo-cuando-inicia-o-termina-el-evento-ajax-con-prototype/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Ejemplo rápido y simple de AJAX con PHP y PrototypeJS</title>
		<link>http://blog.jorgeivanmeza.com/2009/11/ejemplo-rapido-y-simple-de-ajax-con-php-y-prototypejs/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=ejemplo-rapido-y-simple-de-ajax-con-php-y-prototypejs</link>
		<comments>http://blog.jorgeivanmeza.com/2009/11/ejemplo-rapido-y-simple-de-ajax-con-php-y-prototypejs/#comments</comments>
		<pubDate>Tue, 24 Nov 2009 17:33:24 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de hardware]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[AJAX]]></category>
		<category><![CDATA[Hipergalaxia]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Prototype]]></category>
		<guid isPermaLink="false">http://blog.jorgeivanmeza.com/?p=2148</guid>
		<description><![CDATA[Introducción. Intentando recuperar mis neuronas que saben de Prototype para continuar por fin con uno de los proyectos que se encontraba en pausa permanente, el día de hoy me día a la breve tarea de recordar un poco la invocación asíncrona y la manipulación del DOM utilizando esta librería.  Para hacer una pequeña práctica decidí [...]]]></description>
			<content:encoded><![CDATA[<h2>Introducción.</h2>
<p>Intentando recuperar mis neuronas que saben de <a href="http://prototypejs.org/" target="_blank">Prototype</a> para continuar por fin con uno de los proyectos que se encontraba en pausa permanente, el día de hoy me día a la breve tarea de recordar un poco la invocación asíncrona y la manipulación del DOM utilizando esta librería.  Para hacer una pequeña práctica decidí modificar el ejemplo de la <a href="http://blog.jorgeivanmeza.com/2009/10/ejemplo-de-ajax-rapido-y-simple-con-php-y-jquery/" target="_blank">calculadora que se basaba en jQuery y PHP</a> para migrar su código de acuerdo con la especificación de Prototype.</p>
<p>Las modificaciones necesarias se centraron en la inclusión de la librería javascript en la página web (<em>frontend</em>) y en reescribir la invocación asíncrona de la aplicación web en PHP (<em>backend</em>).</p>
<h2>Procedimiento.</h2>
<p>Reemplazar la inclusión de la librería de jQuery por la de Prototype.  Para este caso se continúo utilizando el API de Google AJAX.</p>
<pre class="javascript">&lt;script src="http://www.google.com/jsapi"&gt;&lt;/script&gt;
&lt;script&gt;google.load("prototype", "1.6");&lt;/script&gt;</pre>
<p>Posteriormente se asoció el manejo del evento de presión del botón <span style="font-family: courier new,courier;">igual</span> a la invocación de la función <span style="font-family: courier new,courier;">procesar</span>, esto se realiza tan pronto como la estructura de la página (código HTML) se encuentra cargada completamente por el navegador.</p>
<pre class="javascript">/* Código a ejecutarse tan pronto como la
   página ha sido cargada por el navegador */
document.observe('dom:loaded', function()
{
    /* Asociar el evento de clic del botón 'igual'
       con la lógica del negocio de la aplicación */
    Event.observe('igual', 'click', procesar);
});</pre>
<p>Finalmente se implementa la función <span style="font-family: courier new,courier;">procesar</span> que realizará la invocación asíncrona del cálculo matemático.  Esta función consta de las siguientes partes.</p>
<ol>
<li>Información básica del requerimiento.</li>
<li>Que hacer en caso de éxito.</li>
<li>Que hacer en caso de fracaso.</li>
</ol>
<p>El requerimiento incluye la siguiente información básica de conexión.</p>
<ul>
<li>El URL de la aplicación remota a invocar (<em>backend</em>).</li>
<li>El método HTTP a utilizar.</li>
<li>Los parámetros de la página web a enviarse.</li>
</ul>
<pre class="javascript">function procesar()
{
    new Ajax.Request('calcular.php',                                         /* URL a invocar asíncronamente */
    {
        method:       'post',                                                /* Método utilizado para el requerimiento */
        parameters:   $('formulario').serialize(true),                       /* Información local a enviarse con el requerimiento */</pre>
<p>En caso de que la invocación asíncrona tenga un resultado exitoso se deberán realizar los siguientes pasos.</p>
<ul>
<li>Mostrar un mensaje de éxito en color verde.</li>
<li>Desplegar el valor del resultado obtenido en el campo definido para tal fin.</li>
</ul>
<pre class="javascript">        /* Que hacer en caso de ser exitoso el requerimiento */
        onSuccess: function(transport)
        {
            /* Cambiar el color del texto a verde */
            $('mensaje').setStyle('color: #0ab53a');
            /* Mostrar un mensaje informando el éxito sucedido */
            $('mensaje').update("Operación realizada exitosamente");
            /* Mostrar el resultado obtenido del cálculo solicitado */
            $('resultado').update(transport.responseText);
        },</pre>
<p>En caso de que fracase el proceso de invocación asíncrona se deberán realizar los siguientes pasos análogos.</p>
<ul>
<li>Mostrar el mensaje de error proveniente del servidor, en color rojo.</li>
<li>Limpiar cualquier resultado previo para evitar confusiones con la operación.</li>
</ul>
<pre class="javascript">        /* Que hacer en caso de que sea fallido el requerimiento */
        onFailure: function(transport)
        {
            /* Cambiar el color del texto a rojo */
            $('mensaje').setStyle('color: #ff0e0e');
            /* Mostrar el mensaje de error */
            $('mensaje').update('Error: ' + transport.responseText);
            /* Limpiar cualquier resultado anterior */
            $('resultado').update('Error');
        }
    });
}</pre>
<h2>Enlaces.</h2>
<ul>
<li>Demostración &amp; descarga del código fuente.<br />
<a href="http://demo.jorgeivanmeza.com/Prototype/AjaxSimpleRapido-Calc/" target="_blank">http://demo.jorgeivanmeza.com/Prototype/AjaxSimpleRapido-Calc/</a></li>
<li>Prototype Javascript Framework.<br />
<a href="http://prototypejs.org/" target="_blank">http://prototypejs.org/</a></li>
<li>Prototype Introduction to Ajax.<br />
<a href="http://www.prototypejs.org/learn/introduction-to-ajax" target="_blank">http://www.prototypejs.org/learn/introduction-to-ajax</a></li>
<li>Prototype&#8217;s AJAX Request API.<br />
<a href="http://api.prototypejs.org/ajax/ajax/request.html" target="_blank">http://api.prototypejs.org/ajax/ajax/request.html</a></li>
<li>Prototype&#8217;s Element API.<br />
<a href="http://api.prototypejs.org/dom/element.html" target="_blank">http://api.prototypejs.org/dom/element.html</a></li>
<li>Ejemplo de AJAX rápido y simple con PHP y jQuery.<br />
<a href="http://blog.jorgeivanmeza.com/2009/10/ejemplo-de-ajax-rapido-y-simple-con-php-y-jquery/" target="_blank">http://blog.jorgeivanmeza.com/2009/10/ejemplo-de-ajax-rapido-y-simple-con-php-y-jquery/</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/11/ejemplo-rapido-y-simple-de-ajax-con-php-y-prototypejs/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Ejemplo de AJAX rápido y simple con PHP y jQuery</title>
		<link>http://blog.jorgeivanmeza.com/2009/10/ejemplo-de-ajax-rapido-y-simple-con-php-y-jquery/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=ejemplo-de-ajax-rapido-y-simple-con-php-y-jquery</link>
		<comments>http://blog.jorgeivanmeza.com/2009/10/ejemplo-de-ajax-rapido-y-simple-con-php-y-jquery/#comments</comments>
		<pubDate>Sat, 17 Oct 2009 04:54:32 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de software]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[AJAX]]></category>
		<category><![CDATA[Hipergalaxia]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jQuery]]></category>
		<category><![CDATA[PHP]]></category>
		<guid isPermaLink="false">http://blog.jorgeivanmeza.com/?p=2069</guid>
		<description><![CDATA[Introducción. Muy probablemente usted esté aquí, leyendo este artículo porque desea aprender a utilizar AJAX con PHP de una manera muy simple y rápida.  Yo estoy aquí porque hoy no tengo sueño y que mejor manera de esperarlo que escribir un pequeño tutorial acerca del acceso asíncrono de contenidos web utilizando el framework de jQuery. [...]]]></description>
			<content:encoded><![CDATA[<h2>Introducción.</h2>
<p>Muy probablemente usted esté aquí, leyendo este artículo porque desea aprender a utilizar AJAX con PHP de una manera muy simple y rápida.  Yo estoy aquí porque hoy no tengo sueño y que mejor manera de esperarlo que escribir un pequeño tutorial acerca del acceso asíncrono de contenidos web utilizando el <em>framework</em> de jQuery.</p>
<p>Para no tener que dividir el artículo en varias entregas vamos a desarrollar un ejemplo muy sencillo y clásico: la calculadora, sólo que a diferencia de la habitual esta realizará sus cálculos del lado del servidor y presentará sus resultados a través de llamados con AJAX.  La implementación Javascript asociada con el objeto AJAX (el objeto <a href="http://es.wikipedia.org/wiki/XMLHttpRequest" target="_blank"><span style="font-family: courier new,courier;">XMLHTTPRequest</span></a>) no la realizaremos directamente sino que utilizaremos el <em>framework</em> de jQuery el cual simplifica y facilita enormemente el desarrollo en Javascript.  El lado del servidor, los cálculos de nuestra calculadora, se implementarán en el viejo y conocido PHP.  Por supuesto para implementar el nivel de presentación (página web) que recibe el cliente tendremos que hablar un poco de HTML y CSS.</p>
<h2>Qué es AJAX ?</h2>
<p>AJAX es el acrónimo de <em>Asynchronous JavaScript and XML</em>, un conjunto de tecnologías web que permiten que las aplicaciones web desde sus clientes se comuniquen y soliciten información al servidor de manera asíncrona sin interferir con el contenido y comportamientos de la página actual, es decir, sin refrescar (<a href="http://en.wikipedia.org/wiki/Postback" target="_blank"><em>postback</em></a>) la página web por completo.</p>
<p>Su implementación se basa en el objeto <a href="http://en.wikipedia.org/wiki/XMLHttpRequest" target="_blank">XMLHttpRequest</a> o XHR el cual fue originalmente desarrollado por Microsoft y apareció por primera vez en 1999 como un control ActiveX de Internet Explorer 5, posteriormente los demás navegadores lo acogieron desarrollando sus propias implementaciones.</p>
<p>En términos generales el uso de AJAX mejora la usabilidad de las páginas permitiendo a los desarrolladores crear aplicaciones que se comportan de manera similar a las aplicaciones de escritorio.  Un ejemplo de esto son los clientes de correo web de última generación (como <a href="http://www.gmail.com/" target="_blank">GMail</a>) y las aplicaciones geográficas (como <a href="http://maps.google.com/" target="_blank">Google Maps</a>).  También tiene sus desventajas como presentar una mayor dificultad para su depuración, control de favoritos e historial y que los buscadores web comúnmente no pueden acceder a sus contenidos para indexarlos.</p>
<p>Consulte mas información acerca de <a href="http://en.wikipedia.org/wiki/AJAX" target="_blank">AJAX en Wikipedia</a>.</p>
<h2>Procedimiento.</h2>
<p>Estos son los pasos generales que realizaremos para implementar nuestra pequeña aplicación.</p>
<ol>
<li>Crear la estructura básica de la página web.</li>
<li>Implementar el formulario de la calculadora.</li>
<li>Mejorar la presentación del formulario.</li>
<li>Implementar la lógica del negocio de la calculadora.</li>
<li>Incluír una referencia a la librería de jQuery en la página web.</li>
<li>Implementar los llamados asíncronos a la lógica del negocio de la calculadora.</li>
</ol>
<h2>La estructura básica de la página.</h2>
<p>El primer paso es crear la estructura básica de la página web que recibirá el usuario.  Esta se puede crear con cualquier editor de texto desde el <em>bloc de notas</em> hasta otro mas elaborado como <em>Dreamweaver</em> o <em>Eclipse PDT</em>.  Lo importante es que sea un editor de archivos planos.  En mi caso estoy probando <a href="http://www.gphpedit.org/" target="_blank">gPHPEdit</a> para Linux el cual se ve hasta ahora simple y conciso.  Para el caso de Windows un editor simple como el <a href="http://notepad-plus.sourceforge.net/" target="_blank">Notepad++</a> servirá.</p>
<p>Creamos entonces el archivo <span style="font-family: courier new,courier;">calculadora.html</span> con el siguiente contenido.</p>
<pre class="html">&lt;!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
                      "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"&gt;
&lt;html xmlns="http://www.w3.org/1999/xhtml"&gt;
    &lt;head&gt;
       &lt;!-- Documento HTML con carácteres UTF8 --&gt;
       &lt;meta http-equiv="Content-type" content="text/html; charset=utf-8" /&gt;
       &lt;title&gt;Calculadora AJAX&lt;/title&gt;
       &lt;!-- Clases CSS internas --&gt;
       &lt;!-- Referencias a Javascripts externos --&gt;
       &lt;!-- Código Javascript interno --&gt;
    &lt;/head&gt;
    &lt;body&gt;
        &lt;!-- Contenido del documento --&gt;
    &lt;/body&gt;
&lt;/html&gt;</pre>
<p>He incluído algunos <span style="font-family: courier new,courier;">&lt;!--</span> comentarios <span style="font-family: courier new,courier;">--&gt;</span> que nos servirán mas adelante para ubicar donde en el documento se deberán agregar segmentos de código adicionales.  Como se puede apreciar, esperamos ceñirnos al <em>XHTML 1.1 transitional</em>.</p>
<h2>El formulario de la calculadora.</h2>
<p>Este deberá contar con las siguientes partes básicas.</p>
<ol>
<li>Una sección para los mensajes de error (<em>mensaje</em>) de la aplicación.</li>
<li>Un <span style="font-family: courier new,courier;">form</span> (<em>formulario</em>) que representa al formulario en HTML.</li>
<li>Un campo de texto (<em>operando1</em>) para 4 dígitos para que el usuario ingrese al primer operando.</li>
<li>Un campo de selección (<em>operador</em>) para que el usuario elija la operación a efectuarse: suma, resta, multiplicación o división.</li>
<li>Un campo de texto (<em>operando2</em>) para 4 dígitos para que el usuario ingrese al segundo operando.</li>
<li>Un botón (<em>igual</em>) para invocar la operación de los datos.</li>
<li>Una sección (<em>resultado</em>) para mostrar el resultado de la operación.</li>
</ol>
<p>La siguiente es la implementación de esta sección y debe insertarse como el <em>Contenido del documento</em> en la plantilla de la estructura básica de la página web.</p>
<pre class="html">&lt;div id='pagina'&gt;
    &lt;div id='mensaje'&gt;&amp;nbsp;&lt;/div&gt;
    &lt;form id='formulario' action='#' method='post'&gt;
        &lt;input type='text' id='operando1' name='operando1' value='' size='4' maxlength='4' /&gt;
        &lt;select id='operador' name='operador'&gt;
            &lt;option value='SU'&gt;+&lt;/option&gt;
            &lt;option value='RE'&gt;-&lt;/option&gt;
            &lt;option value='MU'&gt;*&lt;/option&gt;
            &lt;option value='DI'&gt;/&lt;/option&gt;
        &lt;/select&gt;
        &lt;input type='text' id='operando2' name='operando2' value='' size='4' maxlength='4' /&gt;
        &lt;input type='button' id='igual' value='=' /&gt;
        &lt;span id='resultado'&gt;&amp;nbsp;&lt;/span&gt;
    &lt;/form&gt;
 &lt;/div&gt;</pre>
<div style="border: 1px dotted #ff0000; margin: auto; padding: 5px; width: 90%;"><span style="color: #ff0000;"><strong>Nota</strong></span>.  El atributo del nombre (<span style="font-family: courier new,courier;">name</span>) es requerido en los campos del formulario que se van a transmitir a través de la invocación asíncrona cuando el formulario es enviado completo como lo vamos a hacer en esta práctica.</div>
<h2>Mejorar la presentación del formulario.</h2>
<p>Este es el producto final de la actualización de la presentación de la página web, es necesario modificar los atributos visuales de cada una de las partes del formulario recién creado.</p>
<div id="attachment_2077" class="wp-caption aligncenter" style="width: 511px"><a href="http://blog.jorgeivanmeza.com/wp-content/uploads/2009/10/screenshot_034.png"><img class="size-full wp-image-2077" title="screenshot_034" src="http://blog.jorgeivanmeza.com/wp-content/uploads/2009/10/screenshot_034.png" alt="Interfaz de usuario de la calculadora" width="501" height="136" /></a><p class="wp-caption-text">Interfaz de usuario de la calculadora</p></div>
<p>Las nuevas características se especifican utilizando hojas de estilo (<a href="http://en.wikipedia.org/wiki/CSS" target="_blank">CSS</a>) y se referencian a través de sus identificadores, etiquetas o clases.</p>
<p>El siguiente código CSS realiza las modificaciones propuestas al formulario.  Estas se deben insertar en la sección de <em>Clases CSS Internas</em>.</p>
<pre class="css">&lt;style type="text/css"&gt;
 #pagina                                       /* Envoltura general */
 {
       margin: auto;                           /* Margenes (centrado) */
       width: 600px;                           /* Ancho */
       text-align: center;                     /* Textos internos centrados */
       font-family: "arial, sans-serif";       /* Fuente del texto */
 }
 #mensaje                                      /* Mensaje de error */
 {
       width: 100%;                            /* Ancho */
       margin-top: 20px;                       /* Margen superior */
       margin-bottom: 30px;                    /* Margen inferior */
       color: #ff0e0e;                         /* Color del texto (foreground) */
       font-size: 12px;                        /* Tamaño de la fuente */
 }
 #operando1, #operando2                        /* Campos de texto de los operandos */
 {
       font-size: 25px;                        /* Tamaño de la fuente */
       border-style: groove;                   /* Estilo del borde */
 }
 #operador                                     /* Selector del operador */
 {
       font-size: 25px;                        /* Tamaño de la fuente */
 }
 #igual                                        /* Botón para realizar la operación */
 {
       font-size: 25px;                        /* Tamaño de la fuente */
 }
 #resultado                                    /* Campo de texto donde se despliega el resultado */
 {
       font-size: 25px;                        /* Tamaño de la fuente */
       font-style: italic;                     /* Atributo de fuente itálica o cursiva */
 }
 &lt;/style&gt;</pre>
<h2>La lógica del negocio de la calculadora.</h2>
<p>El hecho de calcular el valor resultante de la operación elegida a partir de los operandos especificados es lo que llamamos la lógica del negocio.  Esta lógica, como se dijo inicialmente, la vamos a implementar en PHP en el archivo <span style="font-family: courier new,courier;">calcular.php</span>.</p>
<p>Los pasos generales que deben realizarse para llevar a cabo exitosamente el cálculo del valor resultante son los siguientes.</p>
<ol>
<li>Obtener la información provista por el usuario: operandos y operador.</li>
<li>Verificar que la información proporcionada por el usuario sea válida.</li>
<li>Realizar la operación indicada con los valores suministrados.</li>
<li>Mostrar el resultado.</li>
</ol>
<p>Como veremos a continuación la implementación de estos pasos es ligeramente mas interesante que su simple mención.</p>
<p>Para iniciar el código PHP, le indicamos al navaegador que la respuesta del <em>script</em> será un texto.  Este paso específico es opcional ya que para PHP este es el tipo de respuesta por defecto.</p>
<pre class="php">&lt;?php
/* Indicar el tipo de contenido que tendrá la respuesta */
header('Content-type: text/html');</pre>
<p>La implementación de las siguientes acciones la vamos a recubrir en un bloque <span style="font-family: courier new,courier;">try</span>/<span style="font-family: courier new,courier;">catch</span> ya que es suceptible de generar errores y consecuentemente, lanzar excepciones.</p>
<p>El siguiente paso es el obtener, intentar sanear y verificar los operandos proporcionados por el usuario desde el formulario HTML.  Los parámetros fueron transmitidos a través del método <em>post</em> y los elementos se diferencian por su identificador.</p>
<pre class="php">try
{
    /* Obtener y sanear los valores de los operadores */
    $operando1 = filter_var($_POST['operando1'], FILTER_SANITIZE_NUMBER_FLOAT);
    $operando2 = filter_var($_POST['operando2'], FILTER_SANITIZE_NUMBER_FLOAT);
    /* Verificar que los valores de los operadores correspondan
       con los tipos esperados */
    if(!filter_var($operando1, FILTER_VALIDATE_FLOAT) ||
       !filter_var($operando1, FILTER_VALIDATE_FLOAT))
           throw new Exception("Operandos inválidos: [{$operando1}] y [{$operando2}]");</pre>
<p>Realizamos una tarea similar con el operador, obtenemos su valor y verificamos que sea válido.</p>
<pre class="php">    /* Obtener el valor del operador */
    $operador = $_POST['operador'];
    /* Verificar que el operador suministrado sea válido */
    if(!in_array($operador, array('SU', 'RE', 'MU', 'DI')))
        throw new Exception ("Operador inválido: [{$operador}]");</pre>
<p>Definimos una variable para almacenar el resultado de la operación solicitada.</p>
<pre class="php">    /* Almacenar resultado, inicialmente desconocido */
    $resultado = 0;</pre>
<p>Realizamos la operacion correspondiente al operador recibido.  Se deben tener en cuenta dos posibles contingencias que pueden suceder: en el caso de la division, el denominador, es decir, el segundo operador no puede ser cero.  El segundo caso que debe tenerse en cuenta es que el operador recibido no corresponda con ninguna de las operaciones conocidas, esto habria sido validado inicialmente al verificar el operador suministrado despues de su recuperacion.</p>
<pre class="php">    /* Realizar la operación solicitada */
    switch($operador)
    {
        case 'SU':    $resultado = $operando1 + $operando2;
        break;
        case 'RE':    $resultado = $operando1 - $operando2;
        break;
        case 'MU':    $resultado = $operando1 * $operando2;
        break;
        case 'DI':    /* Verificar si el denominador es cero,
                         en ese caso, la división no puede realizarse */
                      if ($operando2 == 0)
                          throw new Exception ('División por cero');
                      $resultado = $operando1 / $operando2;
        break;
        default:      /* Si ninguna operación se ejecutó significa
                         que el operador era inválido (segunda verificación) */
                      throw new Exception('Operador desconocido');
        break;
    }
}</pre>
<p>Para terminar la lógica de la calculadora debemos lidiar con los dos posibles resultados.  Si el procesamiento tuvo algún error (se lanzó una excepción durante el proceso) o si su terminación fue exitosa.</p>
<p>En caso de haber sucedido un error este se indica al usuario mediante un mensaje descriptivo y al navegador al enviarle un código 400.</p>
<pre class="php">catch(Exception $e)            /* La operación produjo un error */
{
    /* Indica al navegador la condición de error */
    header("Status: 400 Bad Request", true, 400);
    /* Despliega el mensaje de error para el usuario */
    echo $e -&gt; getMessage();
    exit(1);
}</pre>
<p>En caso de terminar la operación exitosamente, se deberá mostrar al usuario el resultado de la misma e informarle al navegador con un código 200.</p>
<pre class="php">/* La operación se realizó exitosamente */
/* Indica al navegador la condición de éxito */
header("Status: 200 OK", true, 200);
/* Despliega el resultado de la operación para el usuario */
echo number_format($resultado, 4);
exit(0);
?&gt;</pre>
<h2>Incluír la referencia a jQuery.</h2>
<p>En este paso lo que hacemos en incluír a la librería jQuery en nuestro proyecto web para poder utilizarla en nuestros fragmentos de código Javascript.</p>
<p>Para hacer esto se debe agregar la siguiente línea en la sección <em>Referencias de Javascript externos</em>.</p>
<pre class="php">&lt;script src="http://www.google.com/jsapi"&gt;&lt;/script&gt;
&lt;script&gt;google.load("jquery", "1");&lt;/script&gt;</pre>
<p>Este fragmento utiliza <a href="http://code.google.com/apis/ajaxlibs/" target="_blank">Google AJAX Libraries</a> que nos permite incluír los principales <em>frameworks</em> de Javascript en nuestros sitios web sin preocuparnos por su almacenamiento o implementación, en este caso, incluír la distribución estable mas reciente de la rama 1.x.  Obviamente este método requiere que el cliente tenga acceso a Internet además de la aplicación web.</p>
<p>Una forma mas tradicional de hacer lo mismo es el descargar por nuestra propia cuenta la distribución de jQuery desde su <a href="http://docs.jquery.com/Downloading_jQuery#Download_jQuery" target="_blank">sitio web</a>, almacenar el archivo en nuestro servidor y hacer una referencia desde la página web como se muestra a continuación.</p>
<pre class="php">&lt;script src='http://www.servidor.com/ruta/jquery.js' type='text/javascript'&gt;&lt;/script&gt;</pre>
<h2>Implementar las invocaciones asíncronas.</h2>
<p>La implementación de la invocación asíncrona se realiza directamente en Javascript utilizando a la librería jQuery recién referenciada.  Su código se agrega bajo la sección <em>Código Javascript interno</em>.</p>
<p>El primer paso que se debe realizar para su implementación es relacionar el evento de presionar el botón <span style="font-family: courier new,courier;">igual</span> con la invocación del llamado asíncrono.  Para hacer esto vamos a utilizar un método no invasivo, es decir, no vamos a contaminar el HTML con el atributo <span style="font-family: courier new,courier;">onClick</span> para el elemento <span style="font-family: courier new,courier;">INPUT</span> sino que lo haremos desde el código Javascript favoreciendo la separación entre presentación/lógica del negocio y maximizando la flexibilidad de esta última.</p>
<p>Para hacer esto, tan pronto como se carga la página se asocia el evento de clic sobre el botón de <span style="font-family: courier new,courier;">igual </span>para que se invoque la función <span style="font-family: courier new,courier;">procesar</span>.</p>
<pre class="javascript">&lt;script type='text/javascript'&gt;
/* Código a ejecutarse tan pronto como la
   página ha sido cargada por el navegador */
$(document).ready(function ()
{
	/* Asociar el evento de clic del botón 'igual'
	   con la lógica del negocio de la aplicación */
	$('#igual').click(function()
	{
		procesar();
	});
});</pre>
<p>El siguiente paso es la implementación de la función <span style="font-family: courier new,courier;">procesar</span>.  En ella se realiza el llamado asíncrono a través de AJAX a la aplicación web en PHP desarrollada anteriormente para realizar el cálculo solicitado.</p>
<p>Una invocación asíncrona típica incluye la siguiente información básica.</p>
<ol>
<li>El URL de la aplicación web a invocarse.</li>
<li>El tipo del requerimiento a realizarse (<span style="font-family: courier new,courier;">GET</span> o <span style="font-family: courier new,courier;">POST</span> normalmente).</li>
<li>Los datos a enviarse como parámetros desde el formulario web (en formato <a href="http://en.wikipedia.org/wiki/Query_string" target="_blank"><em>QueryString</em></a>).</li>
<li>Definir la implementación de que hacer si la invocación es exitosa.</li>
<li>Definir la implementación de que hacer si la invocación es fallida.</li>
</ol>
<p>En el siguiente fragmento de código se especifican los primeros tres elementos de la lista.  El llamado asíncrono accederá a la aplicación web <span style="font-family: courier new,courier;">calcular.php</span> mediante el método <span style="font-family: courier new,courier;">post</span> y se le enviarán como parámetros los campos del formulario <span style="font-family: courier new,courier;">formulario</span>.</p>
<pre class="javascript">function procesar()
{
	$.ajax ({
		url: 	'calcular.php',                   /* URL a invocar asíncronamente */
		type:   'post',                           /* Método utilizado para el requerimiento */
		data: 	$('#formulario').serialize(),     /* Información local a enviarse con el requerimiento */</pre>
<p>En caso de ser exitoso se deberá mostrará un mensaje verde informándolo y se desplegará el resultado obtenido de la operación en la ubicación definida para este fin.</p>
<pre class="javascript">		/* Que hacer en caso de ser exitoso el requerimiento */
		success: 	function(request, settings)
		{
			/* Cambiar el color del texto a verde */
			$('#mensaje').css('color', '#0ab53a');
			/* Mostrar un mensaje informando el éxito sucedido */
			$('#mensaje').html("Operación realizada exitosamente");
			/* Mostrar el resultado obtenido del cálculo solicitado */
			$('#resultado').html(request);
		},</pre>
<p>En caso de que la invocación sea fallida se deberá mostrar un mensaje rojo informando el error sucedido y se removerá cualquier resultado previo que pueda haber para no confundir al usuario con información anterior.</p>
<pre class="javascript">		/* Que hacer en caso de que sea fallido el requerimiento */
		error: 	function(request, settings)
		{
			/* Cambiar el color del texto a rojo */
			$('#mensaje').css('color', '#ff0e0e');
			/* Mostrar el mensaje de error */
			$('#mensaje').html('Error: ' + request.responseText);
			/* Limpiar cualquier resultado anterior */
			$('#resultado').html('Error');
		}
	});  // Fin de la invocación al método ajax
}  // Fin de la función procesar
&lt;/script&gt;</pre>
<h2>Enlaces.</h2>
<ul>
<li>Demostración &amp; descarga del código fuente.<br />
<a href="http://demo.jorgeivanmeza.com/jQuery/AjaxSimpleRapido-Calc/" target="_blank">http://demo.jorgeivanmeza.com/jQuery/AjaxSimpleRapido-Calc/</a></li>
<li>jQuery.<br />
<a href="http://jquery.com/" target="_blank">http://jquery.com/</a></li>
<li>Simplify Ajax development with jQuery<br />
<a href="http://www.ibm.com/developerworks/library/x-ajaxjquery.html" target="_blank">http://www.ibm.com/developerworks/library/x-ajaxjquery.html</a></li>
</ul>
<div id="_mcePaste" style="overflow: hidden; position: absolute; left: -10000px; top: 1096px; width: 1px; height: 1px;">
<pre class="html">id='operador'</pre>
</div>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/10/ejemplo-de-ajax-rapido-y-simple-con-php-y-jquery/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Hacer algo cuando inicia o termina el evento AJAX con jQuery</title>
		<link>http://blog.jorgeivanmeza.com/2009/10/hacer-algo-cuando-inicia-o-termina-el-evento-ajax-con-jquery/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=hacer-algo-cuando-inicia-o-termina-el-evento-ajax-con-jquery</link>
		<comments>http://blog.jorgeivanmeza.com/2009/10/hacer-algo-cuando-inicia-o-termina-el-evento-ajax-con-jquery/#comments</comments>
		<pubDate>Wed, 14 Oct 2009 21:15:23 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de software]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[AJAX]]></category>
		<category><![CDATA[Hipergalaxia]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jQuery]]></category>
		<guid isPermaLink="false">http://blog.jorgeivanmeza.com/?p=2061</guid>
		<description><![CDATA[Introducción. Este pequeño fragmento de código es muy útil, permite manipular un objeto del DOM cuando suceden los eventos de inicio o terminación del AJAX.  Muy útil para mostrar de manera fácil y automatizada un indicador de AJAX para informar al usuario que hay una transacción asíncrona en curso. Procedimiento. $('#loader').ajaxStart(function () { $(this).fadeIn(); }); [...]]]></description>
			<content:encoded><![CDATA[<h2>Introducción.</h2>
<p>Este pequeño fragmento de código es muy útil, permite manipular un objeto del DOM cuando suceden los eventos de inicio o terminación del AJAX.  Muy útil para mostrar de manera fácil y automatizada un indicador de AJAX para informar al usuario que hay una transacción asíncrona en curso.</p>
<h2>Procedimiento.</h2>
<pre class="javascript">$('#loader').ajaxStart(function () {
    $(this).fadeIn();
});
$('#loader').ajaxStop(function () {
    $(this).fadeOut();
});</pre>
<p>Adicionalmente hay otros eventos que pueden manejarse de igual manera <a href="http://docs.jquery.com/Ajax/ajaxComplete#callback" target="_blank">ajaxComplete</a>, <a href="http://docs.jquery.com/Ajax/ajaxError#callback" target="_blank">ajaxError</a>, <a href="http://docs.jquery.com/Ajax/ajaxSend#callback" target="_blank">ajaxSend</a> y <a href="http://docs.jquery.com/Ajax/ajaxSuccess#callback" target="_blank">ajaxSuccess</a>, además de los ya mencionados <a href="http://docs.jquery.com/Ajax/ajaxStart#callback" target="_blank">ajaxStart</a> y <a href="http://docs.jquery.com/Ajax/ajaxStop#callback" target="_blank">ajaxStop</a>.</p>
<h2>Enlaces.</h2>
<ul>
<li>7 things i wish i had known about jquery.<br />
<a href="http://blog.themeforest.net/tutorials/7-things-i-wish-i-had-known-about-jquery/" target="_blank">http://blog.themeforest.net/tutorials/7-things-i-wish-i-had-known-about-jquery/</a></li>
<li>jQuery: AJAX API Documentation.<br />
<a href="http://docs.jquery.com/Ajax" target="_blank">http://docs.jquery.com/Ajax</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/10/hacer-algo-cuando-inicia-o-termina-el-evento-ajax-con-jquery/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Como crear un mapa con GoogleMaps version 2, en pasos simples</title>
		<link>http://blog.jorgeivanmeza.com/2009/09/como-crear-un-mapa-con-googlemaps-version-2-en-pasos-simples/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=como-crear-un-mapa-con-googlemaps-version-2-en-pasos-simples</link>
		<comments>http://blog.jorgeivanmeza.com/2009/09/como-crear-un-mapa-con-googlemaps-version-2-en-pasos-simples/#comments</comments>
		<pubDate>Mon, 28 Sep 2009 20:02:34 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de software]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[Google]]></category>
		<category><![CDATA[GoogleMaps]]></category>
		<category><![CDATA[Hiper]]></category>
		<category><![CDATA[Hipergalaxia]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[PHP]]></category>
		<guid isPermaLink="false">http://blog.jorgeivanmeza.com/?p=2022</guid>
		<description><![CDATA[Introducción. Utilizar el API de Google Maps para crear mapas interactivos con Javascript en nuestros sitios web es muy fácil de implementar.  Este servicio ofrece dos alternativas: los Mapplets que se ejecutan de manera asíncrona, directamente en el sitio de maps.google.com y los desarrolladores sólo debemos especificar y albergar un documento XML donde se encuentra [...]]]></description>
			<content:encoded><![CDATA[<h2>Introducción.</h2>
<p>Utilizar el API de <a href="http://maps.google.com/" target="_blank">Google Maps</a> para crear mapas interactivos con Javascript en nuestros sitios web es muy fácil de implementar.  Este servicio ofrece dos alternativas: los Mapplets que se ejecutan de manera asíncrona, directamente en el sitio de <a href="http://maps.google.com/" target="_blank">maps.google.com</a> y los desarrolladores sólo debemos especificar y albergar un documento XML donde se encuentra la especificación y los datos del mapa.  Por el otro lado están los mapas implementados directamente con el API de manera síncrona, se incrustan en nuestras propias páginas web y su comportamiento se define a través del Javascript que implementemos.</p>
<p>En otras ocasiones me he referido a los <a href="http://blog.jorgeivanmeza.com/tag/GoogleMapplets/" target="_blank">Mapplets</a> por esto la implementación de hoy la vamos a realizar utilizando el API síncrono.</p>
<h2>Objetivo.</h2>
<p>El objetivo del presente artículo es el de visitar a Cuba donde ubicaremos marcadores sobre 5 ciudades de este país y asociaremos globitos con mensajes personalizados que aparecerán cuando el usuario haga clic sobre las diferentes ciudades.</p>
<div id="attachment_2024" class="wp-caption aligncenter" style="width: 650px"><a href="http://blog.jorgeivanmeza.com/wp-content/uploads/2009/09/Objetivo_Cuba5.png"><img class="size-full wp-image-2024" title="Objetivo_Cuba5" src="http://blog.jorgeivanmeza.com/wp-content/uploads/2009/09/Objetivo_Cuba5.png" alt="Resultado final" width="640" height="478" /></a><p class="wp-caption-text">Resultado final</p></div>
<h2>Procedimiento.</h2>
<h3>Condiciones inciales.</h3>
<p>Para el desarrollo de esta mini aplicación vamos a utilizar PHP y <a href="http://en.wikipedia.org/wiki/Vanilla_software" target="_blank">vanilla</a> Javascript, es decir, no nos apoyaremos en ningún <em>framework</em> de Javascript adicional a lo comúnmente soportado por los navegadores web actuales.</p>
<p>En mi caso, mi servidor web de destino será <a href="http://demo.jorgeivanmeza.com/" target="_blank">http://demo.jorgeivanmeza.com/</a>.  Es muy importante determinar esto para la próxima etapa, la creación de la llave del API.</p>
<h3>Creación de la llave del API.</h3>
<p>Acceda al siguiente enlace y cree su propia llave para el API de Google.  Es necesario especificar el dominio bajo el cual se ejecutará la aplicación web.  En el caso de desarrollar la aplicación de manera local, puede obtener una llave para <a href="http://localhost/" target="_blank">http://localhost/</a> y después la deberá modificar antes de desplegarla en el servidor de producción.  Si no especifica el dominio correcto, la aplicación no podrá generar el mapa.</p>
<p style="padding-left: 30px;"><a href="http://code.google.com/apis/maps/signup.html" target="_blank">http://code.google.com/apis/maps/signup.html</a></p>
<p>Es necesario contar con una cuenta de Google, así que de no contar con una es necesario <a href="http://mail.google.com/mail/signup" target="_blank">abrirla</a> antes de intentar crear una llave del API.</p>
<h3>Creación de una estructura básica para la página web.</h3>
<p>Cree el archivo <span style="font-family: courier new,courier;">simpleGoogleMaps.php</span> (o como desee llamarlo) en una ubicación pública de su servidor web (bajo el <span style="font-family: courier new,courier;">DOCUMENT_ROOT</span>).  Agregue siguiente contenido al archivo y guárdelo.</p>
<pre class="html">&lt;!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
                      "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"&gt;
&lt;html xmlns='http://www.w3.org/1999/xhtml'&gt;
&lt;head&gt;
    &lt;meta http-equiv="Content-type" content="text/html; charset=utf-8" /&gt;
    &lt;meta name="Author" content="Jorge Iván Meza Martínez - http://jorgeivanmeza.com/ - jimezam@gmail.com" /&gt;
    &lt;meta name="Description" content="Demostración Simple de Google Maps" /&gt;
    &lt;title&gt;Demostración Simple de Google Maps&lt;/title&gt;
    &lt;!-- Llave del API --&gt;
    &lt;!-- Estilos CSS --&gt;
    &lt;!-- Implementación Javascript --&gt;
&lt;/head&gt;
&lt;body&gt;
    &lt;!-- Ubicación del mapa --&gt;
&lt;/body&gt;
&lt;/html&gt;</pre>
<h3>Especificar la Llave del API.</h3>
<p>En el contenido del archivo PHP actualice el siguiente código por la marca de <span style="font-family: courier new,courier;">Llave del API</span>.</p>
<pre class="php">&lt;script src='http://maps.google.com/maps?file=api&amp;v=2&amp;sensor=false&amp;hl=es&amp;key=XXXXX' type='text/javascript'&gt;&lt;/script&gt;</pre>
<p>Reemplace la cadena <span style="font-family: courier new,courier;">XXXXX</span> por su Llave del API específica que obtuvo durante el paso anterior correspondiente.</p>
<h3>Especificar la ubicación del mapa.</h3>
<p>El mapa se generará en un <span style="font-family: courier new,courier;">div</span> que determinemos dentro del <span style="font-family: courier new,courier;">body</span> para tal fin, este puede estar integrado normalmente con el resto del diseño de la página.  En nuestro caso particular debido a su simplicidad, el contenido de la página será solamente dicho <span style="font-family: courier new,courier;">div</span>.</p>
<p>Reemplace la etiqueta <span style="font-family: courier new,courier;">Ubicación del mapa</span> con el siguiente código.</p>
<pre class="php">&lt;div id='MiMapa'&gt;Aqui viene el mapa!&lt;/div&gt;</pre>
<p>Es necesario identificar al <span style="font-family: courier new,courier;">div</span> con un <span style="font-family: courier new,courier;">id</span> único que utilizaremos posteriormente.</p>
<h3>Actualizar el estilo del mapa.</h3>
<p>El siguiente paso es el especificar un estilo para el <span style="font-family: courier new,courier;">div</span> que contendrá al mapa.  Este estilo finalmente dependerá del diseño de la página.  Para este caso utilizamos CSS para definirle un alto y un ancho al mapa.</p>
<p>Reemplace la etiqueta <span style="font-family: courier new,courier;">Estilos CSS</span> con el siguiente código.</p>
<pre class="css">&lt;style content="text/css"&gt;
#MiMapa
{
    width: 640px;
    height: 480px;
}
&lt;/style&gt;</pre>
<h3>Especificar la implementación Javascript.</h3>
<p>El código faltante hace referencia a código Javascript que va a determinar el contenido y comportamiento del mapa.  Reemplace la etiqueta <span style="font-family: courier new,courier;">Implementación Javascript</span> con el siguiente código base.</p>
<pre class="javascript">&lt;script type='text/javascript'&gt;
// El código de las siguiente secciones se incluye aquí ...
&lt;/script&gt;</pre>
<h3>Preparar el mapa.</h3>
<p>Para crear el mapa y establecer sus parámetros iniciales se realizan las siguientes acciones.</p>
<ol>
<li>Verificar que exista la compatibilidad adecuada con el navegador.</li>
<li>Crear la instancia del mapa asociada al <span style="font-family: courier new,courier;">div</span> especifico.</li>
<li>Establecer la ubicación inicial del mapa.</li>
<li>Establecer el tipo inicial del mapa.</li>
</ol>
<p>Para hacer esto creamos al objeto <span style="font-family: courier new,courier;">mapa1</span> y a la función <span style="font-family: comic sans ms,sans-serif;">prepararMapa</span> con el siguiente código.</p>
<pre class="javascript">/*
 * Objeto que hace referencia al mapa desplegado.
 */
var mapa1 = null;
/*
 * Establece los parámetros iniciales del mapa instanciando
 * al objeto 'mapa'.
 *
 * @param String  - Nombre del DIV que albergará al mapa.
 * @param Double  - Latitud donde se centrará el mapa.
 * @param Double  - Longitud donde se centrará el mapa.
 * @param Integer - Altura donde se centrará el mapa.
 *
 * @return el mapa en éxito, null en fracaso.
 */
function prepararMapa(div, centerLat, centerLang, centerAlt)
{
    /* Verifica que el navegador sea compatible con
       Google Maps */
    if (GBrowserIsCompatible())   // [1]
    {
        /* Crea la instancia del objeto 'mapa' asociándole
           el div correspondiente */
        mapa = new GMap2(document.getElementById(div));    // [2]
        /* Centra el mapa en la ubicacion (latitud, longitud
           y altura) especificadas */
        mapa.setCenter(new GLatLng(centerLat, centerLang), centerAlt);     // [3]
        /* Establece el tipo de mapa.  Disponibles:
               - G_NORMAL_MAP
               - G_SATELLITE_MAP
               - G_HYBRID_MAP
           Enlace: http://code.google.com/apis/maps/documentation/controls.html */
        mapa.setMapType(G_HYBRID_MAP);      // [4]
        /* Establece el comportamiento por defecto de los
           elementos del UI del mapa.
           Enlace: http://code.google.com/apis/maps/documentation/reference.html#GMap2.setUIToDefault */
        mapa.setUIToDefault();
        /* Éxito */
        return mapa;
    }
    else     /* Fracaso */
        return null;
}</pre>
<h3>Agregar un marcador.</h3>
<p>Posteriormente implementamos la función <span style="font-family: courier new,courier;">agregarMarcador</span> que se ocupará de agregar un marcador creado con cierta información específica al mapa.  Su código es el siguiente.</p>
<pre class="javascript">/*
 * Agrega un marcado con la información especificada
 * al mapa.
 *
 * @param GMap2   - Referencia externa al mapa.
 * @param Double  - Latitud donde se centrará el mapa.
 * @param Double  - Longitud donde se centrará el mapa.
 * @param String  - Mensaje que tendrá la burbuja asociada.
 *
 * @return void.
 */
 function agregarMarcador(mapa, latitud, longitud, mensaje)
 {
    /* Crea el punto asociado a la longitud y latitud
       especificadas. */
    var punto = new GLatLng(latitud, longitud);
    /* Crea un marcador asociado a la ubicación anterior */
    var marcador = new GMarker(punto);
    /* Establece que en el evento 'onclick' del marcador
       muestre la burbuja con el mensaje especificado */
     GEvent.addListener(marcador, "click", function()
     {
         mapa.openInfoWindowHtml(punto, mensaje);
     });
     /* Agrega el marcador recién creado al mapa */
     mapa.addOverlay(marcador);
 }</pre>
<h3>Información de las ciudades de Cuba.</h3>
<p>Los marcadores del mapa corresponderán como se dijo anteriormente, con cinco ciudades de Cuba que se predefinieron y de las cuales se conoce su ubicación: latitud y longitud.  Su información se almacena en el arreglo puntos en el cual cada una de sus celdas corresponde con una ciudad.</p>
<pre class="javascript">/* Información para los marcadores del mapa: Ciudades de
 * Cuba. */
 var puntos = new Array(
    {
        'nombre'  : 'La habana',
        'latitud' : 23.132,
        'longitud': -82.364
    },
    {
        'nombre'  : 'Santa Clara',
        'latitud' : 22.4,
        'longitud': -79.967
    },
    {
        'nombre'  : 'Bayamo',
        'latitud' : 20.379,
        'longitud': -76.643
    },
    {
        'nombre'  : 'Las Tunas',
        'latitud' : 20.962,
        'longitud': -76.951
    },
    {
        'nombre'  : 'Manzanillo',
        'latitud' : 20.343,
        'longitud': -77.117
    }
 );</pre>
<p>Para automatizar el proceso de agregación de los marcadores basados en la información de los <span style="font-family: courier new,courier;">puntos</span> creamos a la función <span style="font-family: courier new,courier;">agregarMarcadores</span> cuya misión es la de invocar repetidas veces a la función <span style="font-family: courier new,courier;">agregarMarcador</span>.  En ella se define además el contenido del globito de cada uno de las ciudades (<span style="font-family: courier new,courier;">mensaje</span>).</p>
<pre class="javascript">/*
 * Automatiza el agregar los marcadores basados en la
 * información del arreglo de puntos.
 *
 * @param GMap2   - Referencia externa al mapa.
 * @param Array   - Información de los marcadores a agregar.
 *
 * @return void.
 */
 function agregarMarcadores(mapa, informacion)
 {
    for(var i=0; i&lt;informacion.length; i++)
    {
        var nombre   = puntos[i]['nombre'];
        var latitud  = puntos[i]['latitud'];
        var longitud = puntos[i]['longitud'];
        var mensaje  = "Este es &lt;b&gt;" + nombre + "&lt;/b&gt;,&lt;br /&gt; su latitud es &lt;b&gt;" +
                       latitud + "&lt;/b&gt;&lt;br /&gt; y su longitud es &lt;b&gt;" + longitud + "&lt;/b&gt;.";
        agregarMarcador(mapa, latitud, longitud, mensaje);
    }
 }</pre>
<h3>Finalmente, el programa principal.</h3>
<p>En este fragmento del código definimos la ejecución del programa principal del mapa.  Se ejecuta tan pronto como la página se encuentra cargada (<span style="font-family: courier new,courier;">onLoad</span>) y desarrolla las siguiente actividades.</p>
<ol>
<li>Prepara el mapa.</li>
<li>Verifica que el mapa haya sido creado exitosamente.</li>
<li>Agrega los marcadores sobre las ciudades especificadas.</li>
</ol>
<p>Su código es el siguiente.</p>
<pre class="javascript">/* Inicio del programa Javascript (setup) */
window.onload = function()
{
    /* Solicita la creación del mapa especificando el DIV
       que lo albergará y la ubicación (latitud, longitud,
       altura). */
    mapa1 = prepararMapa('MiMapa', 21.4, -79.8, 7);
    if(mapa1 == null)
    {
        alert("Su navegador no incluye soporte para Google Maps!");
        return false;
    }
    /* Solicita la agregación de los marcadores de ejemplo
       especificando la referencia al mapa y el arreglo con
       la información de los puntos */
    agregarMarcadores(mapa1, puntos);
    return true;
}</pre>
<h3>Listo!</h3>
<p>Probar la página web utilizando un navegador como <a href="http://getfirefox.com/" target="_blank">Firefox</a>.</p>
<h2>Enlaces.</h2>
<ul>
<li>Programa de demostración - versión 0.1.<br />
<a href="http://demo.jorgeivanmeza.com/GMaps/SimpleDemoCuba/" target="_blank">http://demo.jorgeivanmeza.com/GMaps/SimpleDemoCuba/</a></li>
<li>Google Maps API Versión 2.<br />
<a href="http://code.google.com/apis/maps/" target="_blank">http://code.google.com/apis/maps/</a></li>
<li>Abrir una cuenta de usuario con Google.<br />
<a href="http://mail.google.com/mail/signup" target="_blank">http://mail.google.com/mail/signup</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/09/como-crear-un-mapa-con-googlemaps-version-2-en-pasos-simples/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Introducción al AJAX con Mootools 1.2.1</title>
		<link>http://blog.jorgeivanmeza.com/2009/03/introduccion-al-ajax-con-mootools-121/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=introduccion-al-ajax-con-mootools-121</link>
		<comments>http://blog.jorgeivanmeza.com/2009/03/introduccion-al-ajax-con-mootools-121/#comments</comments>
		<pubDate>Wed, 01 Apr 2009 02:46:01 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de software]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[AJAX]]></category>
		<category><![CDATA[Hiper]]></category>
		<category><![CDATA[Hipergalaxia]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[MooTools]]></category>
		<guid isPermaLink="false">http://blog.jorgeivanmeza.com/?p=1607</guid>
		<description><![CDATA[Introducción. De vuelta a Mootools, fue el primero de los frameworks de Javascript que utilicé hace un poco mas de un año.  Después he experimentado un poco mas con Prototype/Scriptaculous y ahora estoy empezando a leer un poco acerca de jQuery.  Sin embargo siempre me ha gustado Mootools y es hora de documentar, tal y [...]]]></description>
			<content:encoded><![CDATA[<h2>Introducción.</h2>
<p>De vuelta a Mootools, fue el primero de los frameworks de Javascript que utilicé hace un poco mas de un año.  Después he experimentado un poco mas con Prototype/Scriptaculous y ahora estoy empezando a leer un poco acerca de jQuery.  Sin embargo siempre me ha gustado Mootools y es hora de documentar, tal y como se hizo <a href="http://blog.jorgeivanmeza.com/2009/02/25/resumen-de-ajax-con-prototype/" target="_blank">con Prototype</a>, como se realizan los llamados asíncronos (AJAX) con él.</p>
<p>En este artículo voy a describir las cuatro maneras como es posible realizar llamados con AJAX utilizando MooTools.</p>
<ol>
<li>El método <span style="font-family: courier new,courier;">load</span> de los elementos.</li>
<li>El método <span style="font-family: courier new,courier;">Request.HTML</span>.</li>
<li>El objeto <span style="font-family: courier new,courier;">Request</span> directamente.</li>
<li>El método <span style="font-family: courier new,courier;">Request.JSON</span>.</li>
</ol>
<h2>1. El método <span style="font-family: courier new,courier;">load</span> de los elementos.</h2>
<p>Este método lo tienen los elementos (componentes) de Mootools.  Es muy útil porque permite actualizar rápidamente cualquier elemento con el contenido HTML retornado por un llamado asíncrono.  A pesar de ser muy fácil de utilizar, carece de las opciones y la flexibilidad de los métodos siguientes, por ejemplo, del paso de parámetros.</p>
<p>Para hacer uso de este método se utiliza la siguiente instrucción.</p>
<pre class="javascript">$('componente').load(urlRemota);</pre>
<p>Donde <span style="font-family: courier new,courier;">componente</span> es el elemento que se desea actualizar (un <span style="font-family: courier new,courier;">div</span> por ejemplo) y <span style="font-family: courier new,courier;">urlRemota</span> es el URL que se invoca de manera asíncrona para obtener el código HTML con el que se reemplazará el contenido del elemento.</p>
<p>Para más información acerca de este método consultar la <a href="http://mootools.net/docs/Request/Request.HTML" target="_blank">documentación de Request.HTML</a>.</p>
<h2>2. El método <span style="font-family: courier new,courier;">Request.HTML</span>.</h2>
<p>Este método es una facilidad implementada sobre el método analizado a continuación.  Permite obtener el mismo objetivo del método anterior con una mayor flexibilidad.</p>
<pre class="javascript">    var myHTMLRequest = new Request
        .HTML({
            url:       urlRemota,
            update:    'componente',
            method:    'post',
            data:      $('formulario'),
            onRequest: function()
            {
                // Al iniciar la solicitud.
            },
            onComplete: function(html)
            {
                // Al completarse la solicitud.
            },
            onSuccess: function(responseTree, responseElements, responseHTML, responseJavaScript)
            {
                // Si la solicitud se completó exitosamente.
                /*
                   responseTree - (element) The node list of the remote response.
                   responseElements - (array) An array containing all elements of the remote response.
                   responseHTML - (string) The content of the remote response.
                   responseJavaScript - (string) The portion of JavaScript from the remote response.
                */
            },
            onFailure: function(elemento)
            {
                // Si la solicitud se completó con problemas.
            }
        })
        .send();</pre>
<p>De manera similar al método anterior, el atributo <span style="font-family: courier new,courier;">url</span> define el URL que se invocará para obtener de manera asíncrona el código HTML para actualizar el elemento referenciado por el atributo <span style="font-family: courier new,courier;">update</span>.  El atributo <span style="font-family: courier new,courier;">method</span> define si se utilizará POST o GET para la invocación del llamado.</p>
<p>El resto de atributos son opcionales.   El atributo <span style="font-family: courier new,courier;">data</span> permite especificar variables que van a ser incluídas con el requerimiento.  Pueden especificarse como un <em>query string</em> de la forma <span style="font-family: courier new,courier;">&#8220;var1=valor1&amp;var2=valor2&#8243;</span>, como un <em>hash</em> de la forma <span style="font-family: courier new,courier;">{&#8220;var1&#8243;: &#8220;valor1&#8243;, &#8220;var2&#8243;: &#8220;valor2&#8243;}</span> o enviando un formulario por completo de la forma <span style="font-family: courier new,courier;">$(&#8216;id_formulario&#8217;)</span>.</p>
<p>Los atributos <span style="font-family: courier new,courier;">onXXX</span> son manejadores de eventos a manera de <em>callbacks</em> y son ejecutados según lo que acontezca durante la solicitud del llamado asíncrono.</p>
<ul>
<li><span style="font-family: courier new,courier;">onRequest</span>: ha sido iniciado el proceso de la solicitud.</li>
<li><span style="font-family: courier new,courier;">onComplete</span>: la solicitud ha terminado.</li>
<li><span style="font-family: courier new,courier;">onSuccess</span>: la solicitud ya ha terminado y terminó exitosamente.</li>
<li><span style="font-family: courier new,courier;">onFailure</span>: la solicitud ya ha terminado y terminó de manera fallida.</li>
</ul>
<p>Para más información acerca de este método consultar la <a href="http://mootools.net/docs/Request/Request.HTML" target="_blank">documentación de Request.HTML</a>.</p>
<h2>3. El objeto <span style="font-family: courier new,courier;">Request</span> directamente.</h2>
<p>Esta es la forma mas flexible de utilizar AJAX con MooTools ya que permite realizar la solicitud y manipular que se desea hacer con el resultado obtenido, ya no necesariamente actualizar un elemento.</p>
<pre class="javascript">    var myRequest = new Request({
        url:    urlRemota,
        method: 'post',
        data:   $('formulario'),
        onRequest: function()
        {
            // Al iniciar la solicitud.
        },
        onComplete: function(html)
        {
            // Al completarse la solicitud.
        },
        onSuccess: function(responseText, responseXML)
        {
            // Si la solicitud se terminó exitosamente.
            /*
                responseText - (string) The returned text from the request.
                responseXML - (mixed) The response XML from the request.
            */
            // Aquí se implementa que hacer con la respuesta del llamado asíncrono
            // cuando el procedimiento fue exitoso.
            /*
                Actualizando manualmente el componente,
                reproduce la funcionalidad de Request.HTML:
                $('componente').set('html', responseText);
            */
        },
        onFailure: function(xhr)
        {
            // Si la solicitud se completó con problemas.
            /*
                xhr - (XMLHttpRequest) The transport instance.
            */
            // Aquí se implementa que hacer con la respuesta del llamado asíncrono
            // cuando el procedimiento fue fallido.
        },
        onCancel: function()
        {
            // La solicitud fue cancelada.
        },
        onException: function(headerName, value)
        {
            // La transmisión de la cabecerá falló.
            /*
                headerName - (string) The name of the failing header.
                value - (string) The value of the failing header.
            */
        }
    }).send();</pre>
<p>Se incluyen dos manejadores de eventos adicionales.</p>
<ul>
<li><span style="font-family: courier new,courier;">onCancel</span>: la solicitud ha sido cancelada.</li>
<li><span style="font-family: courier new,courier;">onException</span>: la transmisión de la cabecera (<em>header</em>) provocó una excepción.</li>
</ul>
<p>Se incluyen además, entre otras cosas, la propiedad <span style="font-family: courier new,courier;">running</span> que permite verificar si el objeto <span style="font-family: courier new,courier;">myRequest</span> se encuentra o no actualmente procesando una solicitud y al método <span style="font-family: courier new,courier;">cancel()</span> que permite cancelar la solicitud activa, generando consecuentemente un evento de cancelación (ver <span style="font-family: courier new,courier;">onCancel</span>).</p>
<p>Para más información acerca de este método consultar la <a href="http://mootools.net/docs/Request/Request" target="_blank">documentación de Request</a>.</p>
<h2>4. El método <span style="font-family: courier new,courier;">Request.JSON</span>.</h2>
<p>Es una facilidad construída sobre el objeto <span style="font-family: courier new,courier;">Request</span> que permite manipular respuestas de llamadas asíncronas en formato JSON (<a href="http://en.wikipedia.org/wiki/JSON" target="_blank"><em>Javascript Object Notation</em></a>).</p>
<pre class="javascript">    var jsonRequest = new Request.JSON({
        url:    urlRemota,
        method: 'post',
        data:   $('formulario'),
        onRequest: function()
        {
            // Al iniciar la solicitud.
        },
        onComplete: function(responseJSON)
        {
            // Al completarse la solicitud.
        },
        onSuccess: function(responseJSON, responseText)
        {
            // Si la solicitud se terminó exitosamente.
            /*
                responseJSON - (object) The JSON response object from the remote request.
                responseText - (string) The JSON response as string.
            */
            /*
                La información recibida del llamado asíncrono se puede obtener como atributos
                del objeto responseJSON, por ejemplo acceder a responseJSON.nombres
            */
        },
        onFailure: function(xhr)
        {
            // Si la solicitud se completó con problemas.
            /*
                xhr - (XMLHttpRequest) The transport instance.
            */
        }
    }).send();</pre>
<p>Para más información acerca de este método consultar la <a href="http://mootools.net/docs/Request/Request.JSON" target="_blank">documentación de Request.JSON</a>.</p>
<h2>Ejemplo funcional.</h2>
<p>La aplicación de ejemplo obtiene información dinámica del servidor de manera asíncrona, para actualizar los campos <span style="font-family: courier new,courier;">DIV</span> de la página utilizando cada una de las cuatro técnicas descritas en este artículo.</p>
<p>Para la generación de la información dinámica del lado del servidor se utilizaron dos <em>scripts</em> muy simples desarrollado en PHP, uno de ellos genera una cadena constante junto con la fecha actual y el otro prepara la respuesta JSON a partir de la información recibida.  Además muestra la información recibida a través del POST.  El <em>script</em> <span style="font-family: courier new,courier;">ContenidoRemoto.php</span> es utilizado para los métodos 1, 2 y 3 mientras que el <em>script</em> <span style="font-family: courier new,courier;">Contenido RemotoJson.php</span> es utilizado para el método 4.</p>
<p>Para consultar el ejemplo funcionando en el servidor de demostración se debe seguir <a href="http://demo.jorgeivanmeza.com/MooTools/AjaxDemo/" target="_blank">este enlace</a>.</p>
<p>Para consultar el código fuente de cada uno de los archivos que componen el ejemplo se deben seguir los enlaces dispuestos a continuación: <a href="http://demo.jorgeivanmeza.com/MooTools/AjaxDemo/index.php?source" target="_blank">index.php</a>, <a href="http://demo.jorgeivanmeza.com/MooTools/AjaxDemo/ContenidoRemoto.php?source" target="_blank">ContenidoRemoto.php</a> y <a href="http://demo.jorgeivanmeza.com/MooTools/AjaxDemo/ContenidoRemotoJson.php?source" target="_blank">ContenidoRemotoJson.php</a>.</p>
<h2>Enlaces.</h2>
<ul>
<li>MooTools.<br />
<a href="http://mootools.net/" target="_blank">http://mootools.net/</a></li>
<li>Documentación de MooTools.<br />
<a href="http://mootools.net/docs/" target="_blank">http://mootools.net/docs/</a></p>
<ul>
<li>Request.<br />
<a href="http://mootools.net/docs/Request/Request" target="_blank">http://mootools.net/docs/Request/Request</a></li>
<li>Request.HTML.<br />
<a href="http://mootools.net/docs/Request/Request.HTML" target="_blank">http://mootools.net/docs/Request/Request.HTML</a></li>
<li>Request.JSON.<br />
<a href="http://mootools.net/docs/Request/Request.JSON" target="_blank">http://mootools.net/docs/Request/Request.JSON</a></li>
</ul>
</li>
<li>Definición de AJAX.<br />
<a href="http://en.wikipedia.org/wiki/AJAX" target="_blank">http://en.wikipedia.org/wiki/AJAX</a></li>
<li>Definición de JSON.<br />
<a href="http://en.wikipedia.org/wiki/JSON" target="_blank">http://en.wikipedia.org/wiki/JSON</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/03/introduccion-al-ajax-con-mootools-121/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Resumen de AJAX con Prototype</title>
		<link>http://blog.jorgeivanmeza.com/2009/02/resumen-de-ajax-con-prototype/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=resumen-de-ajax-con-prototype</link>
		<comments>http://blog.jorgeivanmeza.com/2009/02/resumen-de-ajax-con-prototype/#comments</comments>
		<pubDate>Wed, 25 Feb 2009 22:05:59 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de software]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[AJAX]]></category>
		<category><![CDATA[Hipergalaxia]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Prototype]]></category>
		<guid isPermaLink="false">http://www.jorgeivanmeza.com/blog/?p=1441</guid>
		<description><![CDATA[Introducción. Para finalizar la serie de artículos que había escrito acerca del uso de AJAX con el framework Prototype voy a realizar un muy breve resúmen de la sintaxis de las tres formas de realizar la invocación que me serán útiles para futuras referencias rápidas. Utilizando el Updater. El Ajax.Updater es una facilidad que toma [...]]]></description>
			<content:encoded><![CDATA[<h2>Introducción.</h2>
<p>Para finalizar la <a href="http://www.jorgeivanmeza.com/blog/2008/12/10/ejemplo-2-de-ajax-con-prototype-y-php/" target="_blank">serie de artículos</a> que había escrito acerca del uso de AJAX con el <em>framework</em> <a href="http://www.prototypejs.org/" target="_blank">Prototype</a> voy a realizar un muy breve resúmen de la sintaxis de las tres formas de realizar la invocación que me serán útiles para futuras referencias rápidas.</p>
<h2>Utilizando el <em>Updater</em>.</h2>
<p>El <span style="font-family: courier new,courier;">Ajax.Updater</span> es una facilidad que toma el contenido del resultado del llamado asíncrono y inserta en el interior del componente especificado.</p>
<pre name='code' class="javascript">new Ajax.Updater(ID_COMPONENTE,
                 URL,
{
    parameters: $('FORMULARIO').serialize(true),
    method: 'post'
});</pre>
<h2>Utilizando el <em>Request.</em></h2>
<p>Esta opción es mas flexible que la anterior y permite manipular el contenido de la respuesta del llamado asíncrono.</p>
<pre name='code' class="javascript">new Ajax.Request(URL,
{
    parameters: $('FORMULARIO').serialize(true),
    method: 'post',
    onSuccess: function(transport)
    {
        // Hacer algo en éxito.
    },
    onFailure: function(transport)
    {
        // Hacer algo en fracaso.
    },
    onComplete: function(transport)
    {
        // Hacer algo al terminar.
    }
});</pre>
<h2>Utilizando <em>JSON</em> para el transporte.</h2>
<p>El procedimiento es similar al anterior.  La diferencia es que la respuesta del llamado asíncrono viene empaquetada en un objeto <a href="http://en.wikipedia.org/wiki/Json" target="_blank">JSON</a>, diferente a la invocación anterior en la que se recibe como una cadena de texto.</p>
<pre name='code' class="javascript">new Ajax.Request(URL,
{
    parameters: $('FORMULARIO').serialize(true),
    method: 'post',
    requestHeaders:
    {
        Accept: 'application/json'
    },
    onSuccess: function(transport)
    {
        // Hacer algo en éxito.
        var json = transport.responseText.evalJSON(true);
        // var valorX = json.x;
    },
    onFailure: function(transport)
    {
        // Hacer algo en fracaso.
    },
    onComplete: function(transport)
    {
        // Hacer algo al terminar.
    }
});</pre>
<p>Del lado del servidor, en PHP, el resultado final se debe encapsular en un objeto JSON antes de enviarlo al cliente.</p>
<pre name='code' class="php">echo "/*-secure-\n";
echo json_encode($contacto -&gt; toArray());
echo "\n*/";
header('Content-type: application/json');
header("Status: 200 OK", false, 200);</pre>
<p>En caso de error se debe retornar, al igual que en los demás casos, un mensaje cuyo tipo sea != 200.</p>
<pre name='code' class="php">header("Status: 400 Bad request", false, 400);</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/02/resumen-de-ajax-con-prototype/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Obtener el valor de la selección de un grupo de radiobuttons con Prototype</title>
		<link>http://blog.jorgeivanmeza.com/2009/02/obtener-el-valor-de-la-seleccion-de-un-grupo-de-radiobuttons-con-prototype/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=obtener-el-valor-de-la-seleccion-de-un-grupo-de-radiobuttons-con-prototype</link>
		<comments>http://blog.jorgeivanmeza.com/2009/02/obtener-el-valor-de-la-seleccion-de-un-grupo-de-radiobuttons-con-prototype/#comments</comments>
		<pubDate>Wed, 25 Feb 2009 19:17:12 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de software]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Prototype]]></category>
		<category><![CDATA[XHTML]]></category>
		<guid isPermaLink="false">http://www.jorgeivanmeza.com/blog/?p=1436</guid>
		<description><![CDATA[Suponendo que se tiene el siguiente formulario se requiere determinar cual es el valor seleccionado en el grupo de radiobuttons utilizando las facilidades que ofrece Prototype. &#60;form id='formulario'&#62; &#60;b&#62;Código&#60;/b&#62; &#60;input type='radio' id='opc1' name='opciones' value='vCodigo' /&#62; &#60;b&#62;Nombre&#60;/b&#62; &#60;input type='radio' id='opc2' name='opciones' value='vNombre' /&#62; &#60;b&#62;Documento&#60;/b&#62; &#60;input type='radio' id='opc3' name='opciones' value='vDocumento' /&#62; &#60;/form&#62; Desafortunadamente no es posible realizar [...]]]></description>
			<content:encoded><![CDATA[<p>Suponendo que se tiene el siguiente formulario se requiere determinar cual es el valor seleccionado en el grupo de <em>radiobuttons</em> utilizando las facilidades que ofrece <a href="http://www.prototypejs.org/" target="_blank">Prototype</a>.</p>
<pre name='code' class="html">&lt;form id='formulario'&gt;
    &lt;b&gt;Código&lt;/b&gt; &lt;input type='radio' id='opc1' name='opciones' value='vCodigo' /&gt;
    &lt;b&gt;Nombre&lt;/b&gt; &lt;input type='radio' id='opc2' name='opciones' value='vNombre' /&gt;
    &lt;b&gt;Documento&lt;/b&gt; &lt;input type='radio' id='opc3' name='opciones' value='vDocumento' /&gt;
&lt;/form&gt;</pre>
<p>Desafortunadamente no es posible realizar lo siguiente ya que el <em>radiobuttongroup</em> no es una entidad como tal sino un agrupamiento de las mismas, mas aún, no se referencia por su <em>id</em> sino por su <em>name</em>, motivo por el cual no funcionará con el <span style="font-family: courier new,courier;">getElementById</span>.</p>
<pre name='code' class="html">resultado = $('opciones').value;</pre>
<p>Por suerte Prototype es muy flexible y encontré dos soluciones diferentes para este problema que me parecieron muy interesantes, ambas en una sola instrucción compuesta.</p>
<p>La primera utiliza la búsqueda por selector para obtener los <em>radiobuttons</em> del documento que se encuentren seleccionados y que pertenezcan al <em>radiobuttongroup</em> elegido para posteriormente utilizar el método <a href="http://www.prototypejs.org/api/enumerable/pluck" target="_blank">pluck</a> para extraerle su atributo <span style="font-family: courier new,courier;">value</span>.</p>
<pre name='code' class="html">resultado = $$('input:checked[type="radio"][name="opciones"]').pluck('value');</pre>
<p>La segunda optiene los <em>radiobuttons</em> de un <em>radiobuttongroup</em> específico accediendo directamente al formulario que los contiene para posteriormente utilizar el método <a href="http://www.prototypejs.org/api/enumerable/find" target="_blank">find</a> que retornará al primer elemento encontrado y que se encuentre seleccionado.</p>
<pre name='code' class="html">resultado = $('formulario').getInputs('radio','opciones').find(function(radio) { return radio.checked; }).value;</pre>
<h3>Enlaces.</h3>
<ul>
<li>Get value of radio button group using prototype.<br />
<a href="http://stereointeractive.com/blog/2008/06/05/get-radio-button-value-using-prototype/" target="_blank">http://stereointeractive.com/blog/2008/06/05/get-radio-button-value-using-prototype/</a></li>
<li>Getting Radio buttons value with Prototype.js.<br />
<a href="http://rexchung.com/2007/02/22/getting-radio-buttons-value-with-prototypejs/" target="_blank">http://rexchung.com/2007/02/22/getting-radio-buttons-value-with-prototypejs/</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/02/obtener-el-valor-de-la-seleccion-de-un-grupo-de-radiobuttons-con-prototype/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>haXe - el lenguaje multiplataforma</title>
		<link>http://blog.jorgeivanmeza.com/2009/02/haxe-el-lenguaje-multiplataforma/?utm_source=rss&amp;utm_medium=rss&amp;utm_campaign=haxe-el-lenguaje-multiplataforma</link>
		<comments>http://blog.jorgeivanmeza.com/2009/02/haxe-el-lenguaje-multiplataforma/#comments</comments>
		<pubDate>Mon, 16 Feb 2009 15:16:14 +0000</pubDate>
		<dc:creator>jimezam</dc:creator>
				<category><![CDATA[Desarrollo de software]]></category>
		<category><![CDATA[Linux/Solaris/BSD]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[Flash]]></category>
		<category><![CDATA[Haxe]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Neko]]></category>
		<category><![CDATA[PHP]]></category>
		<guid isPermaLink="false">http://www.jorgeivanmeza.com/blog/?p=1368</guid>
		<description><![CDATA[Introducción. haXe (se pronuncia hex), es otra de los muchos lenguajes de programación que andan por ahí en Internet, opensource y listos para que uno los aprenda, se sorprenda y aproveche según sus características. La finalidad de este lenguaje es la de ser multiplataforma, es decir, puede generar código para las plataformas de JavaScript, Flash, [...]]]></description>
			<content:encoded><![CDATA[<h3>Introducción.</h3>
<p>haXe (se pronuncia <em>hex</em>), es otra de los muchos lenguajes de programación que andan por ahí en Internet, <em>opensource</em> y listos para que uno los aprenda, se sorprenda y aproveche según sus características.</p>
<p>La finalidad de este lenguaje es la de ser multiplataforma, es decir, puede generar código para las plataformas de JavaScript, Flash, PHP, NekoVM y C++.  Según los desarrolladores del lenguaje, el lenguaje le evita al desarrollador tener que aprender los intríngulis a cada una de las plataformas mediante la unificación de estas a través del <a href="http://haxe.org/doc/features" target="_blank">lenguaje unificado</a>, que incluye una librería estándar para todas las plataformas y una serie de librerías para acceder al API de cada una de las plataformas objetivo.</p>
<h3>Instalación.</h3>
<h4>Linux Ubuntu 8.10.</h4>
<p><span style="font-family: courier new,courier;">$ sudo apt-get install haxe</span></p>
<h4>Linux OpenSuse 11.1.</h4>
<p><span style="font-family: courier new,courier;">$ wget http://haxe.org/file/hxinst-linux.tgz</span></p>
<p><span style="font-family: courier new,courier;">$ tar zxvf hxinst-linux.tgz</span></p>
<p><span style="font-family: courier new,courier;">$ ./hxinst-linux</span></p>
<h3>Demostración - Hola Mundo.</h3>
<p><span style="font-family: courier new,courier;">$ vi HelloWorld.hx</span></p>
<p style="padding-left: 30px;"><span style="font-family: courier new,courier;">class HelloWorld<br />
{<br />
public static function main()<br />
{<br />
trace(&#8220;Hello World!&#8221;);<br />
}<br />
}</span></p>
<h4>Compilación con Flash como objetivo.</h4>
<p><span style="font-family: courier new,courier;">$ haxe -swf VersionFlash.swf -main HelloWorld</span></p>
<p><a href="http://www.jorgeivanmeza.com/blog/wp-content/uploads/2009/02/screenshotflash.jpg"><img class="aligncenter size-full wp-image-1370" title="screenshotflash" src="http://www.jorgeivanmeza.com/blog/wp-content/uploads/2009/02/screenshotflash.jpg" alt="screenshotflash" width="309" height="120" /></a><a href="http://haxe.org/doc/start/flash" target="_blank">Ver mas información</a>.</p>
<h4>Compilación con JavaScript como objetivo.</h4>
<p><span style="font-family: courier new,courier;">$ haxe -js HelloWorld.js -main HelloWorld</span></p>
<p><a href="http://www.jorgeivanmeza.com/blog/wp-content/uploads/2009/02/screenshotjavascript.jpg"><img class="aligncenter size-full wp-image-1371" title="screenshotjavascript" src="http://www.jorgeivanmeza.com/blog/wp-content/uploads/2009/02/screenshotjavascript.jpg" alt="screenshotjavascript" width="401" height="147" /></a><a href="http://haxe.org/doc/start/js" target="_blank">Ver mas información</a>.</p>
<h4>Compilación con PHP como objetivo.</h4>
<p><span style="font-family: courier new,courier;">$ haxe -php HelloWorldPHP/ -main HelloWorld</span></p>
<p><a href="http://www.jorgeivanmeza.com/blog/wp-content/uploads/2009/02/screenshotphp.jpg"><img class="aligncenter size-full wp-image-1373" title="screenshotphp" src="http://www.jorgeivanmeza.com/blog/wp-content/uploads/2009/02/screenshotphp.jpg" alt="screenshotphp" width="278" height="201" /></a><a href="http://haxe.org/doc/start/php" target="_blank">Ver mas información</a>.</p>
<h4>Compilación con Neko como objetivo.</h4>
<p><span style="font-family: courier new,courier;">$ haxe -neko HelloWorld.n -main HelloWorld<br />
</span></p>
<p><span style="font-family: courier new,courier;">$ neko HelloWorld.n</span></p>
<p><a href="http://www.jorgeivanmeza.com/blog/wp-content/uploads/2009/02/screenshotneko.jpg"><img class="aligncenter size-full wp-image-1372" title="screenshotneko" src="http://www.jorgeivanmeza.com/blog/wp-content/uploads/2009/02/screenshotneko.jpg" alt="screenshotneko" width="376" height="34" /></a></p>
<p><a href="http://haxe.org/doc/start/php" target="_blank">Ver mas información</a>.</p>
<p>También es posible convertir los <em>bytecodes</em> de Neko a código binari o dependiente de la máquina con las siguiente instrucción.</p>
<p><span style="font-family: courier new,courier;">$ nekotools boot HelloWorld.n</span></p>
<p><span style="font-family: courier new,courier;">$ ./HelloWorld</span></p>
<p>Compilando el <span style="font-family: courier new,courier;">HelloWorld</span> bajo <strong>OpenSuse 11.1</strong> encontré un problema con la librería <span style="font-family: courier new,courier;">libgc</span>.  Cuando intentaba generar la versión para Neko, obtenía siempre el siguiente mensaje.
</p>
<p style="padding-left: 30px;"><span style="font-family: courier new,courier;">nekoc: error while loading shared libraries: libgc.so.1: cannot open shared object file: No such file or directory<br />
Error : Neko compilation failure</span></p>
<p>Este problema se solucionó instalando el paquete <span style="font-family: courier new,courier;">gc</span> de la siguiente manera.</p>
<p><span style="font-family: courier new,courier;">$ sudo zypper install gc</span></p>
<h3>Enlaces.</h3>
<ul>
<li>Homepage.<br />
<a href="http://www.haxe.org/" target="_blank">http://www.haxe.org/</a></li>
<li>Documentación general.<br />
<a href="http://haxe.org/doc" target="_blank">http://haxe.org/doc</a></li>
<li>API.<br />
<a href="http://haxe.org/api" target="_blank">http://haxe.org/api</a></li>
<li>Referencia del lenguaje.<br />
<a href="http://haxe.org/ref" target="_blank">http://haxe.org/ref</a></li>
<li>Librerías.<br />
<a href="http://haxe.org/doc/libraries" target="_blank">http://haxe.org/doc/libraries</a></li>
<li>Descargas.<br />
<a href="http://haxe.org/download" target="_blank">http://haxe.org/download</a></li>
<li>Proyectos que utilizan haXe.<br />
<a href="http://www.haxe.org/com/projects" target="_blank">http://www.haxe.org/com/projects</a></li>
<li>Personas que utilizan haXe.<br />
<a href="http://www.haxe.org/com/people" target="_blank">http://www.haxe.org/com/people</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.jorgeivanmeza.com/2009/02/haxe-el-lenguaje-multiplataforma/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>
