View Javadoc

1   /*
2    *  soapUI, copyright (C) 2004-2010 eviware.com 
3    *
4    *  soapUI is free software; you can redistribute it and/or modify it under the 
5    *  terms of version 2.1 of the GNU Lesser General Public License as published by 
6    *  the Free Software Foundation.
7    *
8    *  soapUI is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without 
9    *  even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 
10   *  See the GNU Lesser General Public License for more details at gnu.org.
11   */
12  
13  package com.eviware.soapui.support.editor;
14  
15  import com.eviware.soapui.support.components.*;
16  
17  import javax.swing.*;
18  import javax.swing.event.ChangeEvent;
19  import javax.swing.event.ChangeListener;
20  import java.awt.*;
21  import java.beans.PropertyChangeEvent;
22  import java.beans.PropertyChangeListener;
23  import java.util.ArrayList;
24  import java.util.List;
25  
26  /***
27   * Editor-framework for Documents
28   * 
29   * @author ole.matzura
30   */
31  
32  @SuppressWarnings( "serial" )
33  public class Editor<T extends EditorDocument> extends JPanel implements PropertyChangeListener,
34  		EditorLocationListener<T>
35  {
36  	private JTabbedPane inputTabs;
37  	private List<EditorView<T>> views = new ArrayList<EditorView<T>>();
38  	private EditorView<T> currentView;
39  	private T document;
40  	private JInspectorPanel inspectorPanel;
41  	private InputTabsChangeListener inputTabsChangeListener;
42  
43  	public Editor( T document )
44  	{
45  		super( new BorderLayout() );
46  		this.document = document;
47  
48  		setBackground( Color.LIGHT_GRAY );
49  		inputTabs = new JTabbedPane( JTabbedPane.LEFT, JTabbedPane.SCROLL_TAB_LAYOUT );
50  		inputTabs.setUI( new VerticalTabbedPaneUI() );
51  
52  		inputTabs.setFont( inputTabs.getFont().deriveFont( 8 ) );
53  		inputTabsChangeListener = new InputTabsChangeListener();
54  		inputTabs.addChangeListener( inputTabsChangeListener );
55  
56  		inspectorPanel = JInspectorPanelFactory.build( inputTabs );
57  		add( inspectorPanel.getComponent(), BorderLayout.CENTER );
58  	}
59  
60  	public void addEditorView( EditorView<T> editorView )
61  	{
62  		views.add( editorView );
63  
64  		inputTabs.addTab( null, new VTextIcon( inputTabs, editorView.getTitle(), VTextIcon.ROTATE_LEFT ), editorView
65  				.getComponent() );
66  
67  		editorView.addPropertyChangeListener( this );
68  		editorView.addLocationListener( this );
69  
70  		editorView.setDocument( document );
71  	}
72  
73  	public void propertyChange( PropertyChangeEvent evt )
74  	{
75  		if( evt.getPropertyName().equals( EditorView.TITLE_PROPERTY ) )
76  		{
77  			int ix = views.indexOf( evt.getSource() );
78  			if( ix == -1 )
79  				return;
80  
81  			inputTabs.setTitleAt( ix, ( String )evt.getNewValue() );
82  		}
83  	}
84  
85  	public void selectView( int viewIndex )
86  	{
87  		inputTabs.setSelectedIndex( viewIndex );
88  	}
89  
90  	public void selectView( String viewId )
91  	{
92  		for( int c = 0; c < views.size(); c++ )
93  		{
94  			if( views.get( c ).getViewId().equals( viewId ) )
95  			{
96  				inputTabs.setSelectedIndex( c );
97  				return;
98  			}
99  		}
100 	}
101 
102 	@SuppressWarnings( "unchecked" )
103 	public void locationChanged( EditorLocation<T> location )
104 	{
105 		if( location != null )
106 		{
107 			for( Inspector inspector : inspectorPanel.getInspectors() )
108 			{
109 				( ( EditorInspector<T> )inspector ).locationChanged( location );
110 			}
111 		}
112 	}
113 
114 	public void requestFocus()
115 	{
116 		if( currentView != null )
117 			currentView.getComponent().requestFocus();
118 	}
119 
120 	public T getDocument()
121 	{
122 		return document;
123 	}
124 
125 	public boolean hasFocus()
126 	{
127 		return currentView == null ? false : currentView.getComponent().hasFocus();
128 	}
129 
130 	public final void setDocument( T document )
131 	{
132 		if( this.document != null )
133 			this.document.release();
134 
135 		this.document = document;
136 
137 		for( EditorView<T> view : views )
138 		{
139 			view.setDocument( document );
140 		}
141 	}
142 
143 	public final EditorView<T> getCurrentView()
144 	{
145 		return currentView;
146 	}
147 
148 	public final JTabbedPane getInputTabs()
149 	{
150 		return inputTabs;
151 	}
152 
153 	public final List<EditorView<T>> getViews()
154 	{
155 		return views;
156 	}
157 
158 	public EditorView<T> getView( String viewId )
159 	{
160 		for( EditorView<T> view : views )
161 		{
162 			if( view.getViewId().equals( viewId ) )
163 				return view;
164 		}
165 
166 		return null;
167 	}
168 
169 	public Inspector getInspector( String inspectorId )
170 	{
171 		return inspectorPanel.getInspector( inspectorId );
172 	}
173 
174 	public void setEditable( boolean enabled )
175 	{
176 		for( EditorView<T> view : views )
177 		{
178 			view.setEditable( enabled );
179 		}
180 	}
181 
182 	public void addInspector( EditorInspector<T> inspector )
183 	{
184 		inspectorPanel.addInspector( inspector );
185 		inspectorPanel
186 				.setInspectorVisible( inspector, currentView == null ? true : inspector.isEnabledFor( currentView ) );
187 	}
188 
189 	private final class InputTabsChangeListener implements ChangeListener
190 	{
191 		private int lastDividerLocation;
192 
193 		@SuppressWarnings( "unchecked" )
194 		public void stateChanged( ChangeEvent e )
195 		{
196 			int currentViewIndex = views.indexOf( currentView );
197 
198 			if( currentView != null )
199 			{
200 				if( inputTabs.getSelectedIndex() == currentViewIndex )
201 					return;
202 
203 				if( !currentView.deactivate() )
204 				{
205 					inputTabs.setSelectedIndex( currentViewIndex );
206 					return;
207 				}
208 			}
209 
210 			EditorView<T> previousView = currentView;
211 			int selectedIndex = inputTabs.getSelectedIndex();
212 			if( selectedIndex == -1 )
213 			{
214 				currentView = null;
215 				return;
216 			}
217 
218 			currentView = views.get( selectedIndex );
219 
220 			if( currentView != null
221 					&& !currentView.activate( previousView == null ? null : previousView.getEditorLocation() ) )
222 			{
223 				inputTabs.setSelectedIndex( currentViewIndex );
224 				if( currentViewIndex == -1 )
225 					return;
226 			}
227 
228 			EditorInspector<T> currentInspector = ( EditorInspector<T> )inspectorPanel.getCurrentInspector();
229 
230 			if( currentInspector != null )
231 			{
232 				lastDividerLocation = inspectorPanel.getDividerLocation();
233 			}
234 
235 			for( Inspector inspector : inspectorPanel.getInspectors() )
236 			{
237 				inspectorPanel.setInspectorVisible( inspector, ( ( EditorInspector<T> )inspector )
238 						.isEnabledFor( currentView ) );
239 			}
240 
241 			if( currentInspector != null && ( ( EditorInspector<T> )currentInspector ).isEnabledFor( currentView ) )
242 			{
243 				if( lastDividerLocation == 0 )
244 					inspectorPanel.setResetDividerLocation();
245 				else
246 					inspectorPanel.setDividerLocation( lastDividerLocation );
247 			}
248 			else
249 				currentInspector = null;
250 
251 			SwingUtilities.invokeLater( new Runnable()
252 			{
253 
254 				public void run()
255 				{
256 					if( currentView != null )
257 						currentView.getComponent().requestFocus();
258 				}
259 			} );
260 		}
261 	}
262 
263 	public void release()
264 	{
265 		for( EditorView<T> view : views )
266 		{
267 			view.release();
268 			view.removePropertyChangeListener( this );
269 		}
270 
271 		views.clear();
272 
273 		inputTabs.removeChangeListener( inputTabsChangeListener );
274 		inputTabs.removeAll();
275 
276 		inspectorPanel.release();
277 		document.release();
278 	}
279 }