Commit 6043d89c authored by Piotr Gawron's avatar Piotr Gawron
Browse files

drawing modifications implemented for all types of modifications

parent b833152e
Pipeline #5750 passed with stage
in 1 minute and 58 seconds
......@@ -404,17 +404,22 @@ public abstract class AbstractCellDesignerAliasConverter<T extends Element> impl
@Override
public Point2D getCoordinatesByPosition(Element element, Double pos) {
throw new NotImplementedException("Not implemented for: "+this.getClass());
return this.getCoordinatesByPosition(element, pos, 0.0);
}
@Override
public Point2D getCoordinatesByPosition(Element element, Double pos, Double width) {
throw new NotImplementedException("Not implemented for: " + this.getClass());
}
@Override
public Double getCellDesignerSize(ModificationResidue mr) {
throw new NotImplementedException("Not implemented for: "+this.getClass());
throw new NotImplementedException("Not implemented for: " + this.getClass());
}
@Override
public Double getWidthBySize(Element element, Double size) {
throw new NotImplementedException("Not implemented for: "+this.getClass());
throw new NotImplementedException("Not implemented for: " + this.getClass());
}
}
package lcsb.mapviewer.converter.model.celldesigner.geometry;
import java.awt.geom.AffineTransform;
import java.awt.geom.GeneralPath;
import java.awt.geom.PathIterator;
import java.awt.geom.Point2D;
import java.util.ArrayList;
import lcsb.mapviewer.common.exception.NotImplementedException;
import lcsb.mapviewer.converter.model.celldesigner.geometry.helper.CellDesignerAnchor;
import lcsb.mapviewer.model.map.species.Element;
import lcsb.mapviewer.model.map.species.Species;
import lcsb.mapviewer.model.map.species.field.AbstractRegionModification;
import lcsb.mapviewer.model.map.species.field.ModificationResidue;
/**
* Class that provides CellDesigner specific graphical information for
* AntisenseRna. It's used for conversion from xml to normal x,y coordinates.
*
* @author Piotr Gawron
*
*/
public class AntisenseRnaCellDesignerAliasConverter extends AbstractCellDesignerAliasConverter<Species> {
/**
* Default constructor.
*
* @param sbgn
* Should the converter use sbgn standard
*/
protected AntisenseRnaCellDesignerAliasConverter(boolean sbgn) {
super(sbgn);
}
/**
* How big should be the arc in rectangle for nucleic acid feature
* representation.
*/
private static final int RECTANGLE_CORNER_ARC_SIZE = 5;
@Override
public Point2D getPointCoordinates(Species alias, CellDesignerAnchor anchor) {
if (invalidAnchorPosition(alias, anchor)) {
return alias.getCenter();
}
if (isSbgn()) {
return getRectangleTransformation().getPointOnRectangleByAnchor(alias.getX(), alias.getY(), alias.getWidth(),
alias.getHeight(), anchor);
}
ArrayList<Point2D> points = getPoints(alias);
return getPolygonTransformation().getPointOnPolygonByAnchor(points, anchor);
}
@Override
protected PathIterator getBoundPathIterator(Species alias) {
return getAntisebseRnaPath(alias).getPathIterator(new AffineTransform());
}
/**
* Returns shape of the AntisenseRna as a list of points.
*
* @param alias
* alias for which we are looking for a border
* @return list of points defining border of the given alias
*/
private ArrayList<Point2D> getPoints(Element alias) {
double x = alias.getX();
double y = alias.getY();
double width = alias.getWidth();
double height = alias.getHeight();
ArrayList<Point2D> points = new ArrayList<Point2D>();
// CHECKSTYLE:OFF
points.add(new Point2D.Double(x + width / 8, y + height / 2));
points.add(new Point2D.Double(x, y));
points.add(new Point2D.Double(x + width * 3 / 8, y));
points.add(new Point2D.Double(x + width * 3 / 4, y));
points.add(new Point2D.Double(x + width * 7 / 8, y + height / 2));
points.add(new Point2D.Double(x + width, y + height));
points.add(new Point2D.Double(x + width * 5 / 8, y + height));
points.add(new Point2D.Double(x + width / 4, y + height));
// CHECKSTYLE:ON
return points;
}
/**
* Returns shape of the AntisenseRna as a GeneralPath object.
*
* @param alias
* alias for which we are looking for a border
* @return GeneralPath object defining border of the given alias
*/
private GeneralPath getAntisebseRnaPath(Element alias) {
// CHECKSTYLE:OFF
GeneralPath path;
if (!isSbgn()) {
path = new GeneralPath(GeneralPath.WIND_EVEN_ODD, 4);
path.moveTo(alias.getX(), alias.getY());
path.lineTo(alias.getX() + alias.getWidth() * 3 / 4, alias.getY());
path.lineTo(alias.getX() + alias.getWidth(), alias.getY() + alias.getHeight());
path.lineTo(alias.getX() + alias.getWidth() / 4, alias.getY() + alias.getHeight());
path.closePath();
} else {
path = new GeneralPath(GeneralPath.WIND_EVEN_ODD, 6);
double x = alias.getX(), y = alias.getY(), width = alias.getWidth(), height = alias.getHeight();
path.moveTo(x, y);
path.lineTo(x, y + height - RECTANGLE_CORNER_ARC_SIZE);
path.curveTo(x, y + height, x + RECTANGLE_CORNER_ARC_SIZE, y + height, x + RECTANGLE_CORNER_ARC_SIZE, y + height);
path.lineTo(x + width - RECTANGLE_CORNER_ARC_SIZE, y + height);
path.curveTo(x + width, y + height, x + width, y + height - RECTANGLE_CORNER_ARC_SIZE, x + width,
y + height - RECTANGLE_CORNER_ARC_SIZE);
path.lineTo(x + width, y);
path.closePath();
}
// CHECKSTYLE:ON
return path;
}
@Override
public Double getCellDesignerPositionByCoordinates(ModificationResidue mr) {
return (mr.getPosition().getX() - mr.getSpecies().getX())
/ (mr.getSpecies().getWidth() * 3.0 / 4.0);
}
@Override
public Point2D getCoordinatesByPosition(Element element, Double pos) {
return new Point2D.Double(element.getX() + element.getWidth() * 3.0 / 4.0 * pos, element.getY());
}
@Override
public Double getCellDesignerSize(ModificationResidue mr) {
if (mr instanceof AbstractRegionModification) {
return ((AbstractRegionModification) mr).getWidth() / (mr.getSpecies().getWidth() * 3.0 / 4.0);
}
throw new NotImplementedException("Not implemented for: " + this.getClass() + ", " + mr.getClass());
}
@Override
public Double getWidthBySize(Element element, Double size) {
return size * (element.getWidth() * 3.0 / 4.0);
}
}
package lcsb.mapviewer.converter.model.celldesigner.geometry;
import java.awt.geom.AffineTransform;
import java.awt.geom.GeneralPath;
import java.awt.geom.PathIterator;
import java.awt.geom.Point2D;
import java.util.ArrayList;
import lcsb.mapviewer.common.exception.NotImplementedException;
import lcsb.mapviewer.converter.model.celldesigner.geometry.helper.CellDesignerAnchor;
import lcsb.mapviewer.model.map.species.Element;
import lcsb.mapviewer.model.map.species.Species;
import lcsb.mapviewer.model.map.species.field.AbstractRegionModification;
import lcsb.mapviewer.model.map.species.field.ModificationResidue;
/**
* Class that provides CellDesigner specific graphical information for
* AntisenseRna. It's used for conversion from xml to normal x,y coordinates.
*
* @author Piotr Gawron
*
*/
public class AntisenseRnaCellDesignerAliasConverter extends AbstractCellDesignerAliasConverter<Species> {
/**
* Default constructor.
*
* @param sbgn
* Should the converter use sbgn standard
*/
protected AntisenseRnaCellDesignerAliasConverter(boolean sbgn) {
super(sbgn);
}
/**
* How big should be the arc in rectangle for nucleic acid feature
* representation.
*/
private static final int RECTANGLE_CORNER_ARC_SIZE = 5;
@Override
public Point2D getPointCoordinates(Species alias, CellDesignerAnchor anchor) {
if (invalidAnchorPosition(alias, anchor)) {
return alias.getCenter();
}
if (isSbgn()) {
return getRectangleTransformation().getPointOnRectangleByAnchor(alias.getX(), alias.getY(), alias.getWidth(),
alias.getHeight(), anchor);
}
ArrayList<Point2D> points = getPoints(alias);
return getPolygonTransformation().getPointOnPolygonByAnchor(points, anchor);
}
@Override
protected PathIterator getBoundPathIterator(Species alias) {
return getAntisebseRnaPath(alias).getPathIterator(new AffineTransform());
}
/**
* Returns shape of the AntisenseRna as a list of points.
*
* @param alias
* alias for which we are looking for a border
* @return list of points defining border of the given alias
*/
private ArrayList<Point2D> getPoints(Element alias) {
double x = alias.getX();
double y = alias.getY();
double width = alias.getWidth();
double height = alias.getHeight();
ArrayList<Point2D> points = new ArrayList<Point2D>();
// CHECKSTYLE:OFF
points.add(new Point2D.Double(x + width / 8, y + height / 2));
points.add(new Point2D.Double(x, y));
points.add(new Point2D.Double(x + width * 3 / 8, y));
points.add(new Point2D.Double(x + width * 3 / 4, y));
points.add(new Point2D.Double(x + width * 7 / 8, y + height / 2));
points.add(new Point2D.Double(x + width, y + height));
points.add(new Point2D.Double(x + width * 5 / 8, y + height));
points.add(new Point2D.Double(x + width / 4, y + height));
// CHECKSTYLE:ON
return points;
}
/**
* Returns shape of the AntisenseRna as a GeneralPath object.
*
* @param alias
* alias for which we are looking for a border
* @return GeneralPath object defining border of the given alias
*/
private GeneralPath getAntisebseRnaPath(Element alias) {
// CHECKSTYLE:OFF
GeneralPath path;
if (!isSbgn()) {
path = new GeneralPath(GeneralPath.WIND_EVEN_ODD, 4);
path.moveTo(alias.getX(), alias.getY());
path.lineTo(alias.getX() + alias.getWidth() * 3 / 4, alias.getY());
path.lineTo(alias.getX() + alias.getWidth(), alias.getY() + alias.getHeight());
path.lineTo(alias.getX() + alias.getWidth() / 4, alias.getY() + alias.getHeight());
path.closePath();
} else {
path = new GeneralPath(GeneralPath.WIND_EVEN_ODD, 6);
double x = alias.getX(), y = alias.getY(), width = alias.getWidth(), height = alias.getHeight();
path.moveTo(x, y);
path.lineTo(x, y + height - RECTANGLE_CORNER_ARC_SIZE);
path.curveTo(x, y + height, x + RECTANGLE_CORNER_ARC_SIZE, y + height, x + RECTANGLE_CORNER_ARC_SIZE, y + height);
path.lineTo(x + width - RECTANGLE_CORNER_ARC_SIZE, y + height);
path.curveTo(x + width, y + height, x + width, y + height - RECTANGLE_CORNER_ARC_SIZE, x + width,
y + height - RECTANGLE_CORNER_ARC_SIZE);
path.lineTo(x + width, y);
path.closePath();
}
// CHECKSTYLE:ON
return path;
}
@Override
public Double getCellDesignerPositionByCoordinates(ModificationResidue mr) {
return (mr.getPosition().getX() - mr.getSpecies().getX()) / (mr.getSpecies().getWidth() * 3.0 / 4.0);
}
@Override
public Point2D getCoordinatesByPosition(Element element, Double pos, Double width) {
double x = element.getX() + element.getWidth() * 3.0 / 4.0 * pos;
x = Math.max(element.getX() + width / 2, x);
x = Math.min(element.getX() + element.getWidth() * 3.0 / 4.0 - width / 2, x);
return new Point2D.Double(x, element.getY());
}
@Override
public Double getCellDesignerSize(ModificationResidue mr) {
if (mr instanceof AbstractRegionModification) {
return ((AbstractRegionModification) mr).getWidth() / (mr.getSpecies().getWidth() * 3.0 / 4.0);
}
throw new NotImplementedException("Not implemented for: " + this.getClass() + ", " + mr.getClass());
}
@Override
public Double getWidthBySize(Element element, Double size) {
return size * (element.getWidth() * 3.0 / 4.0);
}
}
......@@ -145,4 +145,9 @@ public class CellDesignerAliasConverter implements ICellDesignerAliasConverter<E
return converter.getWidthBySize(element, size);
}
@Override
public Point2D getCoordinatesByPosition(Element element, Double pos, Double width) {
return converter.getCoordinatesByPosition(element, pos, width);
}
}
......@@ -95,8 +95,12 @@ public class GeneCellDesignerAliasConverter extends AbstractCellDesignerAliasCon
}
@Override
public Point2D getCoordinatesByPosition(Element element, Double pos) {
Point2D result = new Point2D.Double(element.getX() + element.getWidth() * pos, element.getY());
public Point2D getCoordinatesByPosition(Element element, Double pos, Double modificationWidth) {
double x = element.getX() + element.getWidth() * pos;
x = Math.max(element.getX() + modificationWidth/2, x);
x = Math.min(element.getX() + element.getWidth() - modificationWidth/2, x);
Point2D result = new Point2D.Double(x, element.getY());
return result;
}
......
......@@ -8,8 +8,8 @@ import lcsb.mapviewer.model.map.species.Element;
import lcsb.mapviewer.model.map.species.field.ModificationResidue;
/**
* Interface that defines functions useful in transforming graphical
* information from objects retrieved from CellDesigner xml into absolute values.
* Interface that defines functions useful in transforming graphical information
* from objects retrieved from CellDesigner xml into absolute values.
*
* @author Piotr Gawron
*
......@@ -64,9 +64,33 @@ public interface ICellDesignerAliasConverter<T extends Element> {
public Double getCellDesignerPositionByCoordinates(ModificationResidue mr);
/**
* Gets coordinates on element based on CellDesigner position
*
* @param element
* element on which we want to find coordinates
* @param pos
* CellDesigner position (value between 0-1)
* @return coordinates on the element
*/
public Point2D getCoordinatesByPosition(Element element, Double pos);
/**
* Gets coordinates on element based on CellDesigner position taking into
* account width of the {@link ModificationResidue} that we want to place.
*
* @param element
* element on which we want to find coordinates
* @param pos
* CellDesigner position (value between 0-1)
* @param modificationWidth
* width of the {@link ModificationResidue}
* @return coordinates on the element
*/
public Point2D getCoordinatesByPosition(Element element, Double pos, Double modificationWidth);
public Double getCellDesignerSize(ModificationResidue mr);
public Double getWidthBySize(Element element, Double size);
}
......@@ -126,9 +126,12 @@ public class RnaCellDesignerAliasConverter extends AbstractCellDesignerAliasConv
}
@Override
public Point2D getCoordinatesByPosition(Element element, Double pos) {
return new Point2D.Double(element.getX() + element.getWidth() / 4.0 + element.getWidth() * 3.0 / 4.0 * pos,
element.getY());
public Point2D getCoordinatesByPosition(Element element, Double pos, Double modificationWidth) {
double x = element.getX() + element.getWidth() / 4.0 + element.getWidth() * 3.0 / 4.0 * pos;
x = Math.max(element.getX() + modificationWidth / 2, x);
x = Math.min(element.getX() + element.getWidth() - modificationWidth / 2, x);
return new Point2D.Double(x, element.getY());
}
@Override
......
......@@ -4,11 +4,9 @@ import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.Stroke;
import java.awt.geom.AffineTransform;
import java.awt.geom.Ellipse2D;
import java.awt.geom.GeneralPath;
import java.awt.geom.Path2D;
import java.awt.geom.PathIterator;
import java.awt.geom.Point2D;
import org.apache.log4j.Logger;
......@@ -58,7 +56,7 @@ public class AntisenseRnaConverter extends SpeciesConverter<AntisenseRna> {
graphics.setStroke(stroke);
for (ModificationResidue mr : antisenseRna.getRegions()) {
drawRegion(antisenseRna, mr, graphics, false);
drawModification(mr, graphics, false);
}
drawText(antisenseRna, graphics, params);
......@@ -88,39 +86,4 @@ public class AntisenseRnaConverter extends SpeciesConverter<AntisenseRna> {
return getAntisenseRnaPath(alias).getPathIterator(new AffineTransform());
}
/**
* This method draws antisense rna region for given alias.
*
* @param antisenseRna
* {@link AntisenseRna} on which region should be drawn
* @param region
* {@link AntisenseRnaRegion} to be drawn
* @param graphics
* {@link Graphics2D} where we draw region
* @param drawDescription
* flag determining if we want to draw description as well
*/
private void drawRegion(final AntisenseRna antisenseRna, final ModificationResidue region, final Graphics2D graphics,
final boolean drawDescription) {
double diameter = DEFAULT_MODIFICATION_DIAMETER;
double y = antisenseRna.getY();
Point2D p = new Point2D.Double(region.getPosition().getX(), region.getPosition().getY() - diameter);
Ellipse2D ellipse = new Ellipse2D.Double(p.getX() - diameter / 2, p.getY() - diameter / 2, diameter, diameter);
Color c = graphics.getColor();
graphics.setColor(Color.WHITE);
graphics.fill(ellipse);
graphics.setColor(c);
graphics.draw(ellipse);
graphics.drawLine((int) p.getX(), (int) (p.getY() + diameter / 2), (int) p.getX(), (int) y);
String text = region.getName();
if (!text.equals("") && drawDescription) {
double textWidth = graphics.getFontMetrics().stringWidth(text);
Point2D p2 = new Point2D.Double(p.getX() - textWidth / 2, p.getY() - DEFAULT_SPECIES_MODIFIER_FONT_SIZE);
graphics.drawString(text, (int) p2.getX(), (int) p2.getY());
}
}
}
package lcsb.mapviewer.converter.graphics.bioEntity.element.species;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.Shape;
import java.awt.Stroke;
import java.awt.geom.AffineTransform;
import java.awt.geom.Ellipse2D;
import java.awt.geom.PathIterator;
import java.awt.geom.Point2D;
import org.apache.log4j.Logger;
......@@ -19,8 +16,6 @@ import lcsb.mapviewer.model.map.layout.ColorSchema;
import lcsb.mapviewer.model.map.species.Gene;
import lcsb.mapviewer.model.map.species.Species;
import lcsb.mapviewer.model.map.species.field.ModificationResidue;
import lcsb.mapviewer.model.map.species.field.ModificationSite;
import lcsb.mapviewer.model.map.species.field.ModificationState;
/**
* This class defines methods used for drawing Gene SpeciesAlias on the
......@@ -60,71 +55,12 @@ public class GeneConverter extends SpeciesConverter<Gene> {
graphics.setStroke(stroke);
for (ModificationResidue mr : gene.getModificationResidues()) {
drawModification(gene, mr, graphics, false, false);
drawModification(mr, graphics, false);
}
drawText(gene, graphics, params);
}
/**
* This method draws modification of the alias. If drawEmptyModification is set
* to false then modification is not drawn if empty. If drawDescription is set
* then also description (position) of the modification is drawn on the canvas.
*
* @param gene
* object that is 'parent' of the residue
* @param mr2
* modification to be drawn
* @param graphics
* - where the modification should be drawn
* @param drawEmptyModification
* flag that indicates if we should draw empty modification
* @param drawDescription
* flag that indicates if we should draw description of the
* modification
*/
private void drawModification(final Gene gene, final ModificationResidue mr, final Graphics2D graphics,
final boolean drawEmptyModification, final boolean drawDescription) {
if (mr instanceof ModificationSite) {
ModificationSite modificationSite = (ModificationSite) mr;
if (!drawEmptyModification && modificationSite.getState() == null) {
return;
}
double diameter = DEFAULT_MODIFICATION_DIAMETER;