/* * Licensed Materials - Property of Rogue Wave Software, Inc. * © Copyright Rogue Wave Software, Inc. 2014, 2015 * © Copyright IBM Corp. 2009, 2014 * © Copyright ILOG 1996, 2009 * All Rights Reserved. * * Note to U.S. Government Users Restricted Rights: * The Software and Documentation were developed at private expense and * are "Commercial Items" as that term is defined at 48 CFR 2.101, * consisting of "Commercial Computer Software" and * "Commercial Computer Software Documentation", as such terms are * used in 48 CFR 12.212 or 48 CFR 227.7202-1 through 227.7202-4, * as applicable. */ import ilog.views.IlvGrapher; import ilog.views.IlvManagerView; import ilog.views.IlvPoint; import ilog.views.maps.IlvCoordinate; import ilog.views.maps.IlvCoordinateSystemProperty; import ilog.views.maps.IlvDisplayPreferencesProperty; import ilog.views.maps.IlvMapLayerTreeProperty; import ilog.views.maps.IlvMapScaleLimiter; import ilog.views.maps.beans.IlvJMapsManagerViewControlBar; import ilog.views.maps.beans.IlvLayerTreePanel; import ilog.views.maps.beans.IlvMapLayer; import ilog.views.maps.beans.IlvMapLayerTreeModel; import ilog.views.maps.beans.editor.IlvCoordinatePanelFactory; import ilog.views.maps.datasource.IlvGraphicLayerDataSource; import ilog.views.maps.datasource.IlvMapDataSourceModel; import ilog.views.maps.datasource.IlvMapDataSourceProperty; import ilog.views.maps.defense.symbology.app6a.IlvApp6aSymbol; import ilog.views.maps.defense.symbology.app6a.IlvApp6aSymbologyTreeViewActions; import ilog.views.maps.defense.terrain.IlvMapControllingPolyline; import ilog.views.maps.defense.terrain3d.component.Ilv3DCorridor; import ilog.views.maps.defense.terrain3d.component.Ilv3DExtrudedPolygon; import ilog.views.maps.defense.terrain3d.component.Ilv3DHemisphere; import ilog.views.maps.defense.terrain3d.component.Ilv3DLabel; import ilog.views.maps.defense.terrain3d.model.Ilv3DModel; import ilog.views.maps.defense.terrain3d.symbol.Ilv3DSymbolManager; import ilog.views.maps.defense.terrain3d.view.Ilv3DTrajectory; import ilog.views.maps.defense.terrain3d.view.Ilv3DView; import ilog.views.maps.defense.terrain3d.view.IlvFlyThroughAction; import ilog.views.maps.defense.terrain3d.view.IlvFlyThroughStyle; import ilog.views.maps.defense.terrain3d.view.IlvMapTerrainFlyThrough; import ilog.views.maps.format.dted.IlvRasterDTEDReader; import ilog.views.maps.graphic.style.StyleEvent; import ilog.views.maps.graphic.style.StyleListener; import ilog.views.maps.raster.datasource.IlvRasterDataSourceFactory; import ilog.views.maps.raster.datasource.IlvTiledRasterDataSource; import ilog.views.maps.srs.coordsys.IlvGeographicCoordinateSystem; import ilog.views.maps.symbology.swing.IlvSymbologyTreeView; import ilog.views.sdm.IlvSDMEngine; import ilog.views.sdm.IlvSDMException; import ilog.views.sdm.renderer.IlvRendererUtil; import ilog.views.sdm.renderer.IlvStyleSheetRenderer; import ilog.views.swing.IlvJScrollManagerView; import ilog.views.util.IlvProductUtil; import ilog.views.util.waitcursor.IlvWaitCursorManager; import java.awt.BorderLayout; import java.awt.Color; import java.awt.Dimension; import java.awt.Font; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.io.BufferedReader; import java.io.File; import java.io.IOException; import java.io.InputStreamReader; import java.net.URL; import java.util.StringTokenizer; import javax.swing.JFrame; import javax.swing.JSplitPane; import javax.swing.SwingUtilities; import javax.swing.Timer; /** * This class is a basic sample application that displays a 2D view and a 3D * view of the same DTED elevation data. A few symbols are also added to the * map, and automatically represented in the 3D view as well. * */ public class Simple3DScene extends JFrame { static { // This sample uses JViews Maps for Defense features. When deploying an // application that includes this code, you need to be in possession // of a Rogue Wave JViews Maps for Defense Deployment license. IlvProductUtil.DeploymentLicenseRequired( IlvProductUtil.JViews_Maps_for_Defense_Deployment); // replace the stylesheet renderer with map class. IlvRendererUtil.addRendererAlias(IlvRendererUtil.getRendererAlias(IlvStyleSheetRenderer.class.getName()), ilog.views.sdm.renderer.maps.IlvMapStyleSheetRenderer.class.getName()); } // members private IlvManagerView view; private Ilv3DView view3D; private IlvSDMEngine symbology; private JSplitPane p; private IlvApp6aSymbol moving, ground1, ground2; private Font font = new Font("Times New Roman", Font.ITALIC,16); //$NON-NLS-1$ /** * Convenience method to resolve URLs * @param resource * @return URL */ private static URL findURL(String resource) { URL rtnURL = null; if (new File(resource).exists()) { try { rtnURL = new File(resource).toURI().toURL(); } catch (Exception e) { e.printStackTrace(); } } else { rtnURL = Simple3DScene.class.getResource(resource); } return rtnURL; } /** * Constructor */ private Simple3DScene() { setTitle("Sample 3D application"); //$NON-NLS-1$ getContentPane().setLayout(new BorderLayout()); // create and configure manager view view = new IlvManagerView(); view.setManager(new IlvGrapher()); view.setBackground(new Color(168, 207, 247)); view.setSize(480, 480); view.setKeepingAspectRatio(true); view.getManager().setNamedProperty(new IlvCoordinateSystemProperty(IlvGeographicCoordinateSystem.WGS84)); IlvMapDataSourceModel dsm = IlvMapDataSourceProperty.GetMapDataSourceModel(view.getManager()); IlvMapLayerTreeModel ltm = IlvMapLayerTreeProperty.GetMapLayerTreeModel(view.getManager()); // limit zoom in/out IlvMapScaleLimiter limiter = new IlvMapScaleLimiter(1, (float) (1 / 1E9)); limiter.setView(view); // create DTED reader IlvRasterDTEDReader r = new IlvRasterDTEDReader(); try { // add DTED file r.addMap(findURL("data/N45.DT1"));//$NON-NLS-1$ } catch (IOException e) { // ignore } // Create a data source from the DTED reader, and insert it in the data // source model of the map IlvTiledRasterDataSource ds = IlvRasterDataSourceFactory.buildTiledImageDataSource(view.getManager(), r, true, false, null); dsm.insert(ds); ltm.addChild(null, ds.getInsertionLayer()); ds.getInsertionLayer().setName("DTED N45.DT1"); //$NON-NLS-1$ ds.getInsertionLayer().getStyle().setVisibleIn3DView(true); ds.start(); // create symbols. moving = new IlvApp6aSymbol("SFAPMHR----CUS-", Math.toRadians(10.5), Math.toRadians(45.5)); //$NON-NLS-1$ ground1 = new IlvApp6aSymbol("SFAPMHR----CUS-", Math.toRadians(10.86), Math.toRadians(45.9));//$NON-NLS-1$ ground2 = new IlvApp6aSymbol("SHGPEWMAS-FA--A", Math.toRadians(10.875), Math.toRadians(45.885));//$NON-NLS-1$ // add symbols on the map and start the map loading process buildSymbology(view); // build the 3D view. build3DScene(); buildFlyThrough(view); // configure GUI IlvJScrollManagerView scroll = new IlvJScrollManagerView(view); scroll.setPreferredSize(view.getSize()); p = new JSplitPane(JSplitPane.VERTICAL_SPLIT, scroll, view3D); IlvJMapsManagerViewControlBar toolbar = new IlvJMapsManagerViewControlBar(); toolbar.setView(view); getContentPane().add(toolbar, BorderLayout.NORTH); getContentPane().add(p, BorderLayout.CENTER); IlvLayerTreePanel pp=new IlvLayerTreePanel();pp.setView(view); getContentPane().add(pp,BorderLayout.EAST); setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); pack(); } private void buildFlyThrough(IlvManagerView view1) { // Retrieve some global properties of the manager. IlvMapDataSourceModel dsm = IlvMapDataSourceProperty.GetMapDataSourceModel(view1.getManager()); IlvMapLayerTreeModel ltm = IlvMapLayerTreeProperty.GetMapLayerTreeModel(view1.getManager()); // Create a data source to store the fly through polygon. IlvGraphicLayerDataSource ds = new IlvGraphicLayerDataSource(); ds.setManager(view1.getManager()); // insert the data source into the manager's data source tree. dsm.insert(ds); // set its layer up. final IlvMapLayer layer = ds.getInsertionLayer(); layer.setAllowingMoveObjects(true); layer.setName("Fly Through"); //$NON-NLS-1$ IlvFlyThroughStyle flyThroughStyle=new IlvFlyThroughStyle(); flyThroughStyle.setAltitude(100); flyThroughStyle.setSpeed(100); layer.setStyle(flyThroughStyle); // insert the layer on the manager's layer tree ltm.addChild(null, layer); // Create a fly through graphical object. IlvPoint points[]; points = new IlvPoint[] { new IlvPoint((float)Math.toRadians(10.2), -(float)Math.toRadians(45.2)), new IlvPoint((float)Math.toRadians(10.2), -(float)Math.toRadians(45.3)), new IlvPoint((float)Math.toRadians(10.5), -(float)Math.toRadians(45.4)), new IlvPoint((float)Math.toRadians(10.8), -(float)Math.toRadians(45.8)), }; final IlvMapTerrainFlyThrough flyThroughGraphics = new IlvMapTerrainFlyThrough(points); flyThroughGraphics.setStyle(layer.getStyle()); // add a listener to register a new fly through action on the 3D view when the polygon changes. flyThroughGraphics.addChangeListener(new IlvMapControllingPolyline.ComputeListener() { public void computationDone(IlvMapControllingPolyline tc) { registerFlyThroughAction(tc,layer); } }); // add some control that updates the fly through when layer style changes. flyThroughStyle.addStyleListener(new StyleListener() { public void styleChanged(StyleEvent event) { if (event.getAttribute().equals(IlvFlyThroughStyle.SPEED) ||event.getAttribute().equals(IlvFlyThroughStyle.HEIGHT)) { registerFlyThroughAction(flyThroughGraphics,layer); } } }); // Add the fly through graphical object to the data source. ds.add(flyThroughGraphics,IlvGeographicCoordinateSystem.KERNEL); // Start the data source to transform the polygon and display it on the view. try { ds.start(); } catch (Exception e) { e.printStackTrace(); } // register initial action: registerFlyThroughAction(flyThroughGraphics,layer); } void registerFlyThroughAction(IlvMapControllingPolyline flyThroughGraphics,IlvMapLayer layer) { // retrieve the fly through coordinates: IlvCoordinate []coords=flyThroughGraphics.getLatLongs(); // retrieve other parameters in the object style IlvFlyThroughStyle ftstyle=(IlvFlyThroughStyle)flyThroughGraphics.getStyle(); // create a fly through trajectory Ilv3DTrajectory.Point [] trajPoints=new Ilv3DTrajectory.Point[coords.length]; for (int i = 0; i < coords.length; i++) { Ilv3DTrajectory.Point lookat = null; if (i< (coords.length-1)) { lookat = new Ilv3DTrajectory.Point(ftstyle.getSpeed(),coords[i+1].x,coords[i+1].y,ftstyle.getAltitude()*0.9); } trajPoints[i]=new Ilv3DTrajectory.Point(ftstyle.getSpeed(),coords[i].x,coords[i].y,ftstyle.getAltitude(),lookat); } Ilv3DTrajectory traj= new Ilv3DTrajectory(trajPoints); // Create the fly through action and register it IlvFlyThroughAction action = new IlvFlyThroughAction(layer.getName(), traj,view3D); view3D.registerFlyThrough(layer,action); } /** * This method adds a few symbols on the map * @param v */ private void buildSymbology(IlvManagerView v) { try { URL symbolCss = findURL("data/app6.css");//$NON-NLS-1$ symbology = new IlvSDMEngine(); symbology.setReferenceView(v); symbology.setHighlightingSelection(false); symbology.setGrapher((IlvGrapher) v.getManager()); symbology.setStyleSheets(new String[] { symbolCss.toString() }); symbology.getModel().setAdjusting(true); symbology.getModel().addObject(moving, null, null); symbology.getModel().setObjectProperty(moving, IlvApp6aSymbol.MODIFIER_ALTITUDE_OR_DEPTH, "1000");//$NON-NLS-1$ symbology.getModel().setObjectProperty(moving, IlvApp6aSymbol.MODIFIER_DIRECTION_OF_MOVEMENT_INDICATOR, "100");//$NON-NLS-1$ symbology.getModel().addObject(ground1, null, null); symbology.getModel().addObject(ground2, null, null); symbology.getModel().setAdjusting(false); } catch (IlvSDMException e) { e.printStackTrace(); } // show symbology panel IlvSymbologyTreeView symbPanel = new IlvSymbologyTreeView(symbology); IlvApp6aSymbologyTreeViewActions app6Actions = new IlvApp6aSymbologyTreeViewActions(); app6Actions.setLatLonPicker(new IlvCoordinatePanelFactory.CoordPointInputPanel(v, IlvDisplayPreferencesProperty.GetDisplayPreferences(v.getManager()).getCoordinateFormatter())); symbPanel.setSymbologyTreeViewActions(app6Actions); getContentPane().add(symbPanel, BorderLayout.WEST); Timer timer = new Timer(20, new ActionListener() { public void actionPerformed(ActionEvent e) { long t = System.currentTimeMillis(); double lon = Math.toRadians(10.5 + 0.2 * Math.cos(t / 5000.0)); double lat = Math.toRadians(45.5 + 0.2 * Math.sin(t / 5000.0)); symbology.getModel().setAdjusting(true); symbology.getModel().setObjectProperty(moving, "longitude", new Double(lon)); //$NON-NLS-1$ symbology.getModel().setObjectProperty(moving, "latitude", new Double(lat)); //$NON-NLS-1$ symbology.getModel().setAdjusting(false); } }); timer.start(); } /** * this method monitors performs 3D view creation when the data source. * */ void build3DScene() { view.fitTransformerToContent(); view.repaint(); Ilv3DModel model3D = new Ilv3DModel(view.getManager()); // model3D.setKeepElevationDataCache(false); // build 3D terrain for specified region model3D.buildTerrain(Math.toRadians(10), Math.toRadians(45), Math.toRadians(11), Math.toRadians(46)); URL url = findURL("data/zones.txt"); //$NON-NLS-1$ createExtrudedPolygons(model3D,url); // create 3D hemisphere (radius in meters) Ilv3DHemisphere hemiSphere1 = new Ilv3DHemisphere(ground1.getLongitude(), ground1.getLatitude(), 0, 1000); hemiSphere1.setColor(new Color(0f, 0.5f, 0, 0.3f)); hemiSphere1.setLonLatSteps(40); hemiSphere1.setElevationSteps(40); model3D.add3DComponent(hemiSphere1); // create 3D hemisphere (radius in meters) Ilv3DHemisphere hemiSphere2 = new Ilv3DHemisphere(ground2.getLongitude(), ground2.getLatitude(), 0, 1000); hemiSphere2.setColor(new Color(1.0f, 0.3f, 0.3f, 0.5f)); hemiSphere2.setLonLatSteps(20); hemiSphere2.setElevationSteps(20); model3D.add3DComponent(hemiSphere2); // corridor coordinates final double[] longs; final double[] lats; final double[] elevs; final double[] radiuses; longs = new double[] {Math.toRadians(10.57), Math.toRadians(10.62), Math.toRadians(10.68),Math.toRadians(10.79), ground2.getLongitude()}; lats = new double[] {Math.toRadians(45.53), Math.toRadians(45.6), Math.toRadians(45.65),Math.toRadians(45.75), ground2.getLatitude()}; elevs = new double[] { 3000, 2000, 1200, 500, 250 }; radiuses = new double[] { 2000, 1500, 1000, 500, 200 }; // in meters // create 3D corridor Ilv3DCorridor corridor = new Ilv3DCorridor(longs, lats, elevs, radiuses); corridor.setStepsAlongAxis(1); corridor.setStepsAboutAxis(20); corridor.setColor(new Color(0.3f, 0.3f, 0.6f, 0.5f)); model3D.add3DComponent(corridor); // create 3D labels addLabelForSymbol(ground1,font,model3D); addLabelForSymbol(ground2,font,model3D); // create 3D view view3D = new Ilv3DView(model3D); view3D.setUseLighting(true); view3D.setPreferredSize(new Dimension(640, 400)); // create a 3D symbol manager, and set it on the 3D model Ilv3DSymbolManager symbolManager = new Ilv3DSymbolManager(symbology, view3D); model3D.setSymbolManager(symbolManager); } private void createExtrudedPolygons(Ilv3DModel model3D, URL url) { try { InputStreamReader isr = new InputStreamReader(url.openStream()); BufferedReader buf = new BufferedReader(isr); while(true) { String label = buf.readLine(); if (label == null) { // no more lines to read break; } if (label.length() == 0) { continue; } String color = buf.readLine(); String line = buf.readLine(); StringTokenizer st = new StringTokenizer(line," ,"); //$NON-NLS-1$ int count = st.countTokens() / 2; double[] xi = new double[count]; double[] yi = new double[count]; double centerX = 0; double centerY = 0; for (int i = count-1; i >=0; i--) { String lon = st.nextToken(); String lat = st.nextToken(); xi[i] = Double.parseDouble(lon); yi[i] = Double.parseDouble(lat); centerX += xi[i]; centerY += yi[i]; } // create extruded polygon double altitude = 500; Ilv3DExtrudedPolygon polygon = new Ilv3DExtrudedPolygon(xi,yi,0,400); st = new StringTokenizer(color,","); //$NON-NLS-1$ int[] colorElements = new int[]{128,128,128,255}; int i=0; while (st.hasMoreElements()) { colorElements[i] = Integer.parseInt(st.nextToken()); i++; } polygon.setColor(new Color(colorElements[0],colorElements[1],colorElements[2],colorElements[3])); model3D.add3DComponent(polygon); Ilv3DLabel label1 = new Ilv3DLabel(centerX/count,centerY/count, altitude +20, label,font); label1.setHorizontalOffset(10); label1.setVerticalOffset(10); label1.setOutlineWidth(3.0f); model3D.add3DComponent(label1); } } catch (IOException e) { // ignore } } private void addLabelForSymbol(IlvApp6aSymbol symbol, Font symbolfont, Ilv3DModel model3D) { double groundHeight = model3D.getGroundHeightAt(symbol.getLongitude(), -symbol.getLatitude()); String alt = (String)symbol.getProperty( IlvApp6aSymbol.MODIFIER_ALTITUDE_OR_DEPTH); double altitude = 0; if (alt != null) { altitude = Double.parseDouble(alt); } else { alt = "0"; //$NON-NLS-1$ } Ilv3DLabel label1 = new Ilv3DLabel(symbol.getLongitude(),symbol.getLatitude(), altitude + 1000 + groundHeight, "Alt = " + alt,symbolfont); //$NON-NLS-1$ label1.setHorizontalOffset(20); label1.setVerticalOffset(10); label1.setOutlineWidth(3.0f); model3D.add3DComponent(label1); } /** * Main method * @param args unused parameter. */ public static void main(String[] args) { SwingUtilities.invokeLater(new Runnable() { public void run() { IlvWaitCursorManager.init(); // magically fixes the 'unable to set pixel format ...' jogl exception by pushing a new EventQueue Simple3DScene frame = new Simple3DScene(); frame.setVisible(true); } }); } }