Merge pull request #142 from guzba/master

bugfix blur perf rgba/rgbx
This commit is contained in:
treeform 2021-02-26 16:47:38 -08:00 committed by GitHub
commit 851c15f943
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
24 changed files with 80 additions and 34 deletions

File diff suppressed because one or more lines are too long

View file

@ -283,7 +283,7 @@ Is there a blend masking function with SIMD support?
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:48 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -196,7 +196,7 @@ Linearly interpolate between a and b using t.
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:48 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -182,7 +182,7 @@ Encodes an image into the BMP file format.
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:48 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -182,7 +182,7 @@ Encodes Image into a JPEG data string.
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:48 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -201,7 +201,7 @@ Encodes the mask data into the PNG file format.
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:48 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -171,7 +171,7 @@ Render SVG file and return the image. Defaults to the SVG's view box size.
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:49 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -230,8 +230,8 @@ function main() {
</ul>
<ul class="simple nested-toc-section">blur
<li><a class="reference" href="#blur%2C%2Cfloat32%2Cuint32"
title="blur(target: Image | Mask; radius: float32; offBounds: uint32 = 0)">blur,<wbr>,<wbr>float32,<wbr>uint32</a></li>
<li><a class="reference" href="#blur%2CImage%2Cfloat32"
title="blur(image: Image; radius: float32)">blur,<wbr>Image,<wbr>float32</a></li>
</ul>
<ul class="simple nested-toc-section">dataIndex
@ -450,8 +450,8 @@ Multiplies alpha of the image by opacity.
Inverts all of the colors and alpha.
</dd>
<a id="blur,,float32,uint32"></a>
<dt><pre><span class="Keyword">proc</span> <a href="#blur%2C%2Cfloat32%2Cuint32"><span class="Identifier">blur</span></a><span class="Other">(</span><span class="Identifier">target</span><span class="Other">:</span> <a href="images.html#Image"><span class="Identifier">Image</span></a> <span class="Operator">|</span> <a href="masks.html#Mask"><span class="Identifier">Mask</span></a><span class="Other">;</span> <span class="Identifier">radius</span><span class="Other">:</span> <span class="Identifier">float32</span><span class="Other">;</span> <span class="Identifier">offBounds</span><span class="Other">:</span> <span class="Identifier">uint32</span> <span class="Other">=</span> <span class="DecNumber">0</span><span class="Other">)</span></pre></dt>
<a id="blur,Image,float32"></a>
<dt><pre><span class="Keyword">proc</span> <a href="#blur%2CImage%2Cfloat32"><span class="Identifier">blur</span></a><span class="Other">(</span><span class="Identifier">image</span><span class="Other">:</span> <a href="images.html#Image"><span class="Identifier">Image</span></a><span class="Other">;</span> <span class="Identifier">radius</span><span class="Other">:</span> <span class="Identifier">float32</span><span class="Other">)</span> <span><span class="Other">{</span><span class="Other pragmadots">...</span><span class="Other">}</span></span><span class="pragmawrap"><span class="Other">{.</span><span class="pragma"><span class="Identifier">raises</span><span class="Other">:</span> <span class="Other">[</span><span class="Identifier">PixieError</span><span class="Other">]</span><span class="Other">,</span> <span class="Identifier">tags</span><span class="Other">:</span> <span class="Other">[</span><span class="Other">]</span></span><span class="Other">.}</span></span></pre></dt>
<dd>
Applies Gaussian blur to the image given a radius.
@ -577,7 +577,7 @@ Create a shadow of the image with the offset, spread and blur.
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:48 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -19,7 +19,7 @@ minifyBy2 pixie/images.html#minifyBy2,Image,int images: minifyBy2(image: Image;
magnifyBy2 pixie/images.html#magnifyBy2,Image,int images: magnifyBy2(image: Image; power = 1): Image
applyOpacity pixie/images.html#applyOpacity,,float32 images: applyOpacity(target: Image | Mask; opacity: float32)
invert pixie/images.html#invert images: invert(target: Image | Mask)
blur pixie/images.html#blur,,float32,uint32 images: blur(target: Image | Mask; radius: float32; offBounds: uint32 = 0)
blur pixie/images.html#blur,Image,float32 images: blur(image: Image; radius: float32)
newMask pixie/images.html#newMask,Image images: newMask(image: Image): Mask
getRgbaSmooth pixie/images.html#getRgbaSmooth,Image,float32,float32 images: getRgbaSmooth(image: Image; x, y: float32; wrapped = false): ColorRGBX
draw pixie/images.html#draw,Image,Image,Mat3 images: draw(a, b: Image; mat: Mat3; blendMode = bmNormal)

View file

@ -98,6 +98,11 @@ function main() {
<li><a class="reference" href="#toPremultipliedAlpha%2Cseq%5B%5D"
title="toPremultipliedAlpha(data: var seq[ColorRGBA | ColorRGBX])">toPremultipliedAlpha,<wbr>seq[]</a></li>
</ul>
<ul class="simple nested-toc-section">gaussianLookup
<li><a class="reference" href="#gaussianLookup%2Cint"
title="gaussianLookup(radius: int): seq[uint32]">gaussianLookup,<wbr>int</a></li>
</ul>
<ul class="simple nested-toc-section">unpackAlphaValues
<li><a class="reference" href="#unpackAlphaValues%2CM128i"
@ -128,6 +133,13 @@ function main() {
<div class="section" id="12">
<h1><a class="toc-backref" href="#12">Procs</a></h1>
<dl class="item">
<a id="gaussianLookup,int"></a>
<dt><pre><span class="Keyword">proc</span> <a href="#gaussianLookup%2Cint"><span class="Identifier">gaussianLookup</span></a><span class="Other">(</span><span class="Identifier">radius</span><span class="Other">:</span> <span class="Identifier">int</span><span class="Other">)</span><span class="Other">:</span> <span class="Identifier">seq</span><span class="Other">[</span><span class="Identifier">uint32</span><span class="Other">]</span> <span><span class="Other">{</span><span class="Other pragmadots">...</span><span class="Other">}</span></span><span class="pragmawrap"><span class="Other">{.</span><span class="pragma"><span class="Identifier">raises</span><span class="Other">:</span> <span class="Other">[</span><span class="Other">]</span><span class="Other">,</span> <span class="Identifier">tags</span><span class="Other">:</span> <span class="Other">[</span><span class="Other">]</span></span><span class="Other">.}</span></span></pre></dt>
<dd>
Compute lookup table for 1d Gaussian kernel. Values are [0, 255] * 1024.
</dd>
<a id="toStraightAlpha,seq[]"></a>
<dt><pre><span class="Keyword">proc</span> <a href="#toStraightAlpha%2Cseq%5B%5D"><span class="Identifier">toStraightAlpha</span></a><span class="Other">(</span><span class="Identifier">data</span><span class="Other">:</span> <span class="Keyword">var</span> <span class="Identifier">seq</span><span class="Other">[</span><span class="Identifier">ColorRGBA</span> <span class="Operator">|</span> <span class="Identifier">ColorRGBX</span><span class="Other">]</span><span class="Other">)</span></pre></dt>
<dd>
@ -166,7 +178,7 @@ Unpack the first 32 bits into 4 rgba(0, 0, 0, value)
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:48 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -1,3 +1,4 @@
gaussianLookup pixie/internal.html#gaussianLookup,int internal: gaussianLookup(radius: int): seq[uint32]
toStraightAlpha pixie/internal.html#toStraightAlpha,seq[] internal: toStraightAlpha(data: var seq[ColorRGBA | ColorRGBX])
toPremultipliedAlpha pixie/internal.html#toPremultipliedAlpha,seq[] internal: toPremultipliedAlpha(data: var seq[ColorRGBA | ColorRGBX])
packAlphaValues pixie/internal.html#packAlphaValues,M128i internal: packAlphaValues(v: M128i): M128i

View file

@ -159,6 +159,11 @@ function main() {
<li><a class="reference" href="#getValueUnsafe%2CMask%2Cint%2Cint"
title="getValueUnsafe(mask: Mask; x, y: int): uint8">getValueUnsafe,<wbr>Mask,<wbr>int,<wbr>int</a></li>
</ul>
<ul class="simple nested-toc-section">blur
<li><a class="reference" href="#blur%2CMask%2Cfloat32%2Cuint8"
title="blur(mask: Mask; radius: float32; outOfBounds: uint8 = 0)">blur,<wbr>Mask,<wbr>float32,<wbr>uint8</a></li>
</ul>
<ul class="simple nested-toc-section">dataIndex
<li><a class="reference" href="#dataIndex%2CMask%2Cint%2Cint"
@ -204,7 +209,7 @@ function main() {
<div class="section" id="6">
<h1><a class="toc-backref" href="#6">Imports</a></h1>
<dl class="item">
<a class="reference external" href="common.html">common</a>
<a class="reference external" href="common.html">common</a>, <a class="reference external" href="internal.html">internal</a>
</dl></div>
<div class="section" id="7">
<h1><a class="toc-backref" href="#7">Types</a></h1>
@ -343,6 +348,14 @@ Grows the mask by spread.
A value of 0 stays 0. Anything else turns into 255.
</dd>
<a id="blur,Mask,float32,uint8"></a>
<dt><pre><span class="Keyword">proc</span> <a href="#blur%2CMask%2Cfloat32%2Cuint8"><span class="Identifier">blur</span></a><span class="Other">(</span><span class="Identifier">mask</span><span class="Other">:</span> <a href="masks.html#Mask"><span class="Identifier">Mask</span></a><span class="Other">;</span> <span class="Identifier">radius</span><span class="Other">:</span> <span class="Identifier">float32</span><span class="Other">;</span> <span class="Identifier">outOfBounds</span><span class="Other">:</span> <span class="Identifier">uint8</span> <span class="Other">=</span> <span class="DecNumber">0</span><span class="Other">)</span> <span><span class="Other">{</span><span class="Other pragmadots">...</span><span class="Other">}</span></span><span class="pragmawrap"><span class="Other">{.</span><span class="pragma">
<span class="Identifier">raises</span><span class="Other">:</span> <span class="Other">[</span><span class="Identifier">PixieError</span><span class="Other">]</span><span class="Other">,</span> <span class="Identifier">tags</span><span class="Other">:</span> <span class="Other">[</span><span class="Other">]</span></span><span class="Other">.}</span></span></pre></dt>
<dd>
Applies Gaussian blur to the image given a radius.
</dd>
</dl></div>
@ -354,7 +367,7 @@ A value of 0 stays 0. Anything else turns into 255.
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:48 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -15,3 +15,4 @@ fill pixie/masks.html#fill,Mask,uint8 masks: fill(mask: Mask; value: uint8)
getValueSmooth pixie/masks.html#getValueSmooth,Mask,float32,float32 masks: getValueSmooth(mask: Mask; x, y: float32): uint8
spread pixie/masks.html#spread,Mask,float32 masks: spread(mask: Mask; spread: float32)
ceil pixie/masks.html#ceil,Mask masks: ceil(mask: Mask)
blur pixie/masks.html#blur,Mask,float32,uint8 masks: blur(mask: Mask; radius: float32; outOfBounds: uint8 = 0)

View file

@ -243,7 +243,7 @@ Angular gradient.
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:49 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -662,7 +662,7 @@ Return elements in pairs: (1st, 2nd), (2nd, 3rd) ... (n - 1, last).
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:49 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -134,7 +134,9 @@ function main() {
</ul></dd>
<dt><a name="blur" href="#blur"><span>blur:</span></a></dt><dd><ul class="simple">
<li><a class="reference external"
data-doc-search-tag="images: blur(target: Image | Mask; radius: float32; offBounds: uint32 = 0)" href="pixie/images.html#blur%2C%2Cfloat32%2Cuint32">images: blur(target: Image | Mask; radius: float32; offBounds: uint32 = 0)</a></li>
data-doc-search-tag="images: blur(image: Image; radius: float32)" href="pixie/images.html#blur%2CImage%2Cfloat32">images: blur(image: Image; radius: float32)</a></li>
<li><a class="reference external"
data-doc-search-tag="masks: blur(mask: Mask; radius: float32; outOfBounds: uint8 = 0)" href="pixie/masks.html#blur%2CMask%2Cfloat32%2Cuint8">masks: blur(mask: Mask; radius: float32; outOfBounds: uint8 = 0)</a></li>
</ul></dd>
<dt><a name="bmColor" href="#bmColor"><span>bmColor:</span></a></dt><dd><ul class="simple">
<li><a class="reference external"
@ -450,6 +452,10 @@ function main() {
<li><a class="reference external"
data-doc-search-tag="common: fractional(v: float32): float32" href="pixie/common.html#fractional%2Cfloat32">common: fractional(v: float32): float32</a></li>
</ul></dd>
<dt><a name="gaussianLookup" href="#gaussianLookup"><span>gaussianLookup:</span></a></dt><dd><ul class="simple">
<li><a class="reference external"
data-doc-search-tag="internal: gaussianLookup(radius: int): seq[uint32]" href="pixie/internal.html#gaussianLookup%2Cint">internal: gaussianLookup(radius: int): seq[uint32]</a></li>
</ul></dd>
<dt><a name="getRgbaSmooth" href="#getRgbaSmooth"><span>getRgbaSmooth:</span></a></dt><dd><ul class="simple">
<li><a class="reference external"
data-doc-search-tag="images: getRgbaSmooth(image: Image; x, y: float32; wrapped = false): ColorRGBX" href="pixie/images.html#getRgbaSmooth%2CImage%2Cfloat32%2Cfloat32">images: getRgbaSmooth(image: Image; x, y: float32; wrapped = false): ColorRGBX</a></li>
@ -915,7 +921,7 @@ function main() {
<div class="twelve-columns footer">
<span class="nim-sprite"></span>
<br/>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-26 01:51:49 UTC</small>
<small style="color: var(--hint);">Made with Nim. Generated: 2021-02-27 00:46:16 UTC</small>
</div>
</div>
</div>

View file

@ -1,4 +1,4 @@
version = "1.0.0"
version = "1.0.1"
author = "Andre von Houck and Ryan Oldenburg"
description = "Full-featured 2d graphics library for Nim."
license = "MIT"

View file

@ -451,7 +451,7 @@ proc blendOverwrite(backdrop, source: ColorRGBX): ColorRGBX =
# proc blendWhite(backdrop, source: ColorRGBX): ColorRGBX =
# ## For testing
# rgba(255, 255, 255, 255)
# rgbx(255, 255, 255, 255)
proc blender*(blendMode: BlendMode): Blender =
## Returns a blend function for a given blend mode.

View file

@ -309,7 +309,7 @@ proc invert*(target: Image | Mask) =
rgba.a = 255 - rgba.a
target.data[j] = rgba
# Inverting rgba(50, 100, 150, 200) becomes rgba(205, 155, 105, 55). This
# Inverting rgbx(50, 100, 150, 200) becomes rgbx(205, 155, 105, 55). This
# is not a valid premultiplied alpha color.
# We need to convert back to premultiplied alpha after inverting.
target.data.toPremultipliedAlpha()
@ -327,7 +327,7 @@ proc blur*(image: Image, radius: float32) =
# TODO support offBounds for images.
template `*`(sample: ColorRGBA, a: uint32): array[4, uint32] =
template `*`(sample: ColorRGBX, a: uint32): array[4, uint32] =
[
sample.r * a,
sample.g * a,
@ -341,8 +341,8 @@ proc blur*(image: Image, radius: float32) =
values[2] += sample[2]
values[3] += sample[3]
template rgba(values: array[4, uint32]): ColorRGBA =
rgba(
template rgbx(values: array[4, uint32]): ColorRGBX =
rgbx(
(values[0] div 1024 div 255).uint8,
(values[1] div 1024 div 255).uint8,
(values[2] div 1024 div 255).uint8,
@ -367,7 +367,7 @@ proc blur*(image: Image, radius: float32) =
a = lookup[step + radius].uint32
values += sample * a
blurX.setRgbaUnsafe(x, y, values.rgba())
blurX.setRgbaUnsafe(x, y, values.rgbx())
# Blur in the Y direction.
for y in 0 ..< image.height:
@ -386,7 +386,7 @@ proc blur*(image: Image, radius: float32) =
a = lookup[step + radius].uint32
values += sample * a
image.setRgbaUnsafe(x, y, values.rgba())
image.setRgbaUnsafe(x, y, values.rgbx())
proc newMask*(image: Image): Mask =
## Returns a new mask using the alpha values of the parameter image.
@ -497,7 +497,7 @@ proc drawCorrect(
else: # b is a Mask
let
sample = b.getValueSmooth(xFloat, yFloat)
blended = blender(backdrop, rgba(0, 0, 0, sample))
blended = blender(backdrop, rgbx(0, 0, 0, sample))
a.setRgbaUnsafe(x, y, blended)
else: # a is a Mask
let backdrop = a.getValueUnsafe(x, y)
@ -767,7 +767,7 @@ proc shift*(target: Image | Mask, offset: Vec2) =
# Reset target for being drawn to
when type(target) is Image:
target.fill(rgba(0, 0, 0, 0))
target.fill(rgbx(0, 0, 0, 0))
else:
target.fill(0)

View file

@ -1,4 +1,4 @@
import benchy, chroma, pixie
import benchy, chroma, pixie, pixie/internal
let image = newImage(2560, 1440)
@ -46,12 +46,12 @@ timeIt "applyOpacity":
reset()
timeIt "toPremultipliedAlpha":
image.toPremultipliedAlpha()
image.data.toPremultipliedAlpha()
reset()
timeIt "toStraightAlpha":
image.toStraightAlpha()
image.data.toStraightAlpha()
reset()

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.9 KiB

BIN
tests/images/maskblur20.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 KiB

View file

@ -104,3 +104,10 @@ block:
a.fill(rgbx(50, 100, 150, 200))
a.invert()
doAssert a[0, 0] == rgbx(44, 33, 22, 55)
block:
let image = newImage(100, 100)
image.fill(rgba(0, 0, 0, 255))
image.fillRect(rect(25, 25, 50, 50), rgba(255, 255, 255, 255))
image.blur(20)
image.writeFile("tests/images/imageblur20.png")

View file

@ -149,3 +149,9 @@ block:
let mask = newMask(100, 100)
mask.strokePolygon(vec2(50, 50), 30, 6, 10)
writeFile("tests/images/masks/strokePolygon.png", mask.encodePng())
block:
let mask = newMask(100, 100)
mask.fillRect(rect(25, 25, 50, 50))
mask.blur(20)
writeFile("tests/images/maskblur20.png", mask.encodePng())