Skip to content

Commit

Permalink
Stop doing a line-by-line splicing in applyDelta
Browse files Browse the repository at this point in the history
Also brings back the functionality where large deltas are split into
smaller deltas so that .splice.apply() calls will work.
  • Loading branch information
aldendaniels committed Jan 11, 2014
1 parent 3a048cd commit 08edcdf
Show file tree
Hide file tree
Showing 2 changed files with 31 additions and 6 deletions.
7 changes: 2 additions & 5 deletions lib/ace/apply_delta.js
Original file line number Diff line number Diff line change
Expand Up @@ -79,9 +79,9 @@ function validateDelta(lines, delta) {
// TODO:
// - Validate that the ending column offset matches the lines.
// - Validate the deleted lines match the lines in the document.
// - Vaiidate that an insert delta does not contain more than 65001 entries.
}


exports.applyDelta = function(lines, delta) {

// Validate delta.
Expand Down Expand Up @@ -114,10 +114,7 @@ exports.applyDelta = function(lines, delta) {

case 'insert':
splitLine(lines, delta.range.start);
for (var i = 0; i < delta.lines.length; i++) {
var row = delta.range.start.row + 1 + i;
lines.splice(row, 0, delta.lines[i]);
}
lines.splice.apply(lines, [delta.range.start.row + 1, 0].concat(delta.lines));
joinLineWithNext(lines, delta.range.start.row);
joinLineWithNext(lines, delta.range.end.row);
break;
Expand Down
30 changes: 29 additions & 1 deletion lib/ace/document.js
Original file line number Diff line number Diff line change
Expand Up @@ -568,8 +568,36 @@ var Document = function(textOrLines) {
* @param {Object} delta A delta object (can include 'insert' and 'remove' actions)
**/
this.applyDelta = function(delta) {

// Split large insert deltas. This is necessary because:
// 1. We need to support splicing delta lines into the document via $lines.splice.apply(...)
// 2. fn.apply() doesn't work for a large number of params. The mallest threshold is on safari 0xFFFF.
//
// To Do: Ideally we'd be consistent and also split 'delete' deltas. We don't do this now, because delete
// delta handling is too slow. If we make delete delta handling faster we can split all large deltas
// as shown in https://gist.github.com/aldendaniels/8367109#file-document-snippet-js
// If we do this, update validateDelta() to limit the number of lines in a delete delta.
var bIsInsert = delta.action == 'insert';
while (bIsInsert && delta.lines.length > 65001)
{
// Get split deltas.
var lines = delta.lines.splice(0, 65000);
lines.push('');
this.applyDelta({
action: delta.action,
lines: lines,
range: new Range(delta.range.start.row, delta.range.start.column,
delta.range.start.row + 65000, 0)
});

// Update remaining delta.
delta.range.start.row += 65000;
delta.range.start.column = 0;
}

// Apply.
applyDelta(this.$lines, delta);
this._emit("change", { data: delta });
this._emit("change", { data: delta });
};

/**
Expand Down

0 comments on commit 08edcdf

Please sign in to comment.