001: /*******************************************************************************
002: * Copyright (c) 2000, 2007 IBM Corporation and others.
003: * All rights reserved. This program and the accompanying materials
004: * are made available under the terms of the Eclipse Public License v1.0
005: * which accompanies this distribution, and is available at
006: * http://www.eclipse.org/legal/epl-v10.html
007: *
008: * Contributors:
009: * IBM Corporation - initial API and implementation
010: *******************************************************************************/package org.eclipse.ui.internal.registry;
011:
012: import java.io.File;
013: import java.io.Serializable;
014:
015: import org.eclipse.core.runtime.Assert;
016: import org.eclipse.core.runtime.CoreException;
017: import org.eclipse.core.runtime.IConfigurationElement;
018: import org.eclipse.jface.resource.ImageDescriptor;
019: import org.eclipse.swt.graphics.Image;
020: import org.eclipse.swt.program.Program;
021: import org.eclipse.ui.IEditorActionBarContributor;
022: import org.eclipse.ui.IEditorDescriptor;
023: import org.eclipse.ui.IEditorMatchingStrategy;
024: import org.eclipse.ui.IEditorPart;
025: import org.eclipse.ui.IMemento;
026: import org.eclipse.ui.IPluginContribution;
027: import org.eclipse.ui.ISharedImages;
028: import org.eclipse.ui.internal.IWorkbenchConstants;
029: import org.eclipse.ui.internal.WorkbenchImages;
030: import org.eclipse.ui.internal.WorkbenchPlugin;
031: import org.eclipse.ui.internal.misc.ProgramImageDescriptor;
032: import org.eclipse.ui.internal.util.Util;
033: import org.eclipse.ui.plugin.AbstractUIPlugin;
034:
035: /**
036: * @see IEditorDescriptor
037: */
038: public final class EditorDescriptor implements IEditorDescriptor,
039: Serializable, IPluginContribution {
040:
041: /**
042: * Generated serial version UID for this class.
043: * @since 3.1
044: */
045: private static final long serialVersionUID = 3905241225668998961L;
046:
047: // @issue the following constants need not be public; see bug 47600
048: /**
049: * Open internal constant. Value <code>0x01</code>.
050: */
051: public static final int OPEN_INTERNAL = 0x01;
052:
053: /**
054: * Open in place constant. Value <code>0x02</code>.
055: */
056: public static final int OPEN_INPLACE = 0x02;
057:
058: /**
059: * Open external constant. Value <code>0x04</code>.
060: */
061: public static final int OPEN_EXTERNAL = 0x04;
062:
063: private String editorName;
064:
065: private String imageFilename;
066:
067: private transient ImageDescriptor imageDesc;
068:
069: private boolean testImage = true;
070:
071: private String className;
072:
073: private String launcherName;
074:
075: private String fileName;
076:
077: private String id = Util.ZERO_LENGTH_STRING;
078:
079: private boolean matchingStrategyChecked = false;
080: private IEditorMatchingStrategy matchingStrategy;
081:
082: private Program program;
083:
084: //The id of the plugin which contributed this editor, null for external editors
085: private String pluginIdentifier;
086:
087: private int openMode = 0;
088:
089: private transient IConfigurationElement configurationElement;
090:
091: /**
092: * Create a new instance of an editor descriptor. Limited
093: * to internal framework calls.
094: * @param element
095: * @param id2
096: */
097: /* package */EditorDescriptor(String id2,
098: IConfigurationElement element) {
099: setID(id2);
100: setConfigurationElement(element);
101: }
102:
103: /**
104: * Create a new instance of an editor descriptor. Limited
105: * to internal framework calls.
106: */
107: /* package */EditorDescriptor() {
108: super ();
109: }
110:
111: /**
112: * Creates a descriptor for an external program.
113: *
114: * @param filename the external editor full path and filename
115: * @return the editor descriptor
116: */
117: public static EditorDescriptor createForProgram(String filename) {
118: if (filename == null) {
119: throw new IllegalArgumentException();
120: }
121: EditorDescriptor editor = new EditorDescriptor();
122:
123: editor.setFileName(filename);
124: editor.setID(filename);
125: editor.setOpenMode(OPEN_EXTERNAL);
126:
127: //Isolate the program name (no directory or extension)
128: int start = filename.lastIndexOf(File.separator);
129: String name;
130: if (start != -1) {
131: name = filename.substring(start + 1);
132: } else {
133: name = filename;
134: }
135: int end = name.lastIndexOf('.');
136: if (end != -1) {
137: name = name.substring(0, end);
138: }
139: editor.setName(name);
140:
141: // get the program icon without storing it in the registry
142: ImageDescriptor imageDescriptor = new ProgramImageDescriptor(
143: filename, 0);
144: editor.setImageDescriptor(imageDescriptor);
145:
146: return editor;
147: }
148:
149: /**
150: * Return the program called programName. Return null if it is not found.
151: * @return org.eclipse.swt.program.Program
152: */
153: private static Program findProgram(String programName) {
154:
155: Program[] programs = Program.getPrograms();
156: for (int i = 0; i < programs.length; i++) {
157: if (programs[i].getName().equals(programName)) {
158: return programs[i];
159: }
160: }
161:
162: return null;
163: }
164:
165: /**
166: * Create the editor action bar contributor for editors of this type.
167: *
168: * @return the action bar contributor, or <code>null</code>
169: */
170: public IEditorActionBarContributor createActionBarContributor() {
171: // Handle case for predefined editor descriptors, like the
172: // one for IEditorRegistry.SYSTEM_INPLACE_EDITOR_ID, which
173: // don't have a configuration element.
174: if (configurationElement == null) {
175: return null;
176: }
177:
178: // Get the contributor class name.
179: String className = configurationElement
180: .getAttribute(IWorkbenchRegistryConstants.ATT_CONTRIBUTOR_CLASS);
181: if (className == null) {
182: return null;
183: }
184:
185: // Create the contributor object.
186: IEditorActionBarContributor contributor = null;
187: try {
188: contributor = (IEditorActionBarContributor) WorkbenchPlugin
189: .createExtension(
190: configurationElement,
191: IWorkbenchRegistryConstants.ATT_CONTRIBUTOR_CLASS);
192: } catch (CoreException e) {
193: WorkbenchPlugin.log(
194: "Unable to create editor contributor: " + //$NON-NLS-1$
195: id, e.getStatus());
196: }
197: return contributor;
198: }
199:
200: /**
201: * Return the editor class name.
202: *
203: * @return the class name
204: */
205: public String getClassName() {
206: if (configurationElement == null) {
207: return className;
208: }
209: return RegistryReader.getClassValue(configurationElement,
210: IWorkbenchRegistryConstants.ATT_CLASS);
211: }
212:
213: /**
214: * Return the configuration element used to define this editor, or <code>null</code>.
215: *
216: * @return the element or null
217: */
218: public IConfigurationElement getConfigurationElement() {
219: return configurationElement;
220: }
221:
222: /**
223: * Create an editor part based on this descriptor.
224: *
225: * @return the editor part
226: * @throws CoreException thrown if there is an issue creating the editor
227: */
228: public IEditorPart createEditor() throws CoreException {
229: Object extension = WorkbenchPlugin.createExtension(
230: getConfigurationElement(),
231: IWorkbenchRegistryConstants.ATT_CLASS);
232: return (IEditorPart) extension;
233: }
234:
235: /**
236: * Return the file name of the command to execute for this editor.
237: *
238: * @return the file name to execute
239: */
240: public String getFileName() {
241: if (program == null) {
242: if (configurationElement == null) {
243: return fileName;
244: }
245: return configurationElement
246: .getAttribute(IWorkbenchRegistryConstants.ATT_COMMAND);
247: }
248: return program.getName();
249: }
250:
251: /**
252: * Return the id for this editor.
253: *
254: * @return the id
255: */
256: public String getId() {
257: if (program == null) {
258: if (configurationElement == null) {
259: return Util.safeString(id);
260: }
261: return Util.safeString(configurationElement
262: .getAttribute(IWorkbenchRegistryConstants.ATT_ID));
263:
264: }
265: return Util.safeString(program.getName());
266: }
267:
268: /**
269: * Return the image descriptor describing this editor.
270: *
271: * @return the image descriptor
272: */
273: public ImageDescriptor getImageDescriptor() {
274: if (testImage) {
275: testImage = false;
276: if (imageDesc == null) {
277: String imageFileName = getImageFilename();
278: String command = getFileName();
279: if (imageFileName != null
280: && configurationElement != null) {
281: imageDesc = AbstractUIPlugin
282: .imageDescriptorFromPlugin(
283: configurationElement.getNamespace(),
284: imageFileName);
285: } else if (command != null) {
286: imageDesc = WorkbenchImages
287: .getImageDescriptorFromProgram(command, 0);
288: }
289: }
290: verifyImage();
291: }
292:
293: return imageDesc;
294: }
295:
296: /**
297: * Verifies that the image descriptor generates an image. If not, the
298: * descriptor is replaced with the default image.
299: *
300: * @since 3.1
301: */
302: private void verifyImage() {
303: if (imageDesc == null) {
304: imageDesc = WorkbenchImages
305: .getImageDescriptor(ISharedImages.IMG_OBJ_FILE);
306: } else {
307: Image img = imageDesc.createImage(false);
308: if (img == null) {
309: // @issue what should be the default image?
310: imageDesc = WorkbenchImages
311: .getImageDescriptor(ISharedImages.IMG_OBJ_FILE);
312: } else {
313: img.dispose();
314: }
315: }
316: }
317:
318: /**
319: * The name of the image describing this editor.
320: *
321: * @return the image file name
322: */
323: public String getImageFilename() {
324: if (configurationElement == null) {
325: return imageFilename;
326: }
327: return configurationElement
328: .getAttribute(IWorkbenchRegistryConstants.ATT_ICON);
329: }
330:
331: /**
332: * Return the user printable label for this editor.
333: *
334: * @return the label
335: */
336: public String getLabel() {
337: if (program == null) {
338: if (configurationElement == null) {
339: return editorName;
340: }
341: return configurationElement
342: .getAttribute(IWorkbenchRegistryConstants.ATT_NAME);
343: }
344: return program.getName();
345: }
346:
347: /**
348: * Returns the class name of the launcher.
349: *
350: * @return the launcher class name
351: */
352: public String getLauncher() {
353: if (configurationElement == null) {
354: return launcherName;
355: }
356: return configurationElement
357: .getAttribute(IWorkbenchRegistryConstants.ATT_LAUNCHER);
358: }
359:
360: /**
361: * Return the contributing plugin id.
362: *
363: * @return the contributing plugin id
364: */
365: public String getPluginID() {
366: if (configurationElement != null) {
367: return configurationElement.getNamespace();
368: }
369: return pluginIdentifier;
370: }
371:
372: /**
373: * Get the program for the receiver if there is one.
374: * @return Program
375: */
376: public Program getProgram() {
377: return this .program;
378: }
379:
380: /* (non-Javadoc)
381: * @see org.eclipse.ui.IEditorDescriptor#isInternal
382: */
383: public boolean isInternal() {
384: return getOpenMode() == OPEN_INTERNAL;
385: }
386:
387: /* (non-Javadoc)
388: * @see org.eclipse.ui.IEditorDescriptor#isOpenInPlace
389: */
390: public boolean isOpenInPlace() {
391: return getOpenMode() == OPEN_INPLACE;
392: }
393:
394: /* (non-Javadoc)
395: * @see org.eclipse.ui.IEditorDescriptor#isOpenExternal
396: */
397: public boolean isOpenExternal() {
398: return getOpenMode() == OPEN_EXTERNAL;
399: }
400:
401: /**
402: * Load the object properties from a memento.
403: *
404: * @return <code>true</code> if the values are valid, <code>false</code> otherwise
405: */
406: protected boolean loadValues(IMemento memento) {
407: editorName = memento.getString(IWorkbenchConstants.TAG_LABEL);
408: imageFilename = memento
409: .getString(IWorkbenchConstants.TAG_IMAGE);
410: className = memento.getString(IWorkbenchConstants.TAG_CLASS);
411: launcherName = memento
412: .getString(IWorkbenchConstants.TAG_LAUNCHER);
413: fileName = memento.getString(IWorkbenchConstants.TAG_FILE);
414: id = Util.safeString(memento
415: .getString(IWorkbenchConstants.TAG_ID));
416: pluginIdentifier = memento
417: .getString(IWorkbenchConstants.TAG_PLUGIN);
418:
419: Integer openModeInt = memento
420: .getInteger(IWorkbenchConstants.TAG_OPEN_MODE);
421: if (openModeInt != null) {
422: openMode = openModeInt.intValue();
423: } else {
424: // legacy: handle the older attribute names, needed to allow reading of pre-3.0-RCP workspaces
425: boolean internal = new Boolean(memento
426: .getString(IWorkbenchConstants.TAG_INTERNAL))
427: .booleanValue();
428: boolean openInPlace = new Boolean(memento
429: .getString(IWorkbenchConstants.TAG_OPEN_IN_PLACE))
430: .booleanValue();
431: if (internal) {
432: openMode = OPEN_INTERNAL;
433: } else {
434: if (openInPlace) {
435: openMode = OPEN_INPLACE;
436: } else {
437: openMode = OPEN_EXTERNAL;
438: }
439: }
440: }
441: if (openMode != OPEN_EXTERNAL && openMode != OPEN_INTERNAL
442: && openMode != OPEN_INPLACE) {
443: WorkbenchPlugin
444: .log("Ignoring editor descriptor with invalid openMode: " + this ); //$NON-NLS-1$
445: return false;
446: }
447:
448: String programName = memento
449: .getString(IWorkbenchConstants.TAG_PROGRAM_NAME);
450: if (programName != null) {
451: this .program = findProgram(programName);
452: }
453: return true;
454: }
455:
456: /**
457: * Save the object values in a IMemento
458: */
459: protected void saveValues(IMemento memento) {
460: memento.putString(IWorkbenchConstants.TAG_LABEL, getLabel());
461: memento.putString(IWorkbenchConstants.TAG_IMAGE,
462: getImageFilename());
463: memento
464: .putString(IWorkbenchConstants.TAG_CLASS,
465: getClassName());
466: memento.putString(IWorkbenchConstants.TAG_LAUNCHER,
467: getLauncher());
468: memento.putString(IWorkbenchConstants.TAG_FILE, getFileName());
469: memento.putString(IWorkbenchConstants.TAG_ID, getId());
470: memento
471: .putString(IWorkbenchConstants.TAG_PLUGIN,
472: getPluginId());
473:
474: memento.putInteger(IWorkbenchConstants.TAG_OPEN_MODE,
475: getOpenMode());
476: // legacy: handle the older attribute names, needed to allow reading of workspace by pre-3.0-RCP eclipses
477: memento.putString(IWorkbenchConstants.TAG_INTERNAL, String
478: .valueOf(isInternal()));
479: memento.putString(IWorkbenchConstants.TAG_OPEN_IN_PLACE, String
480: .valueOf(isOpenInPlace()));
481:
482: if (this .program != null) {
483: memento.putString(IWorkbenchConstants.TAG_PROGRAM_NAME,
484: this .program.getName());
485: }
486: }
487:
488: /**
489: * Return the open mode of this editor.
490: *
491: * @return the open mode of this editor
492: * @since 3.1
493: */
494: private int getOpenMode() {
495: if (configurationElement == null) { // if we've been serialized, return our serialized value
496: return openMode;
497: } else if (getLauncher() != null) {
498: // open using a launcer
499: return EditorDescriptor.OPEN_EXTERNAL;
500: } else if (getFileName() != null) {
501: // open using an external editor
502: return EditorDescriptor.OPEN_EXTERNAL;
503: } else if (getPluginId() != null) {
504: // open using an internal editor
505: return EditorDescriptor.OPEN_INTERNAL;
506: } else {
507: return 0; // default for system editor
508: }
509: }
510:
511: /**
512: * Set the class name of an internal editor.
513: */
514: /* package */void setClassName(String newClassName) {
515: className = newClassName;
516: }
517:
518: /**
519: * Set the configuration element which contributed this editor.
520: */
521: /* package */void setConfigurationElement(
522: IConfigurationElement newConfigurationElement) {
523: configurationElement = newConfigurationElement;
524: }
525:
526: /**
527: * Set the filename of an external editor.
528: */
529: /* package */void setFileName(String aFileName) {
530: fileName = aFileName;
531: }
532:
533: /**
534: * Set the id of the editor.
535: * For internal editors this is the id as provided in the extension point
536: * For external editors it is path and filename of the editor
537: */
538: /* package */void setID(String anID) {
539: Assert.isNotNull(anID);
540: id = anID;
541: }
542:
543: /**
544: * The Image to use to repesent this editor
545: */
546: /* package */void setImageDescriptor(ImageDescriptor desc) {
547: imageDesc = desc;
548: testImage = true;
549: }
550:
551: /**
552: * The name of the image to use for this editor.
553: */
554: /* package */void setImageFilename(String aFileName) {
555: imageFilename = aFileName;
556: }
557:
558: /**
559: * Sets the new launcher class name
560: *
561: * @param newLauncher the new launcher
562: */
563: /* package */void setLauncher(String newLauncher) {
564: launcherName = newLauncher;
565: }
566:
567: /**
568: * The label to show for this editor.
569: */
570: /* package */void setName(String newName) {
571: editorName = newName;
572: }
573:
574: /**
575: * Sets the open mode of this editor descriptor.
576: *
577: * @param mode the open mode
578: *
579: * @issue this method is public as a temporary fix for bug 47600
580: */
581: public void setOpenMode(int mode) {
582: openMode = mode;
583: }
584:
585: /**
586: * The id of the plugin which contributed this editor, null for external editors.
587: */
588: /* package */void setPluginIdentifier(String anID) {
589: pluginIdentifier = anID;
590: }
591:
592: /**
593: * Set the receivers program.
594: * @param newProgram
595: */
596: /* package */void setProgram(Program newProgram) {
597:
598: this .program = newProgram;
599: if (editorName == null) {
600: setName(newProgram.getName());
601: }
602: }
603:
604: /**
605: * For debugging purposes only.
606: */
607: public String toString() {
608: return "EditorDescriptor(id=" + getId() + ", label=" + getLabel() + ")"; //$NON-NLS-2$ //$NON-NLS-3$//$NON-NLS-1$
609: }
610:
611: /* (non-Javadoc)
612: * @see org.eclipse.ui.activities.support.IPluginContribution#getLocalId()
613: */
614: public String getLocalId() {
615: return getId();
616: }
617:
618: /* (non-Javadoc)
619: * @see org.eclipse.ui.activities.support.IPluginContribution#getPluginId()
620: */
621: public String getPluginId() {
622: return getPluginID();
623: }
624:
625: /* (non-Javadoc)
626: * @see org.eclipse.ui.IEditorDescriptor#getEditorManagementPolicy()
627: */
628: public IEditorMatchingStrategy getEditorMatchingStrategy() {
629: if (matchingStrategy == null && !matchingStrategyChecked) {
630: matchingStrategyChecked = true;
631: if (program == null && configurationElement != null) {
632: if (configurationElement
633: .getAttribute(IWorkbenchRegistryConstants.ATT_MATCHING_STRATEGY) != null) {
634: try {
635: matchingStrategy = (IEditorMatchingStrategy) WorkbenchPlugin
636: .createExtension(
637: configurationElement,
638: IWorkbenchRegistryConstants.ATT_MATCHING_STRATEGY);
639: } catch (CoreException e) {
640: WorkbenchPlugin
641: .log(
642: "Error creating editor management policy for editor id " + getId(), e); //$NON-NLS-1$
643: }
644: }
645: }
646: }
647: return matchingStrategy;
648: }
649:
650: }
|