I am using CVCalendar to display calendar . I want to disable the swipe action in the calendar view. how it is possible?
Following code which calls cvcalendar and displays calendar. I had two buttons and nex and prev to change month view.
import UIKit
class CalendarViewController: UIViewController {
#IBOutlet weak var menuView: CVCalendarMenuView!
#IBOutlet weak var calendarView: CVCalendarView!
#IBOutlet weak var monthLabel: UILabel!
#IBOutlet weak var eventTableView: UITableView!
var event : String = "1"
var shouldShowDaysOut = true
var animationFinished = true
override func viewDidLoad() {
super.viewDidLoad()
monthLabel.text = CVDate(date: NSDate()).globalDescription
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
override func viewDidLayoutSubviews() {
super.viewDidLayoutSubviews()
calendarView.commitCalendarViewUpdate()
menuView.commitMenuViewUpdate()
}
}
/*
* CVCalendar library functions to display calender and events
*/
extension CalendarViewController: CVCalendarViewDelegate , MenuViewDelegate {
func presentationMode() -> CalendarMode {
return .MonthView
}
func firstWeekday() -> Weekday {
return .Sunday
}
func shouldShowWeekdaysOut() -> Bool {
return false
}
func didSelectDayView(dayView: CVCalendarDayView) {
let date = dayView.date
if dayView.isCurrentDay {
eventTableView.hidden = false
eventTableView.reloadData()
}
else {
eventTableView.hidden = true
}
println("\(calendarView.presentedDate.commonDescription) is selected!")
}
func presentedDateUpdated(date: CVDate) {
if monthLabel.text != date.globalDescription && self.animationFinished {
let updatedMonthLabel = UILabel()
updatedMonthLabel.textColor = monthLabel.textColor
updatedMonthLabel.font = monthLabel.font
updatedMonthLabel.textAlignment = .Center
updatedMonthLabel.text = date.globalDescription
updatedMonthLabel.sizeToFit()
updatedMonthLabel.alpha = 0
updatedMonthLabel.center = self.monthLabel.center
let offset = CGFloat(48)
updatedMonthLabel.transform = CGAffineTransformMakeTranslation(0, offset)
updatedMonthLabel.transform = CGAffineTransformMakeScale(1, 0.1)
UIView.animateWithDuration(0.35, delay: 0, options: UIViewAnimationOptions.CurveEaseIn, animations: {
self.animationFinished = false
self.monthLabel.transform = CGAffineTransformMakeTranslation(0, -offset)
self.monthLabel.transform = CGAffineTransformMakeScale(1, 0.1)
self.monthLabel.alpha = 0
updatedMonthLabel.alpha = 1
updatedMonthLabel.transform = CGAffineTransformIdentity
}) { _ in
self.animationFinished = true
self.monthLabel.frame = updatedMonthLabel.frame
self.monthLabel.text = updatedMonthLabel.text
self.monthLabel.transform = CGAffineTransformIdentity
self.monthLabel.alpha = 1
updatedMonthLabel.removeFromSuperview()
}
self.view.insertSubview(updatedMonthLabel, aboveSubview: self.monthLabel)
}
}
func topMarker(shouldDisplayOnDayView dayView: CVCalendarDayView) -> Bool {
return false
}
func dotMarker(shouldShowOnDayView dayView: CVCalendarDayView) -> Bool {
let day = dayView.date.day
if dayView.isCurrentDay{
return true
}
return false
}
func dotMarker(colorOnDayView dayView: CVCalendarDayView) -> [UIColor] {
let day = dayView.date.day
let color = UIColor.greenColor()
return [color]
}
func dotMarker(shouldMoveOnHighlightingOnDayView dayView: CVCalendarDayView) -> Bool {
return false
}
}
// MARK: - CVCalendarViewAppearanceDelegate
extension CalendarViewController: CVCalendarViewAppearanceDelegate {
func dayLabelPresentWeekdayInitallyBold() -> Bool {
return true
}
func spaceBetweenDayViews() -> CGFloat {
return 2
}
}
#IBAction func next(sender: AnyObject) {
calendarView.loadNextView()
}
#IBAction func previous(sender: AnyObject) {
calendarView.loadPreviousView()
}
You can disable scrolling of CVCalendarView this way:
Go to CVCalendarContentViewController.swift then find the extension CVCalendarContentViewController.
In that extension change the size of scrollView by replacing this line:
scrollView.contentSize = CGSizeMake(frame.size.width * 3, frame.size.height)
With this line of code:
scrollView.contentSize = CGSizeMake(frame.size.width, frame.size.height)
Hope it will help.
UPDATE:
Go to the project navigator the click on third icon which is Find Navigator as shown in below Image:
And search this line into that textField:
scrollView.contentSize = CGSizeMake(frame.size.width * 3, frame.size.height)
And your result will be like this:
Click on that result and replace that line with this line:
scrollView.contentSize = CGSizeMake(frame.size.width, frame.size.height)
Related
Why can't I use other pencils or colors as expected in this app? It only draws a black color. This is my code:
import UIKit
import PencilKit
import PhotosUI
class ViewController: UIViewController, PKCanvasViewDelegate, PKToolPickerObserver {
#IBOutlet weak var pencilButton: UIBarButtonItem!
#IBOutlet weak var canvasView: PKCanvasView!
let canvasWidth: CGFloat = 768
let canvasOverScrollHeight: CGFloat = 500
let drawing = PKDrawing()
override func viewDidLoad() {
super.viewDidLoad()
canvasView.drawing = drawing
canvasView.delegate = self
canvasView.alwaysBounceVertical = true
canvasView.drawingPolicy = .anyInput
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
let toolPicker = PKToolPicker()
toolPicker.setVisible(true, forFirstResponder: canvasView)
toolPicker.addObserver(canvasView)
canvasView.becomeFirstResponder()
}
override func viewDidLayoutSubviews() {
super.viewDidLayoutSubviews()
let canvasScale = canvasView.bounds.width / canvasWidth
canvasView.minimumZoomScale = canvasScale
canvasView.maximumZoomScale = canvasScale
canvasView.zoomScale = canvasScale
updateContentSizeForDrawing()
canvasView.contentOffset = CGPoint(x: 0, y: -canvasView.adjustedContentInset.top)
}
override var prefersHomeIndicatorAutoHidden: Bool{
return true
}
#IBAction func fingerOrPencil (_ sender: Any) {
canvasView.allowsFingerDrawing.toggle()
pencilButton.title = canvasView.allowsFingerDrawing ? "Finger" : "Pencil"
}
#IBAction func saveToCameraRoll(_ sender: Any) {
UIGraphicsBeginImageContextWithOptions(canvasView.bounds.size, false, UIScreen.main.scale)
canvasView.drawHierarchy(in: canvasView.bounds, afterScreenUpdates: true)
let image = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()
if image != nil {
PHPhotoLibrary.shared().performChanges({
PHAssetChangeRequest.creationRequestForAsset(from: image!)
}, completionHandler: {success, error in
})
}
}
func updateContentSizeForDrawing() {
let drawing = canvasView.drawing
let contentHeight: CGFloat
if !drawing.bounds.isNull {
contentHeight = max(canvasView.bounds.height, (drawing.bounds.maxY + self.canvasOverScrollHeight) * canvasView.zoomScale)
} else {
contentHeight = canvasView.bounds.height
}
canvasView.contentSize = CGSize(width: canvasWidth * canvasView.zoomScale, height: contentHeight)
}
// Delegate Methods
func canvasViewDrawingDidChange(_ canvasView: PKCanvasView) {
updateContentSizeForDrawing()
}
func canvasViewDidEndUsingTool(_ canvasView: PKCanvasView) {
}
func canvasViewDidFinishRendering(_ canvasView: PKCanvasView) {
}
func canvasViewDidBeginUsingTool(_ canvasView: PKCanvasView) {
}
}
These are the outputs in the console:
2023-01-04 18:34:04.429420+0300 Drawing[45460:449613] [Assert] UINavigationBar decoded as unlocked for UINavigationController, or navigationBar delegate set up incorrectly. Inconsistent configuration may cause problems. navigationController=<UINavigationController: 0x123024000>, navigationBar=<UINavigationBar: 0x12140a0a0; frame = (0 47; 0 50); opaque = NO; autoresize = W; layer = <CALayer: 0x6000030afae0>> delegate=0x123024000
2023-01-04 18:34:04.468831+0300 Drawing[45460:449613] Metal API Validation Enabled
2023-01-04 18:34:04.705019+0300 Drawing[45460:449613] [ToolPicker] Missing defaults dictionary to restore state for: PKPaletteNamedDefaults
2023-01-04 18:35:00.196200+0300 Drawing[45460:449613] Keyboard cannot present view controllers (attempted to present <UIColorPickerViewController: 0x121846e00>)
toolPicket released when out of method scope.
You should have a instance of toolPicker in ViewController.
class ViewController: UIViewController {
let toolPicker = PKToolPicker()
...
}
i solved my problem by changing
toolPicker.addObserver(self)
into
toolPicker.addObserver(canvasView)
and adding the toolPicker at the top as #noppefoxwolf suggested
I recently started using CVCalendar to create a CalendarView with a Week presentation.
I created a UILabel called monthLabel which has an outlet to the view's controller
The ViewController for this particular view is this one:
import UIKit
import CVCalendar
class EventsViewController: UIViewController {
#IBOutlet weak var headerView: UIView!
#IBOutlet weak var menuView: CVCalendarMenuView!
#IBOutlet weak var calendarView: CVCalendarView!
#IBOutlet weak var eventsTable: UITableView!
#IBOutlet weak var monthLabel: UILabel!
private var currentCalendar: Calendar?
private var animationFinished: Bool = true
let mainAppViewHeader: MainAppViewHeader = UIView.fromNib()
override func viewDidLoad() {
super.viewDidLoad()
loadViewHeader()
setupTable()
}
override func viewDidLayoutSubviews() {
super.viewDidLayoutSubviews()
setupDatePicker()
}
override func awakeFromNib() {
let timeZoneBias = 480 // (UTC+08:00)
currentCalendar = Calendar(identifier: .gregorian)
currentCalendar?.locale = Locale(identifier: "fr_FR")
if let timeZone = TimeZone(secondsFromGMT: -timeZoneBias * 60) {
currentCalendar?.timeZone = timeZone
}
}
func setupDatePicker() {
menuView.delegate = self
calendarView.delegate = self
menuView.backgroundColor = ColorManager.Gray5
calendarView.backgroundColor = ColorManager.Gray5
calendarView.appearance.dayLabelPresentWeekdaySelectedBackgroundColor = ColorManager.PrimaryColor
calendarView.appearance.dayLabelWeekdaySelectedBackgroundColor = ColorManager.PrimaryColor
if let currentCalendar = currentCalendar {
monthLabel.text = CVDate(date: Date(), calendar: currentCalendar).globalDescription
}
menuView.commitMenuViewUpdate()
calendarView.commitCalendarViewUpdate()
}
func loadViewHeader() {
mainAppViewHeader.setupHeader()
headerView.addSubview(mainAppViewHeader)
}
func setupTable() {
let rowNib = UINib(nibName: "EventTableCell", bundle: nil)
eventsTable.dataSource = self
eventsTable.delegate = self
eventsTable.register(rowNib, forCellReuseIdentifier: "eventCell")
eventsTable.separatorStyle = .none
}
}
extension EventsViewController: CVCalendarViewDelegate, CVCalendarMenuViewDelegate {
func presentationMode() -> CalendarMode {
return .weekView
}
func firstWeekday() -> Weekday {
return .sunday
}
func shouldAutoSelectDayOnWeekChange() -> Bool {
return true
}
func disableScrollingBeforeDate() -> Date {
let currentDate = Date()
return currentDate.addingTimeInterval(-8 * 24 * 60 * 60)
}
func disableScrollingBeyondDate() -> Date {
let currentDate = Date()
return currentDate.addingTimeInterval(180 * 24 * 60 * 60)
}
func maxSelectableRange() -> Int {
return 1
}
func shouldSelectRange() -> Bool {
false
}
func earliestSelectableDate() -> Date {
let currentDate = Date()
return currentDate.addingTimeInterval(-8 * 24 * 60 * 60)
}
func latestSelectableDate() -> Date {
let currentDate = Date()
return currentDate.addingTimeInterval(180 * 24 * 60 * 60)
}
func shouldShowWeekdaysOut() -> Bool {
return true
}
func didShowPreviousWeekView(from startDayView: DayView, to endDayView: DayView) {
print(startDayView, endDayView)
}
func presentedDateUpdated(_ date: CVDate) {
monthLabel.text = "asdf" //calendarView.presentedDate.globalDescription
print(date.globalDescription)
}
}
extension EventsViewController: UITableViewDataSource {
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 3
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
guard let eventCell = tableView.dequeueReusableCell(withIdentifier: "eventCell") as? EventTableCell else {
return UITableViewCell()
}
eventCell.setupCell()
eventCell.updateConstraintsIfNeeded()
return eventCell
}
}
extension EventsViewController: UITableViewDelegate {
}
And the outlet reference:
The issue here is that even tho I'm telling the UILabel to change its text whenever the presented date is updated:
func presentedDateUpdated(_ date: CVDate) {
monthLabel.text = "asdf" //calendarView.presentedDate.globalDescription
print(date.globalDescription)
}
It's not updating its value, yet I get the date.globalDescription value printed in the console.
Is there something I'm missing when trying to update the label?
I tried using the code in the official example:
func presentedDateUpdated(_ date: CVDate) {
if monthLabel.text != date.globalDescription && self.animationFinished {
let updatedMonthLabel = UILabel()
updatedMonthLabel.textColor = monthLabel.textColor
updatedMonthLabel.font = monthLabel.font
updatedMonthLabel.textAlignment = .center
updatedMonthLabel.text = date.globalDescription
updatedMonthLabel.sizeToFit()
updatedMonthLabel.alpha = 0
updatedMonthLabel.center = self.monthLabel.center
let offset = CGFloat(48)
updatedMonthLabel.transform = CGAffineTransform(translationX: 0, y: offset)
updatedMonthLabel.transform = CGAffineTransform(scaleX: 1, y: 0.1)
UIView.animate(withDuration: 0.35, delay: 0, options: UIView.AnimationOptions.curveEaseIn, animations: {
self.animationFinished = false
self.monthLabel.transform = CGAffineTransform(translationX: 0, y: -offset)
self.monthLabel.transform = CGAffineTransform(scaleX: 1, y: 0.1)
self.monthLabel.alpha = 0
updatedMonthLabel.alpha = 1
updatedMonthLabel.transform = CGAffineTransform.identity
}) { _ in
self.animationFinished = true
self.monthLabel.frame = updatedMonthLabel.frame
self.monthLabel.text = updatedMonthLabel.text
self.monthLabel.transform = CGAffineTransform.identity
self.monthLabel.alpha = 1
updatedMonthLabel.removeFromSuperview()
}
self.view.insertSubview(updatedMonthLabel, aboveSubview: self.monthLabel)
}
}
But this approach is only pushing a new view with the updated month and then dismissing the view, and while it contains basically the same code that I was using:
self.monthLabel.text = updatedMonthLabel.text
The monthLabel is not being updated, this is what happens when using the above code, it reverts back to original text.
If I remove this line:
updatedMonthLabel.removeFromSuperview()
Both texts get overlapped, so it's ignoring this line:
self.monthLabel.text = updatedMonthLabel.text
I've done some extra testing, and checked that the label is correctly linked with an outlet to my view, I changed the text color:
func presentedDateUpdated(_ date: CVDate) {
print(Thread.current)
print("Wololo")
monthLabel.textColor = UIColor.green
monthLabel.text = "asdf"
// calendarView.contentController.refreshPresentedMonth()
// monthLabel.text = "asdf" //calendarView.presentedDate.globalDescription
// print(date.globalDescription)
}
It prints:
<NSThread: 0x600002b6c100>{number = 1, name = main}
Wololo
N number of times I change the day by clicking on the calendar, however the text remains unchanged:
For some reason the code inside:
override func awakeFromNib() {
let timeZoneBias = 480 // (UTC+08:00)
currentCalendar = Calendar(identifier: .gregorian)
currentCalendar?.locale = Locale(identifier: "fr_FR")
if let timeZone = TimeZone(secondsFromGMT: -timeZoneBias * 60) {
currentCalendar?.timeZone = timeZone
}
}
was in conflict with not updating the label, if we remove the above code and instead do this:
func setupDatePicker() {
menuView.delegate = self
calendarView.delegate = self
menuView.commitMenuViewUpdate()
calendarView.commitCalendarViewUpdate()
monthLabel.text = calendarView.presentedDate.globalDescription //This line at the bottom of this method
}
Everything works once again.
If someone knows the reason behind it, feel free to make a comment and I'll add it to the answer.
presentedDateUpdated is likely being called on a background thread making it so your UI changes aren't being displayed. you can confirm this by printing Thread.current inside presentedDateUpdated.
a simple solution would be this:
func presentedDateUpdated(_ date: CVDate) {
DispatchQueue.main.async { [weak self] in
self?.monthLabel.text = "asdf" //calendarView.presentedDate.globalDescription
print(date.globalDescription)
}
}
whenever I click a textfield inside the view, then click the other text field, the view disappears. Strange... Can anyone help?
I animate the view using facebook pop. Here is my animation engine code:
import UIKit
import pop
class AnimationEngine {
class var offScreenRightPosition: CGPoint {
return CGPoint(x: UIScreen.main.bounds.width + 250,y: UIScreen.main.bounds.midY - 75)
}
class var offScreenLeftPosition: CGPoint{
return CGPoint(x: -UIScreen.main.bounds.width,y: UIScreen.main.bounds.midY - 75)
}
class var offScreenTopPosition: CGPoint{
return CGPoint(x: UIScreen.main.bounds.midX,y: -UIScreen.main.bounds.midY)
}
class var screenCenterPosition: CGPoint {
return CGPoint(x: UIScreen.main.bounds.midX, y: UIScreen.main.bounds.midY - 75)
}
let ANIM_DELAY : Int = 1
var originalConstants = [CGFloat]()
var constraints: [NSLayoutConstraint]!
init(constraints: [NSLayoutConstraint]) {
for con in constraints {
originalConstants.append(con.constant)
con.constant = AnimationEngine.offScreenRightPosition.x
}
self.constraints = constraints
}
func animateOnScreen(_ delay: Int) {
let time = DispatchTime.now() + Double(Int64(Double(delay) * Double(NSEC_PER_SEC))) / Double(NSEC_PER_SEC)
DispatchQueue.main.asyncAfter(deadline: time) {
var index = 0
repeat {
let moveAnim = POPSpringAnimation(propertyNamed: kPOPLayoutConstraintConstant)
moveAnim?.toValue = self.originalConstants[index]
moveAnim?.springBounciness = 8
moveAnim?.springSpeed = 8
if (index < 0) {
moveAnim?.dynamicsFriction += 10 + CGFloat(index)
}
let con = self.constraints[index]
con.pop_add(moveAnim, forKey: "moveOnScreen")
index += 1
} while (index < self.constraints.count)
}
}
class func animateToPosisition(_ view: UIView, position: CGPoint, completion: ((POPAnimation?, Bool) -> Void)!) {
let moveAnim = POPSpringAnimation(propertyNamed: kPOPLayerPosition)
moveAnim?.toValue = NSValue(cgPoint: position)
moveAnim?.springBounciness = 8
moveAnim?.springSpeed = 8
moveAnim?.completionBlock = completion
view.pop_add(moveAnim, forKey: "moveToPosition")
}
}
Then here is my viewcontroller code where the view is inside in:
import UIKit
import pop
class LoginVC: UIViewController, UITextFieldDelegate {
override var prefersStatusBarHidden: Bool {
return true
}
#IBOutlet weak var emailLoginVCViewConstraint: NSLayoutConstraint!
#IBOutlet weak var emailLoginVCView: MaterialView!
#IBOutlet weak var emailAddressTextField: TextFieldExtension!
#IBOutlet weak var passwordTextField: TextFieldExtension!
var animEngine : AnimationEngine!
override func viewDidAppear(_ animated: Bool) {
self.emailLoginVCView.isUserInteractionEnabled = true
}
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
self.view.bringSubview(toFront: emailAddressTextField)
self.animEngine = AnimationEngine(constraints: [emailLoginVCViewConstraint])
self.emailAddressTextField.delegate = self
self.passwordTextField.delegate = self
emailAddressTextField.allowsEditingTextAttributes = false
}
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
if (textField === emailAddressTextField) {
passwordTextField.becomeFirstResponder()
} else if (textField === passwordTextField) {
passwordTextField.resignFirstResponder()
} else {
// etc
}
return true
}
#IBAction func emailTapped(_ sender: AnyObject) {
AnimationEngine.animateToPosisition(emailLoginVCView, position: AnimationEngine.screenCenterPosition, completion: { (POPAnimation, Bool)
in
})
}
#IBAction func exitTapped(_ sender: AnyObject) {
AnimationEngine.animateToPosisition(emailLoginVCView, position: AnimationEngine.offScreenRightPosition, completion: { (POPAnimation, Bool)
in
})
}
}
Last here is my hierchy and options: (my view's name is emailLoginVCView). Also when I was debugging when I clicked another textfield I set a breakpoint so I got this info: enter image description here
I have a constraint that binds the center of the login view with the center of the main screen
when I create the AnimationEngine,I pass it that constraint, and it sets its constant to be the offScreenRightPosition.x
when I bring up the email login sheet, I'm not changing the constant of the constraint; I'm just changing the position of the view
which means that autolayout thinks it’s supposed to still be offscreen
when the second textfield becomes active, that’s somehow triggering auto-layout to re-evaluate the constraints, and it sees that the login view’s position doesn’t match what the constraint says it should be so....
Autolayout moves it offscreen
So if I add this in emailTapped(_:), the problem goes away :)
#IBAction func emailTapped(_ sender: AnyObject) {
AnimationEngine.animateToPosisition(emailLoginVCView, position: AnimationEngine.screenCenterPosition, completion: { (POPAnimation, Bool)
in
self.emailLoginVCViewConstraint.constant = 0
})
}
This question already has answers here:
Swift - how do I allow the textfield to still recognize spaces after the correct answer inputed as still the correct answer
(2 answers)
Closed 6 years ago.
Then how to I allow only a next question button appear when only the right answer is written? I am using Swift! Below is my code. Any help would be greatly appreciated! Thanks!
This is my code and at
import UIKit
class InputViewController1: UIViewController, UITextFieldDelegate {
#IBOutlet var questionLabel: UILabel!
#IBOutlet var correctAnswerLabel: UILabel!
#IBOutlet var inputTextField: UITextField!
var enteredAnswer: String?
var correctAnswer = "Correct Answer = Small"
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(InputViewController1.keyboardWillShow(_:)), name: UIKeyboardWillShowNotification, object: nil)
NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(InputViewController1.keyboardWillHide), name: UIKeyboardWillHideNotification, object: nil)
inputTextField.delegate = self
titlesForLabels()
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func titlesForLabels() {
questionLabel.text = "What is the size of the lesion(s)?"
correctAnswerLabel.text = correctAnswer
correctAnswerLabel.hidden = true
inputTextField.text = nil
inputTextField.enabled = true
}
func keyboardWillShow(notification: NSNotification) {
let userInfo = notification.userInfo!
let keyboardFrame = (userInfo[UIKeyboardFrameEndUserInfoKey] as! NSValue).CGRectValue()
UIView.animateWithDuration(0.1, animations: { () -> Void in
self.view.frame.origin.y = -keyboardFrame.size.height
})
}
func keyboardWillHide() {
UIView.animateWithDuration(0.1, animations: { () -> Void in
self.view.frame.origin.y = 0
})
}
func textFieldShouldReturn(textField: UITextField) -> Bool {
textField.resignFirstResponder()
enteredAnswer = textField.text
checkForCorrectAnswer()
return true
}
func checkForCorrectAnswer() {
if enteredAnswer!.lowercaseString == correctAnswer.lowercaseString {
print("Correct")
correctAnswerLabel.textColor = UIColor.greenColor()
} else {
print("Wrong Answer")
correctAnswerLabel.textColor = UIColor.redColor()
}
correctAnswerLabel.hidden = false
}
}
Please study this code very carefully before asking questions. Using the addTarget method for UIControlEvents.EditingChanged (.EditingChanged), you can alter the properties of your InputViewController with the live current value of your inputTextField. This is done in the textDidChange function. Notice also, that nexButton.alpha is set to 0.0 in viewDidLoad and altered accordingly in both textDidChange and checkForCorrectAnswer.
class InputViewController1: UIViewController, UITextFieldDelegate {
#IBOutlet weak var questionLabel: UILabel!
#IBOutlet weak var correctAnswerLabel: UILabel!
#IBOutlet weak var inputTextField: UITextField!
#IBOutlet weak var nextButton: UIButton!
#IBAction func nextButtonPressed(sender: UIButton) {
}
var enteredAnswer: String?
var correctAnswer = "Small"
override func viewDidLoad() {
super.viewDidLoad()
NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(InputViewController1.keyboardWillShow(_:)), name: UIKeyboardWillShowNotification, object: nil)
NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(InputViewController1.keyboardWillHide), name: UIKeyboardWillHideNotification, object: nil)
inputTextField.addTarget(self, action: #selector(InputViewController1.textDidChange(_:)), forControlEvents: .EditingChanged)
inputTextField.delegate = self
nextButton.alpha = 0.0
titlesForLabels()
}
func titlesForLabels() {
questionLabel.text = "What is the size of the lesion(s)?"
correctAnswerLabel.text = correctAnswer
correctAnswerLabel.hidden = true
inputTextField.text = nil
inputTextField.enabled = true
}
func keyboardWillShow(notification: NSNotification) {
let userInfo = notification.userInfo!
let keyboardFrame = (userInfo[UIKeyboardFrameEndUserInfoKey] as! NSValue).CGRectValue()
UIView.animateWithDuration(0.1, animations: {
self.view.frame.origin.y = -keyboardFrame.size.height
})
}
func keyboardWillHide() {
UIView.animateWithDuration(0.1, animations: {
self.view.frame.origin.y = 0
})
}
func textFieldShouldReturn(textField: UITextField) -> Bool {
textField.resignFirstResponder()
enteredAnswer = textField.text
checkForCorrectAnswer()
return true
}
func checkForCorrectAnswer() {
if enteredAnswer!.lowercaseString == correctAnswer.lowercaseString {
correctAnswerLabel.textColor = UIColor.greenColor()
UIView.animateWithDuration(0.5, animations: {
self.nextButton.alpha = 1.0
}, completion: nil)
correctAnswerLabel.text = "Correct!"
} else {
print("Wrong Answer")
correctAnswerLabel.textColor = UIColor.redColor()
correctAnswerLabel.text = "Incorrect!"
}
correctAnswerLabel.hidden = false
}
func textDidChange(sender: UITextField) {
enteredAnswer = inputTextField.text
correctAnswerLabel.textColor = UIColor.redColor()
correctAnswerLabel.text = "Incorrect!"
if enteredAnswer!.lowercaseString != correctAnswer.lowercaseString {
UIView.animateWithDuration(0.5, animations: {
self.nextButton.alpha = 0.0
}, completion: nil)
}
}
}
I'm trying to figure out how to set the accessibility Increment/ Decrement of an UISlider with stepping. It keeps saying that the value is 0%, which it shouldn't. I also wonder if this is the reason why the accessibilityValue is not working..
ViewController
import UIKit
class RateAppViewController: UIViewController {
//MARK: IBOutlets
#IBOutlet weak var ratingSlider: UISlider!
let steps: Float = 0.2
override func viewDidLoad() {
super.viewDidLoad()
// UpdateUI
updateUI()
// InitalizeAccessibility
initalizeAccessibility()
}
private func updateUI() {
ratingSlider.value = 0.2
ratingSlider.minimumValue = 0.2
ratingSlider.maximumValue = 1.0
}
private func initalizeAccessibility() {
ratingSlider.isAccessibilityElement = true
ratingSlider.accessibilityTraits = UIAccessibilityTraitAdjustable
ratingSlider.accessibilityLabel = NSLocalizedString("Rating", comment: "RatingView Label")
ratingSlider.accessibilityIncrement()
ratingSlider.accessibilityDecrement()
}
override func accessibilityIncrement() {
ratingSlider.value += steps
setRating(ratingSlider.value)
}
override func accessibilityDecrement() {
ratingSlider.value -= steps
setRating(ratingSlider.value)
}
private func setRating(value: Float) {
let stars: Int = Int(value * 5)
print(stars)
if value == 0.2 {
ratingSlider.accessibilityValue = NSLocalizedString("1 star", comment: "One Star RatingSlider")
} else {
ratingSlider.accessibilityValue = NSLocalizedString("\(stars) Stars", comment: "Multiple Stars RatingSlider")
}
}
#IBAction func ratingValueChanged(sender: UISlider) {
let roundSteps = round(sender.value / steps) * steps
sender.value = roundSteps
}
}
I believe you need to subclass UISlider and implement the methods in that class.