miércoles, 29 de julio de 2015

Merge de ficheros en Git entre ramas

De las cosas que uno se enamora de Git, es que puede llegar el caso en que existan varias maneras de hacer las cosas.

El reto es el siguiente:
- Partiendo de una rama master, se desarrolla una nueva rama incidencia1, en la cual hemos realizado unos commits, y hemos modificado y añadido un par de ficheros.

Por lo tanto , en el C4 de la rama incidencia1 , tenemos ;

file1.c nuevo fichero.
file2.c modificacion del fichero
file3.c nuevo fichero.


Mientras tanto, en la rama incidencia2,  tenemos que incluir solo 2 los ficheros nuevos de la rama incidencia1.

Claro, que no podemos hacer un merge de la rama incidencia1, porque nos fusionaría el file2.c, y este no vamos a modificarlo, porque necesitamos conservar el de la rama incidencia2

Una simple solución es decirle a git que nos lo traiga a la rama donde estamos, incidencia2, los ficheros que necesitamos de la rama incidencia1;

$ git checkout incidencia1 file1.c file3.c
Ahora solo nos queda añadir los ficheros, git add , y hacer un commit ;-)
$ git add file*
$ git commit -m "Ya tenemos los files desde incidencia1"






jueves, 23 de julio de 2015

Historias de Git

Estar mirando la historia de un proyecto, y encontrarme con esto;




                                                       Ole, Ole, necesitamos vacaciones!!




miércoles, 22 de julio de 2015

Android, Evento OnClick de un boton


Una de las cosas cuando estaba con Java y Swing era la gestión de los eventos a través de los Listener.

Pues bueno, con Android 3/4 de lo mismo, por ejemplo, boton que nos va para otra actividad.



Y pensar que hace años en multiples lenguajes / GUIs tenemos evento OnClick....

En fin, arriba vemos como creamos un objeto, btnEuro,  y lo asignamos a través del setOnClickListener, que a su vez, se le pasa un objeto creado a través de new View.OnClickListener(), que se sobreescribe el method onClick,
y ahí, se crea un Intent, que se le pasa al inicio de la Activity.

¿ Lo podemos hacer más simple ? Pues si, de esta manera;


Y ahora, solo nos queda activarlo;


Y nos queda solo sobrescribir el method OnClick en la propia clase MainActivity;




Update: Bien, también con Android Studio,  podemos hacer lo siguiente;

En las propiedades del botón , ponemos el method que recibirá el evento, solo nos queda codificarlo;

 

jueves, 16 de julio de 2015

Empezando con Android


Bueno, después de posponer una y otra vez el empezar con Android, no entenderé la m*erdas de RAD en comparación con otros, con el Android Studio ya me he decidido.

Para empezar, una pequeña calculadora muy simple;
https://github.com/rafathefull/Calculadora

He aquí la imagen del proyecto;


lunes, 6 de julio de 2015

Patrón de Diseño Builder con Harbour

Seguimos con nuestros patrones de diseño. En este post veremos como implementar el patrón de diseño Builder, del tipo creacional.

Como Patrón de diseño, el patrón builder (Constructor) es usado para permitir la creación de una variedad de  objetos complejos desde un objeto fuente (Producto), el objeto fuente se compone de una variedad de partes que contribuyen individualmente a la creación de cada objeto complejo a través de un conjunto de llamadas a interfaces comunes de la clase Abstract Builder.
https://es.wikipedia.org/wiki/Builder_%28patr%C3%B3n_de_dise%C3%B1o%29          

Como siempre, podemos el código que muestra el uso de este patrón;
#include "hbclass.ch"

/* ABSTRACT BUILDER */
CLASS ROBOT
 
    // Metodos que se tienen que declarar en la clase heredada 
      METHOD Trabajar() VIRTUAL       
      METHOD CargarAcciones() VIRTUAL

 END CLASS

/* ----------------------------------------------------  */
CLASS ROBOT_HAMBUERGUESA FROM ROBOT
      DATA Lista_Acciones

      METHOD New() INLINE Self

      METHOD iniciar  HIDDEN
      METHOD getIngredientes HIDDEN
      METHOD Armar    HIDDEN
      METHOD Revisar  HIDDEN
      METHOD Terminar HIDDEN
     
      METHOD CargarAcciones() // Sobrecargado
      METHOD Trabajar()       // Sobrecargado

END CLASS

METHOD Iniciar() CLASS ROBOT_HAMBUERGUESA
  ? "Iniciando hambuerguesa"
RETURN nil

METHOD getIngredientes() CLASS ROBOT_HAMBUERGUESA
  ? "Coge Ingredientes"
RETURN nil

METHOD Armar() CLASS ROBOT_HAMBUERGUESA
  ? "Arma"
RETURN nil

METHOD Revisar() CLASS ROBOT_HAMBUERGUESA
  ? "Revisar"
RETURN nil

METHOD Terminar() CLASS ROBOT_HAMBUERGUESA
  ? "Terminar"
RETURN nil

METHOD CargarAcciones( Lista ) CLASS ROBOT_HAMBUERGUESA
  ::Lista_Acciones := Lista
RETURN nil

METHOD Trabajar() CLASS ROBOT_HAMBUERGUESA
     Local nAccion

     ::iniciar()

     for each nAccion in ::Lista_Acciones
         do case
            case nAccion = 1
                 ::getIngredientes()
            case nAccion = 2
                 ::Armar()
            case nAccion = 3
                 ::Revisar()
            otherwise
                 ? "No existe accion a realizar"
         end case
     next

     ::Terminar()

RETURN nil


/* ----------------------------------------------------  */
CLASS ROBOT_HOTDOG FROM ROBOT
      DATA Lista_Acciones

      METHOD New() INLINE Self

      // Como ejemplo, al ser metodos privados, podemos tener otros nombres
      METHOD Start  HIDDEN
      METHOD getParts HIDDEN
      METHOD build    HIDDEN
      METHOD check  HIDDEN
      METHOD finish HIDDEN
     
      METHOD CargarAcciones() // Sobrecargado
      METHOD Trabajar()       // Sobrecargado

END CLASS

METHOD Start() CLASS ROBOT_HOTDOG
  ? "Start HotDog"
RETURN nil

METHOD getParts() CLASS ROBOT_HOTDOG
  ? "get Pars"
RETURN nil

METHOD build() CLASS ROBOT_HOTDOG
  ? "Build"
RETURN nil

METHOD check() CLASS ROBOT_HOTDOG
  ? "check"
RETURN nil

METHOD finish() CLASS ROBOT_HOTDOG
  ? "finish"
RETURN nil

METHOD CargarAcciones( Lista ) CLASS ROBOT_HOTDOG
  ::Lista_Acciones := Lista
RETURN nil

METHOD Trabajar() CLASS ROBOT_HOTDOG
     Local nAccion

     ::Start()

     for each nAccion in ::Lista_Acciones
         do case
            case nAccion = 1
                 ::getParts()
            case nAccion = 2
                 ::build()
            case nAccion = 3
                 ::check()
            otherwise
                 ? "No existe accion a realizar"
         end case
     next

     ::finish()

RETURN nil

/* ----------------------------------------------------  */
CLASS BUILDER
      DATA Acciones
      DATA ROBOT

      METHOD New() CONSTRUCTOR
      METHOD SetRobot( i )
      METHOD addGetIngredientes inline aadd( ::Acciones, 1 )
      METHOD addArmar           inline aadd( ::Acciones, 2 )
      METHOD addRevisar         inline aadd( ::Acciones, 3 ) 
      METHOD addImposible       inline aadd( ::Acciones, 100 )

      METHOD getRobot()

END CLASS

METHOD New() CLASS BUILDER
    ::Acciones := {}
RETURN Self

/* Crea un robot segun solicitado */
METHOD SetRobot( i ) CLASS BUILDER
    do case
       case i = "1"
            ::robot := ROBOT_HAMBUERGUESA():New()
       case i = "2"
            ::robot := ROBOT_HOTDOG():New()

    end case
RETURN nil

METHOD getRobot() CLASS BUILDER
   
     ::robot:CargarAcciones( ::Acciones )

RETURN ::robot


/* ----------------------------------------------------  */
// Ejemplo de Implementación : ./test 1

function Main( cRobot )     Local oRobot
     Local oBuilder := BUILDER():New()

     oBuilder:SetRobot( cRobot )
     oBuilder:addRevisar()
     oBuilder:addImposible()
     oBuilder:addGetIngredientes()
     oBuilder:addArmar()
     oBuilder:addRevisar()

     oRobot := oBuilder:getRobot()
     oRobot:Trabajar()

return nil

Android y Git. Disponer del hash automáticamente.

Una de las cosas a las que estoy acostumbrado, es tener siempre en mi código, el hash/tag/versión del control de versiones que estoy usan...