I am trying to animate banner view from the bottom to the screen using constraints. the button is attached to the bannerview and it should always be at the same distance from banner. This is what I get: https://vid.me/F008
As you can see the button jumps suddenly, but I wanted it to move slowly with UIView.animateWithDuration method. This is my code
#IBOutlet weak var bannerToBottomGuideConstraint: NSLayoutConstraint!
#IBOutlet weak var buttonToBannerConstraint: NSLayoutConstraint!
#IBOutlet weak var bannerView: ADBannerView!
override func viewDidLoad() {
super.viewDidLoad()
self.canDisplayBannerAds = true
bannerToBottomGuideConstraint.constant -= CGRectGetHeight(bannerView.bounds)
bannerView.backgroundColor = UIColor(red: 0, green: 0, blue: 0, alpha: 0)
}
func bannerViewDidLoadAd(banner: ADBannerView!) {
let time = 0.6
if banner.bannerLoaded == false{
self.view.layoutIfNeeded()
bannerToBottomGuideConstraint.constant += CGRectGetHeight(bannerView.bounds)
UIView.animateWithDuration(time, animations: {
self.view.layoutIfNeeded()
}, completion: {_ in
})
}
}
func bannerView(banner: ADBannerView!, didFailToReceiveAdWithError error: NSError!) {
if bannerView.bannerLoaded{
bannerToBottomGuideConstraint.constant -= CGRectGetHeight(bannerView.bounds)
UIView.animateWithDuration(0, animations: {
self.view.layoutIfNeeded()
}, completion: {_ in
})
}
}
Instead of self.view.layoutIfNeeded() in the animation block, call banner.superview!.layoutIfNeeded().
Related
I need to create a right slide animation for TextField 1 and left slide animation for TextField2 . I tried to accomplish first right slide animation, but there is a problem. I have an slide animation, but there is another textfield under my animation textfield which doesn't move from it's constraints. I do not really understand why.
here is the code:
class ViewController: UIViewController {
#IBOutlet weak var emailField: UITextField!
#IBOutlet weak var PasswordField: UITextField!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
emailField.center.x = self.view.frame.width + 50
UIView.animate(withDuration: 1.0, delay: 0.0, usingSpringWithDamping: 1.0, initialSpringVelocity: 1.0, options: .allowAnimatedContent, animations: {
self.emailField.center.x = self.view.frame.width/2
self.view.layoutIfNeeded()
}, completion: nil)
}
}
Assuming your Storyboard looks similar to this:
Two text fields, with Top constraints, Width constraints equal to 80% of the view width, and CenterX constraints to the view's CenterX
Ctrl-Drag from each .centerX constraint to your view controller code to create #IBOutlet connections to the constraints:
#IBOutlet var emailCenterX: NSLayoutConstraint!
#IBOutlet var passwordCenterX: NSLayoutConstraint!
Your Storyboard will now look like this:
And you can move / animate the views by setting their .constant values at run-time:
class AViewController: UIViewController {
#IBOutlet var emailField: UITextField!
#IBOutlet var PasswordField: UITextField!
#IBOutlet var emailCenterX: NSLayoutConstraint!
#IBOutlet var passwordCenterX: NSLayoutConstraint!
var viewWidth: CGFloat = 0
override func viewDidLoad() {
super.viewDidLoad()
// move the textFields "off-screen"
emailCenterX.constant = UIScreen.main.bounds.width
passwordCenterX.constant = -UIScreen.main.bounds.width
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
// reset the centerX constraints to the center of the view
emailCenterX.constant = 0
passwordCenterX.constant = 0
UIView.animate(withDuration: 1.0, delay: 0.0, usingSpringWithDamping: 1.0, initialSpringVelocity: 1.0, options: .allowAnimatedContent, animations: {
self.view.layoutIfNeeded()
}, completion: nil)
}
}
Hi I'm new to Swift and I want to create a color memory game for IPhone where your app gives you a sequence of colors and you have to repeat it by pressing the right buttons. The sequence becomes longer and longer everytime you pressed the right buttons of the previous sequence.
I want the app to show which button is pressed by using an animation on the button. The sequence will make the buttons flash and then the user can recreate the sequence.
I have a method that does the flash(), which is a part of a class which is an extension of UIButton
func flash() {
let flash = CABasicAnimation(keyPath: "opacity")
flash.duration = 0.2
flash.fromValue = 1
flash.toValue = 0.1
flash.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseInEaseOut)
flash.autoreverses = true
flash.repeatCount = 1
layer.add(flash, forKey: nil)
}
When I perform this method on a sequence of buttons it flashes all of the buttons, written in the sequence, at the same time. This is not the way I want it of course, I want the buttons to flash one after another.
// ViewController.swift
import UIKit
import SpriteKit
class GameViewController: UIViewController {
var colorPattern = [Int]()
#IBOutlet weak var buttonGreen: UIButton!
#IBOutlet weak var buttonRed: UIButton!
#IBOutlet weak var buttonBlue: UIButton!
#IBOutlet weak var buttonYellow: UIButton!
var buttons = [UIButton]()
override func viewDidLoad() {
super.viewDidLoad()
buttons = [buttonGreen, buttonRed, buttonBlue, buttonYellow]
colorPattern = [0, 1, 2, 0, 1, 2]
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
}
#IBAction func colorButtonTouched(_ sender: UIButton) {
print("button touched: ", sender.titleLabel!.text!)
//sender.flash()
doPattern()
}
func doPattern() {
UIView.animateKeyframes(withDuration: 1, delay: 0, options: [.calculationModeCubic], animations: {
// Add animations
for index in self.colorPattern{
print(index);
UIView.addKeyframe(withRelativeStartTime: 0, relativeDuration: 1, animations: self.buttons[index].flash)
}
}, completion:{ _ in
print("I'm done!")
})
}
}
When I perform this code button 1, 2 and 3 flash at the same time. Is there a way to fix this? or are animations just not the right way to go with looping sequences.
Try this
var currentButtonIndex = 0
func doPattern()
{
let currentButton = self.buttons[self.currentButtonIndex]
UIView.animateKeyframes(withDuration: 1, delay: 0, options: [.autoreverse], animations: {
currentButton.alpha = 0
}) { (complete) in
currentButton.alpha = 1
if self.currentButtonIndex == self.buttons.count - 1
{
self.currentButtonIndex = 0
return
}
self.currentButtonIndex += 1
self.doPattern()
}
}
I am doing a transition of an UIImageView's image and would also like to move the image view at the same time. The results so far is that the image transitions, but not while moving.
class ViewController: UIViewController {
#IBOutlet weak var imageView: UIImageView!
#IBOutlet weak var imageViewTopConstraint: NSLayoutConstraint!
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
UIView.transition(with: imageView, duration: 2.0, options: .transitionCrossDissolve, animations: {
self.imageView.image = UIImage(named: "otherImage")
}, completion: nil)
imageViewTopConstraint.constant = 200
UIView.animate(withDuration: 2.0) {
self.view.layoutIfNeeded()
}
}
}
Any ideas on how to solve this?
You can put your imageView inside a container, then animate the constraints of the container while doing the transition on the imageView.
It may sound confusing, but just bear with me.
I have 2 buttons in my ViewController.swift. One that reveals a side menu (this uses the SWRevealViewController), and another one revealing another ViewController.
Once I run the app, it lets me use the slide menu button no problem. However, if I use the other button to reveal another ViewController, THEN come back to the original ViewController (the one with the slide-out menu button), the slide-out-menu button does not work, rather it just blinks and does no action.
I tried programming it and looking at examples, however I have no luck.
Here is my viewController.swift:
import UIKit
class ViewController: UIViewController {
#IBOutlet var BTN4: UIButton!
#IBOutlet var BTN3: UIButton!//This is the button that brings you to the other viewController
#IBOutlet var BTN2: UIButton!
#IBOutlet var BTN1: UIButton!
#IBOutlet var Button: UIButton! //This is the SWRevealViewController being called
#IBOutlet var Bar: UINavigationItem!
var varView = Int()
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
self.view.backgroundColor = UIColor(red: 50 / 255.0, green: 132 / 255.0, blue: 255 / 255.0, alpha: 1.0)
BTN1.alpha = 1.0
BTN4.alpha = 0
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
#IBAction func Clicked(sender: AnyObject) {
UIView.animateWithDuration(1.0, animations: ({
self.BTN2.transform = CGAffineTransformMakeTranslation(0, -90)
self.BTN3.transform = CGAffineTransformMakeTranslation(0, -180)
self.BTN4.transform = CGAffineTransformMakeTranslation(0, 0)
self.BTN1.alpha = 0
self.BTN4.alpha = 1.0
}))
}
#IBAction func ClickedAgain(sender: AnyObject) {
UIView.animateWithDuration(1.0, animations: ({
self.BTN2.transform = CGAffineTransformMakeTranslation(0, 0)
self.BTN3.transform = CGAffineTransformMakeTranslation(0, 0)
self.BTN4.transform = CGAffineTransformMakeTranslation(0, 0)
self.BTN1.alpha = 1.0
self.BTN4.alpha = 0
}))
}
#IBAction func ButtonClicked(sender: AnyObject) {
Button.addTarget(self.revealViewController(), action:#selector(SWRevealViewController.revealToggle(_:)), forControlEvents:UIControlEvents.TouchUpInside)//This is the SWRevealViewController Action
}
}
Any help on this? I know it is a lot, but any type of help would be fantastic.
It's my first try on IOS animation, so if I'm worry from the very beginning, just tell me the right direction.
All I want: when I click ButtonOne, Label disappears slowly.
The code as below:
import UIKit
class ViewController: UIViewController {
#IBOutlet weak var labelHeight: NSLayoutConstraint!
private var isHidden: Bool = false
#IBAction func clickButtonOne(sender: UIButton) {
isHidden = !isHidden
if isHidden {
labelHeight.constant = 0
} else {
labelHeight.constant = 60
}
UIView.animateWithDuration(1.0, animations: {
() -> Void in
self.view.layoutIfNeeded()
}, completion: nil)
}
override func viewDidLoad() {
super.viewDidLoad()
}
}
Before I click ButtonOne:
After I click ButtonOne(label shrinks from bottom to top):
The UILabel is disappearing, but it's content is still visible.
You need to set the clipsToBounds property of the UILabel to true.
label.clipsToBounds = true
You can set the same property in the interface builder by checking the Clip Subviews property in the attributes inspector.
I think you should also animate UIView.alpha property:
import UIKit
class ViewController: UIViewController {
#IBOutlet weak var button: UIButton!
#IBOutlet weak var labelHeight: NSLayoutConstraint!
private var isHidden: Bool = false
#IBAction func clickButtonOne(sender: UIButton) {
isHidden = !isHidden
var alpha: CGFloat = 1
if isHidden {
alpha = 0
labelHeight.constant = 0
} else {
labelHeight.constant = 60
}
UIView.animateWithDuration(1.0, animations: {
() -> Void in
self.button.alpha = alpha
self.view.layoutIfNeeded()
}, completion: nil)
}
override func viewDidLoad() {
super.viewDidLoad()
}
}