Skip to content

Commit b82836f

Browse files
committed
Copy model on subnetwork creation. Add OSGi-style events.
1 parent b6dd4a9 commit b82836f

12 files changed

+219
-80
lines changed

EnrichmentMapPlugin/src/main/java/org/baderlab/csplugins/enrichmentmap/CytoscapeServiceModule.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
import org.cytoscape.model.CyNetworkTableManager;
2626
import org.cytoscape.model.CyTableFactory;
2727
import org.cytoscape.model.CyTableManager;
28+
import org.cytoscape.model.subnetwork.CyRootNetworkManager;
2829
import org.cytoscape.property.CyProperty;
2930
import org.cytoscape.service.util.CyServiceRegistrar;
3031
import org.cytoscape.session.CyNetworkNaming;
@@ -104,6 +105,7 @@ protected void configure() {
104105
bindService(CyNetworkNaming.class);
105106
bindService(CyApplicationConfiguration.class);
106107
bindService(CyColorPaletteChooserFactory.class);
108+
bindService(CyRootNetworkManager.class);
107109

108110
bindService(DialogTaskManager.class);
109111
TypeLiteral<SynchronousTaskManager<?>> synchronousManager = new TypeLiteral<SynchronousTaskManager<?>>(){};

EnrichmentMapPlugin/src/main/java/org/baderlab/csplugins/enrichmentmap/model/EnrichmentMapManager.java

Lines changed: 66 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -43,67 +43,118 @@
4343

4444
package org.baderlab.csplugins.enrichmentmap.model;
4545

46-
import java.beans.PropertyChangeListener;
47-
import java.beans.PropertyChangeSupport;
4846
import java.util.HashMap;
4947
import java.util.LinkedHashMap;
5048
import java.util.Map;
5149

50+
import org.baderlab.csplugins.enrichmentmap.model.event.AssociatedEnrichmentMapsChangedEvent;
51+
import org.baderlab.csplugins.enrichmentmap.model.event.EnrichmentMapAddedEvent;
52+
import org.baderlab.csplugins.enrichmentmap.model.io.ModelSerializer;
5253
import org.baderlab.csplugins.enrichmentmap.view.heatmap.HeatMapParams;
5354
import org.baderlab.csplugins.enrichmentmap.view.postanalysis.PADialogMediator;
55+
import org.cytoscape.event.CyEventHelper;
5456
import org.cytoscape.model.CyNetwork;
57+
import org.cytoscape.model.CyNetworkManager;
5558
import org.cytoscape.model.CyTable;
59+
import org.cytoscape.model.events.NetworkAboutToBeDestroyedEvent;
60+
import org.cytoscape.model.events.NetworkAboutToBeDestroyedListener;
61+
import org.cytoscape.model.subnetwork.CyRootNetwork;
62+
import org.cytoscape.model.subnetwork.CyRootNetworkManager;
5663
import org.cytoscape.view.model.CyNetworkView;
64+
import org.cytoscape.view.model.events.NetworkViewAddedEvent;
65+
import org.cytoscape.view.model.events.NetworkViewAddedListener;
5766

5867
import com.google.inject.Inject;
5968
import com.google.inject.Provider;
6069
import com.google.inject.Singleton;
6170

6271

6372
@Singleton
64-
public class EnrichmentMapManager {
73+
public class EnrichmentMapManager implements NetworkAboutToBeDestroyedListener, NetworkViewAddedListener {
6574

6675
private Map<Long, EnrichmentMap> enrichmentMaps = new LinkedHashMap<>();
6776
private Map<Long, EnrichmentMap> associatedEnrichmentMaps = new LinkedHashMap<>();
6877
private Map<Long, HeatMapParams> heatMapParams = new HashMap<>();
6978
private Map<Long, HeatMapParams> heatMapParamsEdges = new HashMap<>();
7079

7180
@Inject private Provider<PADialogMediator> postAnalysisMediatorProvider;
81+
82+
@Inject private CyEventHelper eventHelper;
83+
@Inject private CyNetworkManager networkManager;
84+
@Inject private CyRootNetworkManager rootNetworkManager;
85+
7286

73-
private final PropertyChangeSupport pcs = new PropertyChangeSupport(this);
87+
/**
88+
* If the user creates a new network under the same network collection, we can just reuse the model.
89+
*/
90+
@Override
91+
public void handleEvent(NetworkViewAddedEvent e) {
92+
if(isEnrichmentMap(e.getNetworkView()))
93+
return;
94+
95+
CyNetwork newNetwork = e.getNetworkView().getModel();
96+
CyRootNetwork newNetworkRoot = rootNetworkManager.getRootNetwork(newNetwork);
97+
98+
for(Long networkSuid : enrichmentMaps.keySet()) {
99+
CyNetwork network = networkManager.getNetwork(networkSuid);
100+
CyRootNetwork root = rootNetworkManager.getRootNetwork(network);
101+
if(root == newNetworkRoot) {
102+
System.out.println("Copying EnrichmentMap model");
103+
// newly created network is under an enrichmentmap network
104+
EnrichmentMap map = getEnrichmentMap(network.getSUID());
105+
if(map != null) {
106+
EnrichmentMap newMap = ModelSerializer.deepCopy(map);
107+
newMap.setNetworkID(newNetwork.getSUID());
108+
registerEnrichmentMap(newMap);
109+
}
110+
return;
111+
}
112+
}
113+
}
114+
115+
@Override
116+
public void handleEvent(NetworkAboutToBeDestroyedEvent e) {
117+
removeEnrichmentMap(e.getNetwork().getSUID());
118+
}
119+
74120

75121
/**
76122
* Registers a newly created Network.
77123
*/
78124
public void registerEnrichmentMap(EnrichmentMap map) {
79-
enrichmentMaps.put(map.getNetworkID(), map);
125+
if(enrichmentMaps.containsKey(map.getNetworkID()))
126+
return;
80127

128+
enrichmentMaps.put(map.getNetworkID(), map);
81129
for (Long id : map.getAssociatedNetworkIDs())
82130
associatedEnrichmentMaps.put(id, map);
131+
132+
// This event is reentrant (fires on the same thread that called registerEnrichmentMap). But that is safe
133+
// because the only listeners are inside this App so we can control what code is actually being run here.
134+
eventHelper.fireEvent(new EnrichmentMapAddedEvent(this, map));
83135
}
84136

137+
85138
public Map<Long, EnrichmentMap> getAllEnrichmentMaps() {
86139
return new LinkedHashMap<>(enrichmentMaps);
87140
}
88141

142+
89143
public EnrichmentMap getEnrichmentMap(Long networkId) {
90144
EnrichmentMap map = enrichmentMaps.get(networkId);
91-
92145
return map != null ? map : associatedEnrichmentMaps.get(networkId);
93146
}
94147

148+
95149
public EnrichmentMap removeEnrichmentMap(Long networkId) {
96150
EnrichmentMap map = enrichmentMaps.remove(networkId);
97-
98151
if (map != null)
99152
postAnalysisMediatorProvider.get().removeEnrichmentMap(map);
100153

101154
// Update our internal genemania map and fire an event if it changed
102-
Map<Long, EnrichmentMap> oldValue = getAssociatedEnrichmentMaps();
103-
104-
if (associatedEnrichmentMaps.remove(networkId) != null)
105-
pcs.firePropertyChange("associatedEnrichmentMaps", oldValue, getAssociatedEnrichmentMaps());
106-
155+
if (associatedEnrichmentMaps.remove(networkId) != null) {
156+
eventHelper.fireEvent(new AssociatedEnrichmentMapsChangedEvent(this, map, getAssociatedEnrichmentMaps()));
157+
}
107158
return map;
108159
}
109160

@@ -127,10 +178,9 @@ public void addAssociatedAppAttributes(CyNetwork network, EnrichmentMap map, Ass
127178
Columns.EM_ASSOCIATED_APP.set(table.getRow(network.getSUID()), app.name());
128179

129180
// Update our internal map and fire an event if it changed
130-
Map<Long, EnrichmentMap> oldValue = getAssociatedEnrichmentMaps();
131-
132-
if (associatedEnrichmentMaps.put(network.getSUID(), map) == null)
133-
pcs.firePropertyChange("associatedEnrichmentMaps", oldValue, getAssociatedEnrichmentMaps());
181+
if (associatedEnrichmentMaps.put(network.getSUID(), map) == null) {
182+
eventHelper.fireEvent(new AssociatedEnrichmentMapsChangedEvent(this, map, getAssociatedEnrichmentMaps()));
183+
}
134184
}
135185

136186
public boolean isAssociatedEnrichmentMap(Long networkId) {
@@ -160,27 +210,9 @@ public HeatMapParams getHeatMapParams(Long networkId, boolean edges) {
160210
}
161211

162212
public void reset() {
163-
for (PropertyChangeListener listener : pcs.getPropertyChangeListeners())
164-
pcs.removePropertyChangeListener(listener);
165-
166213
enrichmentMaps.clear();
167214
associatedEnrichmentMaps.clear();
168215
heatMapParams.clear();
169216
}
170-
171-
public void addPropertyChangeListener(PropertyChangeListener listener) {
172-
pcs.addPropertyChangeListener(listener);
173-
}
174-
175-
public void removePropertyChangeListener(PropertyChangeListener listener) {
176-
pcs.removePropertyChangeListener(listener);
177-
}
178217

179-
public void addPropertyChangeListener(String propertyName, PropertyChangeListener listener) {
180-
pcs.addPropertyChangeListener(propertyName, listener);
181-
}
182-
183-
public void removePropertyChangeListener(String propertyName, PropertyChangeListener listener) {
184-
pcs.removePropertyChangeListener(propertyName, listener);
185-
}
186218
}
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
package org.baderlab.csplugins.enrichmentmap.model.event;
2+
3+
import java.util.Map;
4+
5+
import org.baderlab.csplugins.enrichmentmap.model.EnrichmentMap;
6+
import org.baderlab.csplugins.enrichmentmap.model.EnrichmentMapManager;
7+
import org.cytoscape.event.AbstractCyEvent;
8+
9+
public class AssociatedEnrichmentMapsChangedEvent extends AbstractCyEvent<EnrichmentMapManager> {
10+
11+
private final EnrichmentMap map;
12+
private final Map<Long,EnrichmentMap> associatedMaps;
13+
14+
public AssociatedEnrichmentMapsChangedEvent(EnrichmentMapManager source, EnrichmentMap map, Map<Long,EnrichmentMap> associatedMaps) {
15+
super(source, AssociatedEnrichmentMapsChangedListener.class);
16+
this.map = map;
17+
this.associatedMaps = associatedMaps;
18+
}
19+
20+
public EnrichmentMap getEnrichmentMap() {
21+
return map;
22+
}
23+
24+
public Map<Long,EnrichmentMap> getAssociatedMaps() {
25+
return associatedMaps;
26+
}
27+
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
package org.baderlab.csplugins.enrichmentmap.model.event;
2+
3+
import org.cytoscape.event.CyListener;
4+
5+
public interface AssociatedEnrichmentMapsChangedListener extends CyListener {
6+
7+
public void handleEvent(AssociatedEnrichmentMapsChangedEvent e);
8+
9+
}
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
package org.baderlab.csplugins.enrichmentmap.model.event;
2+
3+
import org.baderlab.csplugins.enrichmentmap.model.EnrichmentMap;
4+
import org.baderlab.csplugins.enrichmentmap.model.EnrichmentMapManager;
5+
import org.cytoscape.event.AbstractCyEvent;
6+
import org.cytoscape.view.model.CyNetworkView;
7+
8+
public class EnrichmentMapAboutToBeRemovedEvent extends AbstractCyEvent<EnrichmentMapManager> {
9+
10+
private final EnrichmentMap map;
11+
private final CyNetworkView networkView;
12+
13+
public EnrichmentMapAboutToBeRemovedEvent(EnrichmentMapManager source, EnrichmentMap map, CyNetworkView networkView) {
14+
super(source, EnrichmentMapAboutToBeRemovedListener.class);
15+
this.map = map;
16+
this.networkView = networkView;
17+
}
18+
19+
public EnrichmentMap getEnrichmentMap() {
20+
return map;
21+
}
22+
23+
public CyNetworkView getNetworkView() {
24+
return networkView;
25+
}
26+
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
package org.baderlab.csplugins.enrichmentmap.model.event;
2+
3+
import org.cytoscape.event.CyListener;
4+
5+
public interface EnrichmentMapAboutToBeRemovedListener extends CyListener {
6+
7+
public void handleEvent(EnrichmentMapAboutToBeRemovedEvent e);
8+
9+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
package org.baderlab.csplugins.enrichmentmap.model.event;
2+
3+
import org.baderlab.csplugins.enrichmentmap.model.EnrichmentMap;
4+
import org.baderlab.csplugins.enrichmentmap.model.EnrichmentMapManager;
5+
import org.cytoscape.event.AbstractCyEvent;
6+
7+
8+
public class EnrichmentMapAddedEvent extends AbstractCyEvent<EnrichmentMapManager> {
9+
10+
private final EnrichmentMap map;
11+
12+
public EnrichmentMapAddedEvent(EnrichmentMapManager source, EnrichmentMap map) {
13+
super(source, EnrichmentMapAddedListener.class);
14+
this.map = map;
15+
}
16+
17+
public EnrichmentMap getEnrichmentMap() {
18+
return map;
19+
}
20+
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
package org.baderlab.csplugins.enrichmentmap.model.event;
2+
3+
import org.cytoscape.event.CyListener;
4+
5+
public interface EnrichmentMapAddedListener extends CyListener {
6+
7+
public void handleEvent(EnrichmentMapAddedEvent e);
8+
9+
}

EnrichmentMapPlugin/src/main/java/org/baderlab/csplugins/enrichmentmap/model/io/ModelSerializer.java

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,10 +34,16 @@ public class ModelSerializer {
3434

3535
private static final Logger logger = LoggerFactory.getLogger(ModelSerializer.class);
3636

37+
38+
public static EnrichmentMap deepCopy(EnrichmentMap map) {
39+
// This could be done with less memory probably.
40+
return deserialize(serialize(map));
41+
}
42+
3743
public static String serialize(EnrichmentMap map) {
3844
return serialize(map, false);
3945
}
40-
46+
4147
public static String serialize(EnrichmentMap map, boolean pretty) {
4248
// When saving to the session file DO NOT enable pretty printing, the Cytoscape
4349
// CSV parser is very slow for multi-line text

EnrichmentMapPlugin/src/main/java/org/baderlab/csplugins/enrichmentmap/style/EMStyleBuilder.java

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -543,12 +543,11 @@ private void setNodeColors(VisualStyle vs, EMStyleOptions options) {
543543
for (EMSignatureDataSet sds : signatureDataSets) {
544544
for (Long suid : sds.getNodeSuids()) {
545545
CyNode node = net.getNode(suid);
546-
547546
if (node != null) {
548547
View<CyNode> nv = netView.getNodeView(node);
549-
550-
if (nv != null)
548+
if (nv != null) {
551549
nv.setLockedValue(NODE_FILL_COLOR, Colors.SIG_NODE_COLOR);
550+
}
552551
}
553552
}
554553
}

0 commit comments

Comments
 (0)