I am trying to make a FloodFill function JavaScript this is my html code:
html:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/[email protected]/font/bootstrap-icons.min.css">
<link rel="stylesheet" href="style.css">
</head>
<body>
<div id="container">
<div class="container">
<div class="main-container">
<div class="left">
<div class="tools">
<div class="brush tool" >
<i class="bi bi-brush-fill"></i>
</div>
<div class="fill tool">
<i class="bi bi-paint-bucket"></i>
</div>
</div>
<div class="rangeSlide">
<p><span id="selectedIndex"></span> px</p>
<input type="range" id="indexRange" min="0" step="1" value="1">
</div>
</div>
<div class="pixel-grid"></div>
<div class="right" id="colorPalette">
<!-- <div class="color selected" style="background-color: rgb(0, 0, 0);"></div> -->
</div>
</div>
</div>
</div>
<script src="script.js"></script>
</body>
</html>
css:
*{
margin: 0;;
}
.container {
display: flex;
align-items: center;
justify-content: center;
height: 100vh;
background-color: rgb(211,211,211);
}
.main-container{
display: flex;
box-shadow: 0px 0px 20px rgba(0, 0, 0, 0.2);
border-radius: 20px;
}
/*---------------------Left--------------------*/
.left{
background-color: rgb(237,237,237);
display: flex;
flex-direction: column;
justify-content: space-between;
align-items: center;
border-radius: 20px 0 0 20px;
width: 50px;
}
.tools{
/* background-color: rgb(0, 255, 42); */
border-bottom: 1px solid black;
height: 100%;
}
.rangeSlide{
/* background-color: #ff00ff; */
height: 100%;
}
#indexRange {
transform: rotate(270deg);
}
.rangeSlide{
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
width: 50px;
}
.rangeSlide p{
position: relative;
top: -70px;
}
/*---------------------Left--------------------*/
/*---------------------Right--------------------*/
.right{
background-color: rgb(237,237,237);
/* padding: 10px; */
border-radius: 0 20px 20px 0;
display: flex;
flex-direction: column;
justify-content: space-around;
align-items: center;
width: 50px;
}
.color{
border: 1.5px solid rgba(0,0,0,0.2);
border-radius: 50%;
height: 1.4rem;
width: 1.4rem;
cursor: pointer;
/* box-sizing: border-box; */
}
/*---------------------Right--------------------*/
/*---------------------Tools--------------------*/
.tools {
display: flex;
flex-direction: column;
}
.tool {
margin-top: 0.6rem;
border: 1px solid #cccccc;
border-radius: 50%;
height: 1.7rem;
width: 1.7rem;
display: flex;
align-items: center;
justify-content: center;
cursor: pointer;
}
.tool.selected {
border-color: rgba(0, 0, 0, 0.45);
background-color: rgba(0, 0, 0, 0.1);
}
/*---------------------Tools--------------------*/
.pixel-grid {
display: grid;
/* grid-template-columns: repeat(8, 1fr);
grid-template-rows: repeat(8, 1fr); */
background-color: white;
padding: 5px;
width: 400px;
height: 400px;
}
.grid-item {
/* background-color: white; */
border: 1px solid rgba(204, 204, 204, 0.3);
}
javascript:
// Function to check if two colors are the same
function colorsAreSame(color1, color2) {
return color1 === color2;
}
document.addEventListener('DOMContentLoaded', function () {
console.log('Script loaded and DOM content loaded.');
const myRange = {'0': 4, '1': 8, '2': 16, '3': 32, '4': 64};
let selectedColor = 'rgb(0, 0, 0)';
let isBrushSelected = false;
let isDrawing = false;
let isFillSelected = false;
// Color array
const colorPalet = [
'rgb(0, 0, 0)',
'rgb(255, 0, 0)',
'rgb(9, 255, 0)',
'rgb(0, 174, 255)',
'rgb(255, 0, 255)',
'rgb(238, 255, 0)',
'rgb(255, 123, 0)',
'rgb(255, 255, 255)'
];
// Get the colorPalette container
const colorPaletteContainer = document.getElementById('colorPalette');
colorPalet.forEach(color => {
const colorDiv = document.createElement('div');
colorDiv.className = 'color';
colorDiv.style.backgroundColor = color;
colorDiv.addEventListener('click', function () {
selectedColor = color;
setSelectedTool(this);
});
colorPaletteContainer.appendChild(colorDiv);
});
const indexRangeInput = document.getElementById('indexRange');
const selectedIndexSpan = document.getElementById('selectedIndex');
const pixelGridContainer = document.querySelector('.pixel-grid');
const numberOfItems = Object.keys(myRange).length;
const rangeMax = parseInt(numberOfItems) - 1;
indexRangeInput.setAttribute('max', rangeMax.toString());
const selectedValue = myRange[indexRangeInput.value];
selectedIndexSpan.textContent = selectedValue;
createGrid(selectedValue);
indexRangeInput.addEventListener('input', function () {
const selectedIndex = parseInt(indexRangeInput.value);
const selectedValue = myRange[selectedIndex];
selectedIndexSpan.textContent = selectedValue;
console.log(`Selected Value: ${selectedValue}`);
createGrid(selectedValue);
});
// Create the grid
function createGrid(value) {
const rows = value;
const columns = value;
pixelGridContainer.innerHTML = '';
for (let i = 0; i < rows; i++) {
for (let j = 0; j < columns; j++) {
const gridItem = document.createElement('div');
gridItem.className = 'grid-item';
gridItem.style.backgroundColor = 'white';
pixelGridContainer.appendChild(gridItem);
}
}
// Set the grid layout styles after creating all the grid items
pixelGridContainer.style.gridTemplateColumns = `repeat(${columns}, 1fr)`;
pixelGridContainer.style.gridTemplateRows = `repeat(${rows}, 1fr)`;
}
// Tool selection
const tools = document.querySelectorAll('.tool');
tools.forEach(tool => {
tool.addEventListener('click', function () {
isBrushSelected = this.classList.contains('brush');
isFillSelected = this.classList.contains('fill');
setSelectedTool(this);
});
});
function setSelectedTool(selectedTool) {
tools.forEach(tool => {
if (selectedTool.closest('.left')){
tool.classList.remove('selected');
tool.style.borderColor = 'rgba(0, 0, 0, 0.3)';
tool.style.backgroundColor = 'rgba(0, 0, 0, 0)';
}
});
if (selectedTool.closest('.left')){
selectedTool.classList.add('selected');
selectedTool.style.borderColor = 'rgba(0, 0, 0, 0.45)';
selectedTool.style.backgroundColor = 'rgba(0, 0, 0, 0.1)';
}
}
// Trigger a click event on the brush tool to select it by default
const brushTool = document.querySelector('.brush');
brushTool.click();
//color picker
const colors = document.querySelectorAll('.color');
colors.forEach(color => {
color.addEventListener('click', function () {
selectedColor = this.style.backgroundColor;
setSelectedTool(this); // Ensure the brush is selected when choosing a color
});
});
//coloring
pixelGridContainer.addEventListener('mousedown', function (event) {
if (isBrushSelected || isFillSelected) {
isDrawing = true;
if (isBrushSelected) {
draw(event.target);
} else if (isFillSelected) {
floodFill(event.target);
}
}
});
pixelGridContainer.addEventListener('mousemove', function (event) {
// if (isDrawing && isBrushSelected) {
// draw(event.target);
// }
if (isDrawing && (isBrushSelected || isFillSelected)) {
if (isBrushSelected) {
draw(event.target);
} else if (isFillSelected) {
floodFill(event.target);
}
}
});
pixelGridContainer.addEventListener('mouseup', function () {
isDrawing = false;
});
// Draw function
function draw(target) {
if (target.classList.contains('grid-item') && isBrushSelected) {
target.style.backgroundColor = selectedColor;
}
}
// Flood Fill function
//Double click del
pixelGridContainer.addEventListener('dblclick', function (event) {
if (isBrushSelected) {
if (event.target.classList.contains('grid-item')) {
event.target.style.backgroundColor = '';
}
}
});
});
I am trying to make a FloodFill function for a pixel grid canvas i tried multiple ways and still cant figure it out does anyone know how make this function and explain how its done? I tried to check the surrounding grid item and check there element.style since the style is done inline but still nothing works with me. I even tried dfs and bfs.