From 6579a99530984653103d9e07969e06542faf6e94 Mon Sep 17 00:00:00 2001 From: Julian Viereck Date: Sat, 23 Apr 2011 02:40:05 +0200 Subject: [PATCH] Code folding text rendering took off! --- demo/demo.js | 3 +- lib/ace/edit_session.js | 5 +++ lib/ace/layer/text.js | 75 +++++++++++++++++++++++++++++++++++---- lib/ace/theme/textmate.js | 6 ++++ 4 files changed, 82 insertions(+), 7 deletions(-) diff --git a/demo/demo.js b/demo/demo.js index 896518bf..eb227809 100644 --- a/demo/demo.js +++ b/demo/demo.js @@ -149,7 +149,8 @@ exports.launch = function(env) { // BEGING TESTING var Range = require("ace/range").Range; - docs.js.addFold(new Range(1, 10, 2, 999), "foo..."); + docs.js.addFold(new Range(1, 10, 2, 10), "foo..."); + docs.js.addFold(new Range(2, 20, 2, 25), "bar..."); window.s = docs.js; window.e = env.editor; setTimeout(function() { diff --git a/lib/ace/edit_session.js b/lib/ace/edit_session.js index 7a2d0dbc..926491c1 100644 --- a/lib/ace/edit_session.js +++ b/lib/ace/edit_session.js @@ -1397,6 +1397,7 @@ var EditSession = function(text, mode) { } var fold = new Fold(range, placeholder); + // TODO: The folds have to be ordered by range.start! foldData[startRow].push(fold); // Mark all lines folded by this fold as folded. @@ -1446,6 +1447,10 @@ var EditSession = function(text, mode) { return !fold || Array.isArray(fold); }; + this.getRowFoldData = function(docRow) { + return this.$foldData[docRow]; + } + }).call(EditSession.prototype); exports.EditSession = EditSession; diff --git a/lib/ace/layer/text.js b/lib/ace/layer/text.js index 68c350cc..a11966ae 100644 --- a/lib/ace/layer/text.js +++ b/lib/ace/layer/text.js @@ -416,13 +416,76 @@ var Text = function(parentEl) { }; this.$renderFoldLine = function(stringBuilder, row, tokens) { - // TODO: Build a fake tokens array! + var session = this.session, + folds = session.getRowFoldData(row); + + var renderTokens = []; + + function addTokens(tokens, from, to) { + var idx = 0, col = 0; + while ((col + tokens[idx].value.length) < from) { + col += tokens[idx].value.length + idx++ + + if (idx == tokens.length) { + return; + } + } + if (col != from) { + var value = tokens[idx].value.substring(from - col); + // Check if the token value is longer then the from...to spacing. + if (value.length > (to - from)) { + value = value.substring(0, to - from); + } + + renderTokens.push({ + type: tokens[idx].type, + value: value + }); + + col = from + value.length; + idx += 1 + } + + while (col < to) { + var value = tokens[idx].value; + if (value.length + col > to) { + value = value.substring(0, to - col); + } + renderTokens.push({ + type: tokens[idx].type, + value: value + }); + col += value.length; + idx += 1; + } + } + + var lastCol = 0; + for (var i = 0; i < folds.length; i++) { + var fold = folds[i]; + addTokens(tokens, lastCol, fold.start.column); + renderTokens.push({ + type: "fold", + value: fold.placeholder + }); + + if (fold.start.row != fold.end.row) { + row = fold.end.row; + tokens = this.tokenizer.getTokens(row, row)[0].tokens; + folds = session.getRowFoldData(row); + i = -1; + } + + lastCol = fold.end.column; + } + // Add the rest of the line + addTokens(tokens, lastCol, session.getLine(row).length); + // TODO: Build a fake splits array! - var splits - var tokens; - var lastRow; - this.$renderLineCore(stringBuilder, lastRow, tokens, splits); - } + var splits = false; + this.$renderLineCore(stringBuilder, row, renderTokens, splits); + }; }).call(Text.prototype); diff --git a/lib/ace/theme/textmate.js b/lib/ace/theme/textmate.js index 337a8c57..15f37177 100644 --- a/lib/ace/theme/textmate.js +++ b/lib/ace/theme/textmate.js @@ -106,6 +106,12 @@ define(function(require, exports, module) { color: white;\ }\ \ +.ace-tm .ace_line .ace_fold {\ + background-color: #E4E4E4;\ + border: 1px solid rgba(0, 0, 0, 0.3);\ + border-radius: 5px;\ +}\ +\ .ace-tm .ace_line .ace_support.ace_function {\ color: rgb(60, 76, 114);\ }\