Archivo

Entradas Etiquetadas ‘API’

#FunWithDelphi: La foto del día

martes, 31 de enero de 2017 2 comentarios

NASA_DelphiBueno, pues ya está publicada la mía!! Y si todavía no os habéis animado os animo a que lo hagáis.

Desde hace unos días está en marcha la competición #FunWithDelphi que ha promovido Embarcadero y que se basa en la API de la NASA.

La descripción completa de la competición la tenéis en estos links; Esta entrada de Marco Cantú, y esta otra donde se explican algunos detalles más técnicos.

Y las reglas y los pasos prácticos a seguir, en este otro enlace:
https://community.embarcadero.com/competitions/14-fun-with-delphi-nasa-api-mash-up

Al final de la página también tenéis la lista de las publicadas hasta ahora, con las opciones para acceder a ellas y votar.

Básicamente, se trata de hacer una aplicación que utilice la API de la NASA y que muestre características de las últimas versiones de RAD Studio. Cualquier plataforma disponible y con el único límite de la imaginación.

Os muestro un vídeo de la mía en funcionamiento (Windows + Android)

Link al video (https://www.youtube.com/watch?v=CBqpnR6hwlo)

Y os dejo algunas imágenes:

Se puede descargar el binario para windows desde el repositorio de github. El código completo de la aplicación lo publicaré en el blog y en el repositorio, una vez que acabe la competición

Sólo me queda esperar que os guste y si es así que la votéis.

Un saludo.

Google Maps en Delphi – I

jueves, 14 de mayo de 2009 6 comentarios

Después de las dos entradas sobre Codificacióin Geográfica (*), toca entrar de lleno en la Visualización e Integración de Google Maps en nuestro programa, que por otra parte era el objetivo inicial de esta serie de entradas. La Codificación Geográfica (obtención de Latitud y Loingitud a partir de una dirección postal) era un «escollo» a salvar en nuestro camino, hasta nuestro verdadero objetivo.

(*) Lo normal es tener en nuestros programas/aplicaciones una serie de direcciones postales o direcciones de correo que deseamos mostrar o señalar en un Mapa. Para utilizar esas direccones con la API de Google Maps necesitamos obtener las coordenadas de Latitud y Longitud apropiadas. Para ello ya vimos  aquí (Codificación Geográfica – I) y aquí (Codificación Geográfica – II) cómo Google provee métodos para obtener las coordenadas de posicionamiento a partir de direcciones postales.

La idea para conseguir la integración es sencilla. Utilizar un componente TWebBrowser para mostrar una página HTML. Desde Delphi debemos «modificar» esa página para que muestre lo que nosotros deseemos.

Utilizando una sencilla página HTML con un Script, podemos visualizar el mapa correspondiente a coordenadas de Latitud y Longitud.  Con un componente TWebBrowser podemos visualizar esa página dentro de una aplicación delphi.

La página en sí sólo contiene el Script para Visualizar un Mapa.
Dentro del Script vemos cómo se crea un elemento de tipo «map»:

map = new GMap2(document.getElementById("map"));

Se añaden los controles que queremos visualizar en el mapa; En este caso, la selección para el tipo de mapa y control de zoom y posición grande.

        // Controles del mapa
        map.addControl(new GMapTypeControl());
        map.addControl(new GLargeMapControl());

El tipo de mapa que queremos que inicialmente aparezca (Mapa, visión por satélite o lo que Google llama híbrido).

        // Tipo de mapa
        map.setMapType(G_NORMAL_MAP);

Y por último colocamos la posición (latitud y longitud) donde queremos que el mapa salga centrado.

Pero no acaban aquí (ni mucho menos) las posibilidades de Google Maps. Una de las opciones, que dentro de lo sencillo, es muy interesante, es la inclusión de marcas señalando puntos del mapa o incluso ventanas de información no es mucho más complejo.

Para añadir una nueva marca, basta con conocer el punto exacto donde queremos situarla y utilizar un objeto GMarker para mostrarla en el mapa. En cuanto a la ventana, de información, sólo necesitamos el código HTML necesario para crearla.
En este ejemplo la ventana tiene un código sencillo (texto, imagen y link) que se almacena en una variable.

// VENTANA (HTML)
 var html="<img src="http://neftali.clubdelphi.com/images/imagen_neftali_60x54.jpg" alt="" width="60" height="54" />
" + "by Neftalí -Germán Estévez-  2009 <strong>
<a href="http://neftali.clubdelphi.com"
 target="_blank">http://neftali.clubdelphi.com</a>
</strong>
<a href="http://neftali.clubdelphi.com" target="_blank">
    </a>
";

Para mostrarla basta con que utilicemos en método OpenInfoWindowHtml (cuyo nombre es bastante descriptivo, por cierto ;-D ) de la siguiente forma:

    // Visualización de la mrca
    var point = new GLatLng(41.381655,2.122829);
    var marker = new GMarker(point);
    marker.openInfoWindowHtml(html);

Hay más opciones y basta con echarle una vistazo a la API de Google Maps para conocerlas. Además hay muchos ejemplos de utilización que pueden servir para aclarar los conceptos y para ver más cláramente cómo se utilizan los diferentes elementos.

Todo lo visto hasta aquí, está puesto en práctica en un ejemplo Delphi.

Podéis descargar el código completo (incluye EXE -comprimido UPX-) desde aquí:
<Descargar Ejemplo>

Y aquí acabamos esta entrada, que no será la última. Me dejo para una segunda parte, algunos detalles finales, como interactuar con el mapa y obtener datos de él y fusionar los dos conceptos vistos hasta ahora.

Nos vemos.

(Google Maps – API) Codificación Geográfica – II

jueves, 7 de mayo de 2009 4 comentarios

Continuando con la entrada (Google Maps – API) Codificación Geográfica – I, vamos a ver cómo obtener más datos de este servicio de Google Maps.

Si habéis revisado el ejemplo sencillo que vimos en la primera entrada, os habréis fijado que hay un parámetro al final de la dirección del que no hemos hablado. Se trata del formato de salida para los datos. Los formatos que acepta el API de Google Maps son los siguientes:

  • XML: Formato extendido en XML/KLM.
  • KLM: Formato extendido en KL; Se diferencia del anterior en los tipos MIME.
  • JSON: La salida de este formato se guarda en formato de objeto JSON (Javascript Object Notation).
  • CSV: Formato comprimido separado por comas (el que se utilizó en el ejemplo).

Para utilizar un formato diferente, basta con añadir al final de la línea de petición el formato deseado:

&amp;output=csv    &amp;output=klm     &amp;output=xml     &amp;output=json

Retomando el tema inicial, vamos a utilizar uno de los formatos extendidos para obtener más información de una dirección dada, además de las coordenadas de Latitud y Longitud.
Si realizamos una petición HTTP utilizando el formato json obtenemos una respuesta como esta por parte del servidor:

{
  "name": "Barcelona,spain",
  "Status": {
    "code": 200,
    "request": "geocode"
  },
  "Placemark": [ {
    "id": "p1",
    "address": "Barcelona, España",
    "AddressDetails":
       {"Country":
        {"CountryNameCode": "ES","CountryName": "España","AdministrativeArea":
          {"AdministrativeAreaName": "CT","SubAdministrativeArea":
            {"SubAdministrativeAreaName": "Barcelona","Locality":
              {"LocalityName": "Barcelona"}}}},"Accuracy": 4},
    "ExtendedData": {
      "LatLonBox": {
        "north": 41.4682658,
        "south": 41.3199988,
        "east": 2.2261223,
        "west": 2.0524766
      }
    },
    "Point": {
      "coordinates": [ 2.1699187, 41.3879170, 0 ]
    }
  } ]
}

Utilizando un sencillo «parser» con este resultado podemos extraer la información para poder utilizarla en nuestros programas.

El ejempo que se ve en la imagen puede descargarse desde aquí.

He creado además una clase derivada de TThread que permite acceder a la imagen. Me ha parecido que en futuros usos me va a ser más útil así, aunque realmente todavía no la he probado en un entorno «multithread».

TThreadGeoCode = class(TThread)
  private
    FDireccion: string;
    FAllText: TStrings;
    FGeoStatusCode: Integer;
    FGeoAddress: string;
    FGeoCountryCode: string;
    FGeoCountryName: string;
    FGeoAdminArea: string;
    FGeoAddressLine: string;
    FGeoLocalityName: string;
    FGeoPostalCode: string;
    FGeoAccuracy: integer;
    FGeoLatitud: string;
    FGeoLongitud: string;

    procedure _ExtractResult();
    function _StatusCodeToStr(ACode:Integer):string;
    function _AccuracyToStr(ACode:integer):string;
  protected
    procedure Execute; override;
  public
    destructor Destroy; override;
    constructor Create(ADireccion:string;
                       ThreadPriority:TThreadPriority=tpNormal);

    // Direccion a buscar
    property Direccion:string read FDireccion write FDireccion;
    // Salida
    property AllText:TStrings read FAllText write FAllText;
    // propiedades de posición
    property GeoStatusCode:Integer read FGeoStatusCode write FGeoStatusCode;
    property GeoAddress:string read FGeoAddress write FGeoAddress;
    property GeoCountryName:string read FGeoCountryName write FGeoCountryName;
    property GeoCountryCode:string read FGeoCountryCode write FGeoCountryCode;
    property GeoAdminArea:string read FGeoAdminArea write FGeoAdminArea;
    property GeoAddressLine:string read FGeoAddressLine write FGeoAddressLine;
    property GeoLocalityName:string read FGeoLocalityName
       write FGeoLocalityName;
    property GeoPostalCode:string read FGeoPostalCode write FGeoPostalCode;
    property GeoAccuracy:integer read FGeoAccuracy write FGeoAccuracy;
    property GeoLatitud:string read FGeoLatitud write FGeoLatitud;
    property GeoLongitud:string read FGeoLongitud write FGeoLongitud;

  published

  end;

Y aun podemos extraer más, ya que si la dirección es ambigua (pero correcta), google puede devolver más de un resultado. De esta forma, con una dirección tipo:

Obtendremos por parte de Google la lista de direcciones correcta que pueden corresponder a esta calle. Cada una de ellas presenta la estructura mostrada anteriormente variando el identificador (id):

  "Placemark": [ {
    "id": "p1",
...
    "id": "p2",
...

Sucesivamente para las distintas direcciones correctas y posibles para esa combinación: Alava, Burgos, Ciudad Real, Cuenca,…

A partir de aquí, no costaría mucho para modificar el ejemplo anterior de forma que se puedan extraer y mostrar los datos, no sólo de la primera dirección, sino de todas las devueltas en la petición.

Hasta aquí estos dos artículos (I y II), que sirven a modo de introducción y prefacio del próximo que estoy preparando.

Está claro, que la idea final y el objetivo que persigo es poder integrar en un programa Delphi las características de Google Maps. El problema actual es, que en nuestras Base de Datos/programas normalmente no tenemos codificadas nuestras direcciones con Latitud/Longitud, así aque para llegar a nueastro objetivo antes tenemos que conseguir estos dos parámetros. Ahí es donde nos és útil el concepto de «Codificación geográfica».

Una vez que tenemos Latitud y Longitud para nuestra dirección, ya podemos avanzar un paso más…

Utilizar un BMP para cambiar el cursor

martes, 6 de mayo de 2008 1 comentario

Muestra como utilizar un BITMAP (en este caso extraído de un TImage) para modificar el cursor activo. Modificando un poco el Tip/Truco es fácil obtener la imagen de disco o desde un recurso.

Se utiliza la API CreateIconIndirect para generar el cursor que posteriormente se activará.

Se puede usar un color de fondo como transparente para obtener un cursos «opaco» o un segundo BITMAP para combinarlo con el primero y así obtener también efectos de transparencia en el cursor generado.

Imagen del ejemplo

// Crear los bitmaps
BitmapMask := TBitmap.Create;
Bitmap := TBitmap.Create;
// proteccion
try
  // Cargar las imágenes
  BitmapMask.Assign(Image2.Picture.Bitmap);
  Bitmap.Assign(Image1.Picture.Bitmap);
  // Crear el icono del cursor
  with iconInfo do begin
    fIcon := false;
    xHotspot := (Bitmap.Width div 4);
    yHotspot := (Bitmap.Height div 3);
    hbmMask := BitmapMask.Handle;
    hbmColor := Bitmap.Handle;
  end;
 
  // Asignar el icono
  Screen.Cursors[1] := CreateIconIndirect(iconInfo);
  Self.Cursor := 1;
 
finally
  // Liberar
  BitmapMask.Free;
  Bitmap.Free;
end;

Es ejemplo completo se puede descargar <AQUÍ>.
Download Descargar.

Categories: Delphi, Trucos Tags: , , ,

API LockFile para detectar instancias de aplicación activas en red

sábado, 1 de marzo de 2008 Sin comentarios

Éste ejemplo muestra cómo utilizar la API LockFile para detectar aplicaciones que están ejecutándose.

La situación es la siguiente: Una aplicación que se ejecuta en Red. Puede haber muchos puestos/estaciones que la están ejecutándo simultáneamente. Y nos interesa saber en cada momento qué puestos la ejecutan.

Las ventajas de éste método son su sencillez (poco código), fiabilidad (ya que al ser bloqueos controlados por el sistema operativo, si algunas estación «se cuelga» no hace falta ningun código de recuperación de identificadores, el sistema librera el bloqueo) y pocos recursos, ya que aunque bloqueemos mucha posiciones del fichero, el tamaño de éste simpre será de 0 bytes.

Imagen del ejemplo

Download Descargar ejemplo

Categories: Delphi, Ejemplos Tags: ,

Obtener la lista de procesos ejecutándose

domingo, 24 de febrero de 2008 1 comentario

Con ésté trozo de código se puede obtener la lista de los procesos (nombre del ejecutable) que están en marcha en ese momento en la máquina:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
var
  i: Integer;
  bContinue: BOOL;
begin
   // Limpiar la lista
   ListBox1.Items.Clear;
   // Recoge la lista de procesos en éste momento
   aSnapshotHandle := CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
   aProcessEntry32.dwSize := SizeOf(aProcessEntry32);
   // Acceder al primer proceso
   bContinue := Process32First(aSnapshotHandle, aProcessEntry32);
   // Recorerr los procesos activos
   while (Integer(bContinue) <> 0) do begin
      // Añadirlo a la lista
      ListBox1.Items.Add(ExtractFileName(aProcessEntry32.szExeFile));
      // Hay más?
      bContinue := Process32Next(aSnapshotHandle, aProcessEntry32);
   end;
   // cerrar la estructura
   CloseHandle(aSnapshotHandle);

Utilizando aProcessEntry32 se puede obtener más información de cada uno de los procesos, como:

* Identificador
* Nombre competo
* …

IntToHex(aProcessEntry32.th32ProcessID, 4)
aProcessEntry32.szExeFile

Categories: Delphi, Trucos Tags: , , ,

Simular barras flotantes en torno al formulario

miércoles, 2 de enero de 2008 1 comentario

La idea de éste ejemplo llega a partir de una petición de obtener en un formulario unas barras de herramientas (toolbars) similares a las que aparecen en los Expertos para Delphi CnPack/cnWizard (muy buenos y gratuítos, por cierto).
En el caso de los CnPack, cuando aparece un formulario en el IDE de Delphi, aparecen varias barras de herramientas «flotantes» que se «pegan» literalmente al formulario.

De forma que si mueves el form, automáticamente se mueven las barras también. Una imagen descriptiva podría ser esta:

Barras flotantes

La forma de conseguirlo es utlizando el mensaje WM_WINDOWPOSCHANGING accesible desde los descencientes de TCustomForm.

Download Descargar ejemplo

Categories: Delphi, Ejemplos Tags: , , ,

Desplegar por código el menú de sistema de una ventana

martes, 25 de septiembre de 2007 Sin comentarios

Programar en cualquier componente que se desee que responda al click el siguiente código en el evento MouseDown.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
procedure TForm1.Image1MouseDown(Sender: TObject; 
                        Button: TMouseButton;
	                Shift: TShiftState; X, Y: Integer);
var
   h: HMENU;
   p:TPoint;
begin
  // El componente que llama deriva de TControl?
  if (Sender is TControl) then begin
    // Posicion del click
    p.X := x;
    p.Y := y;
    // Calculamos las coordenadas relativas
    P := Self.ScreenToClient(TControl(Sender).ClientToScreen(P));
    // Mostrar el menú
    h := GetSystemMenu(handle, false);
    TrackPopupMenu(h, TPM_LEFTALIGN or TPM_LEFTBUTTON,
    ClientOrigin.X + p.X ,
    ClientOrigin.Y + p.y, 0, handle, nil);
  end;
end;
Categories: Delphi, Trucos Tags: , , ,