- Introduction
- Project Structure
- Key Features
- HTML Structure
- CSS Styling
- JavaScript Functionality
- Application Management
- Error Handling and Debugging
- Conclusion
This project aims to create an extensive fake operating system (OS) within a web browser. It includes features such as draggable and resizable application windows, a taskbar with a clock, and basic window management (minimize, maximize, and close). The purpose of this project is to simulate the look and feel of a real OS using web technologies like HTML, CSS, and JavaScript.
The project is organized into several folders and files:
project-root/
├── apps/
│ ├── terminal/
│ │ ├── index.html
│ │ ├── terminal.js
│ │ └── styles.css
│ └── file-explorer/
│ ├── index.html
│ ├── file-explorer.js
│ └── styles.css
├── scripts/
│ ├── taskbar.js
│ ├── windowManagement.js
│ └── appsConfig.js
├── styles/
│ └── main.css
└── index.html
- Draggable and Resizable Windows: Users can drag and resize application windows.
- Taskbar: Contains app icons and a clock.
- Dynamic Window Initialization: Windows are dynamically created and initialized.
- Focus Management: Clicking on a window brings it to the front.
The main index.html
file serves as the entry point for the fake OS:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Fake Operating System</title>
<link rel="stylesheet" href="styles/main.css">
</head>
<body>
<div id="taskbar"></div>
<script type="module" src="scripts/taskbar.js"></script>
</body>
</html>
The main CSS file styles the overall layout, taskbar, and basic window appearance:
body {
margin: 0;
font-family: Arial, sans-serif;
}
#taskbar {
position: fixed;
bottom: 0;
width: 100%;
background-color: #333;
color: #fff;
display: flex;
justify-content: space-between;
padding: 5px 10px;
}
/* ... additional styles ... */
The taskbar.js
file manages the taskbar and initializes application icons and the clock:
// taskbar.js
import { appsConfig } from './appsConfig.js';
import { initializeWindow, focusWindow } from './windowManagement.js';
document.addEventListener("DOMContentLoaded", function() {
const taskbar = document.getElementById('taskbar');
appsConfig.forEach(app => {
const button = document.createElement('button');
button.classList.add('taskbar-app');
button.id = `${app.id}-icon`;
button.innerHTML = `<img src="${app.icon}" alt="${app.name}">`;
button.addEventListener('click', () => toggleAppWindow(app));
taskbar.appendChild(button);
});
const clock = document.createElement('div');
clock.classList.add('taskbar-clock');
taskbar.appendChild(clock);
updateClock(clock);
setInterval(() => updateClock(clock), 1000);
});
/* ... additional functions ... */
The windowManagement.js
file includes functions to initialize, drag, resize, and focus windows:
// windowManagement.js
export function initializeWindow(appId, appName) {
const appWindow = document.createElement('div');
appWindow.id = `${appId}-window`;
appWindow.classList.add('window');
const titleBar = document.createElement('div');
titleBar.classList.add('window-titlebar');
titleBar.innerHTML = `
<span>${appName}</span>
<div class="window-controls">
<button class="minimize-btn" onclick="minimizeWindow('${appId}-window')">-</button>
<button class="close-btn" onclick="closeWindow('${appId}-window', '${appId}-icon')">x</button>
</div>
`;
appWindow.appendChild(titleBar);
document.body.appendChild(appWindow);
makeWindowDraggableAndResizable(appWindow);
centerWindow(appWindow);
focusWindow(appWindow);
}
export function makeWindowDraggableAndResizable(windowElement) {
let isDragging = false;
let isResizing = false;
let startX, startY, startWidth, startHeight;
const titleBar = windowElement.querySelector('.window-titlebar');
const resizeHandle = document.createElement('div');
resizeHandle.classList.add('resize-handle', 'resize-bottom-right');
windowElement.appendChild(resizeHandle);
titleBar.addEventListener('mousedown', startDrag);
windowElement.addEventListener('mousedown', () => focusWindow(windowElement));
resizeHandle.addEventListener('mousedown', startResize);
function startDrag(e) {
isDragging = true;
startX = e.clientX;
startY = e.clientY;
document.addEventListener('mousemove', drag);
document.addEventListener('mouseup', stopDrag);
}
function drag(e) {
if (!isDragging) return;
windowElement.style.left = `${windowElement.offsetLeft + e.clientX - startX}px`;
windowElement.style.top = `${windowElement.offsetTop + e.clientY - startY}px`;
startX = e.clientX;
startY = e.clientY;
}
function stopDrag() {
isDragging = false;
document.removeEventListener('mousemove', drag);
document.removeEventListener('mouseup', stopDrag);
}
function startResize(e) {
isResizing = true;
startX = e.clientX;
startY = e.clientY;
startWidth = windowElement.clientWidth;
startHeight = windowElement.clientHeight;
document.addEventListener('mousemove', resize);
document.addEventListener('mouseup', stopResize);
}
function resize(e) {
if (!isResizing) return;
windowElement.style.width = `${startWidth + e.clientX - startX}px`;
windowElement.style.height = `${startHeight + e.clientY - startY}px`;
}
function stopResize() {
isResizing = false;
document.removeEventListener('mousemove', resize);
document.removeEventListener('mouseup', stopResize);
}
}
export function centerWindow(windowElement) {
const rect = windowElement.getBoundingClientRect();
const winWidth = window.innerWidth;
const winHeight = window.innerHeight;
windowElement.style.left = `${(winWidth - rect.width) / 2}px`;
windowElement.style.top = `${(winHeight - rect.height) / 2}px`;
}
export function focusWindow(windowElement) {
windowElement.style.zIndex = ++zIndexCounter;
}
The taskbar.js
file also manages the taskbar clock and updates it every second:
function updateClock(clock) {
const now = new Date();
const time = now.toLocaleTimeString([], { hour: '2-digit', minute: '2-digit' });
const date = now.toLocaleDateString();
clock.innerHTML = `<time>${time}</time><date>${date}</date>`;
}
The appsConfig.js
file contains the configuration for different applications available in the fake OS:
// appsConfig.js
export const appsConfig = [
{
id: 'terminal',
name: 'Terminal',
icon: 'icons/terminal.png',
html: 'apps/terminal/index.html'
},
{
id: 'file-explorer',
name: 'File Explorer',
icon: 'icons/file-explorer.png',
html: 'apps/file-explorer/index.html'
}
];
When creating and managing dynamic content, errors can occur. Ensure to add proper error handling mechanisms:
// windowManagement.js
fetch(`apps/${appId}/index.html`)
.then(response => response.text())
.then(data => {
appWindow.innerHTML = data;
initializeWindow(appId, appName);
})
.catch(error => {
console.error(`Error loading HTML for ${appName}:`, error);
appWindow.innerHTML = `<p>Error loading ${appName}. Please try again later.</p>`;
});
This project demonstrates how to create a dynamic, web-based fake operating system with features such as draggable and resizable windows,