diff --git a/CHANGELOG b/CHANGELOG index 8fddbae2aa28cd9acd012c9e659cb67dbebf66a7..27846d35f885565812fe10b3aaa33fdf41a86b97 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -15,7 +15,7 @@ minerva (18.1.0) stable; urgency=medium * Bug fix: exporting degraded to SBGN-ML should not produce a label for it (#2194) - -- Piotr Gawron <piotr.gawron@uni.lu> Thu, 19 Dec 2024 13:00:00 +0200 + -- Piotr Gawron <piotr.gawron@uni.lu> Thu, 30 Jan 2025 15:00:00 +0200 minerva (18.0.7) stable; urgency=medium * Bug fix: plugin re-validate did not update md5 of javascript content - this diff --git a/converter-graphics/src/test/java/lcsb/mapviewer/converter/graphics/NormalImageGeneratorTest.java b/converter-graphics/src/test/java/lcsb/mapviewer/converter/graphics/NormalImageGeneratorTest.java index f4293a2a30e835de5a9a48719103bfd3fa9b8946..d63c4b03e7e06cd9d3fc647b1f7147a9f3026fe6 100644 --- a/converter-graphics/src/test/java/lcsb/mapviewer/converter/graphics/NormalImageGeneratorTest.java +++ b/converter-graphics/src/test/java/lcsb/mapviewer/converter/graphics/NormalImageGeneratorTest.java @@ -1,19 +1,19 @@ package lcsb.mapviewer.converter.graphics; -import java.awt.geom.Point2D; -import java.awt.geom.Rectangle2D; - -import org.junit.After; -import org.junit.Before; -import org.junit.Test; - import lcsb.mapviewer.commands.CreateHierarchyCommand; import lcsb.mapviewer.converter.graphics.AbstractImageGenerator.Params; +import lcsb.mapviewer.converter.model.celldesigner.CellDesignerXmlParser; import lcsb.mapviewer.model.graphics.PolylineData; import lcsb.mapviewer.model.map.layout.graphics.Layer; import lcsb.mapviewer.model.map.layout.graphics.LayerText; import lcsb.mapviewer.model.map.model.Model; import lcsb.mapviewer.model.map.model.ModelFullIndexed; +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +import java.awt.geom.Point2D; +import java.awt.geom.Rectangle2D; public class NormalImageGeneratorTest extends GraphicsTestFunctions { @@ -44,7 +44,8 @@ public class NormalImageGeneratorTest extends GraphicsTestFunctions { } @Test - public void testArtifitialInHierarchicalView() throws Exception { + public void testArtificialInHierarchicalView() throws Exception { + CellDesignerXmlParser parser = new CellDesignerXmlParser(); Model model = createCompartmentModel(); Layer layer = model.getLayers().iterator().next(); diff --git a/model-command/src/main/java/lcsb/mapviewer/commands/CreateHierarchyCommand.java b/model-command/src/main/java/lcsb/mapviewer/commands/CreateHierarchyCommand.java index 9db57b4061672e6de5512e362c745ed4468d6409..9f43ffdc9d6ebc9ea170f5a7384caf2bf8c80ec8 100644 --- a/model-command/src/main/java/lcsb/mapviewer/commands/CreateHierarchyCommand.java +++ b/model-command/src/main/java/lcsb/mapviewer/commands/CreateHierarchyCommand.java @@ -42,11 +42,11 @@ public class CreateHierarchyCommand extends ModelCommand { /** * Top left corner x coordinate of the text associated with compartment. */ - private static final double DEFAULT_TITLE_X_COORD_IN_ARTIFITIAL_COMPARTMENT = 10; + private static final double DEFAULT_TITLE_X_COORD_IN_ARTIFICIAL_COMPARTMENT = 10; /** * Top left corner y coordinate of the text associated with compartment. */ - private static final double DEFAULT_TITLE_Y_COORD_IN_ARTIFITIAL_COMPARTMENT = 10; + private static final double DEFAULT_TITLE_Y_COORD_IN_ARTIFICIAL_COMPARTMENT = 10; /** * Default class logger. */ @@ -130,6 +130,7 @@ public class CreateHierarchyCommand extends ModelCommand { protected void clean() { for (final Element alias : getModel().getElements()) { alias.setCompartment(null); + alias.setPathway(null); if (alias.getTransparencyLevel() == null || alias.getTransparencyLevel().isEmpty()) { alias.setTransparencyLevel(""); } @@ -168,10 +169,10 @@ public class CreateHierarchyCommand extends ModelCommand { if (rect.getFillColor() != null) { compartment.setFillColor(rect.getFillColor()); } - compartment.setNameX(rect.getX() + DEFAULT_TITLE_X_COORD_IN_ARTIFITIAL_COMPARTMENT); - compartment.setNameY(rect.getY() + DEFAULT_TITLE_Y_COORD_IN_ARTIFITIAL_COMPARTMENT); - compartment.setNameWidth(rect.getWidth() - 2 * DEFAULT_TITLE_X_COORD_IN_ARTIFITIAL_COMPARTMENT); - compartment.setNameHeight(rect.getHeight() - 2 * DEFAULT_TITLE_Y_COORD_IN_ARTIFITIAL_COMPARTMENT); + compartment.setNameX(rect.getX() + DEFAULT_TITLE_X_COORD_IN_ARTIFICIAL_COMPARTMENT); + compartment.setNameY(rect.getY() + DEFAULT_TITLE_Y_COORD_IN_ARTIFICIAL_COMPARTMENT); + compartment.setNameWidth(rect.getWidth() - 2 * DEFAULT_TITLE_X_COORD_IN_ARTIFICIAL_COMPARTMENT); + compartment.setNameHeight(rect.getHeight() - 2 * DEFAULT_TITLE_Y_COORD_IN_ARTIFICIAL_COMPARTMENT); compartment.setNameHorizontalAlign(HorizontalAlign.LEFT); compartment.setNameVerticalAlign(VerticalAlign.TOP); compartment.setZ(rect.getZ()); @@ -196,10 +197,10 @@ public class CreateHierarchyCommand extends ModelCommand { rap.processNotes(compartment); text.setNotes(compartment.getName() + "\n" + compartment.getNotes()); - compartment.setNameX(text.getX() + DEFAULT_TITLE_X_COORD_IN_ARTIFITIAL_COMPARTMENT); - compartment.setNameY(text.getY() + DEFAULT_TITLE_Y_COORD_IN_ARTIFITIAL_COMPARTMENT); - compartment.setNameWidth(text.getWidth() - 2 * DEFAULT_TITLE_X_COORD_IN_ARTIFITIAL_COMPARTMENT); - compartment.setNameHeight(text.getHeight() - 2 * DEFAULT_TITLE_Y_COORD_IN_ARTIFITIAL_COMPARTMENT); + compartment.setNameX(text.getX() + DEFAULT_TITLE_X_COORD_IN_ARTIFICIAL_COMPARTMENT); + compartment.setNameY(text.getY() + DEFAULT_TITLE_Y_COORD_IN_ARTIFICIAL_COMPARTMENT); + compartment.setNameWidth(text.getWidth() - 2 * DEFAULT_TITLE_X_COORD_IN_ARTIFICIAL_COMPARTMENT); + compartment.setNameHeight(text.getHeight() - 2 * DEFAULT_TITLE_Y_COORD_IN_ARTIFICIAL_COMPARTMENT); compartment.setNameHorizontalAlign(HorizontalAlign.LEFT); compartment.setNameVerticalAlign(VerticalAlign.TOP); @@ -250,11 +251,12 @@ public class CreateHierarchyCommand extends ModelCommand { double rate = computeRate(alias, Configuration.MIN_VISIBLE_OBJECT_SIZE); int logValue = (int) ((int) Math.ceil(Math.log(rate)) / LOG_4); boolean hasCompartment = alias.getCompartment() != null; + boolean hasPathway = alias.getPathway() != null; boolean hasComplex = false; if (alias instanceof Species) { hasComplex = ((Species) alias).getComplex() != null; } - if (!hasCompartment && !hasComplex) { + if (!hasCompartment && !hasPathway && !hasComplex) { logValue = 0; } if (logValue >= zoomLevels) { @@ -280,7 +282,7 @@ public class CreateHierarchyCommand extends ModelCommand { int maxVisibilityLevel = Integer.MAX_VALUE; double rate = computeRate(compartment, Configuration.MAX_VISIBLE_OBJECT_SIZE); maxVisibilityLevel = (int) ((int) Math.ceil(Math.log(rate)) / LOG_4); - for (final Element child : compartment.getElements()) { + for (final Element child : getCompartmentElements(compartment)) { maxVisibilityLevel = Math.min(maxVisibilityLevel, computeVisibility(child)); } if (maxVisibilityLevel >= zoomLevels) { @@ -291,13 +293,68 @@ public class CreateHierarchyCommand extends ModelCommand { } compartment.setTransparencyLevel(maxVisibilityLevel + ""); } - for (final Element child : compartment.getElements()) { - if (child.getVisibilityLevel() == null || child.getVisibilityLevel().isEmpty()) { + for (final Element child : getCompartmentElements(compartment)) { + if (!isExcludedChildVisibility(child)) { child.setVisibilityLevel(compartment.getTransparencyLevel()); } } } + private Set<Element> getCompartmentElements(final Compartment compartment) { + Set<Element> children = new HashSet<>(); + for (Element element : compartment.getModel().getElements()) { + if (element.getCompartment() == compartment) { + if (element.getPathway() == null) { + children.add(element); + } else if (element.getCompartment().getSize() < element.getPathway().getSize()) { + children.add(element); + } + } + } + return children; + } + + private boolean isExcludedChildVisibility(final Element child) { + return child.getVisibilityLevel() != null && !child.getVisibilityLevel().isEmpty(); + } + + private void settingTransparencyLevelForPathway(final PathwayCompartment pathway) { + Set<Element> pathwayChildren = getPathwayChildren(pathway); + if (pathway.getTransparencyLevel() == null || pathway.getTransparencyLevel().isEmpty()) { + double rate = computeRate(pathway, Configuration.MAX_VISIBLE_OBJECT_SIZE); + int maxVisibilityLevel = (int) ((int) Math.ceil(Math.log(rate)) / LOG_4); + for (final Element child : pathwayChildren) { + maxVisibilityLevel = Math.min(maxVisibilityLevel, computeVisibility(child)); + } + if (maxVisibilityLevel >= zoomLevels) { + maxVisibilityLevel = zoomLevels; + } + if (maxVisibilityLevel <= 0) { + maxVisibilityLevel = 1; + } + pathway.setTransparencyLevel(maxVisibilityLevel + ""); + } + for (final Element child : pathwayChildren) { + if (!isExcludedChildVisibility(child)) { + child.setVisibilityLevel(pathway.getTransparencyLevel()); + } + } + } + + private Set<Element> getPathwayChildren(final PathwayCompartment pathway) { + Set<Element> children = new HashSet<>(); + for (Element element : pathway.getModel().getElements()) { + if (element.getPathway() == pathway) { + if (element.getCompartment() == null) { + children.add(element); + } else if (element.getPathway().getSize() < element.getCompartment().getSize()) { + children.add(element); + } + } + } + return children; + } + /** * Sets transparency level in hierarchical view for complex alias. * @@ -320,20 +377,32 @@ public class CreateHierarchyCommand extends ModelCommand { complex.setTransparencyLevel(maxVisibilityLevel + ""); } for (final Element child : complex.getElements()) { - if (child.getVisibilityLevel() == null || child.getVisibilityLevel().isEmpty()) { + if (!isExcludedChildVisibility(child)) { child.setVisibilityLevel(complex.getTransparencyLevel()); } } } + private final Set<Element> excluded = new HashSet<>(); + /** * Sets transparency level in hierarchical view for all elements. * * @param sortedAliases list of aliases */ private void settingOfTransparencyLevel(final List<Element> sortedAliases) { + excluded.clear(); + + for (final Element alias : sortedAliases) { + if (alias.getVisibilityLevel() != null && !alias.getVisibilityLevel().isEmpty()) { + excluded.add(alias); + } + } + for (final Element alias : sortedAliases) { - if (alias instanceof Compartment) { + if (alias instanceof PathwayCompartment) { + settingTransparencyLevelForPathway((PathwayCompartment) alias); + } else if (alias instanceof Compartment) { settingTransparencyLevelForCompartment((Compartment) alias); } else if (alias instanceof Complex) { settingTransparencyLevelForComplex((Complex) alias); @@ -351,15 +420,16 @@ public class CreateHierarchyCommand extends ModelCommand { * @param sortedAliases list of aliases */ private void setChildrening(final List<Element> sortedAliases) { - for (final Element compartment : sortedAliases) { - if (compartment instanceof Compartment) { + for (final Element element : sortedAliases) { + if (element instanceof Compartment) { + Compartment compartment = (Compartment) element; Set<Element> removable = new HashSet<>(); - for (final Element alias : ((Compartment) compartment).getElements()) { + for (final Element alias : compartment.getElements()) { if (alias.getCompartment() != compartment) { removable.add(alias); } } - ((Compartment) compartment).getElements().removeAll(removable); + compartment.getElements().removeAll(removable); } } } @@ -373,7 +443,11 @@ public class CreateHierarchyCommand extends ModelCommand { for (final Element element : getModel().getElements()) { if (element.getCompartment() == null) { for (final Element compartment : sortedAliases) { - if (compartment instanceof Compartment) { + if (compartment instanceof PathwayCompartment) { + if (compartment.contains(element)) { + element.setPathway((PathwayCompartment) compartment); + } + } else if (compartment instanceof Compartment) { if (((Compartment) compartment).getElements().contains(element)) { element.setCompartment((Compartment) compartment); } @@ -414,7 +488,7 @@ public class CreateHierarchyCommand extends ModelCommand { nullCompartment.setWidth(Double.MAX_VALUE); nullCompartment.setHeight(Double.MAX_VALUE); for (final Element element : getModel().getElements()) { - Compartment supposedParent = nullCompartment; + Compartment supposedCompartment = nullCompartment; PathwayCompartment supposedPathway = null; for (final Compartment compartment : getModel().getCompartments()) { if (compartment instanceof PathwayCompartment) { @@ -423,12 +497,12 @@ public class CreateHierarchyCommand extends ModelCommand { supposedPathway = (PathwayCompartment) compartment; } } - } else if (compartment.contains(element) && compartment.getSize() < supposedParent.getSize()) { - supposedParent = compartment; + } else if (compartment.contains(element) && compartment.getSize() < supposedCompartment.getSize()) { + supposedCompartment = compartment; } } - if (supposedParent != nullCompartment) { - supposedParent.addElement(element); + if (supposedCompartment != nullCompartment) { + supposedCompartment.addElement(element); } element.setPathway(supposedPathway); }