Introduction
I recently had the need for a DOS-like console I could put in a browser and manipulate with JavaScript. Specifically, I needed a "window" with a fixed number of rows and columns, that could have text printed to it. The text would wrap at the end of each line, and when the bottom of the screen was reached, all the text would scroll up by one line.
Finally, I needed it to be able to ask for and print user input, allow printing at a specified row and column, and allow the screen to be cleared. Basically, I needed to replicate the shell of a Commodore 64. This article provides the JavaScript source code, and a sample use of the console on a Web page.
Demo
Click here to see the console in action.
Using the Code
The first step is to declare an HTML control hold the console:
<div id="console"></div>
Some style would be good, though. For starters, a fixed-width font is highly desirable, and floating left means the width of the control is only as wide as it needs to be. The following code sets up the console div
to look like the DOS prompt:
<div id="console" style="font-family: Courier;
background-color: Black; color: White;
display:block; float:left;"></div>
The next step is to create a Console
object in your JavaScript, specifying the number of rows and columns you want:
var console = new Console('console' ,
5 , 10 );
Now you can print text and lines to it:
console.println("Hello world");
console.print("Why does Batman drive the batmobile? ");
console.print("Because it's his car.");
This will give the following output:
Now if we print a little bit more, the first line will disappear from the top:
And we can get some input from the user:
console.cls();
var userName = console.input('What is your name?');
console.println('Hello ' + userName);
Here is No Why
It must be said that the circumstances I found myself in which required such a script were peculiar indeed, and I can't help but wonder if anyone else will be able to find a problem for such a solution. Nevertheless, a couple of issues which may be helpful for different types of scripts were solved.
Solving the Blocked window.prompt in Internet Explorer 7
window.print
is a JavaScript method which asks for user input, and the JavaScript blocks until the user responds (i.e. it is a modal prompt). Incredibly, Microsoft destroyed this feature with Internet Explorer 7, breaking millions of scripts (unless it is enabled in the preferences, somewhere). Numerous fixes have been suggested, normally using a DHTML popup, and having a function callback specified for when the user enters something.
However, I really needed the script to block until the user had typed something in. Luckily, Microsoft had introduced a piece of non-standard functionality that opens a modal window. You must supply it with a URL to a Web page that you want to display in the window. This page contains an input textbox and button, which when clicked sends the inputted-text back to the opening window. Because we can assume that only Internet Explorer is willing to disable window.prompt
, we can safely assume that the following function will get the user's input on most people's browsers:
function getInput(message) {
if (window.showModalDialog) {
return window.showModalDialog("PromptWindow.htm", message,
"dialogWidth:300px;dialogHeight:200px");
} else {
return prompt(message);
}
}
In Firefox, and other non-Internet Explorer browsers, you will see a standard JavaScript prompt:
In Internet Explorer, you will get the custom window:
If you need to use the Console.input
method, then you also need to pass the URL to the prompt window in the constructor:
var console = new Console('console',
10, 30, 'PromptWindow.htm');
In either case, the next line of the JavaScript will not execute until the user has provided a response.
Adding Text to a pre Tag from JavaScript
The console relies on the pre
-style whitespace handling, so that multiple spaces are printed rather than being trimmed, as with usual HTML. The first point to note is that if you have a <pre>
tag, or as is the case with the console, the element.style.whiteSpace
property set to pre
, and you assign element.innerHTML
to be ' ', for example, then this may get trimmed down to one space, depending on the browser. In this case you must use document.createTextNode(' ')
, and append that to the element. In the case of the console, one TextNode
is referenced for each row, and the data property of each TextNode
is accessed to manipulate the text in the console.
The next problem is with new-lines. In theory, you shouldn't need <br>
tags in a <pre>
tag. However, when assigning text dynamically, this becomes a problem. If you append \n
to the text, Firefox adds a line break, but Internet Explorer doesn't. If you append \r\n
, Internet Explorer adds a new-line, and FireFox adds two. That's where I gave up, and simply appended document.createElement('br')
to the <pre>
tag, which works on all browsers.
Compatibility and Future Enhancements
I have tested the console on Windows using Internet Explorer 6, Internet Explorer 7, Firefox 2, Opera 9, and Safari 3. In the future, the ability to specify font and background color may be added. That's it.
History
- 15th March, 2008: Initial post