sábado, 4 de febrero de 2012

Guardar información en Base de Datos #Android

Ahora vamos a almacenar lo que recogemos de la pantalla que hicimos en el otro ejemplo aquí y que os muestro a continuación y lo vamos a guardar en base de datos.

Android usa SQLite como motor de base de datos. Se trata de un pequeño motor de base de datos que es usado en muchas aplicaciones o dispositivos como iPhones, Skype, Solaris, Mac OS X, etc. Una base de datos de SQLite es simplemente un archivo que puede ser movido de máquina o de dispositivo y seguirá funcionando sin problemas

Para poder hacer que cuando demos al botón guardar se almacene en base de datos necesitamos varios archivos que vamos a ir explicando a continuación. Primero necesitamos una interfaz con el nombre que le queremos dar a la base de datos y alguna información más. En mi caso llamé a esta clase Constants.java:



Simplemente son variables que usaremos, por ahora, en la clase que maneja la creación de la base de datos. El fichero es algo como lo que sigue.
import android.provider.BaseColumns;

public interface Constants extends BaseColumns {
   public static final String TABLE_NAME = "meetingcost";

   // Columns in the Events database
   public static final String NOMBRE= "nombre";
   public static final String APELLIDOS = "apellidos";
   public static final String COSTEHORA = "costehora";
}
Ahora viene la clase que gestiona la creación y posteriores modificaciones de la base de datos. En mi caso la llamé PersonData.java y tiene que extender de SQLiteOpenHelper. 
import static android.provider.BaseColumns._ID;
import static org.development.meetingCost.Constants.TABLE_NAME;
import static org.development.meetingCost.Constants.NOMBRE;
import static org.development.meetingCost.Constants.APELLIDOS;
import static org.development.meetingCost.Constants.COSTEHORA;
import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;

public class PersonData extends SQLiteOpenHelper {
   
   private static final String DATABASE_NAME = "meetingCost.db";
   private static final int DATABASE_VERSION = 1;

   /** Constructor de la clase */
   public PersonData(Context ctx) {
      super(ctx, DATABASE_NAME, null, DATABASE_VERSION);
   }
  
   /** La primera vez que entremos se creará el archivo */
   @Override
   public void onCreate(SQLiteDatabase db) {
      db.execSQL("CREATE TABLE " + TABLE_NAME + " (" + _ID
            + " INTEGER PRIMARY KEY AUTOINCREMENT, " + NOMBRE + " TEXT," + APELLIDOS + " TEXT,"
              + COSTEHORA + " INTEGER );");
   }

   @Override
   public void onUpgrade(SQLiteDatabase db, int oldVersion,
         int newVersion) {
      db.execSQL("DROP TABLE IF EXISTS " + TABLE_NAME);
      onCreate(db);
   }
}

Como vemos, estamos haciendo un import static de una variable que no nos hemos definido nosotros llamada _ID. Notar que estamos importandola de la misma clase que extendimos en Constant.java, de la clase BaseColumns. Además tenemos el constructor al que le pasamos el nombre de la tabla y el número de versión de la base de datos y dos métodos que sobrescribimos de SQLiteOpenHelper como son onCreate y onUpgrade. Estos se encargan de la creación de la base de datos y de manejar las actualizaciones en caso de que deseemos hacer cambios de versión de base de datos, por ejemplo si añadimos tablas o columnas. En el caso de onCreate estamos creando una cadena para mediante DDL (Data Definition Language) proceder a la creación de la tabla.

Y ya por fin la clase en la que recogemos lo que nos viene de los EditText y lo metemos en la base de datos.En mi caso, la clase la llamé NewPerson.java

import android.app.Activity;
import android.content.ContentValues;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.EditText;
import android.widget.TextView;
import static android.provider.BaseColumns._ID;
import static org.development.meetingCost.Constants.TABLE_NAME;
import static org.development.meetingCost.Constants.NOMBRE;
import static org.development.meetingCost.Constants.APELLIDOS;
import static org.development.meetingCost.Constants.COSTEHORA;

public class NewPerson extends Activity  {
  
    String nombre,apellidos;
    int costehora;
    EditText nombre_edit, apellidos_edit, costehora_edit;
  
    private PersonData person;
  
    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.newperson);
     
        //Inicializamos person
        person = new PersonData(this);
      
        //Asociamos con los EditText del xml  
        nombre_edit = (EditText) findViewById(R.id.nombre_edit);
        apellidos_edit = (EditText) findViewById(R.id.apellidos_edit);
        costehora_edit = (EditText) findViewById(R.id.costehora_edit);
    }
  
    public void guardar(View view) {
      
        nombre = nombre_edit.getText().toString();
        apellidos = apellidos_edit.getText().toString();
        costehora = Integer.valueOf(costehora_edit.getText().toString());
        try{
            addperson(nombre,apellidos,costehora);
        }
        finally{
            person.close();
        }
        finish();
    }
  
    public void addperson (String nombre, String apellidos, int costehora)
    {
        SQLiteDatabase db = person.getWritableDatabase();
        ContentValues values = new ContentValues();
        values.put(NOMBRE, nombre);
        values.put(APELLIDOS, apellidos);
        values.put(COSTEHORA, costehora);
        db.insertOrThrow(TABLE_NAME, null, values);      
    } 
}
Podemos ver como importamos de nuevo las variables de Constant.java. Con private PersonData person; nos creamos un objeto que nos posibilita manejar la base de datos. Tenemos que inicializarlo con person = new PersonData(this). Entonces en el evento del botón leemos lo que tenemos en los EditText
nombre = nombre_edit.getText().toString();
apellidos = apellidos_edit.getText().toString();
costehora = Integer.valueOf(costehora_edit.getText().toString());
Llamamos pues al método que nos va a añadir la persona en cuestión, pero tenemos que meterlo entre un try y finally para que si peta no quede la conexión con la base de datos abierta.
try{
       addperson(nombre,apellidos,costehora);
}
finally{
      person.close();
}

El método addperson al que le pasamos las variables, abre un conector con la base de datos de lectura y escritura con

SQLiteDatabase db = person.getWritableDatabase();
crea el ContentValue donde añadiremos los valores que hemos recogido de los EditText
values.put(NOMBRE, nombre);
values.put(APELLIDOS, apellidos);
values.put(COSTEHORA, costehora);
Y por último ejecuta el insert:

db.insertOrThrow(TABLE_NAME, null, values);

Eso es todo amigos, ya tenemos nuestra aplicación funcionando contra base de datos. Me falta aprender como leer de ella, os lo iré contando por aquí. Os dejo el newperson.xml para que sea mas fácil.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical"  
    android:background="@color/background"
    >
    <LinearLayout
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:orientation="vertical"
            android:paddingLeft="3dip"
            android:paddingRight="3dip" 
            >
            <TextView android:id="@+id/nombre"
                    android:layout_width="fill_parent"
                    android:layout_height="wrap_content"
                    android:paddingLeft="3dip"
                    android:text="@string/nombre_text"
                    />
            <EditText android:id="@+id/nombre_edit"
                    android:layout_width="fill_parent"
                    android:layout_height="wrap_content"
                    android:paddingLeft="3dip"
                     />
            <TextView android:id="@+id/apellidos"
                    android:layout_width="fill_parent"
                    android:layout_height="wrap_content"
                    android:text="@string/apellidos_text"
                    android:paddingLeft="3dip"
                    />
            <EditText android:id="@+id/apellidos_edit"
                    android:layout_width="fill_parent"
                    android:layout_height="wrap_content"
                    android:paddingLeft="3dip"
                    />
            <TextView android:id="@+id/costehora"
                    android:layout_width="fill_parent"
                    android:layout_height="wrap_content"
                    android:text="@string/costehora_text"
                    android:paddingLeft="3dip"
                    />
         </LinearLayout>
         <LinearLayout
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:orientation="horizontal"
            android:paddingLeft="3dip"
            android:paddingRight="3dip" 
            >
            <EditText
                android:id="@+id/costehora_edit"
                android:layout_width="100dip"
                android:layout_height="wrap_content"
                android:paddingLeft="3dip"
                android:gravity="left"
                android:inputType="numberDecimal"
                />
            <TextView
                android:id="@+id/euro"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:paddingLeft="6dip"
                android:text="@string/euro"
                />
         </LinearLayout>
         <LinearLayout
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:orientation="horizontal"
            android:paddingLeft="3dip"
            android:paddingRight="3dip"
            android:paddingTop="5dip" 
            >       
         <Button
                android:id="@+id/BtnGuardar"
                android:layout_width="wrap_content"
                android:layout_height="fill_parent"
                android:text="@string/guardar"
                android:onClick="guardar"
                />
         </LinearLayout>
</LinearLayout>


LIBRO RECOMENDADO PARA APRENDER ANDROID

Uno de los libros fundamientales y que recomiendo para aprender Android y llegar a hacer aplicaciones profesionales es: Android 2 Application Developement de Reto Meier




2 comentarios :

  1. Muy didáctico y fácil de comprender.
    Gracias :)

    ResponderEliminar
  2. Muchas gracias, me ha venido muy bien, fácil de entender y de usar.

    ResponderEliminar