Welcome to the Treehouse Community

Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.

Looking to learn something new?

Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.

Start your free trial

JavaScript

Touchstart and Touchend on Canvas

I have some simple squares drawn on canvas and I was trying to make it change color when using touchstart and touchend. The idea is to add the toggle functionality to each square object so it can be multitouch. Any clue?

Here is the code I have for now:

var canvas = document.getElementById('appArea');
var ctx = canvas.getContext('2d');
var width = window.innerWidth;
var height = window.innerHeight;
var shapelist = [];


var Square = function (x, y, size, ctx) {
    this.x = x;
    this.y = y;
    this.size = size;
    this.ctx = ctx;
    this.selected = false;
    this.color = 'black';
}

Square.prototype.render = function() {
    ctx.beginPath();
    ctx.rect(this.x, this.y, this.size, this.size);
    if (this.selected) {
        ctx.fillStyle = "green";
    } else  {
        ctx.fillStyle = this.color;
    }
    ctx.fill();

};


//Thinking on change object behaviour using an activated functionality
/*
Square.prototype.activated = function(color) {

};
*/


var generateSquares = function () {
    for (var i = 0; i < 3; i++) {
        var theX = i * 30;
        var theY = 20;
        var the Size = 10;
        var square = new Square(theX, theY, theSize, ctx);
        square.render();
        shapelist.push(square);
    };
}

var getCoords = function (x, y) {
    var validCoords = [];

    for(var index in shapelist){
        var shape = shapelist[index];
        var startX = shape.x;
        var endX = shape.x + shape.size;
        var startY = shape.y;
        var endY = shape.y + shape.size;

        if (x >= startX && x <= endX && y >= startY && y <= endY) {
            validCoords.push(shape);
        }
    }
    return validCoords;
} 


var startEvent = function(e) {
    var self = this;
    canvas.addEventListener('touchstart', function (e) {
        resetShapeSelection();
        var shapes = getCoords(e.offsetX, e.offsetY);
        console.log(shapes[shapes.length-1]);
        // if shapes exists from a touch event   
        if (shapes.length) {       
            var selectedShape = shapes[shapes.length-1];
            selectedShape.selected = true;
        }
        render();
    }, false);
}


function resetShapeSelection() {
   for(index in shapelist){
    var shape = shapelist[index];
       shape.selected=false;
   }
}


var render = function(){
    ctx.clearRect(0, 0, this.width, this.height);
    for(index in shapelist){
        shapelist[index].render();
    }
}

generateSquares();
startEvent();
render();

2 Answers

Kenneth Camilleri
Kenneth Camilleri
7,816 Points

<p>Try adding the touchstart / touchend event listeners in the Square's constructor. I don't have the source HTML file so I can't really test this out myself.</p> <pre>``` var Square = function (x, y, size, ctx) { this.x = x; this.y = y; this.size = size; this.ctx = ctx; this.selected = false; this.color = 'black'; this.addEventListener('touchstart', function(e)) { // Code to change colour on boxes } }

<p>This way, each square will create its own touchstart event listener upon being instantiated. I'm not really sure if I answered your question but I don't get the multitouch bit but at least you know that you can add the event listener to every square by modifying the constructor.</p>
<p>For future questions, it always helps to give a mockup or screenshot with arrows pointing at areas saying how you want some parts to behave.</p>

Thanks! I have solved the issue with another technique but anyway I think yours is mucho more effective.