I’m trying to create a words of wonder type game using PixiJS. I’m sharing my code below it’s still in development however I can’t seem to figure out how to make it so users can select and drag letters to find words. Right now it only detects the start and the end of the drag and get’s nothing in between. How can I fix this? Thanks!
<code>window.onload = () => {
const container = document.getElementById('canvas-container');
const app = new PIXI.Application({
width: container.clientWidth * 2,
height: container.clientHeight * 2,
backgroundColor: 0x1099bb,
});
container.appendChild(app.view);
const background = PIXI.Sprite.from('https://cdn.glitch.global/b457296f-514e-47e5-82c6-28bdeeda16ca/background.png?v=1716472339788');
background.width = app.screen.width;
background.height = app.screen.height;
app.stage.addChild(background);
const gridContent = [
[null, null, null, null],
[null, '', null, ''],
[null, null, null, ''],
];
const gridSize = app.screen.width / 5.3;
const gridPadding = gridSize / 10;
const letters = ['L', 'G', 'O', 'D'];
const angleIncrement = (Math.PI * 2) / letters.length;
const circleCenterX = app.screen.width / 2;
const circleCenterY = app.screen.height - app.screen.width / 3 - 170;
const circleRadius = app.screen.width / 3.3;
const letterRadius = circleRadius / 4.2;
const letterColors = ['#ff9933', '#ff9933', '#ff9933', '#ff9933'];
const numRows = gridContent.length;
const numCols = gridContent[0].length;
const gridStartX = (app.screen.width - (numCols * (gridSize + gridPadding))) / 2;
const gridGapY = 120;
const gridStartY = gridGapY;
// Define an array to keep track of selected letters
let selectedLettersArray = [];
function handleLetterDragging(letter) {
console.log('Dragging:', letter);
// Check if the letter has not been selected already
if (!selectedLettersArray.includes(letter)) {
selectedLettersArray.push(letter);
console.log('Selected letters array:', selectedLettersArray);
checkForValidWord();
}
}
function checkForValidWord() {
const selectedLetters = selectedLettersArray.join('');
console.log('Checking for valid word:', selectedLetters);
const foundAnswer = correctAnswers.find(answer => selectedLetters.endsWith(answer));
if (foundAnswer) {
console.log('Found valid word:', foundAnswer);
fillGrid(foundAnswer, selectedLetters.length - foundAnswer.length);
// Reset selected letters array after finding a valid word
selectedLettersArray = [];
}
}
function drawLetterWheel() {
const shuffleButtonUrl = 'images/shuffle.png';
const shuffleButtonSize = 65;
const circle = new PIXI.Graphics();
circle.beginFill(0xfff7e6, 0.7);
circle.drawCircle(circleCenterX, circleCenterY, circleRadius);
circle.endFill();
app.stage.addChild(circle);
letters.forEach((letter, index) => {
const angle = index * angleIncrement;
const letterShiftFactor = 0.8;
const x = circleCenterX + Math.cos(angle) * (circleRadius - letterRadius) * letterShiftFactor;
const y = circleCenterY + Math.sin(angle) * (circleRadius - letterRadius) * letterShiftFactor;
const letterText = new PIXI.Text(letter, {
fontSize: letterRadius * 2,
fill: letterColors[index],
fontFamily: ['Poetsen One', 'Roboto', 'sans-serif']
});
letterText.anchor.set(0.5);
letterText.position.set(x, y);
app.stage.addChild(letterText);
// Enable dragging for each letter
letterText.interactive = true;
letterText.buttonMode = true;
letterText
.on('pointerdown', onDragStart)
.on('pointerup', onDragEnd)
.on('pointerupoutside', onDragEnd);
function onDragStart() {
console.log('Drag start:', letter);
handleLetterDragging(letter);
letterText.interactive = false; // Disable interactivity after selection
}
function onDragEnd() {
console.log('Drag end:', letter);
letterText.interactive = true; // Re-enable interactivity after dragging
}
});
const shuffleButton = PIXI.Sprite.from(shuffleButtonUrl);
shuffleButton.anchor.set(0.5);
shuffleButton.width = shuffleButton.height = shuffleButtonSize;
shuffleButton.position.set(circleCenterX, circleCenterY);
shuffleButton.interactive = true;
shuffleButton.buttonMode = true;
shuffleButton.on('pointerdown', () => {
shuffleLetters();
});
app.stage.addChild(shuffleButton);
}
const correctAnswers = ['GOLD', 'DOG', 'GOD', 'LOG']; // Define correct answers here
function drawGrid() {
for (let row = 0; row < numRows; row++) {
for (let col = 0; col < numCols; col++) {
if (gridContent[row][col] === null) {
const cell = new PIXI.Graphics();
cell.beginFill(0xfff7e6);
cell.drawRoundedRect(0, 0, gridSize, gridSize, 20);
cell.endFill();
cell.position.set(gridStartX + col * (gridSize + gridPadding), gridStartY + row * (gridSize + gridPadding));
app.stage.addChild(cell);
}
}
}
}
function fillGrid(answer, startIndex) {
for (let i = 0; i < answer.length; i++) {
const row = Math.floor(startIndex / 4);
const col = startIndex % 4;
const cell = app.stage.children.find(child => child instanceof PIXI.Graphics &&
child.position.x === col * (gridSize + gridPadding) + gridStartX &&
child.position.y === row * (gridSize + gridPadding) + gridStartY);
if (cell) {
const text = new PIXI.Text(answer[i], { fill: 'black' });
text.anchor.set(0.5);
text.position.set(cell.x + gridSize / 2, cell.y + gridSize / 2);
app.stage.addChild(text);
}
startIndex++;
}
}
function shuffleLetters() {
const letters = ['L', 'G', 'O', 'D'];
for (let i = letters.length - 1; i > 0; i--) {
const j = Math.floor(Math.random() * (i + 1));
[letters[i], letters[j]] = [letters[j], letters[i]];
}
const letterTexts = app.stage.children.filter(child => child instanceof PIXI.Text);
letters.forEach((letter, index) => {
letterTexts[index].text = letter;
letterTexts[index].interactive = true; // Re-enable interactivity after shuffling
});
}
drawGrid();
drawLetterWheel();
</code>
<code>window.onload = () => {
const container = document.getElementById('canvas-container');
const app = new PIXI.Application({
width: container.clientWidth * 2,
height: container.clientHeight * 2,
backgroundColor: 0x1099bb,
});
container.appendChild(app.view);
const background = PIXI.Sprite.from('https://cdn.glitch.global/b457296f-514e-47e5-82c6-28bdeeda16ca/background.png?v=1716472339788');
background.width = app.screen.width;
background.height = app.screen.height;
app.stage.addChild(background);
const gridContent = [
[null, null, null, null],
[null, '', null, ''],
[null, null, null, ''],
];
const gridSize = app.screen.width / 5.3;
const gridPadding = gridSize / 10;
const letters = ['L', 'G', 'O', 'D'];
const angleIncrement = (Math.PI * 2) / letters.length;
const circleCenterX = app.screen.width / 2;
const circleCenterY = app.screen.height - app.screen.width / 3 - 170;
const circleRadius = app.screen.width / 3.3;
const letterRadius = circleRadius / 4.2;
const letterColors = ['#ff9933', '#ff9933', '#ff9933', '#ff9933'];
const numRows = gridContent.length;
const numCols = gridContent[0].length;
const gridStartX = (app.screen.width - (numCols * (gridSize + gridPadding))) / 2;
const gridGapY = 120;
const gridStartY = gridGapY;
// Define an array to keep track of selected letters
let selectedLettersArray = [];
function handleLetterDragging(letter) {
console.log('Dragging:', letter);
// Check if the letter has not been selected already
if (!selectedLettersArray.includes(letter)) {
selectedLettersArray.push(letter);
console.log('Selected letters array:', selectedLettersArray);
checkForValidWord();
}
}
function checkForValidWord() {
const selectedLetters = selectedLettersArray.join('');
console.log('Checking for valid word:', selectedLetters);
const foundAnswer = correctAnswers.find(answer => selectedLetters.endsWith(answer));
if (foundAnswer) {
console.log('Found valid word:', foundAnswer);
fillGrid(foundAnswer, selectedLetters.length - foundAnswer.length);
// Reset selected letters array after finding a valid word
selectedLettersArray = [];
}
}
function drawLetterWheel() {
const shuffleButtonUrl = 'images/shuffle.png';
const shuffleButtonSize = 65;
const circle = new PIXI.Graphics();
circle.beginFill(0xfff7e6, 0.7);
circle.drawCircle(circleCenterX, circleCenterY, circleRadius);
circle.endFill();
app.stage.addChild(circle);
letters.forEach((letter, index) => {
const angle = index * angleIncrement;
const letterShiftFactor = 0.8;
const x = circleCenterX + Math.cos(angle) * (circleRadius - letterRadius) * letterShiftFactor;
const y = circleCenterY + Math.sin(angle) * (circleRadius - letterRadius) * letterShiftFactor;
const letterText = new PIXI.Text(letter, {
fontSize: letterRadius * 2,
fill: letterColors[index],
fontFamily: ['Poetsen One', 'Roboto', 'sans-serif']
});
letterText.anchor.set(0.5);
letterText.position.set(x, y);
app.stage.addChild(letterText);
// Enable dragging for each letter
letterText.interactive = true;
letterText.buttonMode = true;
letterText
.on('pointerdown', onDragStart)
.on('pointerup', onDragEnd)
.on('pointerupoutside', onDragEnd);
function onDragStart() {
console.log('Drag start:', letter);
handleLetterDragging(letter);
letterText.interactive = false; // Disable interactivity after selection
}
function onDragEnd() {
console.log('Drag end:', letter);
letterText.interactive = true; // Re-enable interactivity after dragging
}
});
const shuffleButton = PIXI.Sprite.from(shuffleButtonUrl);
shuffleButton.anchor.set(0.5);
shuffleButton.width = shuffleButton.height = shuffleButtonSize;
shuffleButton.position.set(circleCenterX, circleCenterY);
shuffleButton.interactive = true;
shuffleButton.buttonMode = true;
shuffleButton.on('pointerdown', () => {
shuffleLetters();
});
app.stage.addChild(shuffleButton);
}
const correctAnswers = ['GOLD', 'DOG', 'GOD', 'LOG']; // Define correct answers here
function drawGrid() {
for (let row = 0; row < numRows; row++) {
for (let col = 0; col < numCols; col++) {
if (gridContent[row][col] === null) {
const cell = new PIXI.Graphics();
cell.beginFill(0xfff7e6);
cell.drawRoundedRect(0, 0, gridSize, gridSize, 20);
cell.endFill();
cell.position.set(gridStartX + col * (gridSize + gridPadding), gridStartY + row * (gridSize + gridPadding));
app.stage.addChild(cell);
}
}
}
}
function fillGrid(answer, startIndex) {
for (let i = 0; i < answer.length; i++) {
const row = Math.floor(startIndex / 4);
const col = startIndex % 4;
const cell = app.stage.children.find(child => child instanceof PIXI.Graphics &&
child.position.x === col * (gridSize + gridPadding) + gridStartX &&
child.position.y === row * (gridSize + gridPadding) + gridStartY);
if (cell) {
const text = new PIXI.Text(answer[i], { fill: 'black' });
text.anchor.set(0.5);
text.position.set(cell.x + gridSize / 2, cell.y + gridSize / 2);
app.stage.addChild(text);
}
startIndex++;
}
}
function shuffleLetters() {
const letters = ['L', 'G', 'O', 'D'];
for (let i = letters.length - 1; i > 0; i--) {
const j = Math.floor(Math.random() * (i + 1));
[letters[i], letters[j]] = [letters[j], letters[i]];
}
const letterTexts = app.stage.children.filter(child => child instanceof PIXI.Text);
letters.forEach((letter, index) => {
letterTexts[index].text = letter;
letterTexts[index].interactive = true; // Re-enable interactivity after shuffling
});
}
drawGrid();
drawLetterWheel();
</code>
window.onload = () => {
const container = document.getElementById('canvas-container');
const app = new PIXI.Application({
width: container.clientWidth * 2,
height: container.clientHeight * 2,
backgroundColor: 0x1099bb,
});
container.appendChild(app.view);
const background = PIXI.Sprite.from('https://cdn.glitch.global/b457296f-514e-47e5-82c6-28bdeeda16ca/background.png?v=1716472339788');
background.width = app.screen.width;
background.height = app.screen.height;
app.stage.addChild(background);
const gridContent = [
[null, null, null, null],
[null, '', null, ''],
[null, null, null, ''],
];
const gridSize = app.screen.width / 5.3;
const gridPadding = gridSize / 10;
const letters = ['L', 'G', 'O', 'D'];
const angleIncrement = (Math.PI * 2) / letters.length;
const circleCenterX = app.screen.width / 2;
const circleCenterY = app.screen.height - app.screen.width / 3 - 170;
const circleRadius = app.screen.width / 3.3;
const letterRadius = circleRadius / 4.2;
const letterColors = ['#ff9933', '#ff9933', '#ff9933', '#ff9933'];
const numRows = gridContent.length;
const numCols = gridContent[0].length;
const gridStartX = (app.screen.width - (numCols * (gridSize + gridPadding))) / 2;
const gridGapY = 120;
const gridStartY = gridGapY;
// Define an array to keep track of selected letters
let selectedLettersArray = [];
function handleLetterDragging(letter) {
console.log('Dragging:', letter);
// Check if the letter has not been selected already
if (!selectedLettersArray.includes(letter)) {
selectedLettersArray.push(letter);
console.log('Selected letters array:', selectedLettersArray);
checkForValidWord();
}
}
function checkForValidWord() {
const selectedLetters = selectedLettersArray.join('');
console.log('Checking for valid word:', selectedLetters);
const foundAnswer = correctAnswers.find(answer => selectedLetters.endsWith(answer));
if (foundAnswer) {
console.log('Found valid word:', foundAnswer);
fillGrid(foundAnswer, selectedLetters.length - foundAnswer.length);
// Reset selected letters array after finding a valid word
selectedLettersArray = [];
}
}
function drawLetterWheel() {
const shuffleButtonUrl = 'images/shuffle.png';
const shuffleButtonSize = 65;
const circle = new PIXI.Graphics();
circle.beginFill(0xfff7e6, 0.7);
circle.drawCircle(circleCenterX, circleCenterY, circleRadius);
circle.endFill();
app.stage.addChild(circle);
letters.forEach((letter, index) => {
const angle = index * angleIncrement;
const letterShiftFactor = 0.8;
const x = circleCenterX + Math.cos(angle) * (circleRadius - letterRadius) * letterShiftFactor;
const y = circleCenterY + Math.sin(angle) * (circleRadius - letterRadius) * letterShiftFactor;
const letterText = new PIXI.Text(letter, {
fontSize: letterRadius * 2,
fill: letterColors[index],
fontFamily: ['Poetsen One', 'Roboto', 'sans-serif']
});
letterText.anchor.set(0.5);
letterText.position.set(x, y);
app.stage.addChild(letterText);
// Enable dragging for each letter
letterText.interactive = true;
letterText.buttonMode = true;
letterText
.on('pointerdown', onDragStart)
.on('pointerup', onDragEnd)
.on('pointerupoutside', onDragEnd);
function onDragStart() {
console.log('Drag start:', letter);
handleLetterDragging(letter);
letterText.interactive = false; // Disable interactivity after selection
}
function onDragEnd() {
console.log('Drag end:', letter);
letterText.interactive = true; // Re-enable interactivity after dragging
}
});
const shuffleButton = PIXI.Sprite.from(shuffleButtonUrl);
shuffleButton.anchor.set(0.5);
shuffleButton.width = shuffleButton.height = shuffleButtonSize;
shuffleButton.position.set(circleCenterX, circleCenterY);
shuffleButton.interactive = true;
shuffleButton.buttonMode = true;
shuffleButton.on('pointerdown', () => {
shuffleLetters();
});
app.stage.addChild(shuffleButton);
}
const correctAnswers = ['GOLD', 'DOG', 'GOD', 'LOG']; // Define correct answers here
function drawGrid() {
for (let row = 0; row < numRows; row++) {
for (let col = 0; col < numCols; col++) {
if (gridContent[row][col] === null) {
const cell = new PIXI.Graphics();
cell.beginFill(0xfff7e6);
cell.drawRoundedRect(0, 0, gridSize, gridSize, 20);
cell.endFill();
cell.position.set(gridStartX + col * (gridSize + gridPadding), gridStartY + row * (gridSize + gridPadding));
app.stage.addChild(cell);
}
}
}
}
function fillGrid(answer, startIndex) {
for (let i = 0; i < answer.length; i++) {
const row = Math.floor(startIndex / 4);
const col = startIndex % 4;
const cell = app.stage.children.find(child => child instanceof PIXI.Graphics &&
child.position.x === col * (gridSize + gridPadding) + gridStartX &&
child.position.y === row * (gridSize + gridPadding) + gridStartY);
if (cell) {
const text = new PIXI.Text(answer[i], { fill: 'black' });
text.anchor.set(0.5);
text.position.set(cell.x + gridSize / 2, cell.y + gridSize / 2);
app.stage.addChild(text);
}
startIndex++;
}
}
function shuffleLetters() {
const letters = ['L', 'G', 'O', 'D'];
for (let i = letters.length - 1; i > 0; i--) {
const j = Math.floor(Math.random() * (i + 1));
[letters[i], letters[j]] = [letters[j], letters[i]];
}
const letterTexts = app.stage.children.filter(child => child instanceof PIXI.Text);
letters.forEach((letter, index) => {
letterTexts[index].text = letter;
letterTexts[index].interactive = true; // Re-enable interactivity after shuffling
});
}
drawGrid();
drawLetterWheel();
};