Solución al reto Capture The Flag de #CPMX6

dc-flag

Otro año, otro campus party al que asisto. En esta ocasión me di tiempo de asistir a varias conferencias y workshops que se impartieron durante el evento (y no solo pasármela en la zona gamer :p), además, al igual que en el evento pasado también estuve participando en el reto de seguridad que fue organizado por el Instituto Tecnológico Superior de Atlixco.

El wargame estuvo muy divertido (horas y horas de diversión) y me ayudo a conocer a mas colegas de la seguridad informática durante el evento, bueno sin mas preámbulo comienzo a explicar en que consistía cada uno de los retos y como fue que llegue a la solución.

Reto #1

Comenzando con lo básico, en el reto uno nos daban la IP donde había alojada una pagina web, la pagina tenia varias pestañas y la URL de cada una de las secciones tenia una estructura como la siguiente:

http://52.11.240.182/index.php?file=contacto.html

Jugando un poco con el parámetro file vemos que el sitio tiene una vulnerabilidad de Local File Inclusión. Utilizando la herramienta que desarrollo mi amigo @lightOS para explotar este tipo de vulnerabilidad https://github.com/lightos/Panoptic es posible automatizar el proceso y obtener archivos importantes del servidor, por ejemplo:

http://52.11.240.182/index.php?file=../../../../../../../../../../etc/apache2/envvars
http://52.11.240.182/index.php?file=../../../../../../../../../../etc/logrotate.d/apache2

ctf_cpmx_1

Sin embargo, el reto es mas sencillo que eso, en el archivo robots.txt (corrimos un dirbuster al sitio web) vimos que hay un archivo llamado dir.txt, revisando su contenido nos encontramos:

$ ls -l
html/
secreto.txt

secreto.txt, un archivo interesante, entonces aprovechamos el Local File Inclusion que teníamos y cargamos este archivo.

http://52.11.240.182/index.php?file=../secreto.txt

ctf_cpmx_2

67d71184adf4b700d5cadce0c9bfdcc7e91d01cb <- esta es la bandera del reto :)

Reto #2

El segundo reto nos daba como pista “DNS record types” junto con un dominio gcs-ibero.com, si es la primera vez que escuchan de record types en el siguiente enlace podrán encontrar mas información https://en.wikipedia.org/wiki/List_of_DNS_record_types

Entendiendo un poco mas sobre el tema comenzamos a hacer lookup a los distintos records hasta que llegamos al record TXT http://mxtoolbox.com/TXTLookup.aspx y encontramos la solución.

ctf_cpmx_3

4db055f7386c6bb8a14b5883417a4b61 <- es la bandera de este reto

Reto #3

El reto numero 3 es bastante interesante, al inicio nos dan una captura de paquetes, un archivo .pcapng que procedemos a visualizar con wireshark (si no han escuchado de el o no saben utilizarlo ahora es el momento https://www.wireshark.org/)

ctf_cpmx_4

Como podemos observar hay partes de la lectura que están cifradas (ahí se ve una negociación TLS), por suerte entre los archivos que nos daban también venia una llave privada (llave.pem) que nos servirá para descifrar esas partes. En Wireshark nos vamos al menú Edit > Preferences y en la siguiente ventana del lado derecho seleccionamos Protocol > SSL

ctf_cpmx_5

Damos clic en RSA keys list y agregamos una nueva llave, nos pedirá algunos datos como dirección IP, puerto, protocolo y la llave privada (llave.pem), haciendo un análisis de lo que teníamos anteriormente:

En la captura tenemos dos direcciones IP:

  • 192.168.15.7 (dirección local)
  • 52.27.174.204 (dirección remota a la que nos estamos comunicando)

De igual forma, viendo la captura, sabemos que la comunicación con la maquina remota fue atreves de ftp utilizando el puerto 21 (por default) por lo tanto escribimos esos datos y adjuntamos la llave privada como se muestra en la siguiente imagen.

ctf_cpmx_6

ctf_cpmx_7

Damos ok a las ventanas y Wireshark nos debería de mostrar el trafico descifrado. Para analizar mas rápido vamos a pasar la captura a un archivo de texto, File > Print. Seleccionamos Plaint Text y Output to file.

ctf_cpmx_8

Abrimos el archivo generado con nuestro editor de texto favorito y empezamos a buscar por cadenas interesantes como password, pass, secret, etc

ctf_cpmx_9

La bandera de este reto es: ZXASDF727fa2raSFP!FRA-,aSF

Reto #4

El reto cuatro era facil y consistía en un reto criptográfico, al principio nos daban una cadena de texto que parecía no tener sentido y en mi experiencia la mayoría de los retos de este tipo son cifrados caesar. Con la ayuda de google buscamos un sitio para resolver este tipo de cifrados de sustitución por desplazamiento http://www.xarg.org/tools/caesar-cipher/

Introducimos el texto cifrado y obtenemos la respuesta :)

ctf_cpmx_10

Mas sabe el diablo por viejo que por diablo <- esta es la bandera del reto

Reto #5

Tip: la bandera es el md5 del contenido del archivo zip.

El reto nos da un archivo comprimido en formato zip, que tiene la particularidad que al descomprimirlo nos genera otro archivo zip, y después otro y otro mas, parecería nunca acabar, lo primero que hice fue abrir el archivo con un editor hexadecimal solo para corroborar lo que ya sabíamos.

ctf_cpmx_11

Del lado derecho podemos ver los nombres de los archivos que se van generado: 617.zip, 293.zip, 558.zip, 689.zip, etc. (son bastantes) así que lo mas fácil es realizar un script para descomprimir todo lo que haya que descomprimir recursivamente xd, yo utilice un comando en bash.

$ while [ "`find . -type f -name '*.zip' | wc -l`" -gt 0 ]; do find -type f -name "*.zip" -exec unzip -- '{}' \; -exec rm -- '{}' \;; done

ctf_cpmx_11
Al final del ultimo Zip nos encontramos con un archivo de texto llamado flag.txt, calculamos su hash md5 y obtenemos la bandera :)

$ md5sum flag.txt
da44354d0de702b12934235a51094813 flag.txt

da44354d0de702b12934235a51094813 <- es la bandera del reto (el hash)

Reto #6

El reto 6 nos dio bastante dolor de cabeza a los participantes, a pesar de que su solución era bastante sencilla, en el reto nos daban una dirección IP y se nos pedía utilizar nmap https://nmap.org/ (para escaneo de puertos y servicios) y Hydra para realizar ataques de fuerza bruta, hubo bastante confusión puesto que a aparentemente el servidor solo tenia corriendo un servicio de ssh y fue lo que intente atacar.

El servidor ssh no soportaba autenticación mediante usuario y contraseña por lo que termine creando script en bash, python, etc y probando diferentes tipos de exploits sin éxito :(. Me di cuenta que el primer escaneo que realice no fue un barrido completo de puertos, así que volví a escanear nuevamente esta vez asegurándome de revisar todos los puertos.

$ nmap –sV –p- --version-all --max-retries 1–d IP
...
...
333/tcp open ftp vsftpd 2.0.8 or later
...
...
Service detection performed. Please report any incorrect results at http://nmap.org/submit/ .
# Nmap done at Fri Jul 24 18:08:31 2015 -- 1 IP address (1 host up) scanned in 6.26 seconds

Y ahora si encontramos que en el puerto 333 había un servidor de ftp corriendo.
Empezamos a analizar el servicio, tratamos de conectarnos y vemos como responde.

Intentando conectarse con el usuario admin

$ ftp admin @ 52.26.250.230 333
Connected to 52.26.250.230.
220 Welcome to FTP service.
331 Please specify the password.
Password: 
530 Login incorrect.
ftp: Login failed
ftp> exit
221 Goodbye.

Intentando conectarse con el usuario root

$ ftp root @ 52.26.250.230 333
Connected to 52.26.250.230.
220 Welcome to FTP service.
530 Permission denied.
ftp: Login failed
ftp> exit
221 Goodbye.

El usuario admin parece ser valido (vean como las respuestas son diferentes), pero no tenemos la contraseña, utilizaremos hydra y un buen diccionario, al final y después de un par de horas obtuvimos la contraseña :)

$ hydra -t 1 -l admin -P default_pass_for_services_unhash.txt -vV -s 333 52.26.250.230 ftp

ctf_cpmx_12

La bandera de esto reto era x.x: 12345678 (máximum trolling)

Reto #7

Otro reto bastante sencillo, aquí nos dan una foto y se nos pide encontrar la marca del dispositivo con el que fue tomado la fotografía.

Utilizamos cualquier extractor de metadatos online http://regex.info/exif.cgi y obtenemos que la foto fue tomada con una dispositivo Huawei

ctf_cpmx_13

La bandera del reto es: Huawei

Reto #8

En el reto 8 nos dan un archivo .iv que podemos crackear utilizando aircrack-ng, para quien no sepa aircrack es un software incluido en la distribución de seguridad Kali que sirve para crackear redes inalámbricas http://www.aircrack-ng.org/

En nuestro kali utilizamos aircrack-ng para procesar el archivo .iv del reto:

$ aircrack-ng captura.iv

ctf_cpmx_14

Y obtenemos la contraseña de la red inalámbrica que también es la solución al reto
12345 <- es la bandera de este reto

Reto #9

El ultimo reto del capture the flag consistía en explotar una vulnerabilidad de inyección SQL y obtener la contraseña en texto plano del administrador del sitio. El reto, al inicio nos presenta un sitio web con un catalogo de películas, podemos consultar las películas de un director en especifico con una URL similar a la siguiente:

http://54.68.213.190/busqueda.php?idDirector=1

Esta claro que si queremos inyectar comandos SQL tendremos que empezar por el parámetro idDirector y para hacerlo de una forma mas rápida y automática utilizaremos la herramienta sqlmap http://sqlmap.org/ que viene instalada en nuestro Kali.

$ sqlmap --url=http://54.68.213.190/busqueda.php?idDirector=1 --level=1 --risk=3 --all

ctf_cpmx_15

La herramienta nos hace un dump de la tabla de usuarios y vemos que los passwords son almacenados no en texto plano sino cifrados (probablemente en md5), también observamos que la tabla contiene un campo de salt y un valor que muy seguramente fue utilizado para calcular el hash de la contraseña.

Pues manos a la obra (o mas bien dicho, al teclado), el reto nos pide encontrar la contraseña del usuario maria (que es el administrador del sitio), podemos hacer rápidamente un script para intentar crackear el hash.

<?php 
$salt = "WDUOPALD6N";
$hash = "fa38084963f74741ea1184963fa2cd91";

$handle = fopen("pass2.txt", "r");
if ($handle) {
    while (($line = fgets($handle)) !== false) {
    	
    	$line = str_replace("\n", "", $line);

		if(md5($salt.$line) == $hash || md5($line.$salt) == $hash)
		{
			echo $line . " OK! \n";
			exit(); 
		} else {
			echo $line . ":" . md5($salt.$line) . " Nop\n";
		}   
    }

    fclose($handle);
} else {
    echo "file error \n";
} 

?>

Lo que hace nuestro script es, con la ayuda de un diccionario de 2 millones de contraseñas populares, intentar encontrar cual es el texto plano concatenado al valor salt del hash que obtenemos, para cada contraseña de nuestro diccionario calculamos

  • salt + contraseña = hash
  • Contraseña + salt = hash

Y revisamos si tenemos alguna coincidencia.

ctf_cpmx_16

Afortunadamente la contraseña en texto plano se encontraba en nuestro diccionario y la pudimos encontrar :)

La bandera del reto final era: passw0rd1 (era la contraseña numero 795975 en nuestro diccionario)

ctf_cpmx_17

Nos vemos el siguiente año.
Happy hacking :)

Share

Tutorial Material Design en Android #3

Agregando iconos (actions) al ToolBar

Hola lectores programadores :), continuamos con la serie de tutoriales de Material Design en Android, siguiendo con los post anteriores ahora toca agregar algunos elementos a nuestra Toolbar personalizada, pero primero nos encargaremos de un pequeño “bug estético”, actualmente nuestra app luce así y si hacemos tap en el icono superior derecho (3 puntos) veremos que la letra del popupMenu es apenas visible. Corrijamos eso.
popupmenu_bug

Nos vamos a nuestros ya conocidos archivos styles.xml

  • /app/src/main/res/values/styles.xml
  • /app/src/main/res/values-21/styles.xml (api 21)

Y vamos a agregar un nuevo item con nombre popupTheme, quedando de la siguiente forma

values/style.xml

<resources>

    <!-- Base application theme. -->
    <style name="AppTheme" parent="AppTheme.Base">
        <!-- Customize your theme here. -->
    </style>

    <style name="AppTheme.Base" parent="Theme.AppCompat.Light.NoActionBar">
        <item name="colorPrimary">@color/primaryColor</item>
        <item name="colorPrimaryDark">@color/primaryColorDark</item>
        <item name="colorAccent">@color/colorAccent</item>
        <item name="popupTheme">@style/Base.ThemeOverlay.AppCompat.Dark</item>
    </style>

</resources>

values-21/style.xml (api 21)

<?xml version="1.0" encoding="utf-8"?>
<resources>

    <!-- Base application theme. -->
    <style name="AppTheme" parent="AppTheme.Base">
        <item name="android:colorPrimary">@color/primaryColor</item>
        <item name="android:colorPrimaryDark">@color/primaryColorDark</item>
        <item name="android:textColorPrimary">@color/textColorPrimary</item>
        <item name="android:colorAccent">@color/colorAccent</item>
        <item name="android:popupTheme">@style/Base.ThemeOverlay.AppCompat.Dark</item>
    </style>

</resources>

Guardamos y corremos la aplicación de nuevo y ahora veremos algo como lo siguiente, ¿Mucho mejor cierto?

popupmenu_dark

Es posible personalizar aún mas este elemento del ToolBar, estos son algunos de los atributos que podemos utilizar

  • popupMenuStyle
  • textColorPrimary
  • popupAnimationStyle>
  • popupBackground

Se puede personalizar prácticamente cualquier aspecto del menú, por ejemplo:

popupmenu_custom2

Les dejo de tarea hacer su propio menú custom :) y bueno ahora que tenemos resuelta esa parte del popupMenu toca agregar los iconos, en nuestro proyecto de Android Studio, en la carpeta res (resources) dentro del apartado de menú encontramos un archivo llamado menu_main.xml (si por algún motivo no está entonces deberán crearlo /res/menu/menu_main.xml).

Como en todos los tutoriales les dejo la documentación oficial sobre los lineamientos sobre los iconos, sus dimensiones y formas aqui y aca.

Por default nuestro menú solo tiene 1 elemento como podemos ver en el siguiente código

<menu xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    tools:context="com.alevsk.materialdesignapp.MainActivity">
    <item
        android:id="@+id/action_settings"
        android:orderInCategory="100"
        android:title="@string/action_settings"
        app:showAsAction="never" />
</menu>

El elemento item tiene algunos atributos, por ejemplo app:showAsAction puede tomar tres valores:

  • never: No mostrara el icono
  • ifRoom: Si hay espacio mostrara el icono
  • always: Siempre mostrara el icono

android:title es el atributo donde definimos el nombre de la acción (si por ejemplo deciden no mostrar un icono o mostrarlo solo si hay espacio, por default el título de la acción será el que definan con este atributo).

Por el momento vamos a definir 3 acciones (conforme avance esto los remplazaremos), quedando el código del archivo menu_main.xml de la siguiente manera.

<menu xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    tools:context="com.alevsk.materialdesignapp.MainActivity">
    <item
        android:id="@+id/action_search"
        android:icon="@drawable/abc_ic_search_api_mtrl_alpha"
        android:orderInCategory="1"
        android:title="Busqueda"
        app:showAsAction="always" />
    <item
        android:id="@+id/action_copy"
        android:icon="@drawable/abc_ic_menu_copy_mtrl_am_alpha"
        android:orderInCategory="2"
        android:title="Copiar"
        app:showAsAction="always" />

    <item
        android:id="@+id/action_selectall"
        android:icon="@drawable/abc_ic_menu_selectall_mtrl_alpha"
        android:orderInCategory="3"
        android:title="Seleccionar todo"
        app:showAsAction="always" />
</menu>

Corremos la app y veremos algo como esto

toolbar_icons

¿Los iconos no son muy visibles verdad?, podemos arreglar esto rápidamente, el tema por default de nuestra aplicación es texto oscuro sobre fondos claros, esa es la razón por la que los iconos tienen un color oscuro, sin embargo podemos modificar nuestro archivo app_bar.xml e indicar que queremos que esa parte especifica de la app (ToolBar) utilice el tema de textos claros sobre fondos oscuros, así que editamos /app/src/main/res/layout/app_bar.xml y definimos el tema Holo como se muestra a continuación.

<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.Toolbar xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    app:theme="@style/Theme.AppCompat.NoActionBar"
    android:layout_height="wrap_content"
    android:background="@color/primaryColor">

</android.support.v7.widget.Toolbar>

toolbar_icons3

Eso es todo por ahora, en el siguiente tutorial vamos a definir de que va a tratar nuestra app y aprenderemos a implementar desde cero unos de los elementos más poderosos de Android, el NavigationDrawer :) salu2

Share

Tutorial Material Design en Android #2

Definir la ToolBar

Esta es la tercera parte del tutorial desarrollo de apps para Android utilizando Material Design, ahora aprenderemos acerca de como definir la ToolBar de nuestra aplicación, para hacerlo seguiremos 5 sencillos pasos:

  • En el archivo styles.xml utilizaremos Theme.AppCompat.Light.NoActionBar
  • Definiremos un archivo app_bar.xml para nuestra ToolBar
  • Incluiremos ese archivo con la directiva include en nuestro main_activity.xml (la vista de nuestra Activity)
  • En nuestra actividad principal MainActivity.java vamos a crear una instancia de la ToolBar para poder manipularla
  • Por ultimo nos aseguraremos de incluir soporte para dispositivos pre lollipop (api < 21)

toolbars

Antes que nada, como en las ediciones anteriores les recomiendo que se empapen un poco de la teoría de las ToolBars en el siguiente link, ya que Material Design no es solo escribir código y ya, tenemos que apegarnos a ciertos lineamientos que se explican muy bien en la documentación oficial y pues manos a la obra, o manos al código mejor dicho XD.

En nuestro proyecto vamos a nuestro archivo styles.xml que está en app > res > values > styles.xml y remplazamos Theme.AppCompat.Light.DarkActionBar por Theme.AppCompat.Light.NoActionBar quedando el código de la siguiente manera:

noactionbar

Esto lo hacemos para indicar que no vamos a utilizar la ToolBar por defecto que Android maneja, en cambio elegimos no incluir ninguna (al menos no desde el theme que utilizamos), si corremos nuestra aplicación justo ahora tendremos algo como esto.

app_no_toolbar

Sin Toolbar, ¿qué feo se ve no?, ahora solucionaremos eso de la siguiente forma, en la carpeta layout de nuestro proyecto (app > res > layout) vamos a crear un nuevo archivo xml, ya saben, botón derecho New > Layout resource file y le ponemos de nombre app_bar.xml, puede ser cualquier otro nombre pero por convención utilizaremos ese, también en el campo de Root element utilizaremos ToolBar como se muestra en la siguiente imagen.

new_toolbar

Vemos el contenido del archivo recién creado y notamos que Android Studio nos marca un error en el elemento Toolbar XD, el código que les debió haber generado automáticamente es el siguiente:

<?xml version="1.0" encoding="utf-8"?>
<Toolbar xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent" android:layout_height="match_parent">

</Toolbar>

El error, de nuevo, es debido a la versión mínima de api soportada por nuestra aplicación, si no mal recuerdo al crear nuestro proyecto elegimos la api 14 y el control Toolbar es para api 21 por lo que para solucionar esto remplazaremos el código por el siguiente:

<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.Toolbar xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent" android:layout_height="match_parent">

</android.support.v7.widget.Toolbar>

Y el error desaparecerá :) les dejo mas documentación sobre esta maravillosa librería para dar soporte android.support.v7.app

Lo que siguen, en nuestro archivo main_activity.xml vamos a incluir el app_bar.xml que acabamos de crear, para eso lo abrimos y utilizamos la directiva include de la siguiente forma.

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools" 
    android:layout_width="match_parent"
    android:layout_height="match_parent" 
    tools:context="com.alevsk.materialdesignapp.MainActivity">
    
    <include android:id="@+id/app_bar" layout="@layout/app_bar" />

    <TextView android:text="@string/hello_world" android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

</RelativeLayout>

Ok, ahora nos vamos a nuestro archivo MainActivity.java que nos toca escribir el primer código Java del proyecto, lo que haremos aquí será crear una nueva propiedad (variable privada tipo Toolbar) e instanciar la de nuestra vista XML en el método onCreate

public class MainActivity extends ActionBarActivity {

    private Toolbar toolbar;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        toolbar = (Toolbar) findViewById(R.id.app_bar);
        setSupportActionBar(toolbar);
    }

Cuando agregamos la variable tipo Toolbar un error muy común que he observado es el tipo de librería que importa el proyecto, asegúrense que este importando import android.support.v7.widget.Toolbar; de otra manera el proyecto te marcara errores al momento de compilar la apk.

¿Que acabamos de hacer?, ahora lo explico, creamos una nueva variable Toolbar, después creamos la instancia tomando como referencia la que definimos anteriormente en nuestro main_activity.xml y al final utilizamos el método setSupportActionBar para indicarle a Android que vamos a utilizar nuestra propia Toolbar, procedemos a correr la app y vemos lo que pasa.

app_custom_toolbar

:S horrible ¿cierto? veamos que paso aquí y cómo solucionarlo. Cuando definimos nuestra propia Toolbar tenemos que asegurarnos de definir también el ancho y el alto del elemento, ¿recuerdan el link a la documentación oficial que les deje al inicio?, ahora es un buen momento para revisarla, también tenemos que definir el orden en el que se dibujaran los elementos en la pantalla, para eso en main_activity.xml vamos a utilizar una propiedad llamada layout_below en el elemento TextView para indicar que queremos que aparezca debajo de nuestra Toolbar

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context="com.alevsk.materialdesignapp.MainActivity">

    <include
        android:id="@+id/app_bar"
        layout="@layout/app_bar" />

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_below="@+id/app_bar"
        android:text="@string/hello_world" />

</RelativeLayout>

También definimos el color de fondo en nuestro archivo app_bar.xml y cambiamos su altura de match_parent a wrap_content.

<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.Toolbar xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:background="@color/primaryColor">

</android.support.v7.widget.Toolbar>

Guardamos los cambios y corremos la app de nuevo.

app_custom_toolbar2

Listo, mucho mejor :) , pareciera que no avanzamos nada en este tercer tutorial, sin embargo tenemos ya una Toolbar personalizada funcional y esto nos servirá para lo que sigue que será agregar algunos iconos! salu2

Share

Tutorial Material Design en Android #1

Los colores de la aplicación

En el tutorial anterior aprendimos a Crear un nuevo proyecto de Android Material Design, hicimos algunas configuraciones en el archivo AndroidManifest.xml y creamos algunos nuevos estilos en el archivo style.xml.

Pues en esta ocasión vamos aprender a personalizar los colores de nuestra app, tanto del ToolBar / ActionBar como del StatusBar y los demás elementos de la interfaz gráfica. Recomiendo revisen la documentación oficial más a fondo en el siguiente link

Pero en resumen dice lo que explicare a continuación, básicamente tenemos 5 elementos que podemos personalizar por default:

  • colorPrimary
  • colorPrimaryDark
  • colorAccent
  • textColorPrimary
  • windowBackground
  • navigationBarColor

En la siguiente imagen podemos observar a que parte de la interfaz corresponde cada elemento :)

ThemeColors

Ya se imaginan lo que sigue, les recomiendo las paletas de colores de google, por lo pronto elijamos la que sea y comencemos a configurar los valores en nuestra aplicación para ir viendo cómo va quedando.

Es una buena práctica separar los recursos que utilizara la aplicación en varios archivos por lo que dentro de la carpeta values vamos a crear un nuevo archivo colors.xml, si no recuerdan como crear un nuevo archivo de recursos regresen al primero tutorial donde creamos el archivo styles.xml.

Ya con el archivo colors.xml creado vamos a comenzar agregando los colores de nuestra elección, mi archivo quedo con el siguiente contenido.

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <color name="primaryColor">#E91E63</color>
    <color name="primaryColorDark">#C2185B</color>
    <color name="colorAccent">#8BC34A</color>
</resources>

Y mis colores fueron:

color_pallete

Ahora en nuestro archivo styles.xml en donde hicimos la definición de nuestro Tema AppTheme.Base vamos a definir el uso de los colores que acabamos de crear :) de la siguiente forma:

<resources>

    <!-- Base application theme. -->
    <style name="AppTheme" parent="AppTheme.Base">
        <!-- Customize your theme here. -->
    </style>

    <style name="AppTheme.Base" parent="Theme.AppCompat.Light.DarkActionBar">
        <item name="colorPrimary">@color/primaryColor</item>
        <item name="colorPrimaryDark">@color/primaryColorDark</item>
        <item name="colorAccent">@color/colorAccent</item>
    </style>

</resources>

De la misma manera vamos a agregar esas definiciones de color de elementos en el otro archivo styles.xml (el que tenemos para dispositivos con api 21), quedando de la siguiente manera, noten que en estas definiciones estamos añadiendo el prefijo android:

<?xml version="1.0" encoding="utf-8"?>
<resources>

    <!-- Base application theme. -->
    <style name="AppTheme" parent="AppTheme.Base">
        <item name="android:colorPrimary">@color/primaryColor</item>
        <item name="android:colorPrimaryDark">@color/primaryColorDark</item>
        <item name="android:textColorPrimary">@color/textColorPrimary</item>
        <item name="android:colorAccent">@color/colorAccent</item>
    </style>

</resources>

Corremos la app en nuestro emulador favorito y observamos los resultados :)

material_app

En el siguiente tutorial vamos a aprender acerca del ToolBar y como personalizarla. salu2

Share

Tutorial Material Design en Android #0

Crear un nuevo proyecto de Android Material Design

Hola lectores, esta es la introducción a una serie de tutoriales sobre desarrollo de aplicaciones android utilizando material design que tengo planeado hacer, antes que nada, si quieren saber bien que es el material design lo pueden ver desde el sitio oficial de google aqui, en resumidas cuentas una app hecha con este estilo se ve de esta forma.

howitowkrs

Y eso precisamente es lo que vamos a crear :), así que manos a la obra, si no tienes Android Studio descárgalo aca, después de instalarlo asegúrate de tenerlo completamente actualizado.

En Android Studio, crearemos un nuevo proyecto, para eso nos vamos a:

File > New > New Project

Nos aparecerá una ventana como la siguiente, aquí nos pedirán datos como el nombre de la app, el nombre de la compañía y el nombre del package

create_new_project

En la siguiente pantalla vamos a elegir la versión mínima de SDK api 14: Android 4.0 (IceCreamSandwich) si, es posible hacer material design en apis anteriores a la 21! :)

Después en la siguiente pantalla vamos a elegir una aplicación totalmente en blanco (Add no Activity) esto es porque algunos de los “templates” disponibles utilizan mucho código y técnicas que actualmente son obsoletas,

activity_type

La idea es que nosotros creemos todo desde cero. Por ultimo damos clic en Finish y estamos listos para comenzar a escribir código.
Si no estas familiarizado con la interfaz de Android Studio ahora es un buen momento para hacerlo, primero que nada vale la pena mencionar que Android Studio utiliza gradle para sincronizar y mantener las dependencias de los proyectos, si estas interesado en esto deberías revisar el archivo build.gradle en el apartado de Gradle Scripts donde veras un poco mas acerca de lo que hablo :).

Por otra parte, vamos a revisar el contenido del archivo manifest (App > Manifest > AndroidManifest.xml)

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.alevsk.materialdesignapp">

    <application android:allowBackup="true" android:label="@string/app_name"
        android:icon="@mipmap/ic_launcher" android:theme="@style/AppTheme">

    </application>

</manifest>

Vemos que el theme actual de la aplicación está definido en los archivos de estilos (style.xml), por lo que ahora vamos a revisar que contiene ese.

styles

<resources>

    <!-- Base application theme. -->
    <style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
        <!-- Customize your theme here. -->
    </style>

</resources>

Localizamos el AppTheme y vamos a cambiar el valor de su parámetro parent de Theme.AppCompat.Light.DarkActionBar a AppTheme.Base, justo debajo vamos a agregar el nuevo estilo con el siguiente código que si utilizara Theme.AppCompat.Light.DarkActionBar

    <style name="AppTheme.Base" parent="Theme.AppCompat.Light.DarkActionBar">

    </style>

Quedando el archivo completo de la siguiente forma:

<resources>

    <!-- Base application theme. -->
    <style name="AppTheme" parent="AppTheme.Base">
        <!-- Customize your theme here. -->
    </style>

    <style name="AppTheme.Base" parent="Theme.AppCompat.Light.DarkActionBar">

    </style>

</resources>

Ahora, ya que nuestro objetivo es dar soporte material a las apps, ya sea lollipop (api >= 21) como pre lollipop (api < 21) debemos crear un nuevo archivo styles.xml, para eso en la carpeta values hacemos clic derecho, después New > Value Resource file y nos aparecerá una ventana como la siguiente:

new_styles

Donde en file name ponemos styles.xml, después en available qualifiers nos vamos hasta abajo y seleccionamos versión, en el campo de texto que aparece escribimos 21, esto quiere decir que ese archivo se aplicara a los dispositivos Android que corran utilizando la api 21, ¿entienden a donde va esto? es posible escribir archivos de estilos diferentes para cada versión de la api, 14, 15, 16, 17 … 22 etc y hacer que nuestra api se vea diferente :), por lo pronto solo escribiremos xml para la api 21.

En el archivo styles.xml para la api 21 escribimos el siguiente xml

<?xml version="1.0" encoding="utf-8"?>
<resources>

    <!-- Base application theme. -->
    <style name="AppTheme" parent="AppTheme.Base">
        <!-- Customize your theme here. -->
    </style>

</resources>

En el archivo styles.xml para la api 21 no es necesario que definamos el estilo del tema AppTheme.Base puesto que ya lo definimos en el otro archivo de styles.xml y Android es lo suficientemente inteligente como para saber eso :), lo que vamos a hacer mas adelante sera definir algunas reglas de estilos y colores en cada archivo (ya no themes completos) para la personalizacion por versiones.

Lo que sigue, vamos a comenzar a crear activities, para eso en la carpeta de Java, clic derecho, después New > Activity > Blank Activity

new_activity

Como es la primera Activity podemos dejar los datos por default, explico rapidamente:

  • Activity Name: el nombre de tu clase
  • Layout Name: el nombre del archivo xml que servirá como la vista de tu actividad
  • Title Name: el título de tu actividad (el que aparece en el ActionBar / ToolBar)
  • Menu Resource Name: el nombre del archivo xml que tendrá los items para poblar el ToolBar de tu actividad

Damos clic en Finish.

Android Studio nos habrá creado dos nuevos archivos, MainActivity.java y activity_main.xml

activity

Si corremos la app y por alguna razón crashea es conveniente revisar el log de errores, me sucedió la primera vez que Android Studio no podía determinar cual era la activity por default para lanzar la app, y eso era debido a que en el archivo AndroidManifest.xml no estaba definido … por alguna extraña razón XD.

        <activity
            android:name=".MainActivity"
            android:label="@string/title_activity_main">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>

El intent-filter con sus definiciones es lo que se necesitaba agregar para solucionar el problema y correr la app :), si ejecutamos la app en un teléfono o emulador con Android 4.x o 5.x tendremos algo como lo siguiente.

app

¿Nada impresionante verdad? En el siguiente tutorial aprenderemos a definir los colores de la aplicación y comenzaremos a crear algunos elementos nuevos en la interfaz. salu2

Related Posts Plugin for WordPress, Blogger...

Share