Autocompletar Java Swing (Autocompleter)

A
[alert type=»notice»]Versión Actual 2.0.1 Beta[/alert] [alert type=»warning»]Última actualización 10/10/2014[/alert]

Después de mucho tiempo leyendo correos y comentarios acerca de esta librería (pueden ver información sobre ella aquí), sobre como mejorarla y solución de algunos errores, al fin traigo una actualización para la misma (no crean que no seguía trabajando en ella).

Desafortunadamente debo decir que a pesar de tratar que permanezca todo el funcionamiento intacto muchos de los cambios me forzaron a hacer muchas modificaciones en el mismo, así que es probable que tengan que retocar su código fuente para quienes ya estaban usando la librería antes, sin embargo muchas funciones a pesar de ser diferentes seguirán funcionando con las mismas entradas y tendrán las mismas salidas.

[button link=»http://adf.ly/7046662/autocompleter-v201-beta» style=»light»]Descargar V2.0.1[/button]

[button link=»http://adf.ly/pq7YU» style=»light»]Descargar V2.0[/button]

[button link=»http://adf.ly/pq7al» style=»dark»]Javadoc[/button]

Instalación

Agrega la librería a tu proyecto, como harías con cualquier otra librería. That’s it!! 😉 ya está todo listo para funcionar.

Modo de uso básico

Si ya has hecho la instalación, solo tienes que importar las clases a usar, la clase importante es «TextAutoCompleter»

import com.mxrck.autocompleter.TextAutoCompleter;

Y comenzamos creando una instancia de la clase

TextAutoCompleter textAutoCompleter = new TextAutoCompleter(jTextField1);
textAutoCompleter.addItem("uno");
textAutoCompleter.addItem("dos");
textAutoCompleter.addItem("tres");
textAutoCompleter.addItem("cuatro");

That’s all! ya tienes la librería funcionando, y jTextField1 ahora completará los valores ingresados, «uno», «dos», «tres», «cuatro», de hecho pueden ejecutar como aplicación la librería y verán un ejemplo en uso

Autocompletar Java

Uso avanzado

  • mode – El modo es la manera en la que se buscan items, existen 3 modos diferentes, prefijo (-1), infijo (0), sufijo (1). Por defecto -1.
  • caseSensitive – De la misma manera que el modo afecta la manera en la que se usan y buscan los items caseSensitive es una opción extra, que sirve para diferenciar los items con sensibilidad entre mayúsculas y minúsculas, de esta forma si está activado «Uno» no es igual a «uno» o «uNo», si está desactivada todos los ejemplos anteriores serán tomados de la misma forma. Por defecto false.
  • clearOnIncorrectEsta función actualmente no está disponible y no causará ningún efecto al activarla o desactivarla.

Es posible inicializar todas estas opciones usando los diferentes constructores de TextAutoCompleter:

TextAutoCompleter(JTextComponent comp);
TextAutoCompleter(JTextComponent comp, AutoCompleterCallback callback);
TextAutoCompleter(JTextComponent comp, ArrayList<Object> items);
TextAutoCompleter(JTextComponent comp, ArrayList<Object> items, AutoCompleterCallback callback);
TextAutoCompleter(JTextComponent comp, ArrayList<Object> items, int mode);
TextAutoCompleter(JTextComponent comp, ArrayList<Object> items, int mode, AutoCompleterCallback callback);
TextAutoCompleter(JTextComponent comp, ArrayList<Object> items, int mode, boolean caseSensitive);
TextAutoCompleter(JTextComponent comp, ArrayList<Object> items, int mode, boolean caseSensitive, AutoCompleterCallback callback);
TextAutoCompleter(JTextComponent comp, Object[] items);
TextAutoCompleter(JTextComponent comp, Object[] items, AutoCompleterCallback callback);
TextAutoCompleter(JTextComponent comp, Object[] items, int mode);
TextAutoCompleter(JTextComponent comp, Object[] items, int mode, AutoCompleterCallback callback);
TextAutoCompleter(JTextComponent comp, Object[] items, int mode, boolean caseSensitive);
TextAutoCompleter(JTextComponent comp, Object[] items, int mode, boolean caseSensitive, AutoCompleterCallback callback);

Además de poder inicializarlas por medio de los constructores también podemos modificarlas en cualquier momento usando sus setters y getters:

getMode();
setMode(int mode);
isCaseSensitive();
setCaseSensitive(boolean caseSensitive);

 Todas las funciones para trabajar los items:

Hay varias formas de agregar items, desde items individuales hasta conjunto de items nuevos:

addItem(Object item);
addItems(ArrayList<Object> items);
addItems(Object[] items);

Uno de los cambios principales es que ya no solo se aceptan Strings como pasaba antes, ahora también podemos añadir el objeto que nosotros queramos, de cualquier forma podemos seguir añadiendo simplemente Strings y seguirá funcionando igual que antes, la diferencia más grande es que añadiendo objetos de otras clases podemos trabajar como si de un JList se tratara (esto lo explicaré más adelante).

Seguimos teniendo funciones para remover items:

removeItem(Object item);
removeItemByValue(String value);
removeItemByValueIgnoreCase(String value);
removeAllItems();

Hay que prestar atención especial para «removeItem(Object item)» ya que éste buscará el item por referencia de objetos, es mucho más rápido que la forma original en la que se eliminaban pero debes tener una referencia al objeto que quieres remover, de otra forma no se eliminará nada, «removeItemByValue(String value)» de la misma forma que la siguiente función funciona de la misma forma que antes funcionaba el removeItem de la versión anterior, es más lento que removeItem() pero funciona en caso de no tener referencia del objeto que se quiere eliminar. Adicionalmente estás funciones devuelven TRUE en caso de haber eliminado con éxito el item, o FALSE en caso de que el item no pudo ser eliminado o encontrado en la lista de items.

Otras funciones interesantes:

findItem(String value);
itemExists(String value);
itemExists(Object item);
getItemSelected();

No creo que sea necesario explicar por completo estas funciones, a menos que alguien lo solicite.

getItemSelected()

Esta función servirá para traer el último item seleccionado por el usuario, en caso de no tener seleccionado ningún item, intentará buscar dentro de todos los items el texto que se encuentre actualmente en el JTextField (De la misma forma que se hace al llamar «findItem()»).

En caso de no encontrar ningúna coincidencia o selección devolverá null.

AutoCompleterCallback

Una parte importante de esta actualización es que ya tenemos la posibilidad de saber cuando el usuario ha seleccionado un item, es muy fácil de implementar, y solo pondré un ejemplo de como poder hacerlo.

Cabe mencionar que la única forma de hacerlo es al momento de la inicialización, por lo que hay que tenerlo en cuenta:

TextAutoCompleter textAutoCompleter = new TextAutoCompleter(jTextField1, new AutoCompleterCallback() {
    @Override
    public void callback(Object selectedItem) {
        System.out.println("El usuario seleccionó: " + selectedItem);
    }
});

Esta función será llamada automáticamente cuando el usuario seleccione un item.

Nota: Hay que tener en cuenta que si el usuario no selecciona por medio de «click» o «enter» el item sugerido esta función no será llamada, para estos casos se puede usar la función «getItemSelected()».

Ingresando Objetos definidos por usuario

Bien, debo tomar un respiro…, un poco de agua…, quizá un cafecito…, ya está, ahora y después de todo lo anterior, vamos a terminar con el modo avanzado poniendo dando algunos ejemplos de como usar el autocompletado con sus propios objetos.

Como ya he dicho antes, podemos seguir usando la librería como era antes, con puros String, pero ahora también podemos ingresar nuestros propios objetos; Aún así como solo podemos mostrar cadenas al momento de autocompletar quizá deban hacer algunas modificaciones a sus clases para poder ingresarlas y que se muestren correctamente, no es nada complejo, de hecho la función ya es implementada por las clases solo hay que hacerle @Override para mostrar nuestro propio texto.

¿Como lo hacemos?, únicamente como he dicho, un @Override a nuestra función «toString» de la clase, devolviendo el texto que nostros queramos mostrar al momento de autocompletar.

@Override
public String toString() {
    return "Texto de autocompletado";
}

Ejemplo práctico

Imaginemos que tenemos una clase «Person» que lleva el nombre de la persona y su edad:

public class Person {
    
    private String name;
    private int age;

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public int getAge() {
        return age;
    }

    @Override
    public String toString() {
        return this.name;
    }
    
}

Para agregarlo a nuestro TextAutoCompleter usamos la siguiente forma:

TextAutoCompleter textAutoCompleter = new TextAutoCompleter(jTextField1);
textAutoCompleter.addItem(new Person("Marco", 25));

That’s all!! ( si, de nuevo XD )

Captura de pantalla 2014-06-24 a la(s) 18.58.16Al momento que el usuario seleccione su item, recuerden que tenemos tanto el callback como getItemSelected() lo que nos devolverá directamente el Object representante de ese Person que creamos. Por lo que para usarlo como Person tendrás que castear el objeto devuelto para usar las funciones de person:

Person personSelected = (Person) getItemSelected();
System.out.println(personSelected.getAge()); // Imprime 25

Debido a que puedes ingresar objetos del tipo que tu quieras, es posible que si quieres controlar un poco más esto debas comprobar si el objeto regresado es del tipo que tu esperabas recibir (recuerda que puede devolver null), por lo que si ingresas objetos de diferentes tipos te sugiero que uses «instanceof«:

Object itemSelected = textAutoCompleter.getItemSelected();
if (itemSelected instanceof Person) {
    System.out.println(((Person) itemSelected).getAge()); // Imprime 25
}
else {
    System.out.println("El item es de un tipo desconocido");
}

Y eso es todo ( ahora en español 😀 ), listo para usarse.

Recordar que es una versión BETA por lo que pueden haber algunos bugs (hasta ahora, no hay bugs conocidos) y yo seguiré trabajando en esta librería, la versión anterior será completamente borrada de la faz del servidor XD ya que los cambios han sido regulares y solo seguiré dando soporte a esta versión y posteriores.

Un gran saludo a todos y gracias por sus sugerencias y comentarios.

Cambios con respecto a la versión 2.0

  • Solo ha sido corregido un error en el cual, al dar click en un item el callback devolvía un String en vez del objeto esperado.

Cambios con respecto a la versión 1

  • Puedes agregar un conjunto de items (ArrayList) en una sola llamada.
  • Puedes agregar un conjunto de items (Array) en una sola llamada.
  • Puedes eliminar items por referencia de objetos.
  • Puedes eliminar todos los items para evitar que siga apareciendo el autocompletado.
  • Puedes seleccionar un item dando clic en él, y automáticamente se rellenará el JTextField.
  • Puedes obtener el objeto seleccionado actualmente.
  • Se puede verificar la existencia de un objeto por referencia.
  • Se puede verificar la existencia de un objeto por valor.
  • Se puede obtener un objeto buscándolo por valor en la lista de items.
  • Puedes ingresar cualquier tipo de objeto a la lista de items.
  • Puedes generar un callback para el momento en que el usuario seleccione un item y realizar acciones.

Bugs conocidos

Ninguno

Publicidad

[wp_ad_camp_1]

 

Categorías

Etiquetas