JavaScript Drawing Application Source Code

How To Create a Drawing Application in JavaScript, HTML and CSS

How To Create a Drawing Application in JavaScript, HTML and CSS


In this JavaScript Tutorial, we will see how to create a Drawing application using  JavaScript, HTML5, CSS3.
In this project tutorial we will build a painting project with multiple drawing tools, shapes, colors, and even undo/redo functionality. 

What We Are Gonna Use In This Project:

- JavaScript Programming Language.
- HTML and CSS.
- Font-awesome.
- Visual Studio Editor.






Project Source Code:



     - Canvas History Recorder

Captures the current canvas state as a data URL and stores it in the undo stack for later restoration.


// Save the current drawing to history so we can undo later
function saveState() {
// Convert canvas to a data URL (like a photo of the drawing)
undoStack.push(canvas.toDataURL());
// Clear redo history when new drawing happens
// (can't redo after drawing something new)
redoStack = [];
}



     - Canvas State Restorer
    
Takes a saved canvas state and redraws it on the canvas, clearing any existing content first.

// Put a saved drawing back on the canvas (for undo/redo)
function restoreState(state) {
// Create a new image from the saved data
const img = new Image();
img.src = state;
// When image loads, draw it on the canvas
img.onload = () => {
// Clear canvas first
ctx.clearRect(0, 0, canvas.width, canvas.height);
// Draw the saved state
ctx.drawImage(img, 0, 0);
};
}




     - Drawing Session Initiator

Activates drawing mode when mouse is pressed down and captures the starting coordinates for the drawing operation.


// Start drawing when mouse button is pressed down
function startDrawing(e) {
isDrawing = true;
// Get mouse position and remember it
[lastX, lastY] = [e.offsetX, e.offsetY];

// For shapes, take a snapshot of current canvas
// This helps us show a preview while dragging
if (currentShape !== 'freehand') {
snapshot = ctx.getImageData(0, 0, canvas.width, canvas.height);
}
}



     - Main Drawing Function

Handles all drawing operations based on current tool and shape settings, managing different drawing modes like freehand, lines, rectangles, and circles.


// Do the actual drawing as mouse moves
function draw(e) {
// Don't do anything if we're not in drawing mode
if (!isDrawing) return;

// Get current mouse position
const x = e.offsetX;
const y = e.offsetY;

// Set color based on current tool
// If using eraser, use background color (to "erase")
// Otherwise use the selected drawing color
ctx.strokeStyle = currentTool === 'eraser' ? bgColor : currentColor;
ctx.fillStyle = currentTool === 'eraser' ? bgColor : currentColor;

// Set line thickness and style based on selected tool
if (currentTool === 'brush') {
// Brush is thicker than pencil
ctx.lineWidth = brushSize.value * 2;
ctx.lineCap = 'round'; // Round end caps for smooth lines
ctx.lineJoin = 'round'; // Round corners for smooth lines
} else if (currentTool === 'pencil' || currentTool === 'eraser') {
ctx.lineWidth = brushSize.value;
ctx.lineCap = 'round';
ctx.lineJoin = 'round';
}

// Do different drawing based on selected shape
switch (currentShape) {
case 'freehand':
// Free drawing - follow the mouse movement exactly
ctx.beginPath(); // Start a new line
ctx.moveTo(lastX, lastY); // Move to where we started
ctx.lineTo(x, y); // Draw to current position
ctx.stroke(); // Actually draw the line
[lastX, lastY] = [x, y]; // Update position for next move
break;

case 'line':
// Straight line - from start point to current mouse position
ctx.putImageData(snapshot, 0, 0); // Restore canvas to before drag
ctx.beginPath(); // Start a new line
ctx.moveTo(lastX, lastY); // Move to start position
ctx.lineTo(x, y); // Draw to current position
ctx.stroke(); // Actually draw the line
break;

case 'rectangle':
// Rectangle - from start point with width/height to mouse
ctx.putImageData(snapshot, 0, 0); // Restore canvas to before drag
const width = x - lastX; // Calculate width based on mouse
const height = y - lastY; // Calculate height based on mouse

// Fill the rectangle if fill option is on
if (fillShape) {
ctx.fillRect(lastX, lastY, width, height);
}

// Always draw the outline
ctx.strokeRect(lastX, lastY, width, height);
break;

case 'circle':
// Circle - center at start point, size to mouse position
ctx.putImageData(snapshot, 0, 0); // Restore canvas to before drag

// Calculate radius (distance from center to mouse)
const radius = Math.sqrt(Math.pow(x - lastX, 2) + Math.pow(y - lastY, 2));

ctx.beginPath(); // Start a new shape
ctx.arc(lastX, lastY, radius, 0, 2 * Math.PI); // Draw full circle

// Fill the circle if fill option is on
if (fillShape) { ctx.fill(); }

// Always draw the outline
ctx.stroke();
break;

}

}




     - Drawing Session Finalizer

Deactivates drawing mode when mouse is released and saves the current state to the undo history.


// Stop drawing when mouse button is released
function stopDrawing() {
if (isDrawing) {
isDrawing = false;
// Save to history when finished drawing
// (so we can undo if needed)
saveState();
}
}



     - Previous State Restorer

Moves backward through the drawing history by one step, allowing users to reverse their last action.


// Go back one step in drawing history
function undo() {
// Need at least 2 items in stack (original blank + at least one drawing)
if (undoStack.length > 1) {
// Move current drawing to redo stack
redoStack.push(undoStack.pop());
// Show the previous drawing
restoreState(undoStack[undoStack.length - 1]);
}
}




     - Forward State Restorer

Moves forward through the drawing history by one step, allowing users to restore previously undone actions.


// Go forward one step in drawing history
function redo() {
if (redoStack.length > 0) {
// Get the most recent redo state
const stateToRedo = redoStack.pop();
// Add it back to the undo history
undoStack.push(stateToRedo);
// Show this drawing
restoreState(stateToRedo);
}
}



     - Background Color Updater

Updates the canvas background color using the selected color from the color picker and refreshes the display.


// Change the canvas background color
function changeBackgroundColor() {
// Get color from the color picker
const newColor = customColorPicker.value;
bgColor = newColor;
// Apply by clearing canvas with new background color
clearCanvas();
}



     - Canvas Content Eraser

Completely clears the canvas and fills it with the current background color, then saves this blank state.


// Clear everything from the canvas
function clearCanvas() {
// Fill entire canvas with background color
ctx.fillStyle = bgColor;
ctx.fillRect(0, 0, canvas.width, canvas.height);
// Save this blank state to history
saveState();
}



     - Active Tool Selector

Updates the current tool setting and provides visual feedback by highlighting the selected tool button.


// Highlight the active tool button
function setActiveTool(toolName) {
currentTool = toolName;
// Remove highlight from all buttons first
document.querySelectorAll('.toolbar button').
forEach(btn => btn.classList.remove('active'));
// Add highlight to selected tool button
document.getElementById(`${toolName}Btn`).classList.add('active');
}



     - Drawing Export Handler

Converts the current canvas content to a PNG image and triggers a download for the user.


// Save drawing as a PNG image file
function saveCanvas() {
// Create a download link
const link = document.createElement('a');
link.download = 'drawing.png'; // File name
// Get the canvas data as an image URL
link.href = canvas.toDataURL();
// Trigger the download
link.click();
}











JavaScript Drawing Application Source Code - 1

JavaScript Drawing Application Source Code - 2

JavaScript Drawing Application Source Code - 3

JavaScript Drawing Application Source Code - 4

JavaScript Drawing Application Source Code - 5

JavaScript Drawing Application Source Code - 6

JavaScript Drawing Application Source Code - 7


if you want the source code click on the download button below




disclaimer: you will get the source code with the database script and to make it work in your machine is your responsibility and to debug any error/exception is your responsibility this project is for the students who want to see an example and read the code not to get and run.






Aucun commentaire:

Enregistrer un commentaire