Hi, I’m pretty new to p5 and have never used the pixels array before. I’ve read the documentation and watched some videos on the pixels array but I can’t work out how to achieve the specific effect I’m looking for.
I want to use pixels from vid1, which is hidden, to fill an ellipse that’s rendered when I move my mouse over the canvas so that it paints the same area of vid1 on to the canvas replacing vid2. The effect is sort of like a scratch card that reveals vid1 as you move the mouse over the canvas.
let vid1;
let vid2;
let cnv;
let positions = [];
let button;
function setup() {
cnv = createCanvas(600, 400);
vid1 = createVideo("cut1.mp4");
vid2 = createVideo("cut2.mp4");
button = createButton("play");
button.mousePressed(togglePlaying);
vid1.hide();
vid2.hide();
}
function togglePlaying() {
vid1.loop();
vid1.volume(0);
vid2.loop();
vid2.volume(0);
}
function draw() {
vid1.loadPixels();
image(vid2, 0, 0);
positions.push({ x: mouseX, y: mouseY });
noStroke();
fill(0); // need to fill using pixels from vid1
for (let i = 0; i < positions.length; i++) {
let x = positions[i].x;
let y = positions[i].y;
ellipse(x, y, 80, 80);
}
}
I believe a much more intuitive and easy way would be to use a mask.
Create a pgraphics where you will draw your ellipses (with or without arrays).
Use this as a mask for vid1.
Here’s another thread on how to use a mask with video.
Hi @AuXie2k9, thanks again for your advice, I’ve read up on using a mask and I’ve managed to get it working with an image as a mask on top of video, however, I can’t get it to work with video as a mask on top of video. In p5.js it throws a type error:
Uncaught TypeError: Failed to execute 'drawImage' on 'CanvasRenderingContext2D': The provided value is not of type '(CSSImageValue or HTMLImageElement or SVGImageElement or HTMLVideoElement or HTMLCanvasElement or ImageBitmap or OffscreenCanvas)'
I think this might be because it’s expecting an image as opposed to a video.
Do you know if there’s support for video as a mask in p5? I can’t seem to find any official documentation on this. My updated code is as follows:
let video;
let video2;
let maskedVideo;
let maskImage;
let mask;
function preload() {
video = createVideo(["cut1.mp4"]);
video.hide();
video.size(600, 600);
video2 = createVideo(["cut2.mp4"]);
video2.hide();
video2.size(600, 600);
maskImage = loadImage("mask.png");
}
function setup() {
createCanvas(600, 600);
mask = createGraphics(width, height);
mask.imageMode(CENTER);
maskedVideo = video2.get();
maskedVideo.mask(mask.get());
button = createButton("play");
button.mousePressed(togglePlaying);
}
function togglePlaying() {
video.loop();
video.volume(0);
video2.loop();
video2.volume(0);
}
function draw() {
image(video, 0, 0, 600, 600);
image(maskedVideo, 0, 0, 600, 600);
if (mouseIsPressed) {
mask.image(maskImage, mouseX, mouseY, 100, 100);
maskedVideo = video2.get();
maskedVideo.mask(mask.get());
}
}