Personal tools
gvSIG Desktop
gvSIG Desktop

Cached time 11/22/13 07:47:55 Clear cache and reload

 
Document Actions

Integrándolo con gvSIG

by Joaquin Jose del Cerro Murciano last modified 2012-05-11 12:40
Hasta ahora hemos visto cómo crear nuestros componentes, lógica e interface de usuario, usando 
las librerías de gvSIG para acceder a los datos geográficos o para presentarlos, así como una
forma simple de crear una pequeña aplicación que los utilice. Vamos a ver ahora como integraríamos
esas funcionalidades en la aplicación gvSIG.

Si observamos los proyectos que tenemos en nuestro workspace veremos que aun hay uno sobre el que
no hemos trabajado, **org.gvsig.visor.app.mainplugin** . Es aquí donde está implementado nuestro 
plugin. Antes de ver el código del plugin comentar un detalle. Cuando describíamos lo que tenía
que hacer nuestro plugin, dijimos que debía presentar un *splash* personalizado. Veamos primero 
como podemos hacer esto.

En la carpeta *"src/main/resources"* encontraremos una carpeta *theme*, y dentro de esta un 
fichero *andami-theme.xml*. Este fichero es el encargado de especificar al framework de andami
que *splash* se debe presentar así como si hay que utilizar alguna imagen de fondo en el MDI
de la aplicación o los iconos de las ventanas de gvSIG. Andami, al arrancar, buscará en las 
carpetas de los plugins uno que tenga la carpeta *theme* y dentro este fichero y cuando
encuentre uno lo utilizará. El fichero xml de nuestro ejemplo contiene:

.. code-block:: xml

  
    
      
        
      
      
      
      
    
    
  

Por defecto las rutas que aparezcan en el fichero se interpretarán relativas a 
la ubicación de este fichero, disponiendo de una variable *GVSIG_INSTALL* que 
apuntará a la carpeta en la que está instalado gvSIG. En el ejemplo podemos
ver como en el tag *Splash* no se indica ruta para el fichero *"splash.png"*,
usándose el fichero que hay en la carpeta del plugin mientras que en el tag
*Icon* se usa la variable *GVSIG_INSTALL* para hacer referencia al fichero
que hay en el tema por defecto de Andami.

Podemos arrancar gvSIG y comprobar que sale el *splash* indicado en 
nuestro fichero *andami-theme.xml*.

Una vez visto como podemos cambiar el *splash*, podemos echar un vistazo a la
extensión de nuestro plugin.

.. note el config.xml !!!!!!!!!!

Vamos ahora a ver el código de nuestro *plugin*. Veremos que solo existen 
dos clases, *VisorExtension* y PropertiesOfBlockListener. La clase que integra nuestra funcionalidad
en gvSIG es *VisorExtension*. Esta clase extiende la clase *Extension* de *Andami* 
para integrarse con los menús y barras de herramientas, así como implementa
el interface *ExclusiveUIExtension*, para controlar la visibilidad de otras extensiones de 
gvSIG.

Para controlar la visibilidad de las otras extensiones de gvSIG, el interface
*ExclusiveUIExtension* aporta los métodos:

- **isEnabled** recibiendo como parametro la extensión sobre la que se
  quiere averiguar si debe estar habilitada o no:

  .. code-block:: java

    public boolean isEnabled(IExtension extension)
  
  En nuestro caso, como lo que queremos es deshabilitar todas las extensiones
  de edición, comprobaremos si la extensión que nos llega está en el paquete
  java *"org.gvsig.editing"* y para todas las que se encuentren en ese paquete
  devolveremos *false*, mientras que para el resto, delegaremos en ellas para
  averiguar si deben o no estar habilitadas.
  
- **isVisible** recibiendo como parametro la extensión sobre la que se
  quiere averiguar si debe estar visible o no:

  .. code-block:: java

    public boolean isVisible(IExtension extension)
  
  En nuestro caso, utilizaremos para determinar qué extensiones deben estar visibles
  el mismo que usamos para determinar si deben estar deshabilitadas.

Es muy importante delegar en los métodos *isEnabled* o *isVisible* de cada extensión
y no devolver *true* ya que puede que la extensión precise de algunas condiciones específicas
para estar visible o activa que ella misma comprueba.

Los métodos que nos encontramos en nuestra clase *VisorExtension* que precisa por extender
a *Extension* son:

- **initialize**. Se invoca al cargar la extensión. Aquí nos limitaremos a registrar
  servicios que ofrezca nuestra extensión. En nuestro caso nos limitaremos a informar al 
  *manager* de *plugins* que nuestra clase visor quiere actuar como controladora de la
  visibilidad de todas las extensiones. Esto lo haremos a través del método 
  *setExclusiveUIExtension* :
  
  .. code-block:: java

    PluginsManager manager = PluginsLocator.getManager();
    manager.setExclusiveUIExtension(this);

- **postInitialize**. Se invoca durante la inicialización de los plugins, una vez invocado 
  al método *initialize* de todas las extensiones. Esto nos garantiza que cuando se ejecuta
  estarán disponinles prácticamente todos los servicios de gvSIG. Aprovecharemos este método
  para:
  
  - Añadir nuestra información al *acerca de gvSIG*, esto lo haremos a través de nuestra
    función *addToAbout*. El código que lo realiza es:
    
    .. code-block:: java

      AboutManager about = AboutLocator.getManager();
      
      URL description = getResourceURL("about/description.html");
      URL icon = getResourceURL("about/icon.png");
      AboutParticipant dev = about.addDeveloper("Mi empresa", description, 1, icon);
      dev.addContribution("Mi visor", "Visor para consulta de parcelas catastrales", 2011, 5, 1, 2011, 7, 1);

    Cuando vamos a añadir nuestra información al *"acerca de"*, tendremos que hacer dos
    cosas:
  
    - Añadir una entrada como desarrolladores con nuestra información. Deberemos
      proporcionar el nombre de nuestra empresa y una descripción de esta mediante
      la URL a un documento en HTML. Normalmente este documento formará parte
      de los recursos de nuestro proyecto.
      
      Si dos extensiones intentan añadir más de una vez como desarrollador a empresas
      con el mismo nombre sólo será añadida la primera.
      
    - Añadiremos a nuestra empresa información sobre el desarrollo que hemos hecho, un 
      nombre y una pequeña descripción.
        
    Normalmente cada plugin que realicemos registrará la empresa, como la información del
    desarrollo en concreto de ese plugin.
  
  - Crear el manager de la parte de lógica de nuestra librería.
  
  - Inicializar los *stores* a través de nuestra función *initializeStores*. Como el manager de nuestra
    librería de lógica disponía de métodos para inicializar los *stores* nos limitaremos a 
    invocarlos:

    .. code-block:: java
    
      manager.initialize(
        getResource("data/properties.shp"), 
        getResource("data/blocks.shp")
      );
      
  - Y por último crear y mostrar la venta con nuestra vista, a través del método *createViewWindow*. 
    vamos a ver con un poco más de detalle cómo se realiza esto. Antes de empezar 
    lo primero que haremos será obtener una referencia del objeto *aplicacion* y del
    manager de *proyectos*:

    .. code-block:: java

        ApplicationManager application = ApplicationLocator.getManager();
        ProjectManager projectManager = application.getProjectManager();

    Una vez disponemos de estas referencias, podemos crear nuestra vista:
    
    .. code-block:: java

      // 1. Create a new view and set the name.
      ViewManager viewManager = (ViewManager) projectManager.getDocumentManagers(ViewManager.TYPENAME);
      ViewDocument view = (ViewDocument) viewManager.createDocument();
      view.setName(MY_VIEW_NAME);

    Para crear la vista, pediremos al *ProjectManager* que nos devuelva el manager de vistas, y a
    este le pediremos una nueva instancia del documento vista. Debemos recordar aquí, 
    que una de las principales
    funcionalidades de los *manager* es actuar a modo de factorías para obtener instancias de los 
    objetos que gestiona ese *manager*. Una vez disponemos del documento vista, le asignaremos el
    nombre que nosotros consideremos oportuno.
    
    Con la vista ya creada, procederemos a ver cómo hemos de hacer para añadir a esta las capas que
    necesitemos. Para ello crearemos una capa con las manzamas, esto lo realizaremos a través
    del método *createLayer*, indicándole el nombre de la capa y el *store* en que queremos que
    se base:

    .. code-block:: java
    
      // 2. Create a new layer with the blocks
      FLyrVect layer = (FLyrVect) application.getMapContextManager().createLayer("Blocks", this.manager.getBlocks());

    Con la capa ya creada, añadiremos al *mapa* de la vista la nueva capa:

    .. code-block:: java
    
      // 3. Add this layer to the mapcontext of the new view.
      view.getMapContext().getLayers().addLayer(layer);

    Añadiremos al proyecto corriente la vista:

    .. code-block:: java
    
      // 4. Add the view to the current project.
      projectManager.getCurrentProject().add(view);

    Y por último nos encargaremos de presentar la ventana asocida a la vista que
    acabamos de crear:

    .. code-block:: java
    
      // 5. Force to show the view's window.
      IView viewWindow = (IView) viewManager.getMainWindow(view);

      application.getUIManager().addWindow(viewWindow, GridBagConstraints.CENTER);
      try {
        application.getUIManager().setMaximum((IWindow) viewWindow, true);
      } catch (PropertyVetoException e) {
        logger.info("Can't maximize view.",e);
      }

    Una vez ya tenemos mostrada nuestra ventana de la vista, precisaremos registrar en el
    componente gráfico del mapa la nueva herramienta que aportamos, de forma similar a
    como hicimos para añadirla a nuestro mapa en el proyecto de pruebas:

    .. code-block:: java
    
      // 6. Register my tool in the mapcontrol of the view.
      PropertiesOfBlockListener listener = new PropertiesOfBlockListener();
      viewWindow.getMapControl().addBehavior(TOOL_NAME, new PointBehavior(listener));

  Con todo esto tendremos inicializado nuestro plugin.
  
- *execute*. Este metodo será invocado cada vez que el usuario interactue con las opciones
  de menú o botones que se configuraron en el fichero *config.xml* de nuestro plugin.
  En nuestro caso, se configuró para que se dispare este evento cuando el usuario
  quisiese activar la herramienta de información sobre parcelas catastrales de 
  una manzana. Así que el código que tendríamos que tener ahí debe corresponderse
  con esto:

  .. code-block:: java
  
    if( ACTION_SETINFOTOOL.equalsIgnoreCase(actionCommand) ) {
      // Set the tool in the mapcontrol of the active view.
      ApplicationManager application = ApplicationLocator.getManager();
      if( application.getActiveWindow() != viewWindow ) {
        return;
      }
      viewWindow.getMapControl().setTool(TOOL_NAME);
      }
    }

  Observaremos que lo primero que hacemos es comprobar si el comando que recibimos
  es el correspondiente a la activación de nuestra herramienta, y que fijamos
  en el *config.xml*. Esto es debido a que en una misma extensión podemos
  agrupar varias herramientas, indicando nombres de comando distintos en el
  *config.xml* para cada una de ellas.
  
  Una vez sabemos que se está tratando de activar nuestra herramienta de información,
  comprobaremos si está activa la ventana de nuestra vista, ya que sobre otras vistas u
  otros tipos de documento, no debemos hacer nada. Y por último, nos dedicaremos
  a activar nuestra herramienta en el mapa de la vista. Herramenta que habíamos registrado
  en el *postInitialize* de nuestra extensión.
  

- *isVisible*. En este método deberemos informar si los menús y botones asociados a nuestra
  herramienta deben estar visibles. En nuestro caso dejaremos visible nuestra herramienta
  siempre que la ventana activa sea la de nuestra vista:
  
  .. code-block:: java

    ApplicationManager application = ApplicationLocator.getManager();
    return application.getActiveWindow() == viewWindow;

- *isEnabled*, que devolveremos siempre 'true', ya que nuestra herramienta estará activa 
  siempre que esté visible, y allí ya pusimos las comprobaciones necesarias. Si la 
  logica de nuestra herramienta permite que no esté activa en algunos casos para
  los que sí se permite que esté visible, será aquí donde deberemos realizar esas comprobaciones.

Básicamente, hemos repasado como sería la integración de nuestra funcionalidad en gvSIG.
Nos queda por ver la clase *PropertiesOfBlockListener* que usamos para crear nuestra 
herramienta. El código del *listener* es básicamente similar al empleado por nuestra
aplicación de pruebas.

View source document

View source document Get permanent link


Powered by Plone CMS, the Open Source Content Management System

This site conforms to the following standards: