So I tried what has been suggested on this image

Here's the python code :
apple = cv2.imread('apple.png')
apple = cv2.cvtColor(apple, cv2.COLOR_BGR2GRAY)
# User Inputs (Similar to Photoshop)
angle = 41 # angle of the shift
distance = 100 # distance of the shift
angle = np.deg2rad(180-angle)
tx, ty = (distance*np.cos(angle),distance*np.sin(angle))
# Shifting
shift_matrix1 = np.array([[1,0,tx],[0,1,ty]], dtype=np.float32)
shift_matrix2 = np.array([[1,0,-tx],[0,1,-ty]], dtype=np.float32)
shift1 = cv2.warpAffine(apple, shift_matrix1, apple.shape)
shift2 = cv2.warpAffine(apple,shift_matrix2, apple.shape)
result = cv2.bitwise_not(cv2.bitwise_and(cv2.bitwise_xor(shift1, shift2), apple))
output = cv2.bitwise_and(result, apple)
Which gives us the expect result (similar to what we achieve with photoshop) :

Applying blur
I tried to apply gaussian blur before the XOR operation by adding those two lines of code before calculating the result
shift1 = cv2.GaussianBlur(shift1, (101,101),0)
shift2 = cv2.GaussianBlur(shift2, (101,101),0)
result = ...
and here's what I got :

VS Photoshop result (With approximatively the same configs) :

So I think that I'm missing an operation to handle the intersection of those 2 shapes (where we got those weird pixels)
Does anyone have an Idea about what I'm missing here ?
Edit
I tried another approach:
So instead of using the bitwise XOR operation, I tried to implement the XOR formula (XOR = A.not(B) + not(A).B) by replacing the bitwise AND operation by the MIN and the bitwise OR by the MAX. Here's the lines that I added :
shift2 = ...
# XOR = A.not(B) + not(A).B
xor_first_term = np.minimum(shift1,(255-shift2))
xor_second_term = np.minimum(shift2,(255-shift1))
xor = (255-np.maximum(xor_first_term, xor_second_term))
result = np.minimum(xor, apple)
And here's the result that I got :

So the result is not perfectly similar to what we got using Photoshop, but at least we got rid of the weird pixels.
Any Idea of what we can add in order to have the exact same result ?