001: /*
002: * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
003: *
004: * Copyright 1997-2007 Sun Microsystems, Inc. All rights reserved.
005: *
006: * The contents of this file are subject to the terms of either the GNU
007: * General Public License Version 2 only ("GPL") or the Common
008: * Development and Distribution License("CDDL") (collectively, the
009: * "License"). You may not use this file except in compliance with the
010: * License. You can obtain a copy of the License at
011: * http://www.netbeans.org/cddl-gplv2.html
012: * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
013: * specific language governing permissions and limitations under the
014: * License. When distributing the software, include this License Header
015: * Notice in each file and include the License file at
016: * nbbuild/licenses/CDDL-GPL-2-CP. Sun designates this
017: * particular file as subject to the "Classpath" exception as provided
018: * by Sun in the GPL Version 2 section of the License file that
019: * accompanied this code. If applicable, add the following below the
020: * License Header, with the fields enclosed by brackets [] replaced by
021: * your own identifying information:
022: * "Portions Copyrighted [year] [name of copyright owner]"
023: *
024: * Contributor(s):
025: *
026: * The Original Software is NetBeans. The Initial Developer of the Original
027: * Software is Sun Microsystems, Inc. Portions Copyright 1997-2007 Sun
028: * Microsystems, Inc. All Rights Reserved.
029: *
030: * If you wish your version of this file to be governed by only the CDDL
031: * or only the GPL Version 2, indicate your decision by adding
032: * "[Contributor] elects to include this software in this distribution
033: * under the [CDDL or GPL Version 2] license." If you do not indicate a
034: * single choice of license, a recipient has the option to distribute
035: * your version of this file under either the CDDL, the GPL Version 2 or
036: * to extend the choice of license to its licensees as provided above.
037: * However, if you add GPL Version 2 code and therefore, elected the GPL
038: * Version 2 license, then the option applies only if the new code is
039: * made subject to such option by the copyright holder.
040: */
041:
042: package org.netbeans.modules.visualweb.project.jsfloader;
043:
044: import org.netbeans.modules.visualweb.palette.api.CodeClipPaletteActions;
045: import java.io.InputStream;
046: import java.io.IOException;
047: import java.io.ObjectInput;
048: import java.io.ObjectOutput;
049: import java.lang.ref.WeakReference;
050: import java.util.Enumeration;
051: import javax.swing.Action;
052: import javax.swing.JComponent;
053: import javax.swing.JEditorPane;
054: import javax.swing.text.Document;
055: import javax.swing.text.EditorKit;
056: import javax.swing.text.StyledDocument;
057: import javax.swing.text.BadLocationException;
058: import org.netbeans.spi.palette.PaletteController;
059: import org.netbeans.spi.palette.PaletteFactory;
060: import org.openide.DialogDisplayer;
061:
062: import org.openide.ErrorManager;
063: import org.openide.NotifyDescriptor;
064: import org.openide.cookies.EditorCookie;
065: import org.openide.cookies.PrintCookie;
066: import org.openide.cookies.SaveCookie;
067: import org.openide.filesystems.FileObject;
068: import org.openide.filesystems.FileLock;
069: import org.openide.loaders.DataObject;
070: import org.openide.nodes.Node;
071: import org.openide.text.CloneableEditor;
072: import org.openide.text.DataEditorSupport;
073: import org.openide.text.NbDocument;
074: import org.openide.util.Lookup;
075: import org.openide.util.NbBundle;
076: import org.openide.util.lookup.Lookups;
077: import org.openide.util.lookup.ProxyLookup;
078: import org.openide.windows.CloneableOpenSupport;
079: import org.openide.windows.CloneableTopComponent;
080: import org.openide.windows.TopComponent;
081:
082: import org.netbeans.core.spi.multiview.CloseOperationState;
083: import org.netbeans.core.spi.multiview.MultiViewElement;
084: import org.netbeans.core.spi.multiview.MultiViewElementCallback;
085: import org.netbeans.core.spi.multiview.MultiViewFactory;
086:
087: import org.netbeans.modules.visualweb.api.insync.InSyncService;
088: import org.netbeans.modules.visualweb.palette.api.CodeClipDragAndDropHandler;
089:
090: /**
091: * Editor support for JSF JSP data objects.
092: *
093: * @author Peter Zavadsky
094: * @author Tor Norbye (part copied from formerly changed HTMLEditorSupport + strange designer stuff)
095: */
096: public final class JsfJspEditorSupport extends DataEditorSupport
097: implements EditorCookie.Observable, PrintCookie {
098:
099: private String encoding;
100: private static final String defaultEncoding = "UTF-8"; // NOI18N
101:
102: /** SaveCookie for this support instance. The cookie is adding/removing
103: * data object's cookie set depending on if modification flag was set/unset. */
104: private final SaveCookie saveCookie = new SaveCookie() {
105: /** Implements <code>SaveCookie</code> interface. */
106: public void save() throws IOException {
107: JsfJspEditorSupport.this .saveDocument();
108: JsfJspEditorSupport.this .getDataObject().setModified(false);
109: }
110: };
111:
112: /** Constructor. */
113: JsfJspEditorSupport(JsfJspDataObject obj) {
114: super (obj, new Environment(obj));
115: encoding = null;
116: setMIMEType("text/x-jsp"); // NOI18N
117: }
118:
119: public void openDesigner() {
120: JsfJavaEditorSupport jsfJavaEditorSupport = getJsfJavaEditorSupport(false);
121: if (jsfJavaEditorSupport == null) {
122: // XXX See #6438557
123: return;
124: }
125: jsfJavaEditorSupport.openDesigner();
126: }
127:
128: // XXX Making it accessible within this package.
129: @Override
130: protected boolean canClose() {
131: return super .canClose();
132: }
133:
134: // XXX Making it accessible within this package.
135: @Override
136: protected void notifyClosed() {
137: super .notifyClosed();
138: JsfJspDataObject dataObject = (JsfJspDataObject) getDataObject();
139: // org.netbeans.modules.visualweb.api.designerapi.DesignerServiceHack.getDefault().destroyWebFormForFileObject(dataObject.getPrimaryFile());
140: }
141:
142: /**
143: * Overrides superclass method. Adds adding of save cookie if the document has been marked modified.
144: * @return true if the environment accepted being marked as modified
145: * or false if it has refused and the document should remain unmodified
146: */
147: @Override
148: protected boolean notifyModified() {
149: if (!super .notifyModified()) {
150: return false;
151: }
152:
153: addSaveCookie();
154:
155: updateMultiViewDisplayName();
156:
157: return true;
158: }
159:
160: /** Overrides superclass method. Adds removing of save cookie. */
161: @Override
162: protected void notifyUnmodified() {
163: super .notifyUnmodified();
164:
165: removeSaveCookie();
166:
167: updateMultiViewDisplayName();
168: }
169:
170: /** Helper method. Adds save cookie to the data object. */
171: private void addSaveCookie() {
172: JsfJspDataObject obj = (JsfJspDataObject) getDataObject();
173:
174: // XXX Adds save cookie to the data object.
175: if (obj.getPureCookie(SaveCookie.class) == null) {
176: obj.getCookieSet0().add(saveCookie);
177: obj.setModified(true);
178: }
179: }
180:
181: /** Helper method. Removes save cookie from the data object. */
182: private void removeSaveCookie() {
183: JsfJspDataObject obj = (JsfJspDataObject) getDataObject();
184:
185: // We must use getPureCookie here to make sure we do not get the CompoundCookie
186: Node.Cookie cookie = obj.getPureCookie(SaveCookie.class);
187:
188: if (cookie != null && cookie.equals(saveCookie)) {
189: obj.getCookieSet0().remove(saveCookie);
190: obj.setModified(false);
191: }
192: }
193:
194: @Override
195: public void saveDocument() throws IOException {
196: saveDocument(true);
197: }
198:
199: /** Save the document in this thread.
200: * @param parse true if the parser should be started, otherwise false
201: * @param forceSave if true save always, otherwise only when is modified
202: * @exception IOException on I/O error
203: */
204: private void saveDocument(boolean forceSave) throws IOException {
205: if (forceSave || isModified()) {
206: ((JsfJspDataObject) getDataObject())
207: .updateFileEncoding(true);
208:
209: encoding = ((JsfJspDataObject) getDataObject())
210: .getFileEncoding();
211:
212: if (!isSupportedEncoding(encoding)) {
213: NotifyDescriptor nd = new NotifyDescriptor.Confirmation(
214: NbBundle.getMessage(JsfJspEditorSupport.class,
215: "MSG_BadEncodingDuringSave", //NOI18N
216: new Object[] {
217: getDataObject()
218: .getPrimaryFile()
219: .getNameExt(),
220: encoding, defaultEncoding }),
221: NotifyDescriptor.YES_NO_OPTION,
222: NotifyDescriptor.WARNING_MESSAGE);
223: nd.setValue(NotifyDescriptor.NO_OPTION);
224: DialogDisplayer.getDefault().notify(nd);
225: if (nd.getValue() != NotifyDescriptor.YES_OPTION)
226: return;
227: } else {
228: try {
229: java.nio.charset.CharsetEncoder coder = java.nio.charset.Charset
230: .forName(encoding).newEncoder();
231: Document doc = getDocument();
232:
233: if (coder != null
234: && doc != null
235: && !coder.canEncode(doc.getText(0, doc
236: .getLength()))) {
237: NotifyDescriptor nd = new NotifyDescriptor.Confirmation(
238: NbBundle
239: .getMessage(
240: JsfJspEditorSupport.class,
241: "MSG_BadCharConversion", //NOI18N
242: new Object[] {
243: getDataObject()
244: .getPrimaryFile()
245: .getNameExt(),
246: encoding }),
247: NotifyDescriptor.YES_NO_OPTION,
248: NotifyDescriptor.WARNING_MESSAGE);
249: nd.setValue(NotifyDescriptor.NO_OPTION);
250: DialogDisplayer.getDefault().notify(nd);
251: if (nd.getValue() != NotifyDescriptor.YES_OPTION)
252: return;
253: }
254: } catch (javax.swing.text.BadLocationException e) {
255: ErrorManager.getDefault().notify(
256: ErrorManager.INFORMATIONAL, e);
257: }
258: }
259: super .saveDocument();
260: }
261: }
262:
263: @Override
264: public void open() {
265: ((JsfJspDataObject) getDataObject()).updateFileEncoding(false);
266: encoding = ((JsfJspDataObject) getDataObject())
267: .getFileEncoding(); //use encoding from fileobject
268:
269: if (!isSupportedEncoding(encoding)) {
270: NotifyDescriptor nd = new NotifyDescriptor.Confirmation(
271: NbBundle.getMessage(JsfJspEditorSupport.class,
272: "MSG_BadEncodingDuringLoad", //NOI18N
273: new Object[] {
274: getDataObject().getPrimaryFile()
275: .getNameExt(), encoding,
276: defaultEncoding }),
277: NotifyDescriptor.YES_NO_OPTION,
278: NotifyDescriptor.WARNING_MESSAGE);
279: DialogDisplayer.getDefault().notify(nd);
280: if (nd.getValue() != NotifyDescriptor.YES_OPTION)
281: return;
282: }
283:
284: super .open();
285: }
286:
287: protected void editJsp() {
288: ((JsfJspDataObject) getDataObject()).updateFileEncoding(false);
289: encoding = ((JsfJspDataObject) getDataObject())
290: .getFileEncoding(); //use encoding from fileobject
291:
292: if (!isSupportedEncoding(encoding)) {
293: NotifyDescriptor nd = new NotifyDescriptor.Confirmation(
294: NbBundle.getMessage(JsfJspEditorSupport.class,
295: "MSG_BadEncodingDuringLoad", //NOI18N
296: new Object[] {
297: getDataObject().getPrimaryFile()
298: .getNameExt(), encoding,
299: defaultEncoding }),
300: NotifyDescriptor.YES_NO_OPTION,
301: NotifyDescriptor.WARNING_MESSAGE);
302: DialogDisplayer.getDefault().notify(nd);
303: if (nd.getValue() != NotifyDescriptor.YES_OPTION)
304: return;
305: }
306:
307: final JsfJavaEditorSupport support = getJsfJavaEditorSupport(false);
308: if (support == null)
309: return;
310: support.openJsp();
311: }
312:
313: @Override
314: protected void loadFromStreamToKit(StyledDocument doc,
315: InputStream stream, EditorKit kit) throws IOException,
316: BadLocationException {
317: ((JsfJspDataObject) getDataObject()).updateFileEncoding(false);
318: super .loadFromStreamToKit(doc, stream, kit);
319: }
320:
321: private static boolean isSupportedEncoding(String encoding) {
322: if (encoding == null) {
323: return false;
324: }
325: try {
326: return java.nio.charset.Charset.isSupported(encoding);
327: } catch (java.nio.charset.IllegalCharsetNameException icne) {
328: return false;
329: }
330: }
331:
332: @Override
333: protected CloneableEditor createCloneableEditor() {
334: return new JspEditorTopComponent(
335: (JsfJspDataObject) getDataObject());
336: }
337:
338: /** Trick to get the superclass method equivalent. */
339: private final Object getLock() {
340: return allEditors;
341: }
342:
343: /** Creates multiview element. */
344: MultiViewElement createMultiViewElement() {
345: //synchronized (allEditors) {
346: synchronized (getLock()) {
347: CloneableTopComponent editor = createCloneableTopComponent();
348: editor.setReference(allEditors);
349:
350: return (MultiViewElement) editor;
351: }
352: }
353:
354: /** XXX Making it accessible whitin this package. And overrides it
355: * the way to also include status of corresponding java file. */
356: @Override
357: protected String messageName() {
358: DataObject jspObj = getDataObject();
359: if (!jspObj.isValid()) {
360: return ""; // NOI18N
361: }
362:
363: String name;
364: // #6293578 They don't want to show extensions in any case.
365: // if(org.openide.loaders.DataNode.getShowFileExtensions()) {
366: // name = jspObj.getPrimaryFile().getNameExt();
367: // } else {
368: name = jspObj.getPrimaryFile().getName();
369: // }
370: return addFlagsToName(name, jspObj);
371: }
372:
373: /** XXX Helper only. */
374: private String addFlagsToName(String name, DataObject jspObj) {
375: JsfJavaEditorSupport jsfJavaEditorSupport = getJsfJavaEditorSupport(
376: jspObj.getPrimaryFile(), true);
377: int version = 3;
378: if (isModified()
379: || (jsfJavaEditorSupport != null && jsfJavaEditorSupport
380: .isModified())) {
381: if (!jspObj.getPrimaryFile().canWrite()) {
382: version = 2;
383: } else {
384: version = 1;
385: }
386: } else if (!jspObj.getPrimaryFile().canWrite()) {
387: version = 0;
388: }
389:
390: return NbBundle.getMessage(DataObject.class, "LAB_EditorName",
391: new Integer(version), name);
392: }
393:
394: /** XXX Making it accessible whitin this package. */
395: @Override
396: protected String messageToolTip() {
397: return super .messageToolTip();
398: }
399:
400: /** Nested class. Environment for this support. Extends <code>DataEditorSupport.Env</code> abstract class. */
401: private static class Environment extends DataEditorSupport.Env {
402:
403: private static final long serialVersionUID = 3035543168452715818L;
404:
405: /** Constructor. */
406: public Environment(JsfJspDataObject obj) {
407: super (obj);
408: }
409:
410: /** Implements abstract superclass method. */
411: protected FileObject getFile() {
412: return getDataObject().getPrimaryFile();
413: }
414:
415: /** Implements abstract superclass method.*/
416: protected FileLock takeLock() throws IOException {
417: return ((JsfJspDataObject) getDataObject())
418: .getPrimaryEntry().takeLock();
419: }
420:
421: /**
422: * Overrides superclass method.
423: * @return text editor support (instance of enclosing class)
424: */
425: @Override
426: public CloneableOpenSupport findCloneableOpenSupport() {
427: return (JsfJspEditorSupport) getDataObject().getCookie(
428: JsfJspEditorSupport.class);
429: }
430: } // End of nested Environment class.
431:
432: /** To be accessible whitin package. Tricky method to get the superclass equivalent. */
433: Env env() {
434: return (Env) env;
435: }
436:
437: private static class JspEditorTopComponent extends CloneableEditor
438: implements MultiViewElement {
439: private static final long serialVersionUID = -3126744316624172415L;
440:
441: private transient MultiViewElementCallback multiViewElementCallback;
442:
443: private transient JComponent toolbar;
444:
445: private JsfJspDataObject jsfJspDataObject;
446:
447: private PaletteController jspPaletteController;
448:
449: public JspEditorTopComponent() {
450: super ();
451: }
452:
453: public JspEditorTopComponent(JsfJspDataObject jsfJspDataObject) {
454: super ((JsfJspEditorSupport) jsfJspDataObject
455: .getCookie(JsfJspEditorSupport.class));
456: this .jsfJspDataObject = jsfJspDataObject;
457: initialize();
458: }
459:
460: /** Overriding super class to get it open in multiview. */
461: @Override
462: @SuppressWarnings("deprecation")
463: public void open(org.openide.windows.Workspace workspace) {
464: if (discard()) {
465: JsfJspEditorSupport support = (JsfJspEditorSupport) jsfJspDataObject
466: .getCookie(JsfJspEditorSupport.class);
467: ErrorManager
468: .getDefault()
469: .log(
470: ErrorManager.WARNING,
471: "Can not open "
472: + this
473: + " component," // NOI18N
474: + " its support environment is not valid" // NOI18N
475: + " [support="
476: + support
477: + ", env=" // NOI18N
478: + (support == null ? null
479: : support.env()) + "]"); // NOI18N
480: } else {
481: // Open in multiview.
482: final JsfJavaEditorSupport jsfJavaEditorSupport = Utils
483: .findCorrespondingJsfJavaEditorSupport(
484: jsfJspDataObject.getPrimaryFile(),
485: false);
486: if (jsfJavaEditorSupport == null) {
487: ErrorManager.getDefault().notify(
488: ErrorManager.INFORMATIONAL,
489: new IllegalStateException(
490: "Can't find JsfJavaEditorSupport for "
491: + jsfJspDataObject)); // NOI18N
492: } else {
493: jsfJavaEditorSupport.doOpenDesigner();
494: }
495: }
496: }
497:
498: private boolean discard() {
499: JsfJspEditorSupport support = (JsfJspEditorSupport) jsfJspDataObject
500: .getCookie(JsfJspEditorSupport.class);
501: return support == null || !support.env().isValid();
502: }
503:
504: private void initialize() {
505: if (jsfJspDataObject != null) {
506: setActivatedNodes(new Node[] { jsfJspDataObject
507: .getNodeDelegate() });
508: }
509:
510: initializePalette();
511: }
512:
513: // XXX PaletteController
514: private void initializePalette() {
515: String paletteFolderName = "CreatorJspPalette"; // NOI18N
516: PaletteController controller;
517: try {
518: controller = PaletteFactory.createPalette(
519: paletteFolderName, new CodeClipPaletteActions(
520: paletteFolderName, this ), null,
521: new CodeClipDragAndDropHandler()); // NOI18N
522:
523: } catch (java.io.IOException ex) {
524: ErrorManager.getDefault().notify(
525: ErrorManager.INFORMATIONAL, ex);
526: controller = null;
527: }
528: jspPaletteController = controller;
529: return;
530: }
531:
532: public CloseOperationState canCloseElement() {
533: // If this is not the last cloned jsp editor component, closing is OK.
534: if (!isLastView(multiViewElementCallback.getTopComponent())) {
535: return CloseOperationState.STATE_OK;
536: }
537:
538: // XXX I don't understand this yet. Copied from FormDesigner.
539: // Returns a placeholder state - to be sure our CloseHandler is called.
540: return MultiViewFactory.createUnsafeCloseState(
541: "ID_CLOSING_JSP", // dummy ID // NOI18N
542: MultiViewFactory.NOOP_CLOSE_ACTION,
543: MultiViewFactory.NOOP_CLOSE_ACTION);
544: }
545:
546: public void setMultiViewCallback(
547: MultiViewElementCallback callback) {
548: multiViewElementCallback = callback;
549:
550: // XXX This smells really badly, is this supposed to be the 'typical' way to
551: // deserialize the needed stuff? (comes from FormEditorSupport)
552: // needed for deserialization...
553: JsfJspEditorSupport jsfJspEditorSupport = (JsfJspEditorSupport) jsfJspDataObject
554: .getCookie(JsfJspEditorSupport.class);
555: if (jsfJspEditorSupport != null) {
556: // this is used (or misused?) to obtain the deserialized
557: // multiview topcomponent and set it to JsfJavaEditorSupport
558: // jsfJspEditorSupport.setMultiView((CloneableTopComponent)multiViewElementCallback.getTopComponent());
559: JsfJavaEditorSupport jsfJavaEditorSupport = jsfJspEditorSupport
560: .getJsfJavaEditorSupport(false);
561: if (jsfJavaEditorSupport != null) {
562: jsfJavaEditorSupport.updateMultiViewDisplayName();
563: jsfJavaEditorSupport.updateMultiViewToolTip();
564: }
565: }
566: }
567:
568: public JComponent getToolbarRepresentation() {
569: if (toolbar == null) {
570: JEditorPane jPane = getEditorPane();
571: if (jPane != null) {
572: Document doc = jPane.getDocument();
573: if (doc instanceof NbDocument.CustomToolbar) {
574: toolbar = ((NbDocument.CustomToolbar) doc)
575: .createToolbar(jPane);
576: }
577: }
578: if (toolbar == null) {
579: // attempt to create own toolbar??
580: toolbar = new javax.swing.JPanel();
581: }
582: }
583: return toolbar;
584: }
585:
586: public JComponent getVisualRepresentation() {
587: return this ;
588: }
589:
590: @Override
591: public void componentDeactivated() {
592: super .componentDeactivated();
593: }
594:
595: @Override
596: public void componentActivated() {
597: super .componentActivated();
598: // XXX #6299978 NB #61886 Multiview doesn't handle focus transfer,
599: // once fixed in NB, remove this hack.
600: if (pane != null) {
601: pane.requestFocusInWindow();
602: }
603:
604: InSyncService.getProvider()
605: .jspDataObjectTopComponentActivated(
606: jsfJspDataObject);
607: }
608:
609: @Override
610: public void componentHidden() {
611: super .componentHidden();
612:
613: InSyncService.getProvider()
614: .jspDataObjectTopComponentHidden(jsfJspDataObject);
615: }
616:
617: @Override
618: public void componentShowing() {
619: super .componentShowing();
620:
621: InSyncService.getProvider().jspDataObjectTopComponentShown(
622: jsfJspDataObject);
623: }
624:
625: @Override
626: public void componentClosed() {
627: super .componentClosed();
628: }
629:
630: @Override
631: public void componentOpened() {
632: super .componentOpened();
633: }
634:
635: @Override
636: public void requestVisible() {
637: if (multiViewElementCallback != null) {
638: multiViewElementCallback.requestVisible();
639: } else {
640: super .requestVisible();
641: }
642: }
643:
644: @Override
645: public void requestActive() {
646: if (multiViewElementCallback != null) {
647: multiViewElementCallback.requestActive();
648: } else {
649: super .requestActive();
650: }
651: }
652:
653: @Override
654: public Action[] getActions() {
655: // need to delegate to multiview's actions because of the way editor
656: // constructs actions : NbEditorKit.NbBuildPopupMenuAction
657: return multiViewElementCallback != null ? multiViewElementCallback
658: .createDefaultActions()
659: : super .getActions();
660: }
661:
662: @Override
663: public void writeExternal(ObjectOutput out) throws IOException {
664: super .writeExternal(out);
665:
666: out.writeObject(jsfJspDataObject);
667: }
668:
669: @Override
670: public void readExternal(ObjectInput in) throws IOException,
671: ClassNotFoundException {
672: super .readExternal(in);
673:
674: jsfJspDataObject = (JsfJspDataObject) in.readObject();
675: initialize();
676: }
677:
678: private static boolean isLastView(TopComponent tc) {
679: if (!(tc instanceof CloneableTopComponent))
680: return false;
681:
682: boolean oneOrLess = true;
683: Enumeration en = ((CloneableTopComponent) tc)
684: .getReference().getComponents();
685: if (en.hasMoreElements()) {
686: en.nextElement();
687: if (en.hasMoreElements())
688: oneOrLess = false;
689: }
690: return oneOrLess;
691: }
692:
693: private WeakReference<Lookup> lookupWRef = new WeakReference<Lookup>(
694: null);
695:
696: /** Adds <code>NavigatorLookupHint</code> into the original lookup,
697: * for the navigator. */
698: @Override
699: public Lookup getLookup() {
700: Lookup lookup = lookupWRef.get();
701:
702: if (lookup == null) {
703: Lookup super Lookup = super .getLookup();
704: if (jspPaletteController == null) {
705: lookup = new ProxyLookup(
706: new Lookup[] { super Lookup });
707: } else {
708: lookup = new ProxyLookup(new Lookup[] {
709: super Lookup,
710: Lookups.singleton(jspPaletteController) });
711: }
712: lookupWRef = new WeakReference<Lookup>(lookup);
713: }
714:
715: return lookup;
716: }
717: }
718:
719: /*
720: * EAT! This should really be getContainingMultiView or something, but will stick to this for now.
721: */
722: protected JsfJavaEditorSupport getJsfJavaEditorSupport(
723: boolean quietly) {
724: return getJsfJavaEditorSupport(
725: getDataObject().getPrimaryFile(), quietly);
726: }
727:
728: protected JsfJavaEditorSupport getJsfJavaEditorSupport(
729: FileObject fileObject, boolean quietly) {
730: JsfJavaEditorSupport jsfJavaEditorSupport = Utils
731: .findCorrespondingJsfJavaEditorSupport(fileObject,
732: quietly);
733: return jsfJavaEditorSupport;
734: }
735:
736: public void updateMultiViewDisplayName() {
737: CloneableTopComponent topComponent = allEditors
738: .getArbitraryComponent();
739: if (topComponent != null)
740: topComponent.toString();
741: // XXX Also handle renaming of the multiview.
742: final JsfJavaEditorSupport jsfJavaEditorSupport = getJsfJavaEditorSupport(true);
743: if (jsfJavaEditorSupport == null)
744: return;
745: javax.swing.SwingUtilities.invokeLater(new Runnable() {
746: public void run() {
747: jsfJavaEditorSupport.updateMultiViewDisplayName();
748: }
749: });
750: }
751:
752: }
|