1 /*******************************************************************************
2 * Copyright (c) 2003 Berthold Daum.
3 * All rights reserved. This program and the accompanying materials
4 * are made available under the terms of the Common Public License v1.0
5 * which accompanies this distribution, and is available at
6 * http://www.eclipse.org/legal/cpl-v10.html
10 *******************************************************************************/
11 package net.sourceforge.phpeclipse.ui.overlaypages;
13 import org.eclipse.core.resources.IResource;
14 import org.eclipse.core.runtime.CoreException;
15 import org.eclipse.core.runtime.QualifiedName;
16 import org.eclipse.jface.preference.IPreferenceNode;
17 import org.eclipse.jface.preference.IPreferencePage;
18 import org.eclipse.jface.preference.IPreferenceStore;
19 import org.eclipse.jface.preference.PreferenceDialog;
20 import org.eclipse.jface.preference.PreferenceManager;
21 import org.eclipse.jface.preference.PreferenceNode;
22 import org.eclipse.jface.resource.ImageDescriptor;
23 import org.eclipse.swt.SWT;
24 import org.eclipse.swt.custom.BusyIndicator;
25 import org.eclipse.swt.custom.CTabFolder;
26 import org.eclipse.swt.events.SelectionAdapter;
27 import org.eclipse.swt.events.SelectionEvent;
28 import org.eclipse.swt.layout.GridData;
29 import org.eclipse.swt.layout.GridLayout;
30 import org.eclipse.swt.widgets.Button;
31 import org.eclipse.swt.widgets.Composite;
32 import org.eclipse.swt.widgets.Control;
33 import org.eclipse.swt.widgets.TabFolder;
34 import org.eclipse.ui.dialogs.PropertyPage;
35 import org.eclipse.ui.part.PageBook;
38 * @author Berthold Daum
40 public abstract class OverlayPage extends PropertyPage {
42 /*** Name of resource property for the selection of workbench or project settings ***/
43 public static final String USEPROJECTSETTINGS = "useProjectSettings"; //$NON-NLS-1$
45 private static final String FALSE = "false"; //$NON-NLS-1$
46 private static final String TRUE = "true"; //$NON-NLS-1$
48 // Additional buttons for property pages
49 private Button useWorkspaceSettingsButton,
50 useProjectSettingsButton,
53 // Overlay preference store for property pages
54 private PropertyStore overlayStore;
56 // The image descriptor of this pages title image
57 private ImageDescriptor image;
60 private String pageId;
62 // Container for subclass controls
63 private Composite contents;
68 public OverlayPage() {
74 * @param title - title string
76 public OverlayPage(String title) {
83 * @param title - title string
84 * @param image - title image
86 public OverlayPage(String title, ImageDescriptor image) {
89 setImageDescriptor(image);
94 * Returns the id of the current preference page as defined in plugin.xml
95 * Subclasses must implement.
97 * @return - the qualifier
99 protected abstract String getPageId();
102 * Returns true if this instance represents a property page
103 * @return - true for property pages, false for preference pages
105 public boolean isPropertyPage() {
106 return getElement() != null;
110 * We need to implement createContents method. In case of property pages we insert two radio buttons
111 * and a push button at the top of the page. Below this group we create a new composite for the contents
112 * created by subclasses.
114 * @see org.eclipse.jface.preference.PreferencePage#createContents(org.eclipse.swt.widgets.Composite)
116 protected Control createContents(Composite parent) {
117 if (isPropertyPage())
118 createSelectionGroup(parent);
119 contents = new Composite(parent, SWT.NONE);
120 GridLayout layout = new GridLayout();
121 layout.marginHeight = 0;
122 layout.marginWidth = 0;
123 contents.setLayout(layout);
124 contents.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
129 * Creates and initializes a selection group with two choice buttons and one push button.
130 * @param parent - the parent composite
132 private void createSelectionGroup(Composite parent) {
133 Composite comp = new Composite(parent, SWT.NONE);
134 GridLayout layout = new GridLayout(2, false);
135 layout.marginHeight = 0;
136 layout.marginWidth = 0;
137 comp.setLayout(layout);
138 comp.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
139 Composite radioGroup = new Composite(comp, SWT.NONE);
140 radioGroup.setLayout(new GridLayout());
141 radioGroup.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
142 useWorkspaceSettingsButton = createRadioButton(radioGroup, Messages.getString("OverlayPage.Use_Workspace_Settings")); //$NON-NLS-1$
143 useProjectSettingsButton = createRadioButton(radioGroup, Messages.getString("OverlayPage.Use_Project_Settings")); //$NON-NLS-1$
144 configureButton = new Button(comp, SWT.PUSH);
145 configureButton.setText(Messages.getString("OverlayPage.Configure_Workspace_Settings")); //$NON-NLS-1$
146 configureButton.addSelectionListener(new SelectionAdapter() {
147 public void widgetSelected(SelectionEvent e) {
148 configureWorkspaceSettings();
151 // Set workspace/project radio buttons
154 ((IResource) getElement()).getPersistentProperty(
155 new QualifiedName(pageId, USEPROJECTSETTINGS));
156 if (TRUE.equals(use)) {
157 useProjectSettingsButton.setSelection(true);
158 configureButton.setEnabled(false);
160 useWorkspaceSettingsButton.setSelection(true);
161 } catch (CoreException e) {
162 useWorkspaceSettingsButton.setSelection(true);
167 * Convenience method creating a radio button
168 * @param parent - the parent composite
169 * @param label - the button label
170 * @return - the new button
172 private Button createRadioButton(Composite parent, String label) {
173 final Button button = new Button(parent, SWT.RADIO);
174 button.setText(label);
175 button.addSelectionListener(new SelectionAdapter() {
176 public void widgetSelected(SelectionEvent e) {
177 configureButton.setEnabled(
178 button == useWorkspaceSettingsButton);
179 setControlsEnabled();
186 * In case of property pages we create a new PropertyStore as local overlay store.
187 * After all controls have been create, we enable/disable these controls
189 * @see org.eclipse.jface.preference.PreferencePage#createControl()
191 public void createControl(Composite parent) {
192 // Special treatment for property pages
193 if (isPropertyPage()) {
195 pageId = getPageId();
196 // Create an overlay preference store and fill it with properties
199 (IResource) getElement(),
200 super.getPreferenceStore(),
202 // Set overlay store as current preference store
204 super.createControl(parent);
205 // Update enablement of all subclass controls
206 if (isPropertyPage())
207 setControlsEnabled();
211 * Returns in case of property pages the overlay store - otherwise the standard preference store
212 * @see org.eclipse.jface.preference.PreferencePage#getPreferenceStore()
214 public IPreferenceStore getPreferenceStore() {
215 if (isPropertyPage())
217 return super.getPreferenceStore();
221 * Enables or disables the controls of this page
223 private void setControlsEnabled() {
224 boolean enabled = useProjectSettingsButton.getSelection();
225 setControlsEnabled(enabled);
229 * Enables or disables the controls of this page
230 * Subclasses may override.
232 * @param enabled - true if controls shall be enabled
234 protected void setControlsEnabled(boolean enabled) {
235 setControlsEnabled(contents, enabled);
239 * Enables or disables a tree of controls starting at the specified root.
240 * We spare tabbed notebooks and pagebooks to allow for user navigation.
242 * @param root - the root composite
243 * @param enabled - true if controls shall be enabled
245 private void setControlsEnabled(Composite root, boolean enabled) {
246 Control[] children = root.getChildren();
247 for (int i = 0; i < children.length; i++) {
248 Control child = children[i];
249 if (!(child instanceof CTabFolder) && !(child instanceof TabFolder) && !(child instanceof PageBook))
250 child.setEnabled(enabled);
251 if (child instanceof Composite)
252 setControlsEnabled((Composite) child, enabled);
257 * We override the performOk method. In case of property pages
258 * we save the state of the radio buttons.
260 * @see org.eclipse.jface.preference.IPreferencePage#performOk()
262 public boolean performOk() {
263 boolean result = super.performOk();
264 if (result && isPropertyPage()) {
265 // Save state of radiobuttons in project properties
266 IResource resource = (IResource) getElement();
269 (useProjectSettingsButton.getSelection()) ? TRUE : FALSE;
270 resource.setPersistentProperty(
271 new QualifiedName(pageId, USEPROJECTSETTINGS),
273 } catch (CoreException e) {
280 * We override the performDefaults method. In case of property pages we
281 * switch back to the workspace settings and disable the page controls.
283 * @see org.eclipse.jface.preference.PreferencePage#performDefaults()
285 protected void performDefaults() {
286 if (isPropertyPage()) {
287 useWorkspaceSettingsButton.setSelection(true);
288 useProjectSettingsButton.setSelection(false);
289 configureButton.setEnabled(true);
290 setControlsEnabled();
292 super.performDefaults();
296 * Creates a new preferences page and opens it
297 * @see com.bdaum.SpellChecker.preferences.SpellCheckerPreferencePage#configureWorkspaceSettings()
299 protected void configureWorkspaceSettings() {
301 // create a new instance of the current class
302 IPreferencePage page =
303 (IPreferencePage) this.getClass().newInstance();
304 page.setTitle(getTitle());
305 page.setImageDescriptor(image);
307 showPreferencePage(pageId, page);
308 } catch (InstantiationException e) {
310 } catch (IllegalAccessException e) {
316 * Show a single preference pages
317 * @param id - the preference page identification
318 * @param page - the preference page
320 protected void showPreferencePage(String id, IPreferencePage page) {
321 final IPreferenceNode targetNode = new PreferenceNode(id, page);
322 PreferenceManager manager = new PreferenceManager();
323 manager.addToRoot(targetNode);
324 final PreferenceDialog dialog =
325 new PreferenceDialog(getControl().getShell(), manager);
326 BusyIndicator.showWhile(getControl().getDisplay(), new Runnable() {
329 dialog.setMessage(targetNode.getLabelText());