14 de julio de 2011

[Java] Graficos con Swing Parte 1.

Inicialmente, empezamos a desarrollar utilizando solo la 'consola', con el tipico 'hola mundo', y de esta forma realizamos pequeñas aplicaciones destinadas a la lectura o escritura de archivos, calculos matematicos, etc. Conforme vamos aprendiendo más, nos damos cuenta que tenemos muchos mas recursos de donde tomar.

Es verdad que al
gunos se 'saltan' el desarrollo de aplicaciones para escritorio o el desarrollo de algún applet y se pasan directo al desarrollo web, donde no ven nada de componentes graficos como tales, propios de Java (botones, etiquetas, paneles, etc.). Java permite, además de sus controles, realizar dibujos directamente en una 'Ventana' o algún Panel. Para con ésto realizar aplicaciones especializadas para mostrar Graficos, crear animaciones o desarrollar juegos. En esta entrada veremos el componente principal de una Aplicacion de escritorio y como dibujar y mostrar elementos gráficos directamente en el (o con ayuda de algun otro componente contenido en la ventana).
Tomar en cuenta que
el objetivo de esto no es especializarse en Swing o la clase Graphics, ya que No se explica a detalle.

Pasemos al planteamiento: Se ha de desarollar una pequeña aplicacion que permita visualizar formas basicas en una ventana.


Para esto, como elemento principal necesitamos crear un Contenedor, el cual permitirá mostrar el contenido que necesitemos, para esto utilizaremos el componente llamado JFrame.

Aunque se puede dibujar directamente en un JFrame, utilizaremos un JPanel para este trabajo.

Ambos componentes tienen un método llamado paint(Graphics g), que es el encargado del renderizado de dicho componente. La estructura basica de nuestra clase sería la siguiente:




import java.awt.Color;
import java.awt.Graphics;

import javax.swing.*;

public class PanelGrafico extends JPanel {

public PanelGrafico() { }

public void paint(Graphics g) {
g.drawRect(20, 20, 200, 200);
}

public static void main(String[] args) {

PanelGrafico2 panel = new PanelGrafico2();
JFrame ventana = new JFrame();
ventana.add(panel);
ventana.setSize(400,400);
ventana.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
ventana.setVisible(true);
}

}



Ejecutando el codigo anterior obtenemos lo siguiente:


No
s enfocaremos principalmente en el método paint(). Éste método es el encargado de dibujar en el componente, lleva como parámetro el objeto Graphics, que es el que nos proporciona los elementos graficos que pueden ser dibujados, incluyendo metodos para formas basicas como lineas o circulos, así como también texto. Algunos métodos son los siguientes:

g.drawLine(x1, y1, x2, y2);
g.drawRect(x, y, ancho, alto);
g.drawOval(x, y, ancho, alto);
g.drawString("texto", x, y);

Las variables x, y representan las coordenadas (numero entero) en "pixeles" dentro del contenedor. Las variables ancho y alto también son valores enteros.


Como practica no hace falta mas que experimentar con dichos métodos (así como los demás pertenecientes a la clase Graphics). Podemos agregar este codigo al método paint(), el cual dibujará una fila de pequeños circulos a lo ancho de la ventana:

for(int cont=0; cont<this.getWidth()/10; cont++) {
g.fillOval(cont*10, 10, 10, 10);
}

Lo siguiente dibujará una 'rejilla' a lo ancho y largo de la ventana:


for(int cont=0; cont<getWidth()/20; cont++) {
g.drawLine(cont*20, 0, cont*20, this.getHeight());
g.drawLine(0, cont*20, this.getWidth(),cont*20);
}


Puede agregarce color a las formas, utilizando el siguiente codigo:

g.setColor(Color.blue);

Agregando los ultimos fragmentos de codigo al metodo paint() y ejecutandolo, se obtiene lo siguiente:



Practicar y experimentar es la mejor manera de entender mejor la clase Graphics.

Un ejemplo:




Pero para realizar animaciones, o algun pequeño juego, o cualquier elemento que se 'moverá' dentro de la ventana, lo anterior no es suficiente (o no es recomendado), ya que al momento de refrescar la pantalla ciclicamente, se nota un efecto de 'parpadeo' y por lo cual, no es posible visualizar comodamente los elementos.

Para solucion a este problema hay una tecnica conocida como Doble Buffer, la cual se describirá en la Parte 2 de éste tutorial.

Saludos!

[Flex] Instalar Flash Builder 4.5 como Plugin en Eclipse.

Si quieres tener Flash Builder 4.5 como Plugin en Eclipse es muy sencillo. Sólo tienes que hacer lo siguiente:

1. Instala Flash Builder 4.5 (Standalone). Puedes bajar la versión de prueba de la página de Adobe.


2. Debes tener una versión de Eclipse 3.6 ó superior. La última versión es Eclipse Indigo.


3. Comprueba que en el directorio de eclipse existe el folder dropins.


4. Navega hasta el directorio de instalación de Flash Builder y abre la carpeta utilities (ejemplo: C:\Archivos de programa\Adobe\Adobe Flash Builder 4.5\utilities).


5. Ejecuta la utilería Adobe Flash Builder 4.5 Plug-in Utility.exe.






6. Selecciona el lenguaje deseado (Inglés, Alemán o Frances, no sé ninguno de estos idiomas pero tuve que elegir uno).


7. Probablemente tengas que proporcionar la ruta de instalación de Flash Builder. Si no te pide esta ruta, salta al siguiente paso (a mí no me apareció este paso).


8. Proporciona el directorio de eclipse (en mi caso D:\eclipse).




9. Revisa el resumen de instalación y click en Install.




10. Posterior a la instalación es muy recomendado que edites el archivo eclipse.ini de tu instancia de eclipse (en mi caso D:\eclipse\eclipse.ini) y agregues las siguientes líneas:



-vmargs

-Xms256m

-Xmx512m

-XX:MaxPermSize=256m

-XX:PermSize=64m





Y listo!! Abre Eclipse para crear un proyecto Flex.

Si tienes dudas con alguno de los pasos, deja tu comentario.

[Flex] Como crear una gráfica de valores acumulados

En cierta ocasión me pidieron que hiciera una gráfica que mostrara el avance acumulado por meses pero que la comumna siguiente se dibujara a partir del valor maximo de la barra anterior y lo que se me ocurrió lo dejo en el siguiente link:
http://mybinnacle.blogspot.com/

Espero sea de utilidad.

13 de julio de 2011

[VBA] Serie MSXML - Creando un documento XML en Excel

A veces resulta muy necesario importar información de un archivo de excel, y uno de los formatos mas ampliamente usados por su interoperabilidad es el XML.
Esta es la hoja de excel que convertiremos a XML.


Para lograr esto, tendremos que agregar las referencia Microsoft XML 5.0 (msxml.dll), tienes que ir a Herramientas/Referencias y elige esta versión o la más actual que tengas instalada.





Código VBA:

Sub ConvetirAXml()

Dim fila As Integer

Dim documento As DOMDocument
Dim registros As IXMLDOMElement
Dim registro As IXMLDOMElement
Dim atributo As IXMLDOMAttribute
Dim columna As IXMLDOMElement
Dim encoding As IXMLDOMProcessingInstruction

fila = 2

Set documento = New DOMDocument

Set encoding = documento.createProcessingInstruction("xml", "version='1.0' encoding='iso-8859-1'")
documento.appendChild encoding

Set registros = documento.createElement("registros")
documento.appendChild registros

Do While datos.Cells(fila, "B") <> ""

    Set registro = documento.createElement("registro")
    registros.appendChild registro
    
    'COLUMNA ID
    Set columna = documento.createElement(datos.Cells(1, "A"))
    registro.appendChild columna
    columna.Text = datos.Cells(fila, "A")
    
    Set atributo = documento.createAttribute("id")
    atributo.NodeValue = fila
    registro.setAttributeNode atributo
        
    'COLUMNA DATO
    Set columna = documento.createElement(datos.Cells(1, "B"))
    registro.appendChild columna
    columna.Text = datos.Cells(fila, "B")
    
    Set atributo = documento.createAttribute("id")
    atributo.NodeValue = fila
    registro.setAttributeNode atributo
        

fila = fila + 1

Loop

documento.Save ThisWorkbook.Path & "\datos.xml"

End Sub

Archivo XML Generado:

<?xml version="1.0" encoding="iso-8859-1"?>
<registros>
   <registro id="2">
      <ID>1</ID>
      <DATO>A</DATO>
   </registro>
   <registro id="3">
      <ID>2</ID>
      <DATO>B</DATO>
   </registro>
   <registro id="4">
      <ID>3</ID>
      <DATO>C</DATO>
   </registro>
   <registro id="5">
      <ID>4</ID>
      <DATO>D</DATO>
   </registro>
   <registro id="6">
      <ID>5</ID>
      <DATO>E</DATO>
   </registro>
</registros>

Descargar ejemplo

Descarga el archivo de excel posicionate sobre la hoja que se llama DATOS y presiona F9, en la misma ubicación donde descargaste o colocaste el archivo, si tienes algun problema para ejecutarlo puede deberse a que tendras que habilitar el uso de macros y activeX en excel. Como buena práctica les recomiendo ir guardando y organizando los códigos que vamos haciendo en nuestro día a día, les sugiero un muy buen code snippets manager que se llama SnipItPro.  

Cliente ftp con CSharp

//Aqui les dejo una clase completa para el manejo de archivos por FTP con CSharp
//Framework 2.0
//


using Microsoft.CSharp;
using System.Net;
using System.IO;
using System.Threading;
using System.Configuration;
using System;


public class FTP
{
public string host, user, pass;

public FTP(string host,string user,string pass)
{
this.host = host;
this.user = user;
this.pass = pass;

}



public string eliminarFichero(string fichero)
{
FtpWebRequest peticionFTP;
// Creamos una petición FTP con la dirección del fichero a eliminar
peticionFTP = (FtpWebRequest)WebRequest.Create(new System.Uri(fichero));

// Fijamos el usuario y la contraseña de la petición

peticionFTP.Credentials = new NetworkCredential (user,pass);
// ' Seleccionamos el comando que vamos a utilizar: Eliminar un fichero
peticionFTP.Method = WebRequestMethods.Ftp.DeleteFile;
peticionFTP.UsePassive = false;
try
{

FtpWebResponse respuestaFTP;
respuestaFTP = (FtpWebResponse)peticionFTP.GetResponse();
respuestaFTP.Close();

return string.Empty;
}
catch (Exception ex)
{
return ex.Message;
}
}



public Boolean existeObjeto(ref String dir)
{
FtpWebRequest peticionFTP;
//Creamos una peticion FTP con la dirección del objeto que queremos saber si existe
peticionFTP = (FtpWebRequest)WebRequest.Create(new Uri(dir));
//Fijamos el usuario y la contraseña de la petición
peticionFTP.Credentials = new NetworkCredential(user, pass);
//Para saber si el objeto existe, solicitamos la fecha de creación del mismo
peticionFTP.Method =WebRequestMethods.Ftp.GetDateTimestamp ;
peticionFTP.UsePassive =false;
peticionFTP.KeepAlive = true;
try
{
//si el objeto existe, se devolvera true
FtpWebResponse respuestaFTP;
//respuestaFTP = CType(peticionFTP.GetResponse(), FtpWebResponse)
respuestaFTP = (FtpWebResponse)peticionFTP.GetResponse();

return true;
}
catch (Exception ex)
{
//si el objeto no existe, se producirá un error y al entrar por el Catch
//se devolvera falso
return false;
}

}

public String creaDirectorio(String dir)
{

FtpWebRequest peticionFTP;

// Creamos una peticion FTP con la dirección del directorio que queremos crear
peticionFTP = (FtpWebRequest) WebRequest.Create(new Uri(dir));
peticionFTP.KeepAlive = true;

// Fijamos el usuario y la contraseña de la petición
peticionFTP.Credentials = new NetworkCredential(user, pass);

// Seleccionamos el comando que vamos a utilizar: Crear un directorio
peticionFTP.Method = WebRequestMethods.Ftp.MakeDirectory;
//(FtpWebResponse) request.GetResponse();

try
{
FtpWebResponse respuesta;
respuesta = (FtpWebResponse) peticionFTP.GetResponse();
respuesta.Close();
// Si todo ha ido bien, se devolverá String.Empty
return string.Empty;

}
catch (Exception ex)
{
// Si se produce algún fallo, se devolverá el mensaje del error
return ex.Message;
}

}


public String subirFichero(String fichero, String destino, String dir )
{

FileInfo infoFichero = new FileInfo(fichero);

String uri;
uri = destino;

// Si no existe el directorio, lo creamos
String str="";
if (!existeObjeto(ref dir)) str = creaDirectorio(dir);

FtpWebRequest peticionFTP;

// Creamos una peticion FTP con la dirección del fichero que vamos a subir
peticionFTP = (FtpWebRequest) FtpWebRequest.Create(new Uri(destino));

// Fijamos el usuario y la contraseña de la petición
peticionFTP.Credentials = new NetworkCredential(user, pass);

peticionFTP.KeepAlive = false;
peticionFTP.UsePassive = false;
// Seleccionamos el comando que vamos a utilizar: Subir un fichero
peticionFTP.Method = WebRequestMethods.Ftp.UploadFile;

// Especificamos el tipo de transferencia de datos
peticionFTP.UseBinary = true;

// Informamos al servidor sobre el tamaño del fichero que vamos a subir
try
{
peticionFTP.ContentLength = infoFichero.Length;
}

catch (Exception ex)
{return ex.Message;}

// Fijamos un buffer de 2KB
int longitudBuffer;
longitudBuffer = 2048;
Byte[] lector = new Byte[2048] ; // esti estaba Byte (2048);
int num;

// Abrimos el fichero para subirlo
FileStream fs;
fs = infoFichero.OpenRead();
Stream escritor = null;
try
{ escritor = peticionFTP.GetRequestStream();
// Leemos 2 KB del fichero en cada iteración
num = fs.Read(lector, 0, longitudBuffer);
// num=fs.Read (lector[],0,longitudBuffer);
while (num != 0)
{
// Escribimos el contenido del flujo de lectura en el
// flujo de escritura del comando FTP
escritor.Write(lector, 0, num);
num = fs.Read(lector, 0, longitudBuffer);
}

escritor.Close();
fs.Close();
//Si todo ha ido bien, se devolverá String.Empty
return String.Empty;
}
catch (WebException ex){
if (escritor == null ) escritor.Close();
fs.Close();
// Si se produce algún fallo, se devolverá el mensaje del error
return ex.Message;
}


}

public String subirFicheroSeguimiento(String fichero, String destino , String dir )
{
FileInfo infoFichero = new FileInfo(fichero);

String uri;
uri = destino;

// Si no existe el directorio, lo creamos
if (!existeObjeto(ref dir)) {}
// Dim str As String = creaDirectorio(dir)


FtpWebRequest peticionFTP;

// Creamos una peticion FTP con la dirección del fichero que vamos a subir
peticionFTP = (FtpWebRequest)FtpWebRequest.Create(new Uri(destino));

// Fijamos el usuario y la contraseña de la petición
peticionFTP.Credentials = new NetworkCredential(user, pass);
peticionFTP.KeepAlive = false;
peticionFTP.UsePassive = false;

// Seleccionamos el comando que vamos a utilizar: Subir un fichero
peticionFTP.Method = WebRequestMethods.Ftp.UploadFile;

// Especificamos el tipo de transferencia de datos
peticionFTP.UseBinary = true;

// Informamos al servidor sobre el tamaño del fichero que vamos a subir
try
{
peticionFTP.ContentLength = infoFichero.Length;
}

catch ( Exception ex)
{
return ex.Message;
}
// Fijamos un buffer de 2KB
int longitudBuffer;
longitudBuffer = 2048;
byte[] lector = new Byte[2048];

int num;

// Abrimos el fichero para subirlo
FileStream fs;
fs = infoFichero.OpenRead();
Stream escritor = null;
try
{
escritor = peticionFTP.GetRequestStream();

// Leemos 2 KB del fichero en cada iteración
num = fs.Read(lector, 0, longitudBuffer);

while (num != 0)
{
// Escribimos el contenido del flujo de lectura en el
// flujo de escritura del comando FTP
escritor.Write(lector, 0, num);
num = fs.Read(lector, 0, longitudBuffer);
}

escritor.Close();
fs.Close();
// Si todo ha ido bien, se devolverá String.Empty
return String.Empty;
}
catch (WebException ex)
{
if (!(escritor==null)) escritor.Close();
fs.Close();
// Si se produce algún fallo, se devolverá el mensaje del error
return ex.Message;
}

}

public void descargarDirectorio(string dirD)
{
FtpWebRequest dirFtp = ((FtpWebRequest)FtpWebRequest.Create(host));

// Los datos del usuario (credenciales)
NetworkCredential cr = new NetworkCredential(user, pass);
dirFtp.Credentials = cr;


// El comando a ejecutar
dirFtp.Method = "LIST";

// También usando la enumeración de WebRequestMethods.Ftp
dirFtp.Method = WebRequestMethods.Ftp.ListDirectory;

// Obtener el resultado del comando
StreamReader reader =
new StreamReader(dirFtp.GetResponse().GetResponseStream());

// Leer el stream
string res = "";//reader.ReadLine();
//Response.Write(res);
string nuevo_dir = "";

while (!reader.EndOfStream)
{

res = reader.ReadLine();

if (res.Contains("."))
{
//Response.Write(res + "
");
bajaArchivo(host, dirD, res);
}
else
{
//Response.Write(res + "
");

nuevo_dir = dirD + res;
Directory.CreateDirectory(nuevo_dir);

listarDirRecursivo(host + res + "/", nuevo_dir + "\\", user, pass);


}

}
reader.Close();

}


private void listarDirRecursivo(string dirO, string dirD, string user, string pass)
{
FtpWebRequest dirFtp = ((FtpWebRequest)FtpWebRequest.Create(dirO));

// Los datos del usuario (credenciales)
NetworkCredential cr = new NetworkCredential(user, pass);
dirFtp.Credentials = cr;
// El comando a ejecutar
dirFtp.Method = "LIST";

// También usando la enumeración de WebRequestMethods.Ftp
dirFtp.Method = WebRequestMethods.Ftp.ListDirectory;

// Obtener el resultado del comando
StreamReader reader = new StreamReader(dirFtp.GetResponse().GetResponseStream());

// Leer el stream
string res = "";//reader.ReadLine();
//Response.Write(res);

string nuevo_dir = "";

while (!reader.EndOfStream)
{

res = reader.ReadLine();

if (res.Contains("."))
{
//Response.Write(res + "
");
bajaArchivo(dirO, dirD, res);
}
else
{
//Response.Write(res + "
");
nuevo_dir = dirD + res;
Directory.CreateDirectory(nuevo_dir);
listarDirRecursivo(dirO + res + "/", nuevo_dir + "\\", user, pass);
}


// res = reader.ReadLine();
// Response.Write(res + "
");
}
reader.Close();

// Mostrarlo.
//Console.WriteLine(res);

// Cerrar el stream abierto.

}



private void bajaArchivo(string dirO, string dirD, string archivo)
{
using (WebClient wc = new WebClient())
{
wc.Proxy = null;
wc.BaseAddress = dirO;

// Authenticate, then download a file to the FTP server.
// The same approach also works for HTTP and HTTPS.

string username = user;
string password = pass;
wc.Credentials = new NetworkCredential(username, password);
wc.DownloadFile(archivo, dirD + archivo);
}
}

public void bajaArchivoP(string dirO, string dirD, string archivo)
{
using (WebClient wc = new WebClient())
{
wc.Proxy = null;
wc.BaseAddress = dirO;

// Authenticate, then download a file to the FTP server.
// The same approach also works for HTTP and HTTPS.

string username = user;
string password = pass;
wc.Credentials = new NetworkCredential(username, password);
wc.DownloadFile(archivo, dirD);
}
}

public void subirArchivo(string rutaOrigen, string rutaDestino)
{
using (WebClient wc = new WebClient())
{
wc.Proxy = null;

// Authenticate, then download a file to the FTP server.
// The same approach also works for HTTP and HTTPS.

string username = user;
string password = pass;
wc.Credentials = new NetworkCredential(username, password);
wc.UploadFile(rutaDestino, rutaOrigen);
}

}


public Boolean verificaExitencia(string nombreObjeto)
{
FtpWebRequest dirFtp = ((FtpWebRequest)FtpWebRequest.Create(host));
Boolean respuesta = false;

// Los datos del usuario (credenciales)
NetworkCredential cr = new NetworkCredential(user, pass);
dirFtp.Credentials = cr;


// El comando a ejecutar
dirFtp.Method = "LIST";

// También usando la enumeración de WebRequestMethods.Ftp
dirFtp.Method = WebRequestMethods.Ftp.ListDirectory;

// Obtener el resultado del comando
StreamReader reader =
new StreamReader(dirFtp.GetResponse().GetResponseStream());

// Leer el stream
string res = "";//reader.ReadLine();
//Response.Write(res);

while (!reader.EndOfStream)
{
res = reader.ReadLine();

if (res == nombreObjeto)
{
respuesta= true;
}

}
reader.Close();
return respuesta;
}

}

[MSDOS] Creando carpetas desde un archivo de texto

En dias anteriores me enfrente con el problema de tener que crear a partir de un archivo de texto (.txt) un grupo de carpetas, la forma dificil hubiera sido ir creando una a una cada una de ellas, mediante el explorador de windows (Archivo/Nuevo/Carpeta), el problema era que el nombre de las carpetas podría cambiar y tendría que generar nuevamente todas.

Investigando me encontre con el comando FOR de MSDOS que me resolvió este problema, permitiéndome generar las carpetas, las veces que yo quisiera.

A continuación mostraré un video con los pasos a seguir de como lo resolver este problema:

Video de demostración