Package org.geotools.map

Source Code of org.geotools.map.WMSLayer

/*
*    GeoTools - The Open Source Java GIS Toolkit
*    http://geotools.org
*
*    (C) 2004-2008, Open Source Geospatial Foundation (OSGeo)
*   
*    This library is free software; you can redistribute it and/or
*    modify it under the terms of the GNU Lesser General Public
*    License as published by the Free Software Foundation;
*    version 2.1 of the License.
*
*    This library is distributed in the hope that it will be useful,
*    but WITHOUT ANY WARRANTY; without even the implied warranty of
*    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
*    Lesser General Public License for more details.
*/
package org.geotools.map;

import java.awt.Rectangle;
import java.awt.geom.AffineTransform;
import java.awt.geom.Point2D;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.List;

import org.geotools.data.ows.Layer;
import org.geotools.data.wms.WebMapServer;
import org.geotools.data.wms.request.GetMapRequest;
import org.geotools.factory.CommonFactoryFinder;
import org.geotools.geometry.DirectPosition2D;
import org.geotools.geometry.jts.ReferencedEnvelope;
import org.geotools.referencing.CRS;
import org.geotools.renderer.lite.RendererUtilities;
import org.geotools.styling.FeatureTypeStyle;
import org.geotools.styling.RasterSymbolizer;
import org.geotools.styling.Rule;
import org.geotools.styling.Style;
import org.geotools.styling.StyleFactory;
import org.opengis.referencing.crs.CoordinateReferenceSystem;
import org.opengis.referencing.operation.MathTransform;

/**
* Wraps a WMS layer into a {@link MapLayer} for interactive rendering usage TODO: expose a
* GetFeatureInfo that returns a feature collection TODO: expose the list of named styles and allow
* choosing which style to use
*
* @author Andrea Aime - OpenGeo
*
*
* @source $URL$
*/
public class WMSLayer extends GridReaderLayer {

    /**
     * The default raster style
     */
    static Style STYLE;
    static {
        StyleFactory factory = CommonFactoryFinder.getStyleFactory(null);
        RasterSymbolizer symbolizer = factory.createRasterSymbolizer();

        Rule rule = factory.createRule();
        rule.symbolizers().add(symbolizer);

        FeatureTypeStyle type = factory.createFeatureTypeStyle();
        type.rules().add(rule);

        STYLE = factory.createStyle();
        STYLE.featureTypeStyles().add(type);
    }

    /**
     * Builds a new WMS layer
     *
     * @param wms
     * @param layer
     */
    public WMSLayer(WebMapServer wms, Layer layer) {
        super( new WMSCoverageReader(wms, layer), STYLE );
    }

    public WMSCoverageReader getReader(){
        return (WMSCoverageReader) this.reader;
    }
   

    public synchronized ReferencedEnvelope getBounds() {
        WMSCoverageReader wmsReader = getReader();
        if( wmsReader != null ){
            return wmsReader.bounds;
        }
        return super.getBounds();
    }

    /**
     * Retrieves the feature info as text (assuming "text/plain" is a supported feature info format)
     *
     * @param pos
     *            the position to be checked, in real world coordinates
     * @return
     * @throws IOException
     */
    public String getFeatureInfoAsText(DirectPosition2D pos, int featureCount) throws IOException {
        BufferedReader br = null;
        try {
            GetMapRequest mapRequest = getReader().mapRequest;
            InputStream is = getReader().getFeatureInfo(pos, "text/plain", featureCount, mapRequest);
            br = new BufferedReader(new InputStreamReader(is));
            String line;
            StringBuilder sb = new StringBuilder();
            while ((line = br.readLine()) != null) {
                sb.append(line).append("\n");
            }
            return sb.toString();
        } catch (IOException e) {
            throw e;
        } catch (Throwable t) {
            throw (IOException) new IOException("Failed to grab feature info").initCause(t);
        } finally {
            if (br != null)
                br.close();
        }
    }

    /**
     * Retrieves the feature info as a generic input stream, it's the duty of the caller to
     * interpret the contents and ensure the stream is closed feature info format)
     *
     * @param pos
     *            the position to be checked, in real world coordinates
     * @param infoFormat
     *            The INFO_FORMAT parameter in the GetFeatureInfo request
     * @return
     * @throws IOException
     */
    public InputStream getFeatureInfo(DirectPosition2D pos, String infoFormat, int featureCount)
            throws IOException {
        GetMapRequest mapRequest = getReader().mapRequest;
        return getReader().getFeatureInfo(pos, infoFormat, featureCount, mapRequest);
    }

    /**
     * Allows to run a standalone GetFeatureInfo request, without the need to have previously run a
     * GetMap request on this layer. Mostly useful for stateless users that rebuild the map context
     * for each rendering operation (e.g., GeoServer)
     *
     * @param pos
     * @param infoFormat
     *            The INFO_FORMAT parameter in the GetFeatureInfo request
     * @return
     * @throws IOException
     */
    public InputStream getFeatureInfo(ReferencedEnvelope bbox, int width, int height, int x, int y,
            String infoFormat, int featureCount) throws IOException {
        try {
            getReader().initMapRequest(bbox, width, height, null);
            // we need to convert x/y from the screen to the original coordinates, and then to the ones
            // that will be used to make the request
            AffineTransform at = RendererUtilities.worldToScreenTransform(bbox, new Rectangle(width, height));
            Point2D screenPos = new Point2D.Double(x, y);
            Point2D worldPos = new Point2D.Double(x, y);
            at.inverseTransform(screenPos, worldPos);
            DirectPosition2D fromPos = new DirectPosition2D(worldPos.getX(), worldPos.getY());
            DirectPosition2D toPos = new DirectPosition2D();
            MathTransform mt = CRS.findMathTransform(bbox.getCoordinateReferenceSystem(), getReader().requestCRS, true);
            mt.transform(fromPos, toPos);
            GetMapRequest mapRequest = getReader().mapRequest;
            return getReader().getFeatureInfo(toPos, infoFormat, featureCount, mapRequest);
        } catch(IOException e) {
            throw e;
        } catch(Throwable t) {
            throw (IOException) new IOException("Unexpected issue during GetFeatureInfo execution").initCause(t);
        }
    }

    /**
     * Returns the {@link WebMapServer} used by this layer
     *
     * @return
     */
    public WebMapServer getWebMapServer() {
        return getReader().wms;
    }

    /**
     * Returns the WMS {@link Layer} used by this layer
     *
     * @return
     */
    public List<Layer> getWMSLayers() {
        return getReader().layers;
    }

    /**
     * Returns the CRS used to make requests to the remote WMS
     *
     * @return
     */
    public CoordinateReferenceSystem getCoordinateReferenceSystem() {
        return reader.getCoordinateReferenceSystem();
    }

    /**
     * Returns last GetMap request performed by this layer
     *
     * @return
     */
    public GetMapRequest getLastGetMap() {
        return getReader().mapRequest;
    }

    /**
     * Allows to add another WMS layer into the GetMap requests
     *
     * @param layer
     */
    public void addLayer(Layer layer) {
        getReader().addLayer(layer);
    }

    /**
     * Returns true if the specified CRS can be used directly to perform WMS requests. Natively
     * supported crs will provide the best rendering quality as no client side reprojection is
     * necessary, the image coming from the WMS server will be used as-is
     *
     * @param crs
     * @return
     */
    public boolean isNativelySupported(CoordinateReferenceSystem crs) {
        try {
            String code = CRS.lookupIdentifier(crs, false);
            return code != null && getReader().validSRS.contains(code);
        } catch (Throwable t) {
            return false;
        }
    }

}
TOP

Related Classes of org.geotools.map.WMSLayer

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.