En éste artículo quiero comparar lo que supone crear una aplicación sencilla para un dispositivo Android, con dos diferentes herramientas para el desarrollo de "App's": Android Studio (exclusiva de la plataforma y gratuita) y Omnis Studio (multi-plataforma y de pago). Queremos que la aplicación sea capaz de crear una base de datos SQLite en el dispositivo, con tres campos: ID, Nombre y Apellido y cuatro botones para iteracción con el usuario: "Buscar", "Insertar", "Actualizar" y "Borrar", su aspecto y código necesarios se muestran a continuación:
Aspecto con Android Studio
Aspecto con Omnis Studio
Para añadir los elementos de la "interface" en ambos casos sólo ha sido necesario arrastrar y soltar componentes desde sus respectivas paletas, pero a la hora de girar el dispositivo, "Android Studio" a requerido programación adicional, mientras que con "Omnis Studio" no ha sido necesario incluir programación alguna.
A continuación indicaremos el código que ha sido necesario escribir en cada caso, empezando por la creación de la BBDD SQLite en el dispositivo:
Creación de la BBDD en Android Studio
public class Estructura_BBDD {
private Estructura_BBDD() {}
public static final String TABLE_NAME = "datosPersonales";
public static final String NOMBRE_COLUMNA1 = "id";
public static final String NOMBRE_COLUMNA2 = "nombre";
public static final String NOMBRE_COLUMNA3 = "apellido";
public static final String SQL_CREATE_ENTRIES =
"CREATE TABLE " + Estructura_BBDD.TABLE_NAME + " (" +
Estructura_BBDD.NOMBRE_COLUMNA1 + " INTEGER PRIMARY KEY," +
Estructura_BBDD.NOMBRE_COLUMNA2 + " TEXT," +
Estructura_BBDD.NOMBRE_COLUMNA3 + " TEXT)";
public static final String SQL_DELETE_ENTRIES =
"DROP TABLE IF EXISTS " + Estructura_BBDD.TABLE_NAME;
}
Creación de la BBDD en Omnis Studio
Do $cinst.$sqlobject.$execute('CREATE TABLE Empleados (Id INTEGER UNIQUE, Nombre TEXT, Apellido TEXT)')
Returns IDcreatetable
Un apunte antes de continuar en cuanto a la programación asociada a cada botón, en el caso de "Andriod Studio" ha sido necesario añadir código adicional para poner los botones en modo "OnClickListener", cosa totalmente innecesaria en "Omnis Studio", salvando ésta diferencia, (no trivial) indicamos el asociado a cada botón:
Botón "Buscar" en Android Studio
botonBuscar.setOnClickListener(new View.OnClickListener() {
@Override public void onClick(View v) {
SQLiteDatabase db = helper.getReadableDatabase();
String[] projection = {
Estructura_BBDD.NOMBRE_COLUMNA2,
Estructura_BBDD.NOMBRE_COLUMNA3 };
String selection = Estructura_BBDD.NOMBRE_COLUMNA1 + " = ?";
String[] selectionArgs = { textoId.getText().toString() };
try {
Cursor c = db.query(
Estructura_BBDD.TABLE_NAME,
projection,
selection,
selectionArgs,
null,
null,
null
);
c.moveToFirst();
textoNombre.setText(c.getString(0));
textoApellido.setText(c.getString(1));
}catch (Exception e){
Toast.makeText(getApplicationContext(),"No se han encontrado registros.", Toast.LENGTH_LONG).show();
}
}
});
Botón "Buscar" en Omnis Studio
On evClick
Do lRow.$define(i_ID;i_Nombre;i_Apellido)
Do lRow.$assigncols(i_ID;i_Nombre;i_Apellido)
Do $cinst.$sqlobject.$selectfetch("Select * from Empleados where Id = @[i_ID]";lRow;kFetchAll)
Returns IDselectfetch
Botón "Insertar" en Android Studio
botonInsertar.setOnClickListener(new View.OnClickListener() {
@Override public void onClick(View v) {
SQLiteDatabase db = helper.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(Estructura_BBDD.NOMBRE_COLUMNA1, textoId.getText().toString());
values.put(Estructura_BBDD.NOMBRE_COLUMNA2, textoNombre.getText().toString());
values.put(Estructura_BBDD.NOMBRE_COLUMNA3, textoApellido.getText().toString());
long newRowId = db.insert(Estructura_BBDD.TABLE_NAME, null, values);
Toast.makeText(getApplicationContext(),"Insertado ID: " + newRowId, Toast.LENGTH_LONG).show();
}
});
Botón "Insertar" en Omnis Studio
On evClick
Do lRow.$define(i_ID;i_Nombre;i_Apellido)
Do lRow.$assigncols(i_ID;i_Nombre;i_Apellido)
Do $cinst.$sqlobject.$insert("INSERT INTO Empleados (Id, Nombre, Apellido) VALUES (@[i_ID],@[i_Nombre],@[i_Apellido])";lRow)
Returns IDinsert
Botón "Actualizar" en Android Studio
botonActualizar.setOnClickListener(new View.OnClickListener() {
@Override public void onClick(View v) {
SQLiteDatabase db = helper.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(Estructura_BBDD.NOMBRE_COLUMNA2, textoNombre.getText().toString());
values.put(Estructura_BBDD.NOMBRE_COLUMNA3, textoApellido.getText().toString());
String selection = Estructura_BBDD.NOMBRE_COLUMNA1 + " LIKE ?";
String[] selectionArgs = { textoId.getText().toString() };
int count = db.update(
Estructura_BBDD.TABLE_NAME,
values,
selection,
selectionArgs);
Toast.makeText(getApplicationContext(),"Registro actualizado.", Toast.LENGTH_LONG).show();
}
});
Botón "Actualizar" en Omnis Studio
On evClick
Do lRow.$define(i_ID;i_Nombre;i_Apellido)
Do lRow.$assigncols(i_ID;i_Nombre;i_Apellido)
Do $cinst.$sqlobject.$update("UPDATE Empleados SET Nombre=@[i_Nombre], Apellido=@[i_Apellido] where Id = @[i_ID]";lRow;lRow)
Returns IDupdate
Botón "Borrar" en Android Studio
botonBorrar.setOnClickListener(new View.OnClickListener() {
@Override public void onClick(View v) {
SQLiteDatabase db = helper.getWritableDatabase();
String selection = Estructura_BBDD.NOMBRE_COLUMNA1 + " LIKE ?";
String[] selectionArgs = { textoId.getText().toString() };
db.delete(Estructura_BBDD.TABLE_NAME, selection, selectionArgs);
Toast.makeText(getApplicationContext(),"Registro borrado.", Toast.LENGTH_LONG).show();
textoId.setText("");
textoNombre.setText("");
textoApellido.setText("");
}
});
Botón "Borrar" en Omnis Studio
On evClick
Do lRow.$define(i_ID;i_Nombre;i_Apellido)
Do lRow.$assigncols(i_ID;i_Nombre;i_Apellido)
Do $cinst.$sqlobject.$delete("DELETE FROM Empleados WHERE Id = @[i_ID]";lRow)
Returns IDdelete
Notemos que en el código Android se ha evitado deliberadamente la incorporación del código necesario para tratar las excepciones, salvo en el caso del botón "Buscar" donde se usa un "try-catch", para controlar el hecho que pueda no encontrarse el registro buscado. Omnis predefine un método para tratar las excepciones denominado "$sqldone", a continuación mostramos un ejemplo de uso:
; Se ejecuta cada vez que concluye una operación SQL (asíncrona)
; Abandona el método con el mensaje de error, si se produce.
Do $cinst.$sqlobject.$getlasterrortext() Returns lErr
If lErr<>"OK"
Calculate i_ID as 0
Calculate i_Nombre as ''
Calculate i_Apellido as ''
Do $cinst.$showmessage(lErr;"Error")
Quit method
End If
; Se ejecuta uno u otro proceso según el resultado
Switch pID
Case IDselecttables
If pResult.$linecount=0
Do $cinst.$creaTabla() ;; Si no existe se crea la tabla
End If
Case IDselectfetch
Calculate lRows as pResult.$linecount
If lRows=0
Calculate i_ID as 0
Calculate i_Nombre as ''
Calculate i_Apellido as ''
Do $cinst.$showmessage("No existe el ID";"Respuesta")
Quit method
End If
Calculate i_Nombre as pResult.C2
Calculate i_Apellido as pResult.C3
Case IDcreatetable
Do $cinst.$showmessage("Tabla creada";"Respuesta")
Case IDinsert
Do $cinst.$showmessage("Inserción realizada";"Respuesta")
Case IDdelete
Calculate i_ID as 0
Calculate i_Nombre as ''
Calculate i_Apellido as ''
Do $cinst.$showmessage("Entrada borrada";"Respuesta")
Case IDupdate
Do $cinst.$showmessage("Actualización realizada";"Respuesta")
Default
Calculate i_ID as 0
Calculate i_Nombre as ''
Calculate i_Apellido as ''
Do $cinst.$showmessage("Error inesperado")
End Switch
En ocasiones los programadores y compañías dedicadas al desarrollo y mantenimiento de software, nos preguntamos ¿Porqué pagar por una herramienta, cuando existe otra que es gratis?, pero definitivamente puedo decir que en muchas ocasiones lo "barato" sale caro. Omnis Studio permite el desarrollo de aplicaciones para dispositivos móviles (Android, iOS y Windows), aplicaciones de escritorio (MacOS, Windows, Linux) o aplicaciones para la Web, sin necesidad de usar más herramientas que el propio Omnis Studio. El ejemplo de eficacia que hemos expuesto, compara una herramienta que sólo permite el desarrollo para dispositivos Android, por lo que el código resultante no podrá ser ejecutado en (por ejemplo) un dispositivo iOS, en cambio el código Omnis, puede ser ejecutado sin cambio alguno, sobre dispositivos iOS o Windows 10.
Juzguen ustedes mismos sobre si lo "barato" sale caro, llevo trabajando con Omnis Studio por unos 20 años ya, período durante el que las tecnologías han sufrido muchos y diferentes cambios que han hecho, al mismo tiempo, aparecer y desaparecer lenguajes de programación, pero Omnis Studio a sabido adaptarse a los tiempos y a tiempo con gran lujo y esmero.
Programar con Omnis Studio hace que me guste éste trabajo.