diff --git a/demo/index.html b/demo/index.html
index d4574aa3..9546b697 100644
--- a/demo/index.html
+++ b/demo/index.html
@@ -10,6 +10,7 @@
+
xterm.js: xterm, in the browser
diff --git a/gulpfile.js b/gulpfile.js
index 1f92e537..1dd49887 100644
--- a/gulpfile.js
+++ b/gulpfile.js
@@ -14,6 +14,7 @@ const ts = require('gulp-typescript');
let buildDir = process.env.BUILD_DIR || 'build';
let tsProject = ts.createProject('tsconfig.json');
+let tsProjectSearchAddon = ts.createProject('./src/addons/search/tsconfig.json');
let srcDir = tsProject.config.compilerOptions.rootDir;
let outDir = tsProject.config.compilerOptions.outDir;
@@ -30,13 +31,18 @@ gulp.task('tsc', function () {
let tsResult = tsProject.src().pipe(sourcemaps.init()).pipe(tsProject());
let tsc = tsResult.js.pipe(sourcemaps.write('.', {includeContent: false, sourceRoot: ''})).pipe(gulp.dest(outDir));
+ fs.emptyDirSync(`${outDir}/addons`);
+ fs.emptyDirSync(`${outDir}/addons/search`);
+ let tsResultSearchAddon = tsProjectSearchAddon.src().pipe(sourcemaps.init()).pipe(tsProjectSearchAddon());
+ let tscSearchAddon = tsResultSearchAddon.js.pipe(sourcemaps.write('.', {includeContent: false, sourceRoot: ''})).pipe(gulp.dest(`${outDir}/addons/search`));
+
// Copy all addons from ${srcDir}/ to ${outDir}/
- let copyAddons = gulp.src(`${srcDir}/addons/**/*`).pipe(gulp.dest(`${outDir}/addons`));
+ let copyAddons = gulp.src([`${srcDir}/addons/**/*`, `!${srcDir}/addons/search`, `!${srcDir}/addons/search/**`]).pipe(gulp.dest(`${outDir}/addons`));
// Copy stylesheets from ${srcDir}/ to ${outDir}/
let copyStylesheets = gulp.src(`${srcDir}/**/*.css`).pipe(gulp.dest(outDir));
- return merge(tsc, copyAddons, copyStylesheets);
+ return merge(tsc, tscSearchAddon, copyAddons, copyStylesheets);
});
/**
@@ -63,13 +69,28 @@ gulp.task('browserify', ['tsc'], function() {
.pipe(sourcemaps.write('./'))
.pipe(gulp.dest(buildDir));
+ let browserifyOptionsSearchAddon = {
+ basedir: buildDir,
+ debug: true,
+ entries: [`../${outDir}/addons/search/search.js`],
+ cache: {},
+ packageCache: {}
+ };
+ let bundleStreamSearchAddon = browserify(browserifyOptionsSearchAddon)
+ .bundle()
+ .pipe(source('./addons/search/search.js'))
+ .pipe(buffer())
+ .pipe(sourcemaps.init({loadMaps: true, sourceRoot: '..'}))
+ .pipe(sourcemaps.write('./'))
+ .pipe(gulp.dest(buildDir));
+
// Copy all add-ons from ${outDir}/ to buildDir
- let copyAddons = gulp.src(`${outDir}/addons/**/*`).pipe(gulp.dest(`${buildDir}/addons`));
+ let copyAddons = gulp.src([`${outDir}/addons/**/*`, `!${outDir}/addons/search`, `!${outDir}/addons/search/**`]).pipe(gulp.dest(`${buildDir}/addons`));
// Copy stylesheets from ${outDir}/ to ${buildDir}/
let copyStylesheets = gulp.src(`${outDir}/**/*.css`).pipe(gulp.dest(buildDir));
- return merge(bundleStream, copyAddons, copyStylesheets);
+ return merge(bundleStream, bundleStreamSearchAddon, copyAddons, copyStylesheets);
});
gulp.task('instrument-test', function () {
diff --git a/src/addons/search/search.ts b/src/addons/search/search.ts
new file mode 100644
index 00000000..b049eba7
--- /dev/null
+++ b/src/addons/search/search.ts
@@ -0,0 +1,56 @@
+/**
+ * @license MIT
+ */
+
+import { SearchHelper } from './SearchHelper';
+
+declare var exports: any;
+declare var module: any;
+declare var define: any;
+declare var require: any;
+
+(function (addon) {
+ if ('Terminal' in window) {
+ /*
+ * Plain browser environment
+ */
+ addon((window).Terminal);
+ } else if (typeof define == 'function') {
+ /*
+ * Require.js is available
+ */
+ define(['../../xterm'], addon);
+ } else if (typeof exports === 'object' && typeof module === 'object') {
+ /*
+ * CommonJS environment
+ */
+ var xterm = '../../xterm'; // Put in a variable do it's not pulled in by browserify
+ module.exports = addon(require(xterm));
+ }
+})((Terminal: any) => {
+ /**
+ * Find the next instance of the term, then scroll to and select it. If it
+ * doesn't exist, do nothing.
+ * @param term The term to search for.
+ * @return Whether a result was found.
+ */
+ Terminal.prototype.findNext = function(term: string): boolean {
+ if (!this._searchHelper) {
+ this.searchHelper = new SearchHelper(this, Terminal.translateBufferLineToString);
+ }
+ return (this.searchHelper).findNext(term);
+ };
+
+ /**
+ * Find the previous instance of the term, then scroll to and select it. If it
+ * doesn't exist, do nothing.
+ * @param term The term to search for.
+ * @return Whether a result was found.
+ */
+ Terminal.prototype.findPrevious = function(term: string): boolean {
+ if (!this._searchHelper) {
+ this.searchHelper = new SearchHelper(this, Terminal.translateBufferLineToString);
+ }
+ return (this.searchHelper).findPrevious(term);
+ };
+});
diff --git a/src/SearchHelper.ts b/src/addons/search/searchHelper.ts
similarity index 91%
rename from src/SearchHelper.ts
rename to src/addons/search/searchHelper.ts
index 300daef6..6f88e04b 100644
--- a/src/SearchHelper.ts
+++ b/src/addons/search/searchHelper.ts
@@ -2,8 +2,8 @@
* @license MIT
*/
-import { ITerminal } from './Interfaces';
-import { translateBufferLineToString } from './utils/BufferLine';
+// import { ITerminal } from '../../Interfaces';
+// import { translateBufferLineToString } from '../../utils/BufferLine';
interface ISearchResult {
term: string;
@@ -12,7 +12,7 @@ interface ISearchResult {
}
export class SearchHelper {
- constructor(private _terminal: ITerminal) {
+ constructor(private _terminal: any, private _translateBufferLineToString: any) {
// TODO: Search for multiple instances on 1 line
// TODO: Don't use the actual selection, instead use a "find selection" so multiple instances can be highlighted
// TODO: Highlight other instances in the viewport
@@ -103,7 +103,7 @@ export class SearchHelper {
private _findInLine(term: string, y: number): ISearchResult {
const bufferLine = this._terminal.lines.get(y);
- const lowerStringLine = translateBufferLineToString(bufferLine, true).toLowerCase();
+ const lowerStringLine = this._translateBufferLineToString(bufferLine, true).toLowerCase();
const lowerTerm = term.toLowerCase();
const searchIndex = lowerStringLine.indexOf(lowerTerm);
if (searchIndex >= 0) {
diff --git a/src/addons/search/tsconfig.json b/src/addons/search/tsconfig.json
new file mode 100644
index 00000000..f20bdf3d
--- /dev/null
+++ b/src/addons/search/tsconfig.json
@@ -0,0 +1,10 @@
+{
+ "compilerOptions": {
+ "module": "commonjs",
+ "target": "es5",
+ "rootDir": ".",
+ "outDir": "./c",
+ "sourceMap": true,
+ "removeComments": true
+ }
+}
diff --git a/src/xterm.js b/src/xterm.js
index b485069a..dc57cc21 100644
--- a/src/xterm.js
+++ b/src/xterm.js
@@ -21,12 +21,12 @@ import { Parser } from './Parser';
import { Renderer } from './Renderer';
import { Linkifier } from './Linkifier';
import { SelectionManager } from './SelectionManager';
-import { SearchHelper } from './SearchHelper';
import { CharMeasure } from './utils/CharMeasure';
import * as Browser from './utils/Browser';
import * as Mouse from './utils/Mouse';
import { CHARSETS } from './Charsets';
import { getRawByteCoords } from './utils/Mouse';
+import { translateBufferLineToString } from './utils/BufferLine';
/**
* Terminal Emulation References:
@@ -224,7 +224,6 @@ function Terminal(options) {
this.renderer = this.renderer || null;
this.selectionManager = this.selectionManager || null;
this.linkifier = this.linkifier || new Linkifier();
- this.searchHelper = this.searchHelper || null;
// user input states
this.writeBuffer = [];
@@ -708,7 +707,6 @@ Terminal.prototype.open = function(parent, focus) {
this.selectionManager.on('refresh', data => this.renderer.refreshSelection(data.start, data.end));
this.on('scroll', () => this.selectionManager.refresh());
this.viewportElement.addEventListener('scroll', () => this.selectionManager.refresh());
- this.searchHelper = new SearchHelper(this);;
// Setup loop that draws to screen
this.refresh(0, this.rows - 1);
@@ -1408,26 +1406,6 @@ Terminal.prototype.selectAll = function() {
this.selectionManager.selectAll();
}
-/**
- * Find the next instance of the term, then scroll to and select it. If it
- * doesn't exist, do nothing.
- * @param term The term to search for.
- * @return Whether a result was found.
- */
-Terminal.prototype.findNext = function(term) {
- return this.searchHelper.findNext(term);
-}
-
-/**
- * Find the previous instance of the term, then scroll to and select it. If it
- * doesn't exist, do nothing.
- * @param term The term to search for.
- * @return Whether a result was found.
- */
-Terminal.prototype.findPrevious = function(term) {
- return this.searchHelper.findPrevious(term);
-}
-
/**
* Handle a keydown event
* Key Resources:
@@ -2408,6 +2386,7 @@ function keys(obj) {
* Expose
*/
+Terminal.translateBufferLineToString = translateBufferLineToString;
Terminal.EventEmitter = EventEmitter;
Terminal.inherits = inherits;