Skip to content

Assignment 3

Gabriel Ivanica edited this page Dec 26, 2018 · 2 revisions

Tema 3 - Canvas Painting with Compute Shader

Description

Implement a simple canvas painting tool using Compute Shader.

Resources

  • Canvas Painting DEMO
    • keys: 0-9 (brush color)
    • Key - (eraser brush)
    • Key [ and ] - control brush radius
    • Keypad 0-9 (control brush opacity - not mandatory)
    • Key S saves the current canvas painting to local file awesome.png

Deadline

  • 20 Ianuarie 2019 23:59 (soft deadline)
  • After the soft deadline, penalty is 10 pct/per day up to a maximum of 50% (100 pct)

Tasks

Setup

  • Disable window vsync
window->SetVSync(false); // in Init()
  • Create 2 RGBA (8 bits per pixel) textures [10 pct]
    • 1 texture for keeping the resulting canvas painting
    • 1 texture for layer painting
    • you can ignore window resizing (as in the Demo)
auto resolution = window->GetResolution();
texture = new Texture2D();
texture->Create(nullptr, resolution.x, resolution.y, 4);
  • Render the canvas texture as a full-screen texture [10 pct]
    • make sure that the window resolution perfectly matches the texture resolution
    • as long as the textures are created with the default window resolution it should
  • Default canvas color should be white [rgb(1, 1, 1)] [5 pct]
  • README: [5 pct]

Painting

  • Draw brush position (and radius) [10 pct]
  • Add support for simple brush painting (steps below) [80 pct]
  • Add support for brush radius [30 pct]
    • default brush radius is 5px
    • add keys for increasing and decreasing brush radius with stepping of 1 pixel
    • grading is considered only if brush painting works
  • Clear the canvas using a compute shader when key N is pressed [20 pct]
  • Real-time feedback: Render the layer texture over the canvas texture during the painting operation [20 pct]
  • Add support for the following 10 brush colors using the keyboard alpha-numeric keys [10 pct]
	if (key == GLFW_KEY_1) brushColor = glm::vec4(1, 0, 0, 1);	// red
	if (key == GLFW_KEY_2) brushColor = glm::vec4(1, 0.5, 0, 1);	// orange
	if (key == GLFW_KEY_3) brushColor = glm::vec4(1, 1, 0, 1);	// yellow
	if (key == GLFW_KEY_4) brushColor = glm::vec4(0, 1, 0, 1);	// green
	if (key == GLFW_KEY_5) brushColor = glm::vec4(0, 1, 1, 1);	// cyan
	if (key == GLFW_KEY_6) brushColor = glm::vec4(0, 0.5, 1, 1);	// light blue
	if (key == GLFW_KEY_7) brushColor = glm::vec4(0, 0, 1, 1);	// blue
	if (key == GLFW_KEY_8) brushColor = glm::vec4(0.5, 0, 1, 1);	// purple
	if (key == GLFW_KEY_9) brushColor = glm::vec4(1, 0, 1, 1);	// magenta
	if (key == GLFW_KEY_0) brushColor = glm::vec4(0, 0, 0, 1);	// white (erase)

Brush painting steps

  • painting starts when left click is pressed OnMouseBtnPress
  • While the mouse button is held down the layer textures must be updated with the paint area created by mouse movements [60 pct]
    • since mouse input is registered less frequently than the real movement the brush painting has to be interpolated
    • each frame
      • send to the compute shader the previous mouse position and the current mouse position
      • paint a line between the 2 points (with the specified line radius)
      • Point to line equation (In demo a variation of the cross product method is used)
        • from each compute thread (pixel) the distance to the line must be computed in order to decide if the pixel will be painted or not
  • painting finished when the user release the left click OnMouseBtnRelease
  • Using a compute shader copy the layer texture into the canvas texture [20 pct]

Total: 200 pct

Bonuses

  • Optimize canvas brush painting by computing an AABB between the mouse position (current and previous) and do an early return for the compute threads that are outside of it
  • Implement a simple clone-stamp tool
    • use shift to position a
    • copy from canvas texture in the layer texture
    • after mouse release
  • Add brush opacity like in the demo
    • layer combination can be done like this (in demo is the)
canvasColor.rgb = layerColor.rgb * layerColor.a + canvasColor.rgb * (1 - layerColor.a);

Project Archive

  • make sure you don't include temporary compiled files in the archive
    • right of Solution Explorer → Clean Solution
    • delete /Visual Studio/obj and /Visual Studio/.vs folder
  • the archive should only contain
    • /Visual Studio
    • /Source
    • /Resources
    • /libs
    • README.txt - readme for the assignment

Clone this wiki locally