Page 1 of 1
Resize using only certain pixels
Posted: 2012-04-17T15:54:03-07:00
by BryantMoore
Is there a way to do this currently in ImageMagick? What I was thinking is that I could use a checker pattern as a mask to only take into account certain pixels when resizing, but the -mask parameter doesn't seem to allow for resizing.
Re: Resize using only certain pixels
Posted: 2012-04-17T16:18:34-07:00
by anthony
I don't follow. How can you resize just a specific pixel?
You can resize specific rows or columns, but not specific pixels.
Or you can 'magnify' a set of pixels so that it overwrites neighbouring pixels (like a magnifying glass).
A small example may help. Also what OS?
Re: Resize using only certain pixels
Posted: 2012-04-17T17:22:01-07:00
by BryantMoore
What I have is an image that is 64 times larger than the image I wish to end up with.
So for each 8x8 area.
I wish to use a mask such as this.
And use the masked pixels to generate a final color value such as this in the resized image.
Re: Resize using only certain pixels
Posted: 2012-04-17T17:28:09-07:00
by fmw42
Do you want the color corresponding to the black squares or all of the white area?
Assuming the black, then
color=`convert 8x8.png \( checker85.png -negate \) \
-alpha off -compose copy_opacity -composite \
-scale 1x1! -alpha off -format "%[pixel:u.p{0,0}]" info:`
convert -size 128x128 xc:"$color" 1tmp.png
If you want the white, then leave off the -negate.
Re: Resize using only certain pixels
Posted: 2012-04-17T17:40:29-07:00
by anthony
Hmmm I assume your image has LOTS of 8x8 pixels...
I would probably convolve with a negation of that mask, that generates a 'average of just those pixels. Then just 'sample' every 8x8 pixels.
The trick, is lining up exactly which pixel in each 8x8 area you want to sample, with the 'origin' of the convolve kernel for that 8x8 area.
Re: Resize using only certain pixels
Posted: 2012-04-17T17:43:04-07:00
by BryantMoore
I'm trying to resize down not up, I enlarged the images so the pixels where easier to see.
Re: Resize using only certain pixels
Posted: 2012-04-17T17:44:52-07:00
by BryantMoore
fmw42 wrote:Do you want the color corresponding to the black squares or all of the white area?
Assuming the black, then
color=`convert 8x8.png \( checker85.png -negate \) \
-alpha off -compose copy_opacity -composite \
-scale 1x1! -alpha off -format "%[pixel:u.p{0,0}]" info:`
convert -size 128x128 xc:"$color" 1tmp.png
If you want the white, then leave off the -negate.
This doesn't seem to work in Cygwin.
Re: Resize using only certain pixels
Posted: 2012-04-17T17:56:11-07:00
by fmw42
I don't know why it would not.
try escaping the -scale 1x1! to -scale 1x1\! and see if that help.
But I am not sure I understand what you want when you say you want to resize down and not up. I was assuming that your image and your mask correspond in scale. If that is not true, then what I recommended is not appropriate. Please clarify.\
What version of IM are you using?
Which is failing -- the extraction of color or the convert? See if echo $color shows anything meaningful.
Re: Resize using only certain pixels
Posted: 2012-04-17T17:58:32-07:00
by anthony
A small test shows that sampling an 8x8 area will grab the 5th pixel...
Code: Select all
convert -size 8x8 gradient: \( +clone -sample 1x1\! -scale 1x8\! \) +append -scale 800% show:
convert -size 8x8 gradient: -rotate -90 \( +clone -sample 1x1\! -scale 8x1\! \) -append -scale 800% show:
Frist de-pixelize your test image!
Code: Select all
convert 8x8.png -sample 8x8 image.png
As such the kernel origin will be at +4+4 (top-left pixel is +0+0)
Code: Select all
convert image.png -define convolve:scale='!' -morphology convolve \
'8x8+4+4:
0 0 0 0 0 0 0 0
1 0 0 0 1 0 0 0
0 0 0 0 0 0 0 0
0 0 1 0 0 0 1 0
0 0 0 0 0 0 0 0
1 0 1 0 1 0 0 0
0 0 0 0 0 0 0 0
0 0 1 0 0 0 1 0
' -sample 12.5% -scale 800% result.png
The scale is optional!
however I get a lighter color than what you did. Perhaps the 'white' is the sample points
Code: Select all
convert image.png -define convolve:scale='!' -morphology convolve \
'8x8+4+4:
1 1 1 1 1 1 1 1
0 1 1 1 0 1 1 1
1 1 1 1 1 1 1 1
1 1 0 1 1 1 0 1
1 1 1 1 1 1 1 1
0 1 0 1 0 1 1 1
1 1 1 1 1 1 1 1
1 1 0 1 1 1 0 1
' -sample 12.5% -scale 800% result.png
nope still a bit light. Are your sure you test images provided are correct?
Re: Resize using only certain pixels
Posted: 2012-04-17T18:01:35-07:00
by anthony
ASIDE; the kernel data can be read from a file!
Code: Select all
-morphology convolve '@kernel_data.txt'
Re: Resize using only certain pixels
Posted: 2012-04-17T18:08:18-07:00
by BryantMoore
The images I provided were meant to show an example of a group of colors from the source image and the final destination color. My source images are 15360x8640 and I wish for them to be downsized to 1920x1080. The reason I'm trying to use only certain pixels from the source image when resizing to the destination image is because I want to mimic a sub-pixel jitter anti-aliasing by using only certain pixels from the source which correspond to sub-pixel color values in the final image once downsized.
For more information on what I'm trying to achieve, read that here.
http://en.wikipedia.org/wiki/Supersampl ... ersampling
What I'm doing is taking large screenshots of video games and then resizing them to introduce anti-aliasing. However typical resizing corresponds to an ordered grid which isn't what I want.
Re: Resize using only certain pixels
Posted: 2012-04-17T18:15:52-07:00
by anthony
The convolve example will do what you have specified. For any sized image that is a multiple of 8
Just leave out the
-scale 800%
Essentually standard -resize is doing somethign similar, but using a 'weighted average' of all the pixels.
The 'support' is the mutliplyier of the number of pixels to be merged, while the 'filter' specifies how the pixels should be weighted.
A resize is in essence does exactly the same as what I did with the examples above. A sampled convolve (with the kernel scaled up, to match the down scale). It just avoides doing the 'convolve' on pixels that will not be used in the final image, where as I convolved everything, then sampled the specific pixels wanted.
Resize by the fact that it is doing a weighted average pixels, is in essense 'anti-aliasing' the result.
See Resize Filters
http://www.imagemagick.org/Usage/resize/#filter
Actually reading the section before this Resize Artifacts
http://www.imagemagick.org/Usage/resize/#artifacts
is a better start as it shows what you are trying to combat!
Super sampling is more commonly used as a 'fast' sampling method, when distortions (resize is a linear distort) makes 'area resampling' (what resize uses) difficult. That is when scaling is very non-linear (such as in De-Polar distortions), or indeterminanate (as in Ray-tracing, or Shepard's distortion). In that case it become prohibitive to calculate all the pixels that need to be 'averaged' to generate the destination image color. But a reverse mapping of a select 'sampling' of sub-pixel, that map into the final pixel will provide a reasonable result.
But it is by no means a replacment for resize, or 'area resampling', when you can do it. Though it is generally FASTER when extreme distortions are involved.
See Distorts Super-Samping, verses Area Resampling.
http://www.imagemagick.org/Usage/distorts/#super_sample
(that is a good summary -- adding to Im Examples Distorts)
Re: Resize using only certain pixels
Posted: 2012-04-17T18:28:55-07:00
by BryantMoore
Thanks anthony, that does exactly what I need.