World Wind Forums

Go Back   World Wind Forums > WorldWind JAVA forums > Development Help

Development Help Help for building applications or diagnosing problems with WWJ

Reply
 
Thread Tools Display Modes
Old 07-07-2010, 08:02 PM   #1
scottseeker
Junior Member
 
Join Date: Jul 2008
Posts: 10
scottseeker is on a distinguished road
Default Bug with BasicDragger?

Hello.

Using: worldwind-0.6.505.13458

I am using the 'BasicDragger' class.

The problem happens when I drag an instance of a IconLayer (UserFacingIcon).

Before dragging: I can zoom in and out and the layer is always visible.

After dragging: Once I zoom in to where the map scale is ~ 200km the layer disappears.

I tried setting alwaysOnTop(true), and a few other things but I can't seem to get rid of this behavior.

Any suggestions?

test: You can see this in the KeepObjectsInView.java example. Happens with the icons, but not with shapes.

Last edited by scottseeker; 07-07-2010 at 08:10 PM.
scottseeker is offline   Reply With Quote
Old 07-19-2010, 05:01 PM   #2
Unregistered
Guest
 
Posts: n/a
Default

so.. no?
  Reply With Quote
Old 07-19-2010, 05:02 PM   #3
Unregistered
Guest
 
Posts: n/a
Default

bump?
  Reply With Quote
Old 07-23-2010, 11:14 AM   #4
MAU
Junior Member
 
Join Date: Feb 2010
Posts: 6
MAU is on a distinguished road
Default

the problem is in IconLayer the method getActiveIcons... "dc.getSurfaceGeometry()" returns 0 geometrySurfaces and BasicQuadTree ... it returns a empty list:
it's force returning always ALL icons;

i remplazed with this lines:

Code:

        /*
Copyright (C) 2001, 2006 United States Government
as represented by the Administrator of the
National Aeronautics and Space Administration.
All Rights Reserved.
*/
package es.udc.lbd.xeoeduca.geolayers.images;

import gov.nasa.worldwind.geom.*;
import gov.nasa.worldwind.layers.AbstractLayer;
import gov.nasa.worldwind.render.*;
import gov.nasa.worldwind.terrain.SectorGeometryList;
import gov.nasa.worldwind.util.*;

import java.util.*;

/**
 * The <code>IconLayer</code> class manages a collection of {@link gov.nasa.worldwind.render.WWIcon} objects for
 * rendering and picking. <code>IconLayer</code> delegates to its internal {@link gov.nasa.worldwind.render.IconRenderer}
 * for rendering and picking operations.
 *
 * @author tag
 * @version $Id: IconLayer.java 13233 2010-03-20 02:12:56Z tgaskins $
 * @see gov.nasa.worldwind.render.WWIcon
 * @see gov.nasa.worldwind.render.IconRenderer
 */
public class IconLayer extends AbstractLayer
{
    //protected final BasicQuadTree<WWIcon> icons = new BasicQuadTree<WWIcon>(4, Sector.FULL_SPHERE, null);
    protected  Set<WWIcon> icons = new HashSet<WWIcon>();
    protected Iterable<WWIcon> iconsOverride;
    protected IconRenderer iconRenderer = new IconRenderer();
    private Pedestal pedestal;
    private boolean regionCulling = true;

    // These enable the render pass to use the same non-culled icons computed by the pick pass.
    protected Set<WWIcon> lastActiveIcons;
    protected long frameId;

    /** Creates a new <code>IconLayer</code> with an empty collection of Icons. */
    public IconLayer()
    {
    }

    /**
     * Adds the specified <code>icon</code> to this layer's internal collection. If this layer's internal collection has
     * been overriden with a call to {@link #setIcons}, this will throw an exception.
     *
     * @param icon Icon to add.
     *
     * @throws IllegalArgumentException If <code>icon</code> is null.
     * @throws IllegalStateException    If a custom Iterable has been specified by a call to <code>setIcons</code>.
     */
    public void addIcon(WWIcon icon)
    {
        if (icon == null)
        {
            String msg = Logging.getMessage("nullValue.Icon");
            Logging.logger().severe(msg);
            throw new IllegalArgumentException(msg);
        }
        if (this.iconsOverride != null)
        {
            String msg = Logging.getMessage("generic.LayerIsUsingCustomIterable");
            Logging.logger().severe(msg);
            throw new IllegalStateException(msg);
        }

        this.icons.add(icon);
        //this.icons.add(icon, icon.getPosition().asDegreesArray());
    }

    /**
     * Adds the contents of the specified <code>icons</code> to this layer's internal collection. If this layer's
     * internal collection has been overriden with a call to {@link #setIcons}, this will throw an exception.
     *
     * @param icons Icons to add.
     *
     * @throws IllegalArgumentException If <code>icons</code> is null.
     * @throws IllegalStateException    If a custom Iterable has been specified by a call to <code>setIcons</code>.
     */
    public void addIcons(Iterable<WWIcon> icons)
    {
        if (icons == null)
        {
            String msg = Logging.getMessage("nullValue.IterableIsNull");
            Logging.logger().severe(msg);
            throw new IllegalArgumentException(msg);
        }
        if (this.iconsOverride != null)
        {
            String msg = Logging.getMessage("generic.LayerIsUsingCustomIterable");
            Logging.logger().severe(msg);
            throw new IllegalStateException(msg);
        }

        for (WWIcon icon : icons)
        {
            // Internal list of icons does not accept null values.
            if (icon != null){
            	//this.icons.add(icon, icon.getPosition().asDegreesArray());
            	this.icons.add(icon);
            }
                
        }
    }

    /**
     * Removes the specified <code>icon</code> from this layer's internal collection, if it exists. If this layer's
     * internal collection has been overriden with a call to {@link #setIcons}, this will throw an exception.
     *
     * @param icon Icon to remove.
     *
     * @throws IllegalArgumentException If <code>icon</code> is null.
     * @throws IllegalStateException    If a custom Iterable has been specified by a call to <code>setIcons</code>.
     */
    public void removeIcon(WWIcon icon)
    {
        if (icon == null)
        {
            String msg = Logging.getMessage("nullValue.Icon");
            Logging.logger().severe(msg);
            throw new IllegalArgumentException(msg);
        }
        if (this.iconsOverride != null)
        {
            String msg = Logging.getMessage("generic.LayerIsUsingCustomIterable");
            Logging.logger().severe(msg);
            throw new IllegalStateException(msg);
        }

        this.icons.remove(icon);
    }

    /**
     * Clears the contents of this layer's internal Icon collection. If this layer's internal collection has been
     * overriden with a call to {@link #setIcons}, this will throw an exception.
     *
     * @throws IllegalStateException If a custom Iterable has been specified by a call to <code>setIcons</code>.
     */
    public void removeAllIcons()
    {
        if (this.iconsOverride != null)
        {
            String msg = Logging.getMessage("generic.LayerIsUsingCustomIterable");
            Logging.logger().severe(msg);
            throw new IllegalStateException(msg);
        }

        this.clearIcons();
    }

    protected void clearIcons()
    {
        if (this.icons != null)
            this.icons.clear();
    }

    /**
     * Returns the Iterable of Icons currently in use by this layer. If the caller has specified a custom Iterable via
     * {@link #setIcons}, this will returns a reference to that Iterable. If the caller passed <code>setIcons</code> a
     * null parameter, or if <code>setIcons</code> has not been called, this returns a view of this layer's internal
     * collection of Icons.
     *
     * @return Iterable of currently active Icons.
     */
    public Iterable<WWIcon> getIcons()
    {
        if (this.icons != null)
            return this.icons;

        return Collections.emptyList();
    }

    /**
     * Indicates whether the layer culls icons whose latitude-longitude location is outside the visible terrain area.
     * See {@link #setRegionCulling(boolean)} for a fuller description of region culling.
     *
     * @return regionCulling true if region culling is performed, otherwise false.
     */
    public boolean isRegionCulling()
    {
        return this.regionCulling;
    }

    /**
     * Indicates whether the layer culls icons whose latitude-longitude location is outside the visible terrain area.
     * This typically provides better performance when some icons are not in view. However, it might remove icons at
     * high altitude over the horizon.
     *
     * @param regionCulling true if region culling is performed, otherwise false.
     */
    public void setRegionCulling(boolean regionCulling)
    {
        this.regionCulling = regionCulling;
    }

    /**
     * Returns the Iterable of currently active Icons. If the caller has specified a custom Iterable via {@link
     * #setIcons}, this will returns a reference to that Iterable. If the caller passed <code>setIcons</code> a null
     * parameter, or if <code>setIcons</code> has not been called, this returns a view of this layer's internal
     * collection of Icons, culled to eliminate those outside the current sector geometry.
     *
     * @param dc a current DrawContext.
     *
     * @return Iterable of currently active Icons.
     */
    protected Iterable<WWIcon> getActiveIcons(DrawContext dc)
    {
    	
    	
        if (this.iconsOverride != null)
            return this.iconsOverride;

        if (this.lastActiveIcons != null && this.frameId == dc.getFrameTimeStamp())
            return this.lastActiveIcons;

        
        //this.lastActiveIcons = null;

        
        if (!this.isRegionCulling())
            return this.icons;

        
        //SectorGeometryList sgList = dc.getSurfaceGeometry();

//        if (sgList == null || sgList.size() == 0)
//            return Collections.emptyList();


//        if (this.lastActiveIcons== null)
        	this.lastActiveIcons = this.icons;//.getItemsInRegions(sgList, new HashSet<WWIcon>());
        
        if (this.lastActiveIcons== null) {
        	Collections.emptyList();
        }
        
        //System.out.println("lastActiveIcons "+lastActiveIcons.size());
        
        this.frameId = dc.getFrameTimeStamp();

//        for(int i=0;i<lastActiveIcons.size();i++){
//        	System.out.println(lastActiveIcons.toArray()[i]);
//        }
        return this.lastActiveIcons;
    }

    /**
     * Overrides the collection of currently active Icons with the specified <code>iconIterable</code>. This layer will
     * maintain a reference to <code>iconIterable</code> strictly for picking and rendering. This layer will not modify
     * the Iterable reference. However, this will clear the internal collection of Icons, and will prevent any
     * modification to its contents via <code>addIcon, addIcons, or removeIcons</code>.
     * <p/>
     * If the specified <code>iconIterable</code> is null, this layer will revert to maintaining its internal
     * collection.
     *
     * @param iconIterable Iterable to use instead of this layer's internal collection, or null to use this layer's
     *                     internal collection.
     */
    public void setIcons(Iterable<WWIcon> iconIterable)
    {
        this.iconsOverride = iconIterable;
        // Clear the internal collection of Icons.
        clearIcons();
    }

    /**
     * Returns the <code>Pedestal</code> used by this layers internal <code>IconRenderer</code>.
     *
     * @return <code>Pedestal</code> used by this layers internal <code>IconRenderer</code>.
     */
    public Pedestal getPedestal()
    {
        return pedestal;
    }

    /**
     * Sets the <code>Pedestal</code> used by this layers internal <code>IconRenderer</code>.
     *
     * @param pedestal <code>Pedestal</code> to be used by this layers internal <code>IconRenderer</code>.
     */
    public void setPedestal(Pedestal pedestal)
    {
        this.pedestal = pedestal;
    }

    /**
     * Indicates whether horizon clipping is performed.
     *
     * @return <code>true</code> if horizon clipping is performed, otherwise <code>false</code>.
     *
     * @see #setHorizonClippingEnabled(boolean)
     */
    public boolean isHorizonClippingEnabled()
    {
        return this.iconRenderer.isHorizonClippingEnabled();
    }

    /**
     * Indicates whether to render icons beyond the horizon. If view culling is enabled, the icon is also tested for
     * view volume inclusion. The default is <code>false</code>, horizon clipping is not performed.
     *
     * @param horizonClippingEnabled <code>true</code> if horizon clipping should be performed, otherwise
     *                               <code>false</code>.
     *
     * @see #setViewClippingEnabled(boolean)
     */
    public void setHorizonClippingEnabled(boolean horizonClippingEnabled)
    {
        this.iconRenderer.setHorizonClippingEnabled(horizonClippingEnabled);
    }

    /**
     * Indicates whether view volume clipping is performed.
     *
     * @return <code>true</code> if view volume clipping is performed, otherwise <code>false</code>.
     *
     * @see #setViewClippingEnabled(boolean)
     */
    public boolean isViewClippingEnabled()
    {
        return this.iconRenderer.isViewClippingEnabled();
    }

    /**
     * Indicates whether to render icons outside the view volume. This is primarily to control icon visibility beyond
     * the far view clipping plane. Some important use cases demand that clipping not be performed. If horizon clipping
     * is enabled, the icon is also tested for horizon clipping. The default is <code>false</code>, view volume clipping
     * is not performed.
     *
     * @param viewClippingEnabled <code>true</code> if view clipping should be performed, otherwise <code>false</code>.
     *
     * @see #setHorizonClippingEnabled(boolean)
     */
    public void setViewClippingEnabled(boolean viewClippingEnabled)
    {
        this.iconRenderer.setViewClippingEnabled(viewClippingEnabled);
    }

    /**
     * Indicates whether picking volume clipping is performed.
     *
     * @return <code>true</code> if picking volume clipping is performed, otherwise <code>false</code>.
     *
     * @see #setViewClippingEnabled(boolean)
     */
    public boolean isPickFrustumClippingEnabled()
    {
        return this.iconRenderer.isPickFrustumClippingEnabled();
    }

    /**
     * Indicates whether to render icons outside the picking volume when in pick mode. This increases performance by
     * only drawing the icons within the picking volume when picking is enabled. Some important use cases demand that
     * clipping not be performed. The default is <code>false</code>, picking volume clipping is not performed.
     *
     * @param pickFrustumClippingEnabled <code>true</code> if picking clipping should be performed, otherwise
     *                                   <code>false</code>.
     */
    public void setPickFrustumClippingEnabled(boolean pickFrustumClippingEnabled)
    {
        this.iconRenderer.setPickFrustumClippingEnabled(pickFrustumClippingEnabled);
    }

    /**
     * Indicates whether an icon's elevation is treated as an offset from the terrain or an absolute elevation above sea
     * level.
     *
     * @return <code>true</code> if icon elevations are treated as absolute, <code>false</code> if they're treated as
     *         offsets from the terrain.
     */
    public boolean isAlwaysUseAbsoluteElevation()
    {
        return this.iconRenderer.isAlwaysUseAbsoluteElevation();
    }

    /**
     * Normally, an icon's elevation is treated as an offset from the terrain when it is less than the globe's maximum
     * elevation. Setting #setAlwaysUseAbsoluteElevation to <code>true</code> causes the elevation to be treated as an
     * absolute elevation above sea level.
     *
     * @param alwaysUseAbsoluteElevation <code>true</code> to treat icon elevations as absolute, <code>false</code> to
     *                                   treat them as offsets from the terrain.
     */
    public void setAlwaysUseAbsoluteElevation(boolean alwaysUseAbsoluteElevation)
    {
        this.iconRenderer.setAlwaysUseAbsoluteElevation(alwaysUseAbsoluteElevation);
    }

    /**
     * Opacity is not applied to layers of this type. The icon image is assumed to indicates its opacity.
     *
     * @param opacity the current opacity value, which is ignored by this layer.
     */
    @Override
    public void setOpacity(double opacity)
    {
        super.setOpacity(opacity);
    }

    /**
     * Returns the layer's opacity value, which is ignored by this layer the icon's image is assumed to indicate its
     * opacity.
     *
     * @return The layer opacity, a value between 0 and 1.
     */
    @Override
    public double getOpacity()
    {
        return super.getOpacity();
    }

    /**
     * Indicates whether icons are picked as a batch and therefore a {@link gov.nasa.worldwind.event.SelectEvent} will
     * contain only one icon from the layer. Batch picking is much faster than individual picking, so this attribute
     * should be used judiciously.
     *
     * @return true if batch picking is allowed, otherwise false.
     *
     * @see #setAllowBatchPicking(boolean)
     */
    public boolean isAllowBatchPicking()
    {
        return this.iconRenderer.isAllowBatchPicking();
    }

    /**
     * Specifies whether batch picking is allowed. If so, a {@link gov.nasa.worldwind.event.SelectEvent} from the layer
     * will contain only one icon even if several overlapping icons are at the pick point. Batch picking is much faster
     * than individual picking so the default value is true.
     *
     * @param allowBatchPicking true if batch picking is allowed, otherwise false.
     */
    public void setAllowBatchPicking(boolean allowBatchPicking)
    {
        this.iconRenderer.setAllowBatchPicking(allowBatchPicking);
    }

    @Override
    protected void doPick(DrawContext dc, java.awt.Point pickPoint)
    {
        this.iconRenderer.setPedestal(this.pedestal);
        this.iconRenderer.pick(dc, getActiveIcons(dc), pickPoint, this);
    }

    @Override
    protected void doRender(DrawContext dc)
    {
    	
        this.iconRenderer.setPedestal(this.pedestal);
        this.iconRenderer.render(dc, getActiveIcons(dc));
    }

    @Override
    public String toString()
    {
        return Logging.getMessage("layers.IconLayer.Name");
    }
}

Last edited by MAU; 07-23-2010 at 12:05 PM.
MAU is offline   Reply With Quote
Old 07-27-2010, 02:25 PM   #5
scottseeker
Junior Member
 
Join Date: Jul 2008
Posts: 10
scottseeker is on a distinguished road
Default Thanks

The only line that didn't work for me was:

this.lastActiveIcons = this.icons;

what I did instead was change the final line from:

return this.lastActiveIcons; ->
return this.icons;


Thank you MAU!
scottseeker is offline   Reply With Quote
Old 09-17-2010, 05:13 AM   #6
adlaws
Junior Member
 
Join Date: Sep 2010
Posts: 5
adlaws is on a distinguished road
Default

Howdy,

Another way to get around this is to manage the icons yourself by using the setIcons(Iterable<WWIcon> iconIterable) method on IconLayer.

This means you'll need to manage the addition/removal of icons yourself (by adding/removing them from whatever Iterable<WWIcon> you pass in - I use a HashSet myself), but it's not that hard.

If you look at the IconLayer source code, you'll see that by doing this it sidesteps the whole SurfaceGeometry issue because it ends up dropping out of the getActiveIcons() method before it gets to the problem.

Anyway, just a suggestion that worked for me - your mileage may vary.
adlaws is offline   Reply With Quote
Old 09-17-2010, 01:21 PM   #7
scottseeker
Junior Member
 
Join Date: Jul 2008
Posts: 10
scottseeker is on a distinguished road
Default

Thanks for the suggestion!
scottseeker is offline   Reply With Quote
Old 01-04-2011, 09:39 PM   #8
dramajohny
Guest
 
Posts: n/a
Default

Another solution is;

IconLayer iconlayer;

iconLayer.setRegionCulling(false);
  Reply With Quote
Reply


Currently Active Users Viewing This Thread: 1 (0 members and 1 guests)
 
Thread Tools
Display Modes

Posting Rules
You may post new threads
You may post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Forum Jump

Similar Threads
Thread Thread Starter Forum Replies Last Post
Possible Rendering Bug flem Bug Reports 0 01-26-2010 09:02 PM
Sector clipping bug? nigel_ht Development Help 5 05-06-2009 05:04 AM
Bug in the visualization for the terrain of CompoundElevationModel? mao Development Help 8 03-20-2009 05:12 AM
Possible Bug in WorldWind 0.5.0 IconRenderer Griff241 Development Help 5 06-16-2008 11:24 PM
Thread bug? Hang and error message rogene Development Help 6 10-09-2007 08:14 AM


All times are GMT +1. The time now is 06:38 PM.


Powered by vBulletin® Version 3.7.1
Copyright ©2000 - 2013, Jelsoft Enterprises Ltd.