49798


# 実現したいこと・問題点

Swift初心者です。  
表題の通り、他の.swiftファイルから直接、ViewController.swiftに関連付けされているUILabelのテキストを変更することはできないかと思い、後述のようなコードを書きました。

storyboard上にSliderとLabelを配置し、Sliderを変更した際の処理をLowPass.swift内に記述するというようにしています。

このまま実行するとビルドはされるのですが、Sliderの値を変更するとエラーが出てしまいます。  
エラーの原因は、LowPass.swiftのvcにnilが入ってしまっていることだとは分かるのですが、改善策が分かりません。

どなたかご教授頂けますでしょうか。

# 該当のソースコード

[code]

    //ViewController.swift
    import UIKit
    
    class ViewController: UIViewController {
    
        @IBOutlet weak var label: UILabel!
        @IBOutlet weak var slider: UISlider!
    
        // LowPass.swiftのインスタンス生成
        let lowPass = LowPass()
    
    
        override public func viewDidLoad() {
            super.viewDidLoad()
            // Do any additional setup after loading the view, typically from a nib.
        
            slider.maximumValue = Float(150)
            slider.minimumValue = 0
            slider.setValue(lowPass.R, animated: true)
            slider.addTarget(lowPass, action: #selector(lowPass.RChange(sender:)), for: UIControl.Event.valueChanged)
        
            label.text = String(lowPass.R)
        
        }
    
    
    }
    
[/code]

* * *
[code]

    //LowPass.swift
    import UIKit
    
    class LowPass: NSObject {
    
        weak var vc: ViewController!
    
        var R: Float = 30.0
    
        @objc func RChange(sender: UISlider){
            R = Float(sender.value)
            vc.label.text = String(R)
        }
    
    }
    
[/code]


CC BY-SA 4.0
2018-10-30T10:51:45.990
49797
2018-10-30T12:04:14.397
2020-06-17T08:14:45.997
-1
30140
question
swift ios
他のファイルからViewControllerのUILabelを変更したい


まず、`LowPass.swift`は

[code]

    weak var vc: ViewController!
    
[/code]

を、`vc`に「クラス外からアクセス出来る変数だよ」と明示的に宣言するため、

[code]

    public weak var vc: ViewController!
    
[/code]

としておいたほうがいいでしょう。  
これで、`nil`だった変数`vc`の中にクラス外から値を代入できるようになります

次に、`ViewController.swift`の中で、

[code]

    let lowPass = LowPass()
    
[/code]

としているところをを

[code]

    let lowPass = LowPass()
    lowPass.vc = self
    
[/code]

として、`LowPass`クラスのインスタンスを生成した後に一行追加します。  
これで、インスタンス変数`lowPass`の中で宣言したメンバー変数`vc`  
の中に`ViewController`の`self`つまりクラスのインスタンス自身を保持できるようになります。

これで、`vc`が`LowPass`クラスの初期化が終わるまでは`nil`ですが、コンストラクター(=`init`)が終了すると、`ViewController.swift`の`lowPass.vc
= self`が実行され、`nil`ではなくなりますので、それ以降は`vc`が`nil`で落ちることはなくなると思います。


CC BY-SA 4.0
2018-10-30T11:17:38.320
49798
2018-10-30T11:17:38.320
14745
49797
answer