View | Details | Raw Unified | Return to bug 184074 | Differences between
and this patch

Collapse All | Expand All

(-)Eclipse UI/org/eclipse/ui/part/MultiPageEditorPart.java (-50 / +229 lines)
Lines 37-42 Link Here
37
import org.eclipse.ui.IEditorSite;
37
import org.eclipse.ui.IEditorSite;
38
import org.eclipse.ui.IKeyBindingService;
38
import org.eclipse.ui.IKeyBindingService;
39
import org.eclipse.ui.INestableKeyBindingService;
39
import org.eclipse.ui.INestableKeyBindingService;
40
import org.eclipse.ui.IPartService;
40
import org.eclipse.ui.IPropertyListener;
41
import org.eclipse.ui.IPropertyListener;
41
import org.eclipse.ui.IWorkbenchPart;
42
import org.eclipse.ui.IWorkbenchPart;
42
import org.eclipse.ui.IWorkbenchPartSite;
43
import org.eclipse.ui.IWorkbenchPartSite;
Lines 45-51 Link Here
45
import org.eclipse.ui.internal.misc.Policy;
46
import org.eclipse.ui.internal.misc.Policy;
46
import org.eclipse.ui.internal.services.INestable;
47
import org.eclipse.ui.internal.services.INestable;
47
import org.eclipse.ui.internal.util.Util;
48
import org.eclipse.ui.internal.util.Util;
49
import org.eclipse.ui.services.IDisposable;
48
import org.eclipse.ui.services.IServiceLocator;
50
import org.eclipse.ui.services.IServiceLocator;
51
import org.eclipse.ui.services.IServiceLocatorCreator;
49
52
50
/**
53
/**
51
 * A multi-page editor is an editor with multiple pages, each of which may
54
 * A multi-page editor is an editor with multiple pages, each of which may
Lines 73-87 Link Here
73
 * @see org.eclipse.ui.part.MultiPageEditorActionBarContributor
76
 * @see org.eclipse.ui.part.MultiPageEditorActionBarContributor
74
 */
77
 */
75
public abstract class MultiPageEditorPart extends EditorPart {
78
public abstract class MultiPageEditorPart extends EditorPart {
76
79
	
77
	/**
80
	/**
81
	 * Subclasses that override {@link #createPageContainer(Composite)} can use
82
	 * this constant to get a site for the container that can be active while
83
	 * the current page is deactivated.
78
	 * 
84
	 * 
85
	 * @since 3.4
86
	 * @see #activateSite()
87
	 * @see #deactivateSite(boolean, boolean)
88
	 * @see #getPageSite(int)
89
	 */
90
	protected static final int PAGE_CONTAINER_SITE = 65535;
91
92
	/**
93
	 * Private tracing output.
79
	 */
94
	 */
80
	private static final String TRACING_COMPONENT = "MPE"; //$NON-NLS-1$
95
	private static final String TRACING_COMPONENT = "MPE"; //$NON-NLS-1$
81
96
82
	/**
97
	/**
83
	 * The active service locator. This value may be <code>null</code> if
98
	 * The active service locator. This value may be <code>null</code> if
84
	 * there is no selected page, or if the selected page is a control.
99
	 * there is no selected page, or if the selected page is a control with
100
	 * no site.
85
	 */
101
	 */
86
	private INestable activeServiceLocator;
102
	private INestable activeServiceLocator;
87
103
Lines 97-102 Link Here
97
	 * point.
113
	 * point.
98
	 */
114
	 */
99
	private ArrayList nestedEditors = new ArrayList(3);
115
	private ArrayList nestedEditors = new ArrayList(3);
116
	
117
	private List pageSites = new ArrayList(3);
118
119
	private IServiceLocator pageContainerSite;
100
120
101
	/**
121
	/**
102
	 * Creates an empty multi-page editor with no pages.
122
	 * Creates an empty multi-page editor with no pages.
Lines 341-346 Link Here
341
			disposePart(editor);
361
			disposePart(editor);
342
		}
362
		}
343
		nestedEditors.clear();
363
		nestedEditors.clear();
364
		if (pageContainerSite instanceof IDisposable) {
365
			((IDisposable) pageContainerSite).dispose();
366
			pageContainerSite = null;
367
		}
368
		for (int i = 0; i < pageSites.size(); i++) {
369
			IServiceLocator sl = (IServiceLocator) pageSites.get(i);
370
			if (sl instanceof IDisposable) {
371
				((IDisposable) sl).dispose();
372
			}
373
		}
374
		pageSites.clear();
344
	}
375
	}
345
376
346
	/**
377
	/**
Lines 434-439 Link Here
434
		}
465
		}
435
		return null;
466
		return null;
436
	}
467
	}
468
	
469
	/**
470
	 * Returns the service locator for the given page index. This method can be
471
	 * used to create service locators for pages that are just controls. The
472
	 * page index must be valid.
473
	 * <p>
474
	 * This will return the editor site service locator for an editor, and
475
	 * create one for a page that is just a control.
476
	 * </p>
477
	 * 
478
	 * @param pageIndex
479
	 *            the index of the page
480
	 * @return the editor for the specified page, or <code>null</code> if the
481
	 *         specified page was not created with
482
	 *         <code>addPage(IEditorPart,IEditorInput)</code>
483
	 * @since 3.4
484
	 */
485
	protected final IServiceLocator getPageSite(int pageIndex) {
486
		if (pageIndex == PAGE_CONTAINER_SITE) {
487
			return getPageContainerSite();
488
		}
489
		
490
		Item item = getItem(pageIndex);
491
		if (item != null) {
492
			Object data = item.getData();
493
			if (data instanceof IEditorPart) {
494
				return ((IEditorPart) data).getSite();
495
			} else if (data instanceof IServiceLocator) {
496
				return (IServiceLocator) data;
497
			} else if (data == null) {
498
				IServiceLocatorCreator slc = (IServiceLocatorCreator) getSite()
499
						.getService(IServiceLocatorCreator.class);
500
				IServiceLocator sl = slc.createServiceLocator(getSite(), null);
501
				item.setData(sl);
502
				pageSites.add(sl);
503
				return sl;
504
			}
505
		}
506
		return null;
507
	}
508
509
	/**
510
	 * @return A site that can be used with a header.
511
	 * @since 3.4
512
	 * @see #createPageContainer(Composite)
513
	 * @see #PAGE_CONTAINER_SITE
514
	 * @see #getPageSite(int)
515
	 */
516
	private IServiceLocator getPageContainerSite() {
517
		if (pageContainerSite == null) {
518
			IServiceLocatorCreator slc = (IServiceLocatorCreator) getSite()
519
					.getService(IServiceLocatorCreator.class);
520
			pageContainerSite = slc.createServiceLocator(getSite(), null);
521
		}
522
		return pageContainerSite;
523
	}
437
524
438
	/**
525
	/**
439
	 * Returns the tab item for the given page index (page index is 0-based).
526
	 * Returns the tab item for the given page index (page index is 0-based).
Lines 581-594 Link Here
581
	 *            the index of the activated page
668
	 *            the index of the activated page
582
	 */
669
	 */
583
	protected void pageChange(int newPageIndex) {
670
	protected void pageChange(int newPageIndex) {
584
		// Deactivate the nested services from the last active service locator.
671
		deactivateSite(false, false);
585
		if (activeServiceLocator != null) {
672
586
			activeServiceLocator.deactivate();
673
		IPartService partService = (IPartService) getSite().getService(
587
			activeServiceLocator = null;
674
				IPartService.class);
675
		if (partService.getActivePart() == this) {
676
			setFocus(newPageIndex);
588
		}
677
		}
589
678
590
		setFocus();
591
		IEditorPart activeEditor = getEditor(newPageIndex);
679
		IEditorPart activeEditor = getEditor(newPageIndex);
680
592
		IEditorActionBarContributor contributor = getEditorSite()
681
		IEditorActionBarContributor contributor = getEditorSite()
593
				.getActionBarContributor();
682
				.getActionBarContributor();
594
		if (contributor != null
683
		if (contributor != null
Lines 596-610 Link Here
596
			((MultiPageEditorActionBarContributor) contributor)
685
			((MultiPageEditorActionBarContributor) contributor)
597
					.setActivePage(activeEditor);
686
					.setActivePage(activeEditor);
598
		}
687
		}
599
		if (activeEditor != null) {
600
601
			// Activate the services for the new service locator.
602
			final IServiceLocator serviceLocator = activeEditor.getEditorSite();
603
			if (serviceLocator instanceof INestable) {
604
				activeServiceLocator = (INestable) serviceLocator;
605
				activeServiceLocator.activate();
606
			}
607
688
689
		if (activeEditor != null) {
608
			ISelectionProvider selectionProvider = activeEditor.getSite()
690
			ISelectionProvider selectionProvider = activeEditor.getSite()
609
					.getSelectionProvider();
691
					.getSelectionProvider();
610
			if (selectionProvider != null) {
692
			if (selectionProvider != null) {
Lines 627-632 Link Here
627
				}
709
				}
628
			}
710
			}
629
		}
711
		}
712
713
		activateSite();
714
	}
715
	
716
	/**
717
	 * This method can be used by implementors of
718
	 * {@link MultiPageEditorPart#createPageContainer(Composite)} to deactivate
719
	 * the active inner editor services while their header has focus. A
720
	 * deactivateSite() must have a matching call to activateSite() when
721
	 * appropriate.
722
	 * <p>
723
	 * An new inner editor will have its site activated on a
724
	 * {@link MultiPageEditorPart#pageChange(int)}.
725
	 * </p>
726
	 * <p>
727
	 * <b>Note:</b> This API is evolving in 3.4 and this might not be its final
728
	 * form.
729
	 * </p>
730
	 * 
731
	 * @param immediate
732
	 *            immediately deactivate the legacy keybinding service
733
	 * @param containerSiteActive
734
	 *            Leave the page container site active.
735
	 * @since 3.4
736
	 * @see #activateSite()
737
	 * @see #createPageContainer(Composite)
738
	 * @see #getPageSite(int)
739
	 * @see #PAGE_CONTAINER_SITE
740
	 */
741
	protected final void deactivateSite(boolean immediate,
742
			boolean containerSiteActive) {
743
		// Deactivate the nested services from the last active service locator.
744
		if (activeServiceLocator != null) {
745
			activeServiceLocator.deactivate();
746
			activeServiceLocator = null;
747
		}
748
749
		final int pageIndex = getActivePage();
750
		final IKeyBindingService service = getSite().getKeyBindingService();
751
		if (pageIndex < 0 || pageIndex >= getPageCount() || immediate) {
752
			// There is no selected page, so deactivate the active service.
753
			if (service instanceof INestableKeyBindingService) {
754
				final INestableKeyBindingService nestableService = (INestableKeyBindingService) service;
755
				nestableService.activateKeyBindingService(null);
756
			} else {
757
				WorkbenchPlugin
758
						.log("MultiPageEditorPart.setFocus()   Parent key binding service was not an instance of INestableKeyBindingService.  It was an instance of " + service.getClass().getName() + " instead."); //$NON-NLS-1$ //$NON-NLS-2$
759
			}
760
		}
761
		
762
		if (containerSiteActive) {
763
			IServiceLocator containerSite = getPageContainerSite();
764
			if (containerSite instanceof INestable) {
765
				activeServiceLocator = (INestable) containerSite;
766
				activeServiceLocator.activate();
767
			}
768
		}
769
	}
770
	
771
	/**
772
	 * This method can be used by implementors of
773
	 * {@link #createPageContainer(Composite)} to activate the active inner
774
	 * editor services when their header loses focus.
775
	 * <p>
776
	 * An new inner editor will have its site activated on a
777
	 * {@link #pageChange(int)}.
778
	 * </p>
779
	 * <p>
780
	 * <b>Note:</b> This API is evolving in 3.4 and this might not be its final
781
	 * form.
782
	 * </p>
783
	 * 
784
	 * @since 3.4
785
	 * @see #deactivateSite(boolean,boolean)
786
	 * @see #createPageContainer(Composite)
787
	 * @see #getPageSite(int)
788
	 */
789
	protected final void activateSite() {
790
		if (activeServiceLocator != null) {
791
			activeServiceLocator.deactivate();
792
			activeServiceLocator = null;
793
		}
794
795
		final IKeyBindingService service = getSite().getKeyBindingService();
796
		final int pageIndex = getActivePage();
797
		final IEditorPart editor = getEditor(pageIndex);
798
799
		if (editor != null) {
800
			// active the service for this inner editor
801
			if (service instanceof INestableKeyBindingService) {
802
				final INestableKeyBindingService nestableService = (INestableKeyBindingService) service;
803
				nestableService.activateKeyBindingService(editor
804
						.getEditorSite());
805
806
			} else {
807
				WorkbenchPlugin
808
						.log("MultiPageEditorPart.setFocus()   Parent key binding service was not an instance of INestableKeyBindingService.  It was an instance of " + service.getClass().getName() + " instead."); //$NON-NLS-1$ //$NON-NLS-2$
809
			}
810
			// Activate the services for the new service locator.
811
			final IServiceLocator serviceLocator = editor.getEditorSite();
812
			if (serviceLocator instanceof INestable) {
813
				activeServiceLocator = (INestable) serviceLocator;
814
				activeServiceLocator.activate();
815
			}
816
817
		} else {
818
			Item item = getItem(pageIndex);
819
820
			// There is no selected editor, so deactivate the active service.
821
			if (service instanceof INestableKeyBindingService) {
822
				final INestableKeyBindingService nestableService = (INestableKeyBindingService) service;
823
				nestableService.activateKeyBindingService(null);
824
			} else {
825
				WorkbenchPlugin
826
						.log("MultiPageEditorPart.setFocus()   Parent key binding service was not an instance of INestableKeyBindingService.  It was an instance of " + service.getClass().getName() + " instead."); //$NON-NLS-1$ //$NON-NLS-2$
827
			}
828
829
			if (item.getData() instanceof INestable) {
830
				activeServiceLocator = (INestable) item.getData();
831
				activeServiceLocator.activate();
832
			}
833
		}
630
	}
834
	}
631
835
632
	/**
836
	/**
Lines 668-673 Link Here
668
872
669
		// get control for the item if it's not an editor
873
		// get control for the item if it's not an editor
670
		CTabItem item = getItem(pageIndex);
874
		CTabItem item = getItem(pageIndex);
875
		IServiceLocator pageLocator = null;
876
		if (item.getData() instanceof IServiceLocator) {
877
			pageLocator = (IServiceLocator) item.getData();
878
		}
671
		Control pageControl = item.getControl();
879
		Control pageControl = item.getControl();
672
880
673
		// dispose item before disposing editor, in case there's an exception
881
		// dispose item before disposing editor, in case there's an exception
Lines 683-688 Link Here
683
			nestedEditors.remove(editor);
891
			nestedEditors.remove(editor);
684
			disposePart(editor);
892
			disposePart(editor);
685
		}
893
		}
894
		if (pageLocator != null) {
895
			pageSites.remove(pageLocator);
896
			if (pageLocator instanceof IDisposable) {
897
				((IDisposable) pageLocator).dispose();
898
			}
899
		}
686
	}
900
	}
687
901
688
	/**
902
	/**
Lines 731-776 Link Here
731
	 *            the index of the page
945
	 *            the index of the page
732
	 */
946
	 */
733
	private void setFocus(int pageIndex) {
947
	private void setFocus(int pageIndex) {
734
		final IKeyBindingService service = getSite().getKeyBindingService();
735
		if (pageIndex < 0 || pageIndex >= getPageCount()) {
736
			// There is no selected page, so deactivate the active service.
737
			if (service instanceof INestableKeyBindingService) {
738
				final INestableKeyBindingService nestableService = (INestableKeyBindingService) service;
739
				nestableService.activateKeyBindingService(null);
740
			} else {
741
				WorkbenchPlugin
742
						.log("MultiPageEditorPart.setFocus()   Parent key binding service was not an instance of INestableKeyBindingService.  It was an instance of " + service.getClass().getName() + " instead."); //$NON-NLS-1$ //$NON-NLS-2$
743
			}
744
			return;
745
		}
746
747
		final IEditorPart editor = getEditor(pageIndex);
948
		final IEditorPart editor = getEditor(pageIndex);
748
		if (editor != null) {
949
		if (editor != null) {
749
			editor.setFocus();
950
			editor.setFocus();
750
			// There is no selected page, so deactivate the active service.
751
			if (service instanceof INestableKeyBindingService) {
752
				final INestableKeyBindingService nestableService = (INestableKeyBindingService) service;
753
				if (editor != null) {
754
					nestableService.activateKeyBindingService(editor
755
							.getEditorSite());
756
				} else {
757
					nestableService.activateKeyBindingService(null);
758
				}
759
			} else {
760
				WorkbenchPlugin
761
						.log("MultiPageEditorPart.setFocus()   Parent key binding service was not an instance of INestableKeyBindingService.  It was an instance of " + service.getClass().getName() + " instead."); //$NON-NLS-1$ //$NON-NLS-2$
762
			}
763
951
764
		} else {
952
		} else {
765
			// There is no selected editor, so deactivate the active service.
766
			if (service instanceof INestableKeyBindingService) {
767
				final INestableKeyBindingService nestableService = (INestableKeyBindingService) service;
768
				nestableService.activateKeyBindingService(null);
769
			} else {
770
				WorkbenchPlugin
771
						.log("MultiPageEditorPart.setFocus()   Parent key binding service was not an instance of INestableKeyBindingService.  It was an instance of " + service.getClass().getName() + " instead."); //$NON-NLS-1$ //$NON-NLS-2$
772
			}
773
774
			// Give the page's control focus.
953
			// Give the page's control focus.
775
			final Control control = getControl(pageIndex);
954
			final Control control = getControl(pageIndex);
776
			if (control != null) {
955
			if (control != null) {

Return to bug 184074