diff --git a/src/strands/p5.strands.js b/src/strands/p5.strands.js index 1099b397cd..9eb2269a13 100644 --- a/src/strands/p5.strands.js +++ b/src/strands/p5.strands.js @@ -742,6 +742,146 @@ if (typeof p5 !== "undefined") { * } */ +/** + * Retrieves the current color of a given texture at given coordinates. + * + * The given coordinates should be between [0, 0] representing the top-left of + * the texture, and [1, 1] representing the bottom-right of the texture. + * + * The given texture could be, for example: + * * p5.Image, + * * a p5.Graphics, or + * * a p5.Framebuffer. + * + * The retrieved color that is returned will behave like a vec4, with components + * for red, green, blue, and alpha, each between 0.0 and 1.0. + * + * Linear interpolation is used by default. For Framebuffer sources, you can + * prevent this by creating the buffer with: + * ```js + * createFramebuffer({ + * textureFiltering: NEAREST + * }) + * ``` + * This can be useful if you are using your texture to store data other than color. + * See createFramebuffer. + * + * Note: The `getTexture` function is only available when using p5.strands. + * + * @method getTexture + * @beta + * + * @param texture The texture to sample from. + * (e.g. a p5.Image, p5.Graphics, or p5.Framebuffer). + * + * @param coords The 2D coordinates to sample from. + * This should be between [0,0] (the top-left) and [1,1] (the bottom-right) + * of the texture. It should be compatible with a vec2. + * + * @returns {*} The color of the given texture at the given coordinates. This + * will behave as a vec4 holding components r, g, b, and a (alpha), with each component being in the range 0.0 to 1.0. + * + * @example + *
+ * + * // A filter shader (using p5.strands) which will + * // sample and invert the color of each pixel + * // from the canvas. + * function setup() { + * createCanvas(100, 100, WEBGL); + * let myShader = buildFilterShader(buildIt); + * + * background("white"); + * fill("red"); + * circle(0, 0, 50); + * + * filter(myShader); //Try commenting this out! + * + * describe("A cyan circle on black background"); + * } + * + * function buildIt() { + * filterColor.begin(); + * + * //Sample the color of the pixel from the + * //canvas at the same coordinate. + * let c = getTexture(filterColor.canvasContent, + * filterColor.texCoord); + * + * //Make a new color by inverting r, g, and b + * let newColor = [1 - c.r, 1 - c.g, 1 - c.b, c.a]; + * + * //Finally, use it for this pixel! + * filterColor.set(newColor); + * + * filterColor.end(); + * } + * + * + * + * @example + *
+ * + * // This primitive edge-detection filter samples + * // and compares the colors of the current pixel + * // on the canvas, and a little to the right. + * // It marks if they differ much. + * let myShader; + * + * function setup() { + * createCanvas(100, 100, WEBGL); + * myShader = buildFilterShader(myShaderBuilder); + * describe("A rough partial outline of a square rotating around a circle"); + * } + * + * function draw() { + * drawADesign(); + * + * filter(myShader); // try commenting this out + * } + * + * function myShaderBuilder() { + * filterColor.begin(); + * + * //The position of the current pixel... + * let coordHere = filterColor.texCoord; + * //and some small amount to the right. + * let coordRight = coordHere + [0.01, 0]; + * + * //The canvas content is a texture. + * let cnvTex = filterColor.canvasContent; + * + * //Sample the colors from it at our two positions + * let colorHere = getTexture(cnvTex, coordHere); + * let colorRight = getTexture(cnvTex, coordRight); + * + * // Calculate a (very rough) color difference. + * let difference = length(colorHere - colorRight); + * + * //We'll use a black color by default... + * let resultColor = [0, 0, 0, 1]; + * //or white if the samples were different. + * if (difference > 0.3) { + * resultColor = [1, 1, 1, 1]; + * } + * filterColor.set(resultColor); + * + * filterColor.end(); + * } + * + * //Draw a few shapes, just to test the filter with + * function drawADesign() { + * background(50); + * noStroke(); + * lights(); + * sphere(20); + * rotate(frameCount / 300); + * square(0, 0, 30); + * } + * + *
+ */ + /** * @method getWorldInputs * @param {Function} callback diff --git a/src/webgl/material.js b/src/webgl/material.js index 62b9a6392c..6bd6cc7639 100644 --- a/src/webgl/material.js +++ b/src/webgl/material.js @@ -555,6 +555,7 @@ function material(p5, fn) { * In your function, you can use `filterColor` with a function * that will be called for each pixel on the image to determine its final color. You can * read the color of the current pixel with `getTexture(canvasContent, coord)`. + * See getTexture(). * * ```js example * async function setup() {