How to create a transparent radial gradient with python?
Asked Answered
A

2

5

I am trying to create a radial gradient that fades to the clear background. My goal is to create this gradient and paste it as the background to another image.

So far, i have been able to create a circular gradient, but it i not transparent. i found the code below in stackoverflow :

imgsize=(650,650)
image = Image.new('RGBA', imgsize)
innerColor = [153,0,0]
for y in range(imgsize[1]):
    for x in range(imgsize[0]):
         distanceToCenter = math.sqrt((x - imgsize[0]/2) ** 2 + (y - imgsize[1]/2) ** 2)
         distanceToCenter = float(distanceToCenter) / (math.sqrt(2) * imgsize[0]/2)
         r = distanceToCenter + innerColor[0] * (1 - distanceToCenter)
         g =  distanceToCenter + innerColor[1] * (1 - distanceToCenter)
         b =  distanceToCenter + innerColor[2] * (1 - distanceToCenter)
         image.putpixel((x, y), (int(r), int(g), int(b)))

this is the image that is produced i would like to not have it fade to black, but to clear instead.

thank you for your help :)

Archdeaconry answered 27/5, 2020 at 14:9 Comment(0)
S
5

I think I would just draw your solid red and calculate a transparency layer with Numpy and push it in:

#!/usr/bin/env python3

import numpy as np
from PIL import Image

# Define width and height of image
W, H = 650, 650

# Create solid red image
im = Image.new(mode='RGB', size=(W,H), color=(153,0,0))

# Create radial alpha/transparency layer. 255 in centre, 0 at edge
Y = np.linspace(-1, 1, H)[None, :]*255
X = np.linspace(-1, 1, W)[:, None]*255
alpha = np.sqrt(X**2 + Y**2)
alpha = 255 - np.clip(0,255,alpha)

# Push that radial gradient transparency onto red image and save
im.putalpha(Image.fromarray(alpha.astype(np.uint8)))
im.save('result.png')

enter image description here

Keywords: Python, image processing, radial gradient, alpha, transparency.

Smoot answered 27/5, 2020 at 23:9 Comment(2)
Thank You!!! you are the best! Worked perfectly, the image is completely clear. The previous answer allowed me to get transparency, outter edged were opaque and not completely clear. THANKS !Archdeaconry
Mark Setchell, I created another question similar to this. Please check it out, if you think you can help. #62457412Archdeaconry
G
3

It's simple math: white/opaque is 255, so you need i-th dimension to be innerColor[i] + distanceToCenter * (255 - innerColor[i]) and add transparency parameter to pixel tuple int((1 - distanceToCenter) * 255):

imgsize=(650,650)
image = Image.new('RGBA', imgsize)
innerColor = [153,0,0]
for y in range(imgsize[1]):
    for x in range(imgsize[0]):
         distanceToCenter = math.sqrt((x - imgsize[0]/2) ** 2 + (y - imgsize[1]/2) ** 2)
         distanceToCenter = float(distanceToCenter) / (math.sqrt(2) * imgsize[0]/2)
         r =  innerColor[0] + distanceToCenter * (255 - innerColor[0])
         g =  innerColor[1] + distanceToCenter * (255 - innerColor[1])
         b =  innerColor[2] + distanceToCenter * (255 - innerColor[2])
         # Or just 
         # r = innerColor[0]
         # g = innerColor[1]
         # b = innerColor[2]
         # if not blending with white as you get farther away from the center.
         image.putpixel((x, y), (int(r), int(g), int(b), int((1 - distanceToCenter) * 255)))

Result is:

enter image description here

Gallegos answered 27/5, 2020 at 14:27 Comment(2)
It looks like you're blending with white as you get farther away from the center. Why are you doing that? Just changing the alpha should be enough by itself.Montalvo
This worked in getting me the transparency but as Mark said, it blends with white on the edges, giving it an opaque look.Archdeaconry

© 2022 - 2024 — McMap. All rights reserved.