// Copyright 2015 the V8 project authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. "use strict"; class CodeView extends View { constructor(divID, PR, sourceText, sourcePosition, broker) { super(divID, broker, null, false); let view = this; view.PR = PR; view.mouseDown = false; view.broker = broker; view.allSpans = []; var selectionHandler = { clear: function() { broker.clear(selectionHandler); }, select: function(items, selected) { var handler = this; var broker = view.broker; for (let span of items) { if (selected) { span.classList.add("selected"); } else { span.classList.remove("selected"); } } var locations = []; for (var span of items) { locations.push({pos_start: span.start, pos_end: span.end}); } broker.clear(selectionHandler); broker.select(selectionHandler, locations, selected); }, selectionDifference: function(span1, inclusive1, span2, inclusive2) { var pos1 = span1.start; var pos2 = span2.start; var result = []; var lineListDiv = view.divNode.firstChild.firstChild.childNodes; for (var i = 0; i < lineListDiv.length; i++) { var currentLineElement = lineListDiv[i]; var spans = currentLineElement.childNodes; for (var j = 0; j < spans.length; ++j) { var currentSpan = spans[j]; if (currentSpan.start > pos1 || (inclusive1 && currentSpan.start == pos1)) { if (currentSpan.start < pos2 || (inclusive2 && currentSpan.start == pos2)) { result.push(currentSpan); } } } } return result; }, brokeredSelect: function(locations, selected) { let firstSelect = view.selection.isEmpty(); for (let location of locations) { let start = location.pos_start; let end = location.pos_end; if (start && end) { let lower = 0; let upper = view.allSpans.length; if (upper > 0) { while ((upper - lower) > 1) { var middle = Math.floor((upper + lower) / 2); var lineStart = view.allSpans[middle].start; if (lineStart < start) { lower = middle; } else if (lineStart > start) { upper = middle; } else { lower = middle; break; } } var currentSpan = view.allSpans[lower]; var currentLineElement = currentSpan.parentNode; if ((currentSpan.start <= start && start < currentSpan.end) || (currentSpan.start <= end && end < currentSpan.end)) { if (firstSelect) { makeContainerPosVisible( view.divNode, currentLineElement.offsetTop); firstSelect = false; } view.selection.select(currentSpan, selected); } } } } }, brokeredClear: function() { view.selection.clear(); }, }; view.selection = new Selection(selectionHandler); broker.addSelectionHandler(selectionHandler); view.handleSpanMouseDown = function(e) { e.stopPropagation(); if (!e.shiftKey) { view.selection.clear(); } view.selection.select(this, true); view.mouseDown = true; } view.handleSpanMouseMove = function(e) { if (view.mouseDown) { view.selection.extendTo(this); } } view.handleCodeMouseDown = function(e) { view.selection.clear(); } document.addEventListener('mouseup', function(e) { view.mouseDown = false; }, false); view.initializeCode(sourceText, sourcePosition); } initializeContent(data, rememberedSelection) { this.data = data; } initializeCode(sourceText, sourcePosition) { var view = this; if (sourceText == "") { var newHtml = "
";
view.divNode.innerHTML = newHtml;
} else {
var newHtml =
"" + sourceText + "
";
view.divNode.innerHTML = newHtml;
try {
// Wrap in try to work when offline.
view.PR.prettyPrint();
} catch (e) {
}
view.divNode.onmousedown = this.handleCodeMouseDown;
var base = sourcePosition;
var current = 0;
var lineListDiv = view.divNode.firstChild.firstChild.childNodes;
for (let i = 0; i < lineListDiv.length; i++) {
var currentLineElement = lineListDiv[i];
currentLineElement.id = "li" + i;
var pos = base + current;
currentLineElement.pos = pos;
var spans = currentLineElement.childNodes;
for (let j = 0; j < spans.length; ++j) {
var currentSpan = spans[j];
if (currentSpan.nodeType == 1) {
currentSpan.start = pos;
currentSpan.end = pos + currentSpan.textContent.length;
currentSpan.onmousedown = this.handleSpanMouseDown;
currentSpan.onmousemove = this.handleSpanMouseMove;
view.allSpans.push(currentSpan);
}
current += currentSpan.textContent.length;
pos = base + current;
}
while ((current < sourceText.length) &&
(sourceText[current] == '\n' || sourceText[current] == '\r')) {
++current;
}
}
}
view.resizeToParent();
}
deleteContent() {}
}