I have some animated GIF with a transparent background, e.g:
https://i.imgur.com/5yRvEDc.gif
I also have a mask PNG file, where some pixels are transparent, which I want to apply to the GIF, e.g
https://i.imgur.com/8Ly6Exg.png
I want all transparent pixels on the mask to be transparent on the GIF (for each frame) - just like the image below, but animated AND keep the original GIF transparent pixels.
https://i.imgur.com/08kIjse.png
How it can be achieved with ImageMagick?
Here is one way to do that in ImageMagick 6. First multiply the mask with the alpha channels of the animation. Then put the new alpha channels back with the animation.
I note that your mask, has the circle in the alpha channel of the PNG and the underlying image is totally black. So the important part of your mask image is its alpha channel.
Animation:
Mask:
convert lips.gif -coalesce -alpha extract null: \( lips_mask.png -alpha extract \) -compose multiply -layers composite alpha.gif
convert lips.gif null: alpha.gif -alpha off -compose copy_opacity -layers composite lips_masked.gif
If using ImageMagick 7, change convert to magick.
Related
I have a small icon GIF that I would like to change the color. All opaque GIF pixels should be replaced by this new color, but preserve transparency for the gif. Then I need to place that new colored GIF over a background map, all in one command line. Here is what I have, but it's not changing all gif opaque pixels. Attached is the GIF icon. (Edit: I know im only targeting the white here, but just can't figure out how to target ALL opaque pixels in the GIF)
exec("{$convert} {$map_image} \( {$map_icon} -fill orange -opaque white -geometry +1700+600 \) -composite map2.jpg ");
Use +opaque none to fill all non-transparent colors in ImageMagick. The +opaque means everything "but" that color.
convert grid.gif -fill orange +opaque none x.png
As the title suggests I have a PNG image that has some transparency. I'd like to fill that transparency with a second image (which is currently a JPEG, but it's not a problem to convert it to a PNG).
Every post I have found searching on the Internet was about the "inverse" problem (from an image with a background to an image with transparency), so obviously it did not work out for my situation; for example, I tried
convert -flatten myimg.png myimg.png
(taken from here) and
convert myimg1.png -transparent white myimg.png
(taken from here).
In ImageMagick 6, if the two images are the same size, then you can just flatten the transparent image over the background image.
Background (lena.jpg):
Transparent (logo_crop_trans.png):
convert lena.jpg logo_crop_trans.png -flatten lena_logo.jpg
If using ImageMagick 7, then change convert to magick.
If you want to anti-alias the transparent image so that it is not so jagged, then use some blur to smooth the outline (Unix syntax):
convert lena.jpg \( logo_crop_trans.png -channel a -blur 0x1 -level 50x100% +channel \) -compose over -composite lena_logo2.jpg
If on Windows remove the \ before the parentheses.
Is it possible to set the alpha channel of an image according to a gradient with ImageMagick?
I'd like the pixels on the left border of an image to be 100% transparent, and the ones on the right border to be 100% opaque, and with the ones in the middle having progressively lower transparency values.
Or in a more general case - given a grayscale image, set the alpha channel of another image as a function of the B&W values (black = 100% alpha, white 0% alpha).
With ImageMagick you can use -sparse-color to apply a gradient only to the alpha channel to get the result you describe.
convert in.png -alpha set -background none -channel A \
-sparse-color barycentric "0,0 none %[w],0 white" +channel out.png
That command starts by activating the alpha channel and setting the background color to transparent. Then it uses -channel A to apply the following operation only to the alpha channel. The -sparse-color operation tells it to start with transparent at the far left edge, pixel 0,0 and graduate to opaque at pixel %[w],0. The %[w] means the width or far right edge.
Although there are many ways to accomplish the effect you've described, by using -sparse-color you can easily make the gradient start and end at any positions on the image without having to create any intermediate masking images.
Simple. You would use -composite CopyOpacity to set the alpha channel from a gradient mask.
Given I have the following images. image.png & transparent_mask.png
We can set the image transparency (where black is alpha, and white is opaque) by copying values from the mask image to the input image alpha channel.
convert image.png transparent_mask.png -compose CopyOpacity -composite output.png
I've got 2 versions of 1 image
Is it possible to get a transparent png file representing this watermark? Can ImageMagick do this?
SilverMonkey has the basic solution using Imagemagick. But the request was for a transparent PNG. So I will add a little bit more to his code to make it transparent by adding -alpha copy.
convert kitty2.jpg kitty1.jpg -compose minus -composite -auto-level -alpha copy watermark1.png
Here is another approach that makes a binary mask for the watermark by thresholding. But it leaves a lot of noise. So I use some morphology open to remove the noise and then some morpholgy close to try to fill in where the text is broken up. Then I add -alpha copy to make the image transparent. But the text is white and the original watermark was light gray. So I turn alpha off, multiply by 0.75 to reduce the brightness of the white letters to gray without affecting the alpha channel. Then turn the alpha channel back on.
convert kitty2.jpg kitty1.jpg -compose minus -composite -threshold 0.6% -morphology open diamond:1 -morphology close octagon:1 -alpha copy -alpha off -evaluate multiply 0.75 -alpha on watermark2.png
For more on morphology, see https://imagemagick.org/Usage/morphology/
You can achieve your goal by calculating the difference between both images (subtract the pixels of both images and calculate the absolute value). This will result in:
ImageMagick seems to be capable of image subtraction, look here:
The code:
convert image2 image1 -compose minus -composite result
I've got a PNG image with transparency:
original.png
Now I want to use ImageMagick to apply a diagonal gradient to its alpha channel. I mean so that its opacity remains in the top left corner, and gradually fades out to completely transparent in the bottom right corner. Like this:
result.png
So basically I want to generate a gradient, and use that as a mask for the image. But the image already has an alpha channel (transparency) of its own. Here's a visualisation of what I'm trying:
(original and result here displayed on checkerboard for visiblity, but I mean actual transparency)
I think I understand how to generate a diagonal gradient (the barycentric gradient command is very useful for this). But this creates a gradient in the color channels i.e. a colored or grayscale gradient. Whereas I want to apply the gradient on the alpha channel.
From the IM manual I understand the -compose CopyOpacity operator could be used for this. However this seems to copy the alpha from the mask on to my image. I need to "apply" this gradient color on my existing alpha channel, so basically I need my image's alpha channel to be multiplied by the grayscale color from the gradient image.
What would be the correct IM command line to perform the operation displayed above?
Here is one way you could do it:
convert tree.png -write MPR:orig -alpha extract \
\( +clone -colorspace gray -fx "1-j/h" \) \
-compose multiply -composite -write alpha.png \
MPR:orig +swap -compose copyopacity -composite result.png
The -write alpha.png can be omitted - it just shows the alpha layer for debugging and illustration purposes.
The MPR is just a temporary copy of the original image that I hold in memory while I am dinking around with the alpha channel and which I bring back near the end. The gradient in the alpha channel is generated by the -fx and I made the colorspace gray first so it only has to run once, instead of three times.
If you knew the dimensions of the tree image up front, you could replace the part in parentheses with:
-size WxH gradient:black-white
but I don't know the dimensions up front and I don't want a second convert command to get them, so I basically clone the original image's alpha channel to get a canvas the right size and fill it in with -fx.