-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathalgorithm.js
More file actions
155 lines (128 loc) · 4.41 KB
/
algorithm.js
File metadata and controls
155 lines (128 loc) · 4.41 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
/**
* Boundary Fill Algorithm Visualizer
* Simulates the 4-connected seed fill logic.
*/
let isPickerEnabled = false;
let startX = -1;
let startY = -1;
let grid = [];
let maxRows = 0;
let maxCols = 0;
let isDrawing = false;
function resetAll() {
const table = document.getElementById("grid");
table.innerHTML = "";
grid = [];
startX = -1;
startY = -1;
isPickerEnabled = false;
document.getElementById("status").innerHTML = "No";
document.getElementById("select").classList.remove("active");
}
function generateGrid() {
const rows = parseInt(document.getElementById("rows").value);
const cols = parseInt(document.getElementById("cols").value);
if (isNaN(rows) || isNaN(cols) || rows < 1 || cols < 1) {
alert("Please enter valid dimensions");
return;
}
resetAll();
maxRows = rows;
maxCols = cols;
drawGrid(rows, cols);
}
function togglePicker() {
isPickerEnabled = !isPickerEnabled;
const btn = document.getElementById("select");
const status = document.getElementById("status");
if (isPickerEnabled) {
btn.classList.add("active");
status.innerHTML = "Waiting for click...";
} else {
btn.classList.remove("active");
status.innerHTML = startX !== -1 ? "Yes" : "No";
}
}
async function startFill() {
if (startX === -1 || startY === -1) {
alert("Please select a seed point first!");
return;
}
// Disable controls during animation
document.getElementById("fill").disabled = true;
document.getElementById("submit").disabled = true;
await boundaryFill(startX, startY);
document.getElementById("fill").disabled = false;
document.getElementById("submit").disabled = false;
}
/**
* Recursive Boundary Fill Algorithm with animation delay
*/
async function boundaryFill(x, y) {
if (x < 0 || x >= maxCols || y < 0 || y >= maxRows) return;
const cell = grid[y][x];
// Check if cell is already filled or is a boundary
if (cell.classList.contains("filling") || cell.classList.contains("boundary")) {
return;
}
// Fill the pixel
cell.classList.add("filling");
cell.classList.add("pixel-fill");
// Add a small delay for visualization effect
await new Promise(resolve => setTimeout(resolve, 50));
// Recurse to neighbors (4-connected)
await boundaryFill(x + 1, y);
await boundaryFill(x - 1, y);
await boundaryFill(x, y + 1);
await boundaryFill(x, y - 1);
}
function drawGrid(rows, cols) {
const table = document.getElementById("grid");
for (let i = 0; i < rows; i++) {
grid[i] = [];
const row = table.insertRow(i);
for (let j = 0; j < cols; j++) {
const cell = row.insertCell(j);
grid[i][j] = cell;
// Handle drawing boundaries
cell.addEventListener("mousedown", () => {
if (!isPickerEnabled) {
isDrawing = true;
toggleBoundary(cell);
}
});
cell.addEventListener("mouseenter", () => {
if (isDrawing && !isPickerEnabled) {
toggleBoundary(cell);
}
});
// Handle seed selection
cell.addEventListener("click", () => {
if (isPickerEnabled) {
// Clear previous start point
if (startX !== -1) {
grid[startY][startX].classList.remove("start-point");
}
startX = j;
startY = i;
cell.classList.add("start-point");
cell.classList.remove("boundary"); // Start point can't be a boundary
isPickerEnabled = false;
document.getElementById("select").classList.remove("active");
document.getElementById("status").innerHTML = "Yes (" + x + "," + y + ")";
document.getElementById("status").innerHTML = `Yes (${j}, ${i})`;
}
});
}
}
}
function toggleBoundary(cell) {
if (!cell.classList.contains("filling") && !cell.classList.contains("start-point")) {
cell.classList.toggle("boundary");
}
}
window.addEventListener("mouseup", () => {
isDrawing = false;
});
// Initialize default grid
window.onload = generateGrid;