I started writing Swift extensions on my view controllers. So I have three files right now:
My header file, ViewController.h
:
@interface MyViewController : UIViewController
@end
My Obj-C implementation file, ViewController.m
:
@interface MyViewController () <UIScrollViewDelegate>
@property (strong, nonatomic) UIScrollView *scrollView;
@end
@implementation MyViewController
- (void)viewDidLoad {
[super viewDidLoad];
self.scrollView = [[UIScrollView alloc] init];
[self customiseScrollView]; //This is Swift method called from Obj-C file
}
@end
And finally, ViewController.swift
:
extension MyViewController {
func customiseScrollView() {
}
}
My question is, is it possible to access my Obj-C properties from my Swift implementation file? Every time I refer to it, I got an error:
Value of type 'MyViewController' has no member 'scrollView'
Bonus 1: Can someone also clarify if the Swift component can see what the .m is a delegate of as well. (To clarify, doing scrollView.delegate = self
in Swift is a compile error because the Swift file does not realise that the .m file is a UIScrollViewDelegate).
Bonus 2: Can Swift extension file call Obj-C methods that are declared from the .m counterpart?
Extensions can add new computed properties, but they can't add stored properties, or add property observers to existing properties.
Even when written without a single line of Objective-C code, every Swift app executes inside the Objective-C runtime, opening up a world of dynamic dispatch and associated runtime manipulation.
I think that you can't access private properties from extension. Your scrollView property is in .m file, not .h - which means it's private and it's not visible from extension file.
Solution: move
@property (strong, nonatomic) UIScrollView *scrollView;
to your header file.
You can access internal objc properties and methods if you declare the objc class extension in a separate header and include that header in the bridging header.
MyClass.h
@interface MyClass : NSObject
@property (nonatomic, copy, readonly) NSString *string;
@end
MyClass+Private.h
#import "MyClass.h"
@interface MyClass ()
@property (nonatomic, copy) NSString *string;
@end
MyClass.m
#import "MyClass+private.h"
@implementation MyClass
//...
@end
Project-Bridging-Header.h
#import "MyClass.h"
#import "MyClass+Private.h"
In Swift, private properties are not accessible from another file. This is the meaning of private
in Swift. For example:
file1.swift
class MyClass {
private var privateProperty: String = "Can't get to me from another file!"
}
extension MyClass: CustomStringConvertible {
var description: String {
return "I have a `var` that says: \(privateProperty)"
}
}
file2.swift
extension MyClass {
func cantGetToPrivateProperties() {
self.privateProperty // Value of type 'MyClass' has no memeber 'privateProperty'
}
}
A property declared in the implementation of an Objective-C class is a private property. As such, the property cannot be accessed from a Swift extension since this will be necessarily from a different (.swift
) file...
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With