Last active
March 9, 2021 16:58
-
-
Save Coder-ACJHP/6bca1d6e69f10333e57a16a461c5e8b0 to your computer and use it in GitHub Desktop.
With this function you can draw 3D text in Core graphics api in swift
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Original code in obj-c = https://stackoverflow.com/questions/13766268/3d-text-effect-in-ios | |
private func draw3D(text: NSString, usingfont font: UIFont, depthValue depth: CGFloat, foregroundColor: UIColor, shadowColor: UIColor, outlineColor: UIColor) -> UIImage? { | |
let attributes: [NSAttributedString.Key: Any] = [ | |
.font : font, | |
.foregroundColor : foregroundColor | |
] | |
var textSize = view.bounds.size | |
textSize.width += depth + 5 | |
textSize.height += depth + 5 | |
UIGraphicsBeginImageContext(textSize) | |
guard let context = UIGraphicsGetCurrentContext() else { return nil } | |
var colorList = Array<UIColor>() | |
colorList.append(foregroundColor) | |
var colorComponents = foregroundColor.cgColor.components | |
let colorSteps = floor(100 / depth) | |
for _ in stride(from: 0, to: depth, by: 1) { | |
for kIndex in stride(from: 0, to: 2, by: 1) { | |
if colorComponents![kIndex] > colorSteps / 255.0 { | |
colorComponents?[kIndex] -= (colorSteps / 255.0) | |
} | |
} | |
let newColor = UIColor(red: colorComponents![0], green: colorComponents![1], blue: colorComponents![2], alpha: foregroundColor.cgColor.alpha) | |
colorList.insert(newColor, at: 0) | |
} | |
for iIndex in stride(from: 0, to: depth, by: 1) { | |
let newColor = colorList[Int(iIndex)] | |
context.saveGState() | |
context.setShouldAntialias(true) | |
//draw outline if this is the last layer (front one) | |
if iIndex + 1 == depth { | |
context.setLineWidth(1.0) | |
context.setLineJoin(.round) | |
context.setTextDrawingMode(.stroke) | |
outlineColor.setStroke() | |
text.draw(at: CGPoint(x: 1, y: 1), withAttributes: attributes) | |
} | |
// Fill drawing | |
newColor.set() | |
context.setTextDrawingMode(.fill) | |
if iIndex == 0 { | |
context.setShadow(offset: CGSize(width: -1, height: -1), blur: 4.0, color: shadowColor.cgColor) | |
} else if iIndex + 1 != depth { | |
//add glow like blur | |
context.setShadow(offset: CGSize(width: -1, height: -1), blur: 3.0, color: newColor.cgColor) | |
} | |
text.draw(at: CGPoint(x: iIndex, y: iIndex), withAttributes: attributes) | |
} | |
let colorSpace:CGColorSpace = CGColorSpaceCreateDeviceRGB() | |
let bitmapInfo = CGBitmapInfo(rawValue: CGImageAlphaInfo.premultipliedLast.rawValue) | |
let bitmapContext = CGContext(data: nil, | |
width: Int(textSize.width), | |
height: Int(textSize.height), | |
bitsPerComponent: 8, | |
bytesPerRow: Int(textSize.width) * 4, | |
space: colorSpace, | |
bitmapInfo: bitmapInfo.rawValue) | |
UIGraphicsPushContext(bitmapContext!) | |
bitmapContext?.setTextDrawingMode(.fill) | |
text.draw(at: CGPoint(x: depth - 1, y: depth - 1), withAttributes: attributes) | |
let alphaMask = bitmapContext?.makeImage() | |
UIGraphicsPopContext() | |
var drawRect: CGRect = .zero | |
drawRect.size = textSize | |
context.saveGState() | |
context.clip(to: drawRect, mask: alphaMask!) | |
context.setBlendMode(.luminosity) | |
let locations: [CGFloat] = [0.0, 0.4, 0.6, 1.0] | |
let gradientComponents: [CGFloat] = [ | |
0.0, 0.0, 0.0, 1.0, | |
0.6, 0.6, 0.6, 1.0, | |
0.8, 0.8, 0.8, 1.0, | |
0.0, 0.0, 0.0, 1.0 | |
] | |
let gradient = CGGradient(colorSpace: colorSpace, | |
colorComponents: gradientComponents, | |
locations: locations, count: locations.count) | |
let startPoint: CGPoint = .zero | |
let endPoint: CGPoint = CGPoint(x: 0, y: textSize.height) | |
context.drawLinearGradient(gradient!, | |
start: startPoint, | |
end: endPoint, | |
options: .drawsAfterEndLocation) | |
context.restoreGState() | |
guard let finalImage = UIGraphicsGetImageFromCurrentImageContext() else { | |
return nil | |
} | |
UIGraphicsEndImageContext() | |
return finalImage | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment