Intervention / image

PHP Image Processing
https://image.intervention.io
MIT License
13.79k stars 1.5k forks source link

Rounded Corners with V3 ? #1369

Closed Mobinkh closed 1 month ago

Mobinkh commented 1 month ago

Hey guys i just noticed you removed mask in V3 ! how we can create circle avatar images now ?!

olivervogel commented 1 month ago

Unfortunately, this is currently not possible in version 3. My impression was that the mask() method was rarely used and was implemented very resource-intensively with GD. For this reason, I have decided not to include this feature in the new version. I don't want to rule out the mask method becoming part of Intervention Image again at some point, but this is not a priority at the moment.

ursoforte commented 1 week ago

I used the mask() method to crop a circular profile photo. It seems that now with V3 this is not possible. Please, @olivervogel

olivervogel commented 4 days ago

Here is a mask modifier class that can be used as an external modifier with the Imagick driver of version 3 via the custom modifier api. It picks up the functionality from the mask command of version 2.

Code Example

$image = ImageManager::imagick()
    ->read('example.png')
    ->modify(new MaskModifier('mask.png', true));

Modifier

use Imagick;
use Intervention\Image\Interfaces\ImageInterface;
use Intervention\Image\Interfaces\ModifierInterface;

class MaskModifier implements ModifierInterface
{
    public function __construct(protected mixed $mask, protected $mask_with_alpha_channel = false)
    {
    }

    public function apply(ImageInterface $image): ImageInterface
    {
        // build mask image instance
        $mask = $image->driver()->handleInput($this->mask);

        // resize mask to size of image
        $mask = $mask->resize($image->width(), $image->height());

        // enable alpha channel
        $image->core()->native()->setImageMatte(true);

        if ($this->mask_with_alpha_channel) {
            // mask with alpha channel of mask
            $image->core()->native()->compositeImage(
                $mask->core()->native(),
                Imagick::COMPOSITE_DSTIN,
                0,
                0
            );
        } else {
            // get alpha channel of original as greyscale image
            $original_alpha = clone $image->core()->native();
            $original_alpha->separateImageChannel(Imagick::CHANNEL_ALPHA);

            // use red channel from mask ask alpha
            $mask_alpha = clone $mask->core()->native();
            $mask_alpha->compositeImage($mask->core()->native(), Imagick::COMPOSITE_DEFAULT, 0, 0);
            $mask_alpha->separateImageChannel(Imagick::CHANNEL_ALL);

            // combine both alphas
            $original_alpha->compositeImage($mask_alpha, Imagick::COMPOSITE_COPYOPACITY, 0, 0);

            // mask the image with the alpha combination
            $image->core()->native()->compositeImage(
                $original_alpha,
                Imagick::COMPOSITE_DSTIN,
                0,
                0
            );
        }

        return $image;
    }
}