Vision Quest
A Simple Color Gradient Edged Detector
An alternative to the Sobel
I'm thinking
But really, what do I know...
If the images are not in sync, refreshing page might help in comparing one image to the next...
The first uses a (3,3) filter kernel, the second a (5,5), and the third a (10,10).
Note: a composite of the different filter sizes along with much simplified code can be found closer to the bottom of the webpage. So for some, that might just be the place to start
I believe the effects could be improved by throwing out any outliers (say the top and bottom two on a 5x5), but for the moment such an exercise is beyond me. (I don't have the patience to wait for my computer to do a 250x250 loop on the test image, so I am using pre-packaged ufuncs as the operand.)
I've thought about using a Gaussian blur to pre-process the images, but haven't actually done it, as I've got a hunch it would just blur any 'edge effect' away.
Code as follows:
Or if you don't read code or don't care to read code, what the following function does is:
- A filter of size r is applied to the image.
- The minimum value in this filter area
- Is subtracted from the maximum value in the filter area
- Which yields a value from 0.00 to 1.00.
- These values are then used to segregate the image pixels,
- which are added back to the above gif's at the rate of 0.05 grayscaleUnits/frame
Pretty basic stuff.
import numpy
import scipy.ndimage
from skimage import io
image = "butterflyFairy.png"
img = io.imread(image, as_grey=True)
def nFL(n):
'''
nFL = numberForLabel
a simply utility function for keeping
output images ordered correctly
inserts leading '00' onto numbers
'''
if n < 10:
t = "00" + str(n)
elif n < 100:
t = "0" + str(n)
else:
t = str(n)
return t
def blackWhiteEdge(img):
'''a simple min/max edge detector
Finds the difference in filter window r between min and max value
and if in specified range (see n loop) keeps value,
otherwise, that pixel is zeroed out
'''
z = numpy.zeros_like(img)
#other values for r on this page include r=(5,5), r=(10,10)
#as expected, r=(1,1) kicks out a blank image
r = (3,3)
#These functions find the min/max in the filter area
minA = scipy.ndimage.filters.minimum_filter(img, size=r)
maxA = scipy.ndimage.filters.maximum_filter(img, size=r)
#m is the range in the given area
m = maxA - minA
#This loop slice the image up into bands
#Based on 'm'
for n in range(5,101,5):
iO = numpy.where((m<(n/100.0)),m, z)
#If the following two lines are commented out
#Instead of sliced bands, we get additive layers
iO = numpy.where((iO>((n-5)/100.0)),iO,z)
#This brightens the individual bands
#If the above line is commented out
#Then this line should be commented out to
#Or the results will include lots of static effects
iO = iO * 100 / n
#Name your 'png's'
sN = ".sweetFairyMaiden_%s.png" % nFL(n)
io.imsave(sN, iO)
Two images r=(2,2) and r=(3,3).
This time rather than being additive (as per the top images on this page)
these images are split into bands.
Note: r=(1,1) (not shown) gives a blank image as might be expected.
And I thought that would be all, but you know how it is, I got to playing and...
At the bare bones, the code for this last is much simpler:
def gradientFilter(img, r=(3,3)):
'''simple difference gradient filter
for grayscale img
using filter size r
'''
minA = scipy.ndimage.filters.minimum_filter(img, size=r)
maxA = scipy.ndimage.filters.maximum_filter(img, size=r)
return (maxA - minA)
tuples = [(x*x,x*x) for x in range(0,11,1)]
From here down doesn't really apply (it probably won't make much sense).
But for completeness, it is how I get from a simple function to a working gif complete with watermark. Of course, since makebutterflyGIF()
is a private function that I'm not going to post at this, it is perhaps exactly the type of inclusion on person makes on a website for their own use rather than any others that might stumble upon it.
for (x,y) in tuples:
tI = gradientFilter(io.imread("./butterfly/PNG/bW250.jpg", as_grey=True), r=(x,y))
sN = "./butterfly/PNG/GIF/gradientFileter_%s.png" % nFL(x)
io.imsave(sN, tI)
sN = "./butterfly/PNG/butterflyGif_min_max_simple_increasing_r.gif"
makebutterflyGIF(sN, False, s=0.25)
And then, last but not least, we have a pretty picture.
I mean, that is why we're doing this stuff, right?
Like some Androgynous Android Fairy Princess on the run from the law and coming to a theatre near you this fall!