Category Archives: Swift

Simulated Metrics for View Controllers

I had a trouble with navigation controllers. Child view controllers were programmatically pushed, and I did not know how to get customized navigation bars. I first attached navigation controllers to those child view controllers and it seemed to work. Then, I got warning messages saying that the navigation controllers was not unreachable. It is only warnings but I decided to dig about what I do not know.

The first thing I tried was to delete those navigation controllers from the storyboard. Surprisingly, it still worked as expected. The items on the customized navigation bars were still there. In fact, they belonged to view controllers, not navigation controllers. According to Apple, it should be possible to have customized navigation bars. Usually, something that can be programmatically set may be done with the interface builder. Then, I found that Simulated Metrics in the Attribute Inspector allows one to show and hide navigation bars in the interface builder. After some tries, I ended up the setting Translucent Navigation Bar for the Top Bar entry of the Simulated Metrics.

Screen Shot 2018-03-04 at 8.37.06 PM.png

Presenting view controllers

I am building an app using a tab bar view controller. What happens is as follows.

  1. I presented a view controller modally over a current context. I used present(_:animated:completion:) with the property modalPresentationStyle set to currentContext
  2. I selected a different tab bar item.
  3. I came back to the original tab bar item. So I saw the view controller presented in Step 1.
  4. I dismissed the view controller and got a black screen.

It seems that the instance method present(_:animated:completion:) is dedicated to the case wherein the user comes back directly to the presenting view controller. So I guess I am supposed to disable any options that send a user to a different scene.

Another resolution would be using a navigation controller. I wondered whether I need to put additional navigation controllers to build a stack of view controllers, but it was not the case. I just need to use the method pushViewController(_:animated:) of an instance of UINavigationController. So I only need one navigation controller. Once I used pushViewController(_:animated:), I can dismiss the view controller by popping or popViewController(animated:). In fact, there are two other options: popToRootViewController(animated:) and popToViewController(_:animated:).

The following page is very helpful here: Pushing, Popping, Presenting, & Dismissing ViewControllers

I also checked Wikepedia. It says:
Users must interact with the modal window before they can return the parent application.

Vector.swift

precedencegroup DotProductPrecedence {
    lowerThan: AdditionPrecedence
    associativity: left
}

infix operator ∙ : DotProductPrecedence

class Vector<Element: Numeric> {
    var components = [Element]()

    // Variables conforming VectorProtocol
    var dimension: Int { return components.count }

    init(with array: [Element]) {
        components = array
    }
}

// Methods conforming Equatable
extension Vector: Equatable {
    static func == (lhs: Vector, rhs: Vector) -> Bool {
        guard lhs.dimension == rhs.dimension else {
            return false
        }

        for k in 0..<lhs.dimension {
            if lhs.components[k] != rhs.components[k] {
                return false
            }
        }

        return true
    }
}

// Methods
extension Vector {
    static func ∙ (lhs: Vector, rhs: Vector) -> Element {
        var temp = [Element]()
        for k in 0..<lhs.dimension {
            temp.append(lhs.components[k] * rhs.components[k])
        }
        return temp.reduce(0, {x, y in x + y})
    }
}

// Methods conforming CustomStringConvertible
extension Vector: CustomStringConvertible {
    var description: String {
        var string = "("
        for k in 0..<self.dimension {
            string += String(describing: self.components[k]) + ","
        }
        string.removeLast()
        return string + ")"
    }
}

Complex.swift

import Foundation

struct Complex: CustomStringConvertible {
    let real: Double
    let imag: Double

    typealias IntegerLiteralType = Double

    var conj: Complex {
        return Complex(real: self.real, imag: -1.0 * self.imag)
    }

    var abs: Double {
        return sqrt( self.real * self.real + self.imag * self.imag )
    }

    var amplitude: Double {
        return self.abs
    }

    var magnitude: Double {
        return self.abs
    }

    var phase: Double {
        return atan2( self.imag, self.real )
    }

    var description: String {
        return "\(self.real) + 1i * \(self.imag)"
    }

    init(real: Double, imag: Double) {
        self.real = real
        self.imag = imag
    }

    init(integerLiteral: IntegerLiteralType) {
        self.real = integerLiteral
        self.imag = 0
    }

    init?<T: BinaryInteger>(exactly source: T) {
        if let real = Int(exactly: source), let realDouble = Double(exactly: real) {
            self.real = realDouble
            self.imag = 0
        } else {
            return nil
        }
    }

}

// Numeric protocol
extension Complex: Numeric {
    static func +(left: Complex, right: Complex) -> Complex {
        return Complex(real: left.real + right.real, imag: left.imag + right.imag)
    }

    static func -(left: Complex, right: Complex) -> Complex {
        return Complex(real: left.real - right.real, imag: left.imag - right.imag)
    }

    static func *(left: Complex, right: Complex) -> Complex {
        let real = left.real * right.real - left.imag * right.imag
        let imag = left.real * right.imag + left.imag * right.real
        return Complex(real: real, imag: imag)
    }

    static func /(left: Complex, right: Complex) -> Complex {
        let numerator = left * right.conj
        let denominator = right.abs
        return Complex(real: numerator.real / denominator, imag: numerator.imag / denominator)
    }

    static func +=(left: inout Complex, right: Complex) {
        left = left + right
    }

    static func -=(left: inout Complex, right: Complex) {
        left = left - right
    }

    static func *=(left: inout Complex, right: Complex) {
        left = left * right
    }

    prefix static func + (x: Complex) -> Complex {
        return x
    }

    prefix static func - (x: Complex) -> Complex {
        return Complex(real: -x.real, imag: -x.imag)
    }

}

// Methods conforming Equatable
extension Complex {
    static func == (lhs: Complex, rhs: Complex) -> Bool {
        return (lhs.real == rhs.real) && (lhs.imag == rhs.imag)
    }
}

Referencing a textField inside a tableViewCell

I needed to know which textField within a tableViewCell was updated. In the NMR Calculator app, I kept the references of textFields. Now, I have realized that it is not a good way. So I started searching a solution.

First, I found that it is possible to get an indexPath from the point or frame of something. Then, I found this page from Stack Overflow: Get indexPath of UITextField in UITableViewCell with Swift

With a textField, finding the indexPath of the tableViewCell owning the textField can be done this way. First, the tableViewCell is set to be a delegate of the textField, when the method tableView(_:cellForRowAt:) is called. Second, a protocol for the tableViewCell is defined.

protocol SomeTableViewCellDelegate: AnyObject {
  func didEndEditing(_ cell: SomeTableViewCell)
}

class SomeTableViewCell: UITableViewCell {
  @IBOutlet weak var textField: UITextField!

  weak var delegate: SomeTableViewCellDelegate?

  override func awakeFromNib() {
    super.awakeFromNib()
    textField.delegate = self
  }
}

Now the viewController owning the tableView is set to be a delegate of SomeTableViewCell and conforms to the protocol SomeTableViewCellDelegate.

extension SomeViewController: SomeTableViewCellDelegate {
  func didEndEditing(_ cell: SomeTableViewCell) {
     let indexPath = tableView.indexPath(for: cell)
  }
}

A delegation of a delegation! I would like to adapt this elegant design pattern in the NMR Calculator app.

Passing Data Between View Controllers in iOS

Passing Data Between View Controllers in iOS: the Definitive Guide (Best Practices + Examples)

http://matteomanferdini.com/how-ios-view-controllers-communicate-with-each-other/

I want to pass some information from a child (or destination) view controller to a parent (or source) view controller. The above webpage explains very well how to do the job.

As quoted in the above webpage,

Always use a delegate to communicate information back to other controllers. Your content view controller should never need to know the class of the source view controller or any controllers it doesn’t create.

So I must not create any references of a parent view controller in a child view controller.