arcgissamples\cartography\SplineTextMain.java
/* Copyright 2010 ESRI * * All rights reserved under the copyright laws of the United States * and applicable international laws, treaties, and conventions. * * You may freely redistribute and use this sample code, with or * without modification, provided you include the original copyright * notice and use restrictions. * * See the use restrictions. * */ package arcgissamples.cartography; import java.awt.BorderLayout; import java.awt.Dimension; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; import java.io.IOException; import javax.swing.JFrame; import javax.swing.JLabel; import javax.swing.UIManager; import com.esri.arcgis.beans.map.MapBean; import com.esri.arcgis.carto.LineElement; import com.esri.arcgis.carto.TextElement; import com.esri.arcgis.carto.esriViewDrawPhase; import com.esri.arcgis.controls.IMapControlEvents2Adapter; import com.esri.arcgis.controls.IMapControlEvents2OnDoubleClickEvent; import com.esri.arcgis.controls.IMapControlEvents2OnKeyDownEvent; import com.esri.arcgis.controls.IMapControlEvents2OnKeyUpEvent; import com.esri.arcgis.controls.IMapControlEvents2OnMouseDownEvent; import com.esri.arcgis.controls.IMapControlEvents2OnMouseMoveEvent; import com.esri.arcgis.display.INewBezierCurveFeedback; import com.esri.arcgis.display.IScreenDisplay; import com.esri.arcgis.display.ISymbol; import com.esri.arcgis.display.NewBezierCurveFeedback; import com.esri.arcgis.display.RgbColor; import com.esri.arcgis.display.SimpleLineSymbol; import com.esri.arcgis.display.SimpleTextPath; import com.esri.arcgis.display.TextSymbol; import com.esri.arcgis.display.esriScreenCache; import com.esri.arcgis.display.esriSimpleLineStyle; import com.esri.arcgis.display.esriTextHorizontalAlignment; import com.esri.arcgis.display.esriTextVerticalAlignment; import com.esri.arcgis.geometry.ICurve; import com.esri.arcgis.geometry.IPoint; import com.esri.arcgis.geometry.IPolyline; import com.esri.arcgis.system.AoInitialize; import com.esri.arcgis.system.EngineInitializer; import com.esri.arcgis.system.esriLicenseProductCode; import com.esri.arcgis.system.esriLicenseStatus; import com.esri.arcgis.interop.AutomationException; /** * This sample demonstrates a way to draw a spline text along bezier curve. */ public class SplineTextMain extends JFrame { private static final long serialVersionUID = 1L; static AoInitialize aoInit; boolean tracking = false; MapBean mapBean = new MapBean(); JLabel textLabel = new JLabel(); SimpleTextPath textPath; TextSymbol textSymbol; ICurve curve; boolean typing; INewBezierCurveFeedback newBzCurveFeedback; // Feedback object to track a bezier curve public SplineTextMain() { initUI(); } public static void main(String s[]) { try { EngineInitializer.initializeVisualBeans(); UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); initializeArcGISLicenses(); new SplineTextMain(); } catch (Exception ex) { ex.printStackTrace(); } } static void initializeArcGISLicenses() { try { aoInit = new AoInitialize(); if (aoInit.isProductCodeAvailable(esriLicenseProductCode.esriLicenseProductCodeEngine) == esriLicenseStatus.esriLicenseAvailable) aoInit.initialize(esriLicenseProductCode.esriLicenseProductCodeEngine); else if (aoInit.isProductCodeAvailable(esriLicenseProductCode.esriLicenseProductCodeArcView) == esriLicenseStatus.esriLicenseAvailable) aoInit.initialize(esriLicenseProductCode.esriLicenseProductCodeArcView); } catch (Exception e) { e.printStackTrace(); } } /** * Lay out the User Interface, and set up event listeners */ private void initUI() { this.setTitle("Spline Text Sample Application"); this.setSize(new Dimension(600, 500)); this.getContentPane().setLayout(new BorderLayout()); this.textLabel.setText("Draw spline, doulble click, type letters, hit Enter."); this.getContentPane().add(this.mapBean, BorderLayout.CENTER); this.getContentPane().add(this.textLabel, BorderLayout.SOUTH); this.setVisible(true); // set listeners try { this.mapBean.addIMapControlEvents2Listener( new IMapControlEvents2Adapter() { private static final long serialVersionUID = 1L; public void onMouseDown(IMapControlEvents2OnMouseDownEvent event) throws IOException, AutomationException { supportMouseDown(event); } public void onDoubleClick(IMapControlEvents2OnDoubleClickEvent event) throws IOException, AutomationException { supportDoubleClick(); } public void onMouseMove(IMapControlEvents2OnMouseMoveEvent event) throws IOException, AutomationException { supportMouseMove(event); } public void onKeyDown(IMapControlEvents2OnKeyDownEvent event) throws IOException, AutomationException { supportKeyDown(event); } public void onKeyUp(IMapControlEvents2OnKeyUpEvent event) throws IOException, AutomationException { supportKeyUp(event); } }); } catch( IOException e) { e.printStackTrace(); // never happened } this.addWindowListener(new WindowAdapter() { public void windowClosing(WindowEvent e) { try { aoInit.shutdown(); } catch(IOException ex) { // exit anyway } System.exit(0); } }); } /** * Support mouse events for mapBean */ protected void supportMouseDown(IMapControlEvents2OnMouseDownEvent event) throws IOException, AutomationException { this.tracking = true; IPoint pnt = this.mapBean.getActiveView().getScreenDisplay().getDisplayTransformation().toMapPoint(event.getX(), event.getY()); if( this.newBzCurveFeedback == null ) { // Create a symbol (and color) for the feedback, and set the start point. this.newBzCurveFeedback = new NewBezierCurveFeedback(); this.newBzCurveFeedback.setDisplayByRef( this.mapBean.getActiveView().getScreenDisplay() ); this.newBzCurveFeedback.start(pnt); } else { // Otherwise use the current mouse location to add a vertex to the current feedback. this.newBzCurveFeedback.addPoint(pnt); } } /** * Support mouse events for mapBean */ public void supportDoubleClick() throws IOException, AutomationException { this.tracking = false; // Get the geometry (Line) returned from the feedback IPolyline geomLn = this.newBzCurveFeedback.stop(); this.newBzCurveFeedback = null; // If it is valid then create a LineElement on the ActiveView using the 'AddCreateElement' procedure if( geomLn != null ) { // Create the TextPath and set it's geometry with the new curve. this.curve = geomLn; this.textPath = new SimpleTextPath(); this.textPath.setGeometryByRef(this.curve); // Create a Line so we can see where the text will go. addCreateElement(); this.mapBean.getActiveView().partialRefresh(esriViewDrawPhase.esriViewGraphics, null, null); // User should now enter text. setupSymbol(); drawCurrentText(); this.textSymbol.setText(""); this.typing = true; } } /** * Support mouse events for mapBean */ protected void supportMouseMove(IMapControlEvents2OnMouseMoveEvent event) throws IOException, AutomationException { // Check if the user is currently using the feedback. IPoint pnt = this.mapBean.getActiveView().getScreenDisplay().getDisplayTransformation().toMapPoint(event.getX(), event.getY()); if(this.tracking){ this.newBzCurveFeedback.moveTo(pnt); } } /** * Support mouse events for mapBean */ public void supportKeyDown(IMapControlEvents2OnKeyDownEvent event) throws IOException, AutomationException { // If we are in typing mode (i.e. have finished tracking the Line), check for the user pressing return. int keyCode = event.getKeyCode(); if( (keyCode == 13 || keyCode == 27) && this.typing ) { // 12 - return, 27 - escape // Now finish the Text, and add a TextElement to the view to make the text persistent. makePath(); this.typing = false; } } /** * Support mouse events for mapBean */ public void supportKeyUp(IMapControlEvents2OnKeyUpEvent event) throws IOException, AutomationException { // Add each character to the end of the Text string. int keyCode = event.getKeyCode(); if (keyCode == 16) { // shift key return; } int shiftCode = event.getShift(); if (keyCode >= 65 && keyCode <= 90) { if (shiftCode == 0) { keyCode += 32; } } if( this.typing ) { this.textSymbol.setText(this.textSymbol.getText() + String.valueOf((char)keyCode) ); // Draw the current symbol to the active view. drawCurrentText(); } } /** * This routine creates a Line element. * We use the IElement interface to set the LineElement's Geometry. */ private void addCreateElement() throws IOException, AutomationException { // create line element LineElement elem = new LineElement(); elem.setGeometry(this.curve); RgbColor rgb = new RgbColor(); rgb.setRed(255); rgb.setGreen(0); rgb.setBlue(255); SimpleLineSymbol simpleLnSym = new SimpleLineSymbol(); simpleLnSym.setColor(rgb); simpleLnSym.setStyle(esriSimpleLineStyle.esriSLSSolid); elem.setSymbol(simpleLnSym); // add element in the map this.mapBean.getActiveView().getGraphicsContainer().addElement(elem, 0); } /** * Set up a TextSymbol for drawing the text. */ private void setupSymbol() throws IOException, AutomationException { RgbColor color = new RgbColor(); color.setRGB(0); this.textSymbol = new TextSymbol(); this.textSymbol.setColor(color); this.textSymbol.setHorizontalAlignment(esriTextHorizontalAlignment.esriTHALeft); this.textSymbol.setVerticalAlignment(esriTextVerticalAlignment.esriTVABaseline); this.textSymbol.setClip(false); this.textSymbol.setSize(20); // Set it's TextPath to be the TextPath we created. Now text will be splined along this line. this.textSymbol.setTextPathByRef(this.textPath); this.textSymbol.setText("Text"); this.textSymbol.setXOffset(0); this.textSymbol.setYOffset(0); } /** * Draw the current text to the display. */ private void drawCurrentText() throws IOException, AutomationException { IScreenDisplay screenDisplay = this.mapBean.getActiveView().getScreenDisplay(); screenDisplay.startDrawing(0, (short)esriScreenCache.esriNoScreenCache); ISymbol symbol = this.textSymbol; screenDisplay.setSymbol(symbol); screenDisplay.drawText( this.curve, this.textSymbol.getText() ); screenDisplay.finishDrawing(); } /** * Create a graphic element to persist our new text. */ private void makePath() throws IOException, AutomationException { TextElement textElement = new TextElement(); textElement.setScaleText(false); textElement.setSymbol(this.textSymbol); textElement.setText(this.textSymbol.getText()); // Set the element's Geometry. textElement.setGeometry(this.curve); // If we're using a Line or Bezier curve, we add a graphic to the view to show the line this.mapBean.getActiveView().getGraphicsContainer().addElement(textElement, 0); this.mapBean.getActiveView().partialRefresh(esriViewDrawPhase.esriViewGraphics, null, null); } }