Skip to main content
aboutsummaryrefslogtreecommitdiffstats
blob: 499a447bf5f8743161160d06f203857c497320b5 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
/*****************************************************************************
 * Copyright (c) 2014, 2016 CEA LIST, Christian W. Damus, and others.
 * 
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *   CEA LIST - Initial API and implementation
 *   Christian W. Damus - bugs 485220, 497342, 498414, 499661
 *   
 *****************************************************************************/

package org.eclipse.papyrus.infra.services.resourceloading.internal.ui.editor;

import java.util.Collections;
import java.util.List;
import java.util.Objects;

import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.papyrus.infra.core.sasheditor.contentprovider.IPageModel;
import org.eclipse.papyrus.infra.core.sasheditor.di.contentprovider.utils.IPageUtils;
import org.eclipse.papyrus.infra.core.sasheditor.editor.IPage;
import org.eclipse.papyrus.infra.core.sasheditor.editor.ISashWindowsContainer;
import org.eclipse.papyrus.infra.core.sashwindows.di.service.IPageManager;
import org.eclipse.papyrus.infra.core.services.ServiceException;
import org.eclipse.papyrus.infra.emf.utils.ServiceUtilsForResource;
import org.eclipse.papyrus.infra.tools.util.PlatformHelper;


/**
 * Command to load the diagram related to a resource URI
 * 
 * @author Céline JANSSENS
 *
 */
class LoadDiagramCommand implements Runnable {

	private final IPageManager pageManager;
	private final ISashWindowsContainer sashContainer;

	/**
	 * URI of the resource which the diagram is based on.
	 */
	private final URI uri;

	/**
	 * Initializes me with a page manager and sash-windows container inferred
	 * from the {@code resource}.
	 *
	 * @param resource
	 *            the resource in which there may be diagrams for me to reload
	 *            in the page manager
	 */
	public LoadDiagramCommand(Resource resource) {
		this(resource,
				getService(resource, IPageManager.class),
				getService(resource, ISashWindowsContainer.class));
	}

	private static <S> S getService(Resource resource, Class<S> serviceAPI) {
		S result = null;

		try {
			result = ServiceUtilsForResource.getInstance().getService(serviceAPI, resource);
		} catch (ServiceException e) {
			// nothing to do
		}

		return result;
	}

	/**
	 * Initializes me.
	 *
	 * @param resource
	 *            the resource in which there may be diagrams for me to reload
	 *            in the page manager
	 * @param pageManager
	 *            the page manager in which to reload them, or {@code null} if none
	 * @param sashContainer
	 *            the sash windows container in which to reload them, or {@code null} if none
	 */
	public LoadDiagramCommand(Resource resource, IPageManager pageManager, ISashWindowsContainer sashContainer) {
		super();

		this.pageManager = pageManager;
		this.sashContainer = sashContainer;
		this.uri = resource.getURI();
	}

	/**
	 * Reloads hte pages associated with my resource, if any and if there is a
	 * page manager.
	 */
	@Override
	public void run() {
		List<?> pagesToReload = getPagesToReload();
		if (!pagesToReload.isEmpty()) {
			pagesToReload.forEach(pageManager::reloadPage);
		}
	}

	/**
	 * Queries whether I have any pages to reload. If I have none to reload,
	 * then I don't need to be executed.
	 * 
	 * @return whether I have any pages to reload
	 * @since 1.3
	 */
	public boolean canExecute() {
		List<?> pages = getPagesToReload();
		return !pages.isEmpty() && pages.stream().allMatch(this::needsReload);
	}

	private List<?> getPagesToReload() {
		List<?> result;

		if (pageManager == null) {
			result = Collections.EMPTY_LIST;
		} else {
			// Retrieve open pages related to our URI (in the abstract, without extension)
			result = pageManager.getAssociatedPages(uri.trimFragment().trimFileExtension());
			result.removeIf(Objects::isNull);
		}

		return result;
	}

	private boolean needsReload(Object pageIdentifier) {
		boolean result = false;

		if (sashContainer != null) {
			IPage page = IPageUtils.lookupModelPage(sashContainer, pageIdentifier);

			// If there is no page, it needn't be re-loaded
			result = (page != null) && isUnloadedResourcePage(page);
		}

		return result;
	}

	private boolean isUnloadedResourcePage(IPage page) {
		IPageModel model = PlatformHelper.getAdapter(page, IPageModel.class);
		return (model != null) && (model instanceof UnloadResourcesEditorModel);
	}
}

Back to the top