miércoles, 11 de septiembre de 2013

Estructura de un proyecto Android

Cuando creamos un nuevo proyecto para Android, ya sea desde eclipse o desde el nuevo Android Studio, se nos crearán una serie de directorios necesarios para posteriormente generar/compilar la aplicación.Vamos a repasar brevemente esa estructura de directorios y nos centraremos en uno de los directorios más importantes a la hora de crear una aplicación: el directorio de recursos.
Estructura de un proyecto Android

1. El directorio /src/

Estructura del directorio src de un proyecto AndroidSerá el encargado de contener todo el código fuente de la aplicación que estamos desarrollando. No solo insertaremos en él controlador de las pantallas (actividades), sino que también colocaremos todas nuestras librerías auxiliares. O demás código Java.








2. El directorio /gen/

Nota: si estamos utilizando Android Studio, el contenido de este directorio esta en /build/source/
Es un directorio que no debemos modificar.  Ni su contenido. Ya que en él, el compilador de Android creará automáticamente  una serie de ficheros dirigidos al control de recursos de la aplicación.  Debemos destacar el fichero R.java (y su clase R) ya que será donde se almacenarán cada uno de los identificadores de cada recurso de la aplicación. Esto incluye contenedores, vistas, cadenas de texto, estilos, imágenes... Cada vez que creemos un recurso, el sdk generará una entrada en este fichero. Donde almacenará el identificador que hayamos dado al recurso y un entero auto-asignado. Gracias a esta clase podremos acceder a los recursos desde el código fuente de la aplicación.

 public final class R {  
   public static final class attr {  
   }  
   public static final class dimen {  
     /** Default screen margins, per the Android Design guidelines.   
      Customize dimensions originally defined in res/values/dimens.xml (such as  
      screen margins) for sw720dp devices (e.g. 10" tablets) in landscape here.  
      */  
     public static final int activity_horizontal_margin=0x7f040000;  
     public static final int activity_vertical_margin=0x7f040001;  
   }  
   public static final class drawable {  
     public static final int ic_launcher=0x7f020000;  
   }  
   public static final class id {  
     public static final int AbsoluteLayout1=0x7f080003;  
     public static final int action_settings=0x7f080005;  
     public static final int button1=0x7f080002;  
     public static final int button2=0x7f080004;  
 …  

3. El directorio /assets/

Este es el directorio destinado a los ficheros de configuración o datos a cargar. Aunque se pueden insertar cualquier tipo de elemento auxiliar necesario para la aplicación. Estos ficheros serán accedidos mediante la ruta al directorio. Como veremos posteriormente, habrá otros ficheros (ciertos tipos) que crearán identificadores para su acceso ya que son pre-compilados. Dependiendo de la aplicación nos puede resultar más apropiado tener recursos que se accedan mediante un identificador o mediante su ruta en el sistema de ficheros y tener más libertad de lectura (al no estar pre-compilados).

4. El directorio /bin/

Los elementos de este directorio, al igual que los elementos de /gen/, son generados automáticamente por el IDE. Por lo que no debemos modificarlos. El compilador utiliza este directorio para preparar los ficheros del proyecto que serán empaquetados para crear la aplicación (.apk). Esto incluye compilar tu código Java en ficheros .class y disponer los recursos (incluyendo imágenes) en una cierta estructura para crear dicho fichero compilado .apk (que es la aplicación).

5. Directorio /res/

Android separa los recursos del código fuente, y para ello los organizaremos en este directorio. Esto facilita el mantenimiento y además permite dar soporte a diferentes configuraciones de idiomas o tamaños de pantalla.
Como se ha comentado en el apartado anterior, cada uno de los recursos que añadamos el sistema crea, de forma automática, un id de recurso dentro de la clase R. Dependiendo del tipo de recurso que estemos añadiendo a la aplicación, se tendrán que distribuir en los siguientes subdirectorios básicos:

A) /res/drawable: Directorio destinado a almacenar los recursos de tipo imagen. Podremos insertar 3 tipos de ficheros:
- Ficheros en bitmap (.png, .jpg o .gif ).
- Ficheros PNG en f ormato Nine-patch (.9.png).
- Ficheros XML con descriptores gráficos (Drawable)

B) /res/layout/: Insertaremos los ficheros XML que especifican las pantallas (lo veremos en posteriores tutoriales) de la interfaz gráfica.

C) /res/anim/: Insertaremos cada uno de los ficheros XML que definen las animaciones tween para las vistas.

D) /res/menu/: Insertaremos los ficheros XML que definen los diferentes menús (de opciones, sub-menus o de contexto) de la aplicación.

E) /res/xml/: Insertaremos los XML que no corresponden a ninguna otra de las demás categorías.

F) /res/raw/: Insertaremos los recursos adicionales, normalmente en formato distinto a XML, que no se incluyan en el resto de directorios de recursos.

G) /res/values/: Cada elemento de cada fichero insertado en este directorio será considerado como un único recurso. Por lo que creará una entrada en la clase R. Estos serán los ficheros que podrán estar presentes en este directorio y cada uno de ellos contendrán las etiqueta XML de apertura y la etiqueta de cierre
:
- arrays.xml donde crearemos arrays de recursos. Por ejemplo podría ser utilizado para una lista de cadenas fijas que aparece en una lista. Como los días de la semana.

 <resources>  
      <array name="textArray">  
           <item>First</item>  
           <item>Second</item>  
           <item>Third</item>  
           <item>Fourth</item>  
           <item>Fifth</item>  
      </array>  
      <array name="daysArray">  
           <item>Monday</item>  
           <item>Tuesday</item>  
           <item>Wednesday</item>  
           <item>Thursday</item>  
           <item>Friday</item>  
           <item>Saturaday</item>  
           <item>Sunday</item>  
      </array>  
 </resources>  

- colors.xml donde definiremos valores de colores.

 <resources>  
     <color name="wh_red">#FF990000</color>  
     <color name="wh_blue_lighter">#FF6E9DC6</color>  
     <color name="wh_blue_light">#FF305581</color>  
     <color name="wh_blue">#FF204571</color>  
     <color name="pressed_whitehouse">#CC204471</color>  
 </resources>  

- dimens.xml donde definiremos medidas.

 <resources>  
    <dimen name="cuadro_texto">160sp</dimen>  
 </resources>  

- strings.xml donde definiremos cadenas de texto que aparecen en la app.

 <resources>  
   <string name="app_name">NotePad</string>  
   <string name="live_folder_name">Notes</string>  
   <string name="title_edit_title">Note title:</string>  
   <string name="title_create">Create note</string>  
   <string name="title_edit">Edit: \"%1$s\"</string>  
   <string name="title_notes_list">Notes</string>  
 </resources>  

- styles.xml donde definiremos estilos para las vistas de la interfaz.

 <resources>  
     <style name="CustomText">  
         <item name="android:textSize">20sp</item>  
         <item name="android:textColor">#008</item>  
     </style>  
 </resources>  

Cada uno de estos recursos se verán en posteriores tutoriales.

Recursos alternativos

Una aplicación Android va a poder ser ejecutada en una gran variedad de dispositivos. Además nuestras aplicaciones tienen que estar preparadas para poder ejecutarse en diferentes idiomas. Con lo que la aplicación se tendría podría adaptar a diferentes configuraciones. Y para ello Android permite el uso de recursos alternativos. Con lo que en tiempo de ejecución detectará la configuración actual del dispositivo y cargará los recursos adecuados.

En el apartado anterior hemos visto una lista de directorios que definen tipos de recursos (layout, values, drawable...). Estos directorios se consideran los recursos por defecto (configuración por defecto). Pero si queremos definir recursos alternativos en Android tenemos que crearlos dentro de directorios con sufijos. Por lo tanto tanto los recursos alternativos los colocaremos en directorios al mismo nivel que los directorios de los recursos por defecto. Y el nombre de estos directorios alternativos estará compuesto por el nombre del recurso por defecto (de la citada lista anterior) y el sufijo que especifica el recurso alternativo.

Casos comunes de uso:

1. Imágenes alternativas 

La densidad de pantalla mide la cantidad de píxeles en un área determinada. Este termino también es referido como dpi (dots per inch) o píxeles por pulgada. Si el dispositivo tiene una resolución elevada en una pantalla de poco tamaño físico, tendrá un valor de dpi muy elevado.  Por lo tanto es conveniente proporcionar diferentes imágenes de diferente calidad dependiendo de la citada densidad de la pantalla del dispositivo.
Android usa 4 límites de densidad de pantalla. Por lo tanto disponemos de 4 sufijos para crear los recursos alternativos:
A) ldpi. Recursos para densidades de pantalla de 120dpi.
B) mdpi. Recursos para densidades de pantalla de 160dpi.
C) hdpi. Recursos para densidades de pantalla de 240dpi.
D) xhdpi. Recursos para densidades de pantalla de 320dpi.

Ejemplo:

 res/drawable/    
     icon.png  
     background.png    
 res/drawable-hdpi/   
     icon.png  
     background.png   

2. Interfaz alternativa

Es posible que dependiendo del tipo de pantalla queramos que se muestre una interfaz u otra. Imagina que en pantallas grandes queremos que la interfaz aparezca más completa. Para especificar 'layouts' (pantallas de interfaz gráfica) alternativas, hasta Android 3.2 se utilizaban 4 tipos de tamaños de pantalla para recursos alternativos de tipo 'layout': small, normal, large, y xlarge:
A) xlarge tiene al menos 960dp x 720dp
B) large tiene al menos 640dp x 480dp
C) normal  tiene al menos 470dp x 320dp
D) small tiene al menos 426dp x 320dp

Ejemplo:

 res/layout/my_layout.xml              // layout para pantalla normal  
 res/layout-small/my_layout.xml       // layout para pantalla pequeña  
 res/layout-large/my_layout.xml      // layout para pantalla grande  

Sim embargo, esta notación quedó obsoleta con la llegada de Android 3.2. Ya que la variedad de pantallas hizo que fuera poco recomendable el uso de grupos de tamaño de pantalla generalizados (pequeña, grande, extragrande...). Por lo que apareció la notación swdp. Donde se especifica la anchura mínima disponible en pantalla. 
Es importante el termino de área disponible ya que Android puede utilizar elementos de pantalla  que hagan que no toda la pantalla este disponible para tu interfaz. Evidentemente me refiero a la barra de estado de la parte superior de la pantalla (iconos de batería,red...) o la barra del sistema en la parte inferior de la pantalla.

Ejemplo:

 res/layout/main.xml  
 res/layout-sw700dp/main.xml  

NOTA: dp (Density-independent Pixels). Es una unidad abstracta basada en la densidad física de la pantalla. En una pantalla con una densidad de 160 dpi podemos decir que 1dp es aproximadamente un px. Si luego el dispositivo tiene otra densidad, se realizará la correspondiente regla de tres. Por lo que si una pantalla tiene mayor densidad, el número de píxeles necesarios para dibujar 1dp es escalado superiormante mediante un factor apropiado. Usar esta medida en vez de usar los píxeles de la pantalla es una solución para hacer que las dimensiones de los elementos de la interfaz gráfica cambien de tamaño adecuadamente con las diferentes densidades de pantalla existentes.

3. Aplicación multi-idioma

Para una aplicación multi-idioma sería necesario incluir recursos de tipo cadena (string.xml) para cada idioma que tenga la aplicación. El idioma es definido por el código de lenguaje  ISO 639-1 compuesto de dos letras. Seguido opcionalmente de los caracteres “-r” y por las dos letras del código  ISO 3166-1-alpha-2  que indica la región del idioma.
Por ejemplo, si queremos traducir nuestra aplicación al inglés, español y francés. Siendo el primer idioma el usado por defecto, crearíamos tres versiones del fichero strings.xml y lo guardaríamos en los siguientes tres directorios:

 res/values/strings.xml  
 res/values-es/strings.xml  
 res/values-fr/strings.xml  

4. Orientación de pantalla

Si queremos que la interfaz sea diferente cuando el usuario tiene la pantalla en modo apaisado deberemos proporcionar dos configuraciones dependiendo de la orientación de la pantalla. Las dos orientaciones son portrait (vertical) y landscape (horizontal)

 /res/layout/main_layout.xml  
 /res/layout-port/main_layout.xml  
 /res/layout-land/main_layout.xml  

Evidentemente la lista de sufijo es larga y variable dependiendo del tipo de recurso alternativo. Por lo que lo mejor es ver la documentación oficial de Google:

http://developer.android.com/guide/topics/resources/providing-resources.html
http://developer.android.com/guide/practices/screens_support.html
http://developer.android.com/training/multiscreen/screendensities.html

Nota: Por defecto, el IDE (Eclipse o Android Studio) es posible que cree alguno de estos directorios alternativos vacíos. Pero si no es el caso y los necesitamos,  simplemente los crearemos manualmente.
Además si se crean recursos bajo un sufijo inapropiado serán ignorados. Provocando error si no hay directorio con recursos por defecto.


Entradas relacionadas

Conceptos básicos de Android

No hay comentarios:

Publicar un comentario