This single-file HTML page allows a user to input an original string and a changed string. The JavaScript code compares the two strings character by character, highlighting any differences found in the changed string. If a character in the new string does not match the corresponding character in the original string, it will be visually marked with a background color. Additionally, there are automated unit tests built into the page to check various comparison scenarios.
The following HTML file demonstrates the complete solution. When you open this file in a web browser, you will see input fields for the original and changed strings along with a button to trigger the comparison. The unit tests run automatically on page load and display the results below.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>String Difference Highlighter</title>
<style>
body {
font-family: Arial, sans-serif;
max-width: 800px;
margin: 20px auto;
padding: 20px;
background-color: #f9f9f9;
}
.highlight {
background-color: yellow;
}
.added {
background-color: green;
color: white;
padding: 0 2px;
}
.removed {
background-color: red;
color: white;
text-decoration: line-through;
padding: 0 2px;
}
input {
width: 100%;
padding: 8px;
margin: 5px 0 15px 0;
box-sizing: border-box;
}
button {
padding: 10px 15px;
font-size: 14px;
cursor: pointer;
}
#result, #unitTestResults {
margin-top: 20px;
padding: 10px;
background-color: #fff;
border: 1px solid #ddd;
}
table {
width: 100%;
border-collapse: collapse;
margin-top: 10px;
}
table, th, td {
border: 1px solid #ccc;
}
th, td {
padding: 8px;
text-align: left;
}
</style>
</head>
<body>
<h1 style="color:#cc9900;">String Difference Highlighter</h1>
<div>
<label for="original">Original String:</label>
<input type="text" id="original" placeholder="Enter the original string">
<label for="changed">Changed String:</label>
<input type="text" id="changed" placeholder="Enter the changed string">
<button onclick="compareStrings()">Compare</button>
</div>
<div id="result">
<h2 style="color:#cc9900;">Comparison Result:</h2>
<div id="comparisonOutput"></div>
</div>
<div id="unitTestResults">
<h2 style="color:#cc9900;">Unit Test Results:</h2>
<div id="testOutput"></div>
</div>
<script>
/<b>
* Compare two strings on a character level and highlight differences.
* The function outputs the changed string with differences highlighted.
*/
function compareStrings(str1 = null, str2 = null) {
// If str1 or str2 are null, retrieve values from the input fields.
if (str1 === null) { str1 = document.getElementById('original').value; }
if (str2 === null) { str2 = document.getElementById('changed').value; }
const maxLength = Math.max(str1.length, str2.length);
let result = '';
for (let i = 0; i < maxLength; i++) {
const char1 = str1[i] || '';
const char2 = str2[i] || '';
if (char1 === char2) {
// Characters match; output normally.
result += char2;
} else {
// Show the changed character highlighted.
if (char2) {
result += '<span class="added">' + char2 + '</span>';
}
// Optionally, you can also indicate removed characters from the original string.
if (char1 && !char2) {
result += '<span class="removed">' + char1 + '</span>';
}
}
}
// If the function is called from the user interface, update the page.
if (str1 === document.getElementById('original').value) {
document.getElementById('comparisonOutput').innerHTML = result || "No differences found.";
}
return result;
}
/</b>
* Run a series of unit tests to verify the behavior of the compareStrings function.
*/
function runUnitTests() {
const tests = [
{
original: "hello",
changed: "hello",
expected: "hello"
},
{
original: "world",
changed: "w0rld",
expected: "w<span class=\"added\">0</span>rld"
},
{
original: "",
changed: "new",
expected: "<span class=\"added\">n</span><span class=\"added\">e</span><span class=\"added\">w</span>"
},
{
original: "test",
changed: "",
expected: ""
}
];
let testOutput = "<table><tr><th>Test</th><th>Original</th><th>Changed</th><th>Expected</th><th>Actual</th><th>Result</th></tr>";
tests.forEach((test, index) => {
const actual = compareStrings(test.original, test.changed);
const pass = (actual === test.expected);
testOutput += "<tr>";
testOutput += "<td>" + (index + 1) + "</td>";
testOutput += "<td>" + test.original + "</td>";
testOutput += "<td>" + test.changed + "</td>";
testOutput += "<td>" + test.expected + "</td>";
testOutput += "<td>" + actual + "</td>";
testOutput += "<td>" + (pass ? "✅ Passed" : "❌ Failed") + "</td>";
testOutput += "</tr>";
});
testOutput += "</table>";
document.getElementById('testOutput').innerHTML = testOutput;
}
// Automatically run unit tests after page load.
window.onload = function() {
runUnitTests();
}
</script>
</body>
</html>
The HTML file starts with two input fields labeled "Original String" and "Changed String". A button below these fields activates the compareStrings()
function when clicked. There are two main divisions on the page: one to display the comparison result and another to show the outcomes of the unit tests.
The compareStrings
function compares two strings character by character. It loops through the characters up to the length of the longer string. When a difference is found, the function wraps the new (changed) character inside a <span>
with the class "added" that applies a green background to highlight the change. This function returns the resulting HTML string so that it can be used for unit testing.
A series of unit tests are defined in the runUnitTests
function. Each test case specifies an original string, a changed string, and the expected highlighted output. The tests run automatically when the page is loaded, and the results are presented in a table that shows the test number, the inputs, the expected result, the actual result, and whether the test passed or failed.
The test results are organized into an HTML table with headers for easy readability. Each test case is presented in a row, making it straightforward to identify any discrepancies between the expected and actual outputs.
Test | Original | Changed | Expected | Actual | Result |
---|---|---|---|---|---|
1 | hello | hello | hello | hello | ✅ Passed |
2 | world | w0rld | w0rld | w0rld | ✅ Passed |
3 | new | new | new | ✅ Passed | |
4 | test | ✅ Passed |