Change NSTextField text color with fade animation - Cocoa - swift

I am trying to change NSTextField text color with fade animation by using NSAnimationContext. But it's not working. Please help me to solve this issue. Thanking you all!
Code:
override func viewDidLoad() {
super.viewDidLoad()
label!.animator().textColor = NSColor.black
}
#IBAction func changeColor(_ sender: NSButton){
NSAnimationContext.runAnimationGroup { (context) in
context.duration = 1.0
label!.animator().textColor = NSColor.red
}
}

Here is the outline of one possible solution:
Subclass NSAnimation, say with TextColorAnimation
Have the init take the NSTextField and final NSColor
Override currentProgress as per NSAnimation docs to (a) call the super implementation and (b) set the intermediate color and display the NSTextField
Use NSColor.blend(...) to determine the intermediate color
start this NSAnimation
You should get a nice smooth color transition. HTH

Update the color and alpha value in the completion handler:
#IBAction func changeColor(_ sender: NSButton){
NSAnimationContext.runAnimationGroup({ [self] context in
context.duration = 1.0
context.timingFunction = CAMediaTimingFunction(name: .easeOut)
label.animator().alphaValue = 0.0
label.animator().textColor = NSColor.black
}, completionHandler: { [self] in
NSAnimationContext.runAnimationGroup({ [self] context in
context.duration = 1.0
context.timingFunction = CAMediaTimingFunction(name: .easeIn)
label.animator().alphaValue = 1.0
label.animator().textColor = NSColor.red
}, completionHandler: {
})
})
}

Related

How do I enable a .jpg image to fade in, in swift uiKit

Good evening.
I downloaded a .jpg image and attached it through storyboard, and linked it to Home.swift. At this point, when I run the simulator the image is there. It does nothing at this time, but it's there.
I am trying to modify the code so that the image fades in when the simulator first runs. However, swift isn't liking my approach.
Much appreciate any guidance.
import Foundation
import UIKit
class Home: UIViewController {
#IBOutlet var lonelinessLbl: UILabel!
#IBOutlet var Image: UIImageView!
override func viewDidLoad() {
super.viewDidLoad()
startAnimations()
// Do any additional setup after loading the view.
}
func startAnimations() {
Image.animationImages = [
UIImage(named: "birds.jpg")]
Image.animationDuration = 3
Image.startAnimations()
}
}
Inside startAnimations:
imageView.image = UIImage(named: "birds.jpg")
imageView.alpha = 0
UIViewPropertyAnimator(duration: 5.0, curve: .easeIn) {
self.imageView.alpha = 1.0
}.startAnimation()
(Note that I've renamed Image to imageView -- the Swift convention is to name variables in camel case, starting with a lowercase letter)
You can set the image to image view with animation.
Use the extension to apply animation anywhere.
extension UIImageView{
func setAnimatedImage(_ image: UIImage?) {
UIView.transition(with: self, duration: 0.5, options: .transitionCrossDissolve, animations: {
self.image = image
}, completion: nil)
}
}
Usage
yourImageView.setAnimatedImage(UIImage(named: "birds.jpg"))
Setting an image array to animationImages only helps you when you have a set of images to animate it like a gif.
If you want to present animation like increasing alpha you can do the following.
override func viewDidLoad() {
super.viewDidLoad()
Image.alpha = 0.0
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
UIView.animate(withDuration: 0.3,
animations: {
self.Image.alpha = 1.0
},
completion: nil)
}

How to change button back to its original state

I'm currently working through one of Angela Yu's udemy courses in which one has to develop a working xylophone app.
The final aim was that the buttons (red, blue, green etc.) should change their opacity while pressed, as in the following code:
#IBAction func noteButton(_ sender: UIButton) {
playSound(soundName: sender.currentTitle!)
sender.alpha = 0.5
DispatchQueue.main.asyncAfter(deadline: .now() + 0.2) {
sender.alpha = 1
}
Is there a possibility to not only change the opacity but also the background color as a whole - e.g. grey (pressed) - back to its original color - after the delay?
I guess you'd have to store the button's original background color somehow but I don't know how.
Well one way would be to set the backgroundColor like so:
sender.backgroundColor = .white
You could also override the isHighlighted function if you are working with a UIButton class that you overrode. like so
override open var isHighlighted: Bool {
didSet {
backgroundColor = isHighlighted ? .black :.white
}
}
Obviously this would have to have to be overridden in a child class of UIButton.
you can store the original in a variable like this
#IBAction func noteButton(_ sender: UIButton) {
playSound(soundName: sender.currentTitle!)
let oldColor = sender.backgroundColor
sender.alpha = 0.5
sender.backgroundColor = .white
DispatchQueue.main.asyncAfter(deadline: .now() + 0.2) {
sender.alpha = 1
sender.backgroundColor = oldColor
}

How can I get a slider to change the background color in Swift?

I'm trying to create a flashlight app for school and I wanted to add a slider to change the background from black to white. I can't seem to be able to figure it out.
I've tried some basic things, but nothing I've seen online works. It's either out of date or I'm just not understanding something.
So first you should get slidder value by creating an #IBAction for its value change and then using it to adjust the color of the background
override func viewDidLoad() {
slider.minimumValue = 0.0
slider.maximumValue = 255.0
}
#IBAction func sliderValueChanged(_ sender: UISlider) {
let currentValue = Int(sender.value)
let backgroundColor = UIColor(
red: CGFloat(currentValue),
green: CGFloat(currentValue),
blue: CGFloat(currentValue),
alpha:1.0
)
self.view.backgroundColor = backgroundColor
}
Assuming you want to use a switch. You can make an if-else statement and change the color of the view based on if the switch is enabled or not. This would be an instant change, not a gradual change.
#IBAction func `switch`(_ sender: Any) {
if ((sender as AnyObject).isOn == true){
view.backgroundColor = UIColor.white
} else {
view.backgroundColor = UIColor.black
}
}

Sliding Animation NSView background color in swift

Trying to modifying the color of NSView with sliding animation like Google Trends
let hexColors = ["56A55B", "4F86EC", "F2BC42", "DA5040"]
#IBAction func changeColor(sender: NSButton) {
let randomIndex = Int(arc4random_uniform(UInt32(hexColors.count)))
NSAnimationContext.runAnimationGroup({_ in
//duration
NSAnimationContext.current.duration = 5.0
self.view.animator().layer?.backgroundColor = NSColor(hex: hexColors[randomIndex]).cgColor
}, completionHandler:{
print("completed")
})
}
I tried using NSAnimationContext to set duration of color change, but it does not work. However it works with the alphaValue of the view.
I'm not sure if you have gotten your answer yet. But this might be able get it to work:
let hexColors = ["56A55B", "4F86EC", "F2BC42", "DA5040"]
#IBAction func changeColor(sender: NSButton) {
let randomIndex = Int(arc4random_uniform(UInt32(hexColors.count)))
NSAnimationContext.runAnimationGroup({ context in
//duration
context.duration = 5.0
// This is the key property that needs to be set
context.allowsImplicitAnimation = true
self.view.animator().layer?.backgroundColor = NSColor(hex: hexColors[randomIndex]).cgColor
}, completionHandler:{
print("completed")
})
}
here is what the documentation says:
/* Determine if animations are enabled or not. Using the -animator proxy will automatically set allowsImplicitAnimation to YES. When YES, other properties can implicitly animate along with the initially changed property. For instance, calling [[view animator] setFrame:frame] will allow subviews to also animate their frame positions. This is only applicable when layer backed on Mac OS 10.8 and later. The default value is NO.
*/
#available(macOS 10.8, *)
open var allowsImplicitAnimation: Bool

NSAnimation doesn't work with NSTextField colors

I want to set the text color of a NSTextField using an animation and I tried the following code but it doesn't work. It changes the color immediately without animating the color transition. How do I fix it?
public func changeColor(to: NSColor) {
NSAnimationContext.runAnimationGroup({ (context) in
context.duration = 1.0
context.allowsImplicitAnimation = true
textField.textColor = to
}, completionHandler: nil)
}