Just for @dfd.
So, I went and had a look at Create new UIImage by adding shadow to existing UIImage. After scrolling down a bit, I started to find several Swift based solutions. Intrigued, I threw them into a Playground to see what they could do.
I settled on this solution...
import UIKit
extension UIImage {
/// Returns a new image with the specified shadow properties.
/// This will increase the size of the image to fit the shadow and the original image.
func withShadow(blur: CGFloat = 6, offset: CGSize = .zero, color: UIColor = UIColor(white: 0, alpha: 0.8)) -> UIImage {
let shadowRect = CGRect(
x: offset.width - blur,
y: offset.height - blur,
width: size.width + blur * 2,
height: size.height + blur * 2
)
UIGraphicsBeginImageContextWithOptions(
CGSize(
width: max(shadowRect.maxX, size.width) - min(shadowRect.minX, 0),
height: max(shadowRect.maxY, size.height) - min(shadowRect.minY, 0)
),
false, 0
)
let context = UIGraphicsGetCurrentContext()!
context.setShadow(
offset: offset,
blur: blur,
color: color.cgColor
)
draw(
in: CGRect(
x: max(0, -shadowRect.origin.x),
y: max(0, -shadowRect.origin.y),
width: size.width,
height: size.height
)
)
let image = UIGraphicsGetImageFromCurrentImageContext()!
UIGraphicsEndImageContext()
return image
}
}
let sourceImage = UIImage(named: "LogoSmall.png")!
let shadowed = sourceImage.withShadow(blur: 6, color: .red)

But wait, that's not a drop shadow, it's an outline!
Apparently we need to hand hold everybody now days...
Changing the parameters to ...
let shadowed = sourceImage.withShadow(blur: 6, offset: CGSize(width: 5, height: 5), color: .red)

Produces a drop shadow. I like the solution because it doesn't make assumptions and provides a suitable number of parameters to change the output as desired.
I liked the solution so much, I copied the extension into my personal library, never know when it might come in handy.
Remember, in order to produce this style of image, the original image needs to be transparent.
A little bit like...

Remember, iOS has been around a LONG time, ObjC has been around even longer. You're likely to come across many solutions which are only presented in ObjC, which means, it's still important to have the skill/ability to at least read the code. If we're lucky, other members of the community will produce suitable Swift variants, but this isn't always possible.
I'm sure I don't need to go to the extent of writing a full tutorial on how to include images in Playground, there are plenty of examples about that