@rcsb/rcsb-saguaro
Version:
RCSB 1D Feature Viewer
176 lines (175 loc) • 6.17 kB
JavaScript
import { RcsbAbstractDisplay } from "./RcsbAbstractDisplay";
import { pointer } from "d3-selection";
import { RcsbD3Constants } from "../RcsbD3/RcsbD3Constants";
import { RcsbD3ScaleFactory } from "../RcsbD3/RcsbD3ScaleFactory";
import * as classes from "../../scss/RcsbBoard.module.scss";
import { RcsbD3FastSequenceManager } from "../RcsbD3/RcsbD3DisplayManager/RcsbD3FastSequenceManager";
export class RcsbFastSequenceDisplay extends RcsbAbstractDisplay {
constructor() {
super(...arguments);
this.yScale = RcsbD3ScaleFactory.getLinearScale();
this.intervalRatio = [5, 16];
this.hideFlag = false;
this.nonEmptyDisplay = false;
this.rcsbD3SequenceManager = new RcsbD3FastSequenceManager();
this.definedScale = false;
this.innerData = [];
this.mouseclick = (event) => {
const svgNode = this.g.node();
if (svgNode != null) {
const x = pointer(event, svgNode)[0];
const position = Math.round(this.xScale.invert(x));
const region = { begin: position, end: position };
this.getBoardHighlight()(region, event.shiftKey ? 'add' : 'set', 'select', false);
this.elementSubject.mouseclick.next({ d: region, e: event });
}
};
}
mousemove(event) {
var _a, _b;
const svgNode = (_a = this.g) === null || _a === void 0 ? void 0 : _a.node();
if (svgNode != null) {
const x = pointer(event, svgNode)[0];
this.index = Math.round(this.xScale.invert(x));
this.elementSubject.mouseenter.next({ d: (_b = this.innerData[this.index]) !== null && _b !== void 0 ? _b : { begin: this.index }, e: event });
}
}
mouseleave(event) {
this.elementSubject.mouseleave.next({ d: { begin: this.index }, e: event });
}
setDynamicDisplay() {
this.hideFlag = true;
this.trackSubject.mouseleave.subscribe(() => {
this.hideFlag = true;
this.getElements().remove();
});
this.trackSubject.mouseenter.subscribe(() => {
this.hideFlag = false;
this.update(this.compKey);
});
}
setNonEmptyDisplay(flag) {
this.nonEmptyDisplay = flag;
}
enter(e) {
e.append(RcsbD3Constants.TEXT);
}
_update(where, compKey) {
this.compKey = compKey;
if (this.hideFlag)
return;
this.setInnerData();
if (this.data() == null) {
return;
}
if (this.minIntervalRatio()) {
const dataElems = this.getSequenceData(where);
this.rmSequenceLine();
this.selectElements(dataElems, compKey);
this.getElements().attr("class", classes.rcsbElement)
.classed(classes.rcsbElement + "_" + compKey, typeof compKey === "string")
.call(this.plot.bind(this));
}
else {
this.getElements().remove();
this.displayEmpty();
}
this.checkHideFlag();
}
displayEmpty() {
if (this.nonEmptyDisplay) {
this.plotSequenceLine();
}
}
plot(elements) {
if (this.hideFlag)
return;
if (!this.definedScale) {
this.setScale();
}
const config = {
elements: elements,
trackG: this.g,
xScale: this.xScale,
yScale: this.yScale,
color: this._displayColor,
height: this.height(),
intervalRatio: this.intervalRatio,
mouseclick: this.mouseclick.bind(this),
mousemove: this.mousemove.bind(this),
mouseleave: this.mouseleave.bind(this)
};
this.rcsbD3SequenceManager.plot(config);
this.checkHideFlag();
}
move() {
const config = {
xScale: this.xScale,
intervalRatio: this.intervalRatio,
};
this.rcsbD3SequenceManager.move(config);
}
setScale() {
this.yScale
.domain([0, this.height()])
.range([0, this.height()]);
this.definedScale = true;
}
plotSequenceLine() {
const config = {
xScale: this.xScale,
yScale: this.yScale,
height: this.height(),
trackG: this.g,
mouseclick: this.mouseclick.bind(this),
mousemove: this.mousemove.bind(this),
mouseleave: this.mouseleave.bind(this)
};
RcsbD3FastSequenceManager.plotSequenceLine(config);
}
rmSequenceLine() {
RcsbD3FastSequenceManager.clearLine({ trackG: this.g });
}
checkHideFlag() {
if (this.hideFlag) {
this.getElements().remove();
}
}
minIntervalRatio() {
return (this.getRatio() >= this.intervalRatio[0]);
}
getSequenceData(where) {
const seqPath = new Array();
for (let n = where.from; n <= where.to; n++) {
if (this.innerData[n])
addResToSeqPath(this.innerData[n], seqPath);
}
return seqPath;
}
setInnerData() {
const sequence = this.data();
sequence.forEach(seqRegion => {
if (typeof seqRegion.label !== "undefined") {
if (seqRegion.label.length > 1) {
seqRegion.label.split("").forEach((s, i) => {
this.innerData[seqRegion.begin + i] = Object.assign(Object.assign({}, seqRegion), { begin: (seqRegion.begin + i), label: s });
});
}
else {
this.innerData[seqRegion.begin] = Object.assign(Object.assign({}, seqRegion), { label: seqRegion.label });
}
}
});
}
}
function addResToSeqPath(res, seqPath) {
if (seqPath.length > 0 && seqPath[seqPath.length - 1].label.length + seqPath[seqPath.length - 1].begin == res.begin) {
seqPath[seqPath.length - 1].label += res.label;
}
else {
seqPath.push({
begin: res.begin,
label: res.label
});
}
}