Hertzmann

advertisement

Painterly Rendering with

Curved Brush Strokes of

Multiple Sizes

Aaron Hertzman, NYU

Presented by: Shreeganesh Ramanan

Introduction

• Painterly Rendering is a method of reproducing artistic style and expression of a painting using a source image and/or 3D models

• An Image Space Technique

• A few steps beyond what

Photoshop TM offers.

A Sampler

A Sampler

Things to discuss

• “curved brush strokes of multiple sizes”

• Implementation details(as little as possible  )

• Various parameters and what they can do

So you want to be an artist ?

• Do you have lot of time ?

• A huge smattering of skill ?

• That elusive thing called talent

• And some canvas, paints, a subject, and a dirty rag you call work clothes

Or we can turn to NPR

Previous Work…

• One brush size only

• No multiple passes to refine style

• Support for one style only

• Image looks “flattened”

Previous Work..

• But details need different sized strokes

CBS of MS improves quality

Advantages

• Faster than painting

– Can be used for interactive rendering

• Multiple brush sizes allow for varying detail and continuous color regions

• Multipass method similar to how artist paint

• Different parameters create different styles

Main Loop function paint (sourceImage, R

1

{

… R n

) canvas := a new constant color image

// paint the canvas for each brush radius R i

, from largest to smallest do

{

// apply Gaussian blur referenceImage = sourceImage * G(f

σ

R i

)

}

// paint a layer paintLayer(canvas, referenceImage, Ri)

} return canvas

Painting a Layer function paintLayer(canvas, referenceImage, R) {

S := a new set of strokes, initially empty

D := difference(canvas, referenceImage) grid := f g

R for x=0 to imageWidth stepsize grid do { for y=0 to imageHeight stepsize grid do {

M := the region(x-grid/2…x+grid/2, y-grid/2…y+grid/2) areaError := sumOfError(M, D) / grid 2 if (areaError > T) then {

(x

1

, y

1

) := maxPoint(areaError) stroke := makeStroke(R, x

1

, y

1

, referenceImage) add stroke to S

}

} } paint all strokes S on canvas – random order

}

Curved Brush Strokes

• Anti-aliased cubic B-Splines

• Each stroke models the color gradient of reference image

• Representation

– Control Points

– Color

– Size of brush

Spline Stroke Algorithm function makeSplineStroke(x

0

, y

0

, R, refImage) { strokeColor = refImage.color(x

0

, y

0

)

K := new stroke, radius R, color strokeColor add point (x

0

, y

0

) to K

(x, y) := (x

0

, y

0

)

(lastDx, lastDy) := (0, 0) for i=1 to maxStrokeLength do { if (i > minStrokeLength and (|refImage.color(x,y) – canvas.color(x,y)| < |refImage.color(x,y)strokeColor)) then return K if (refImage.gradientMag(x,y) ==0) then return K

(gx, gy) := refImage.gradientDirection(x, y)

(dx, dy) := (-gy, gx) if (lastDx * dx + lastDy * dy < 0) then

(dx, dy) = (-dx, -dy)

(dx, dy) := f c

* (dx,dy) + (1-f c

) * (lastDx,lastDy)

(dx, dy) := (dx,dy)/(dx2 + dy2)1/2

(x, y) := (x + R*dx, y + R*dy)

(lastDx, lastDy) := (dx, dy) add the point (x, y) to K

} return K }

Calculating Control Points

G

2

D

(x

2

1

, y

2

)

(x

1

, y

D

1

)

0

θ

1

G

1

(x

0

, y

0

)

θ

0

G

0

Parameters of Style

• Approximation Threshold ( T )

• Brush Sizes – Smallest ( R i

), Number ( n ) ,

Size Ratio ( R i

-1 / R i

)

• Curvature Filter ( f c

)

• Blur Factor ( f

σ

)

• Min and max stroke lengths ( minLength , maxLength )

• Opacity (

α

)

• Grid size ( f g

)

• Color Jitter ( j h

, j s

, j v

, j r

, j g

, j b

)

Experiments in Style

Source Image

Experiments in Style

Impressionist

Experiments in Style

Expressionist

Experiments in Style

Colorist Wash

Experiments in Style

Pointillist

Download