<div class="wrapper">
	<div class="controls">
		<div class="controls__group controls__group--radio">
			<div class="controls__rbtn">
				<input id="item__1" type="radio" name="cells"  value="item1" checked>
				<label for="item_1">Grid cell 1</label>
			</div>
			<div class="controls__rbtn">
				<input id="item__2" type="radio" name="cells" value="item2">
				<label for="item_2">Grid cell 2</label>
			</div>
			<div class="controls__rbtn">
				<input id="item__3" type="radio" name="cells" value="item3">
				<label for="item_3">Grid cell 3</label>
			</div>
		</div>
		<div class="controls__group">
			<label for="size">Size</label>
			<input id="size" type="range" min="1" max="6" value="1">
		</div>
		<div class="controls__group">
			<label for="posX">X Position</label>
			<input id="posX" type="range" min="1" max="6" value="1">
		</div>
		<div class="controls__group">
			<label for="posY">Y Position</label>
			<input id="posY" type="range" min="1" max="6" value="1">
		</div>
	</div>
	<div class="grid">
		<div class="grid__item" data-id="item1"></div>
		<div class="grid__item" data-id="item2"></div>
		<div class="grid__item" data-id="item3"></div>
	</div>
</div>
* {
	box-sizing: border-box;
}

:root {
	--gridSize: 6;
	--posX: 1;
	--posY: 1;
	--size: 1;
	--color: blue;
}

.wrapper {
	width: 1200px;
	margin: 50px auto;
	display: flex;
}

.controls {
	margin-right: 40px;
}

.controls__group {
	margin-bottom: 30px;
	
	> * {
		display: block;
	}
}

.controls__rbtn {
	margin-bottom: 10px;
}

.grid {
	display: grid;
	grid-template-columns: repeat(var(--gridSize), 1fr);
	grid-template-rows: repeat(var(--gridSize), 1fr);
	grid-gap: 5px;
	border: 1px solid grey;
	width: 800px;
	height: 800px;
}

.grid__item {
	background-color: var(--color);
	grid-column: var(--posX) / span var(--size);
	grid-row: var(--posY) / span var(--size);
	
	&:nth-child(2) {
		--color: red;
	}
	
	&:nth-child(3) {
		--color: yellow;
	}
}
View Compiled
const ctrlSize = document.querySelector('#size')
const ctrlposX = document.querySelector('#posX')
const ctrlposY = document.querySelector('#posY')
const rBtns = [...document.querySelectorAll(`input[type='radio']`)]
const gridItems = [...document.querySelectorAll('.grid__item')]
const inputs = [ctrlSize, ctrlposX, ctrlposY]

const gridSize = 6

let checked
let currItem
let size
let props

const getValues = (x) => {
	x.props = {
		size: parseInt(getComputedStyle(x).getPropertyValue('--size')),
		posX: parseInt(getComputedStyle(x).getPropertyValue('--posX')),
		posY: parseInt(getComputedStyle(x).getPropertyValue('--posY'))
	}
}

// Find currently selected item
const findCurrItem = () => {
	rBtns.forEach((el) => {
		if (el.checked) {
			currItem = document.querySelector(`[data-id=${el.value}]`)
		}
	})
	console.log(currItem)
}

// Set sliders to correct positions
rBtns.forEach((el, index) => {
	el.addEventListener('click', () => {
		findCurrItem() // find the currently selected item
		getValues(currItem) //get the current properties of the item
		let currItemProperties = Object.values(currItem.props) // create an array from props
		inputs.forEach((el, index) => {
			el.value = currItemProperties[index] // set the sliders to the corresponding values
		})
	})
})

ctrlSize.addEventListener('change', (e) => {
	findCurrItem()
	getValues(currItem)
	size = parseInt(e.target.value)
	let currPos = currItem.props.posX > currItem.props.posY ? currItem.props.posX : currItem.props.posY
	if (size < gridSize - (currPos - 1)) {
		size = size
	} else {
		size = gridSize - (currPos - 1)
	}
	currItem.style.setProperty('--size', size)
})

const calcNewProps = (el, str) => {
	let currSize = currItem.props.size
	console.log(currSize)
	if (posX < gridSize - (currSize - 1)) {
		posX = posX
	} else {
		posX = gridSize - (currSize - 1)
	}
	currItem.style.setProperty(str, el)
}

ctrlposX.addEventListener('change', (e) => {
	findCurrItem()
	getValues(currItem)
	posX = parseInt(e.target.value)
	calcNewProps(posX, '--posX')
})

ctrlposY.addEventListener('change', (e) => {
	findCurrItem()
	getValues(currItem)
	posY = parseInt(e.target.value)
	calcNewProps(posY, '--posY')
})


External CSS

This Pen doesn't use any external CSS resources.

External JavaScript

This Pen doesn't use any external JavaScript resources.