diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index 2ee75eb97..df27defa6 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -227,6 +227,11 @@ const TextInput = createReactClass({
* @platform android
*/
autoGrow: PropTypes.bool,
+ /**
+ * Specifies whether fonts should scale to respect Text Size accessibility settings. The
+ * default is `true`.
+ */
+ allowFontScaling: PropTypes.bool,
/**
* If `false`, text is not editable. The default value is `true`.
*/
@@ -566,7 +571,11 @@ const TextInput = createReactClass({
*/
caretHidden: PropTypes.bool,
},
-
+ getDefaultProps(): Object {
+ return {
+ allowFontScaling: true,
+ };
+ },
/**
* `NativeMethodsMixin` will look for this when invoking `setNativeProps`. We
* make `this` look like an actual native component class.
@@ -704,7 +713,7 @@ const TextInput = createReactClass({
'Cannot specify both value and children.'
);
if (childCount >= 1) {
- children = {children};
+ children = {children};
}
if (props.inputView) {
children = [children, props.inputView];
diff --git a/Libraries/Text/RCTFontAttributes.h b/Libraries/Text/RCTFontAttributes.h
new file mode 100644
index 000000000..37b9954cd
--- /dev/null
+++ b/Libraries/Text/RCTFontAttributes.h
@@ -0,0 +1,31 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ * All rights reserved.
+ *
+ * This source code is licensed under the BSD-style license found in the
+ * LICENSE file in the root directory of this source tree. An additional grant
+ * of patent rights can be found in the PATENTS file in the same directory.
+ */
+
+#import
+
+#import "RCTFontAttributesDelegate.h"
+
+@class RCTAccessibilityManager;
+
+@interface RCTFontAttributes : NSObject
+
+@property (nonatomic, weak) id delegate;
+
+@property (readonly, nonatomic, strong) UIFont *font;
+
+@property (nonatomic, assign) BOOL allowFontScaling;
+@property (nonatomic, copy) NSString *fontFamily;
+@property (nonatomic, strong) NSNumber *fontSize;
+@property (nonatomic, assign) CGFloat fontSizeMultiplier;
+@property (nonatomic, copy) NSString *fontStyle;
+@property (nonatomic, copy) NSString *fontWeight;
+
+- (instancetype)initWithAccessibilityManager:(RCTAccessibilityManager *)accessibilityManager;
+
+@end
diff --git a/Libraries/Text/RCTFontAttributes.m b/Libraries/Text/RCTFontAttributes.m
new file mode 100644
index 000000000..3cb8da119
--- /dev/null
+++ b/Libraries/Text/RCTFontAttributes.m
@@ -0,0 +1,112 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ * All rights reserved.
+ *
+ * This source code is licensed under the BSD-style license found in the
+ * LICENSE file in the root directory of this source tree. An additional grant
+ * of patent rights can be found in the PATENTS file in the same directory.
+ */
+
+#import "RCTFontAttributes.h"
+
+#import
+#import
+#import
+#import
+
+@interface RCTFontAttributes ()
+{
+ RCTAccessibilityManager *_accessibilityManager;
+}
+
+@property (nonatomic, strong) UIFont *font;
+
+@end
+
+@implementation RCTFontAttributes
+
+- (instancetype)initWithAccessibilityManager:(RCTAccessibilityManager *)accessibilityManager
+{
+ RCTAssertParam(accessibilityManager);
+
+ if (self = [super init]) {
+ _accessibilityManager = accessibilityManager;
+ _fontSizeMultiplier = _accessibilityManager.multiplier;
+
+ [[NSNotificationCenter defaultCenter] addObserver:self
+ selector:@selector(contentSizeMultiplierDidChange)
+ name:RCTAccessibilityManagerDidUpdateMultiplierNotification
+ object:_accessibilityManager];
+
+ [self updateFont];
+ }
+ return self;
+}
+
+- (void)dealloc
+{
+ [[NSNotificationCenter defaultCenter] removeObserver:self];
+}
+
+- (void)contentSizeMultiplierDidChange
+{
+ self.fontSizeMultiplier = _accessibilityManager.multiplier;
+}
+
+- (void)setAllowFontScaling:(BOOL)allowFontScaling
+{
+ _allowFontScaling = allowFontScaling;
+ [self updateFont];
+}
+
+- (void)setFontFamily:(NSString *)fontFamily
+{
+ _fontFamily = fontFamily;
+ [self updateFont];
+}
+
+- (void)setFontSize:(NSNumber *)fontSize
+{
+ _fontSize = fontSize;
+ [self updateFont];
+}
+
+- (void)setFontSizeMultiplier:(CGFloat)fontSizeMultiplier
+{
+ _fontSizeMultiplier = fontSizeMultiplier;
+
+ if (_fontSizeMultiplier == 0) {
+ RCTLogError(@"fontSizeMultiplier value must be > zero.");
+ _fontSizeMultiplier = 1.0;
+ }
+
+ [self updateFont];
+}
+
+- (void)setFontStyle:(NSString *)fontStyle
+{
+ _fontStyle = fontStyle;
+ [self updateFont];
+}
+
+- (void)setFontWeight:(NSString *)fontWeight
+{
+ _fontWeight = fontWeight;
+ [self updateFont];
+}
+
+- (void)updateFont
+{
+ CGFloat scaleMultiplier = self.allowFontScaling ? self.fontSizeMultiplier : 1.0;
+ self.font = [RCTFont updateFont:nil
+ withFamily:self.fontFamily
+ size:self.fontSize
+ weight:self.fontWeight
+ style:self.fontStyle
+ variant:nil
+ scaleMultiplier:scaleMultiplier];
+
+ [self.delegate fontAttributesDidChangeWithFont:self.font];
+}
+
+@end
diff --git a/Libraries/Text/RCTFontAttributesDelegate.h b/Libraries/Text/RCTFontAttributesDelegate.h
new file mode 100644
index 000000000..6436c3c8c
--- /dev/null
+++ b/Libraries/Text/RCTFontAttributesDelegate.h
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ * All rights reserved.
+ *
+ * This source code is licensed under the BSD-style license found in the
+ * LICENSE file in the root directory of this source tree. An additional grant
+ * of patent rights can be found in the PATENTS file in the same directory.
+ */
+
+@protocol RCTFontAttributesDelegate
+
+- (void)fontAttributesDidChangeWithFont:(UIFont *)font;
+
+@end
diff --git a/Libraries/Text/RCTText.xcodeproj/project.pbxproj b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
index 9beaaaa51..4b8d30f39 100644
--- a/Libraries/Text/RCTText.xcodeproj/project.pbxproj
+++ b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
@@ -43,6 +43,7 @@
59F60E921E661BDD0081153B /* RCTShadowTextField.m in Sources */ = {isa = PBXBuildFile; fileRef = 59F60E8E1E661BDD0081153B /* RCTShadowTextField.m */; };
59F60E931E661BDD0081153B /* RCTShadowTextView.m in Sources */ = {isa = PBXBuildFile; fileRef = 59F60E901E661BDD0081153B /* RCTShadowTextView.m */; };
59F60E941E661BDD0081153B /* RCTShadowTextView.m in Sources */ = {isa = PBXBuildFile; fileRef = 59F60E901E661BDD0081153B /* RCTShadowTextView.m */; };
+ A85C829A1F742AA20036C019 /* RCTFontAttributes.m in Sources */ = {isa = PBXBuildFile; fileRef = A85C82991F742AA20036C019 /* RCTFontAttributes.m */; };
AF3225F91DE5574F00D3E7E7 /* RCTConvert+Text.m in Sources */ = {isa = PBXBuildFile; fileRef = AF3225F81DE5574F00D3E7E7 /* RCTConvert+Text.m */; };
AF3225FA1DE5574F00D3E7E7 /* RCTConvert+Text.m in Sources */ = {isa = PBXBuildFile; fileRef = AF3225F81DE5574F00D3E7E7 /* RCTConvert+Text.m */; };
/* End PBXBuildFile section */
@@ -111,6 +112,9 @@
59F60E8E1E661BDD0081153B /* RCTShadowTextField.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTShadowTextField.m; sourceTree = ""; };
59F60E8F1E661BDD0081153B /* RCTShadowTextView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTShadowTextView.h; sourceTree = ""; };
59F60E901E661BDD0081153B /* RCTShadowTextView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTShadowTextView.m; sourceTree = ""; };
+ A85C82981F742AA20036C019 /* RCTFontAttributes.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTFontAttributes.h; sourceTree = ""; };
+ A85C82991F742AA20036C019 /* RCTFontAttributes.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTFontAttributes.m; sourceTree = ""; };
+ A85C82BA1F742D8F0036C019 /* RCTFontAttributesDelegate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTFontAttributesDelegate.h; sourceTree = ""; };
AF3225F71DE5574F00D3E7E7 /* RCTConvert+Text.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "RCTConvert+Text.h"; sourceTree = ""; };
AF3225F81DE5574F00D3E7E7 /* RCTConvert+Text.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "RCTConvert+Text.m"; sourceTree = ""; };
/* End PBXFileReference section */
@@ -126,6 +130,9 @@
599DF25D1F0304B30079B53E /* RCTBackedTextInputViewProtocol.h */,
AF3225F71DE5574F00D3E7E7 /* RCTConvert+Text.h */,
AF3225F81DE5574F00D3E7E7 /* RCTConvert+Text.m */,
+ A85C82981F742AA20036C019 /* RCTFontAttributes.h */,
+ A85C82991F742AA20036C019 /* RCTFontAttributes.m */,
+ A85C82BA1F742D8F0036C019 /* RCTFontAttributesDelegate.h */,
58B511C61A9E6C5C00147676 /* RCTRawTextManager.h */,
58B511C71A9E6C5C00147676 /* RCTRawTextManager.m */,
58B511C81A9E6C5C00147676 /* RCTShadowRawText.h */,
@@ -278,6 +285,7 @@
1362F1001B4D51F400E06D8C /* RCTTextField.m in Sources */,
59AF89AA1EDCBCC700F004B1 /* RCTUITextField.m in Sources */,
598F41261F145D4900B8495B /* RCTBackedTextInputDelegateAdapter.m in Sources */,
+ A85C829A1F742AA20036C019 /* RCTFontAttributes.m in Sources */,
58B512161A9E6EFF00147676 /* RCTText.m in Sources */,
599DF2641F03076D0079B53E /* RCTTextInput.m in Sources */,
1362F1011B4D51F400E06D8C /* RCTTextFieldManager.m in Sources */,
diff --git a/Libraries/Text/RCTTextField.m b/Libraries/Text/RCTTextField.m
index 567ab31a9..e6addcaf1 100644
--- a/Libraries/Text/RCTTextField.m
+++ b/Libraries/Text/RCTTextField.m
@@ -12,6 +12,7 @@
#import
#import
#import
+#import
#import
#import
#import
@@ -40,6 +41,7 @@
_backedTextInput = [[RCTUITextField alloc] initWithFrame:self.bounds];
_backedTextInput.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
_backedTextInput.textInputDelegate = self;
+ _backedTextInput.font = self.fontAttributes.font;
[self addSubview:_backedTextInput];
}
diff --git a/Libraries/Text/RCTTextFieldManager.m b/Libraries/Text/RCTTextFieldManager.m
index f43e60765..7e0d1dc24 100644
--- a/Libraries/Text/RCTTextFieldManager.m
+++ b/Libraries/Text/RCTTextFieldManager.m
@@ -35,11 +35,16 @@ RCT_EXPORT_MODULE()
#pragma mark - Unified properties
+RCT_REMAP_VIEW_PROPERTY(allowFontScaling, fontAttributes.allowFontScaling, BOOL)
RCT_REMAP_VIEW_PROPERTY(autoCapitalize, backedTextInputView.autocapitalizationType, UITextAutocapitalizationType)
RCT_REMAP_VIEW_PROPERTY(autoCorrect, backedTextInputView.autocorrectionType, UITextAutocorrectionType)
RCT_REMAP_VIEW_PROPERTY(color, backedTextInputView.textColor, UIColor)
RCT_REMAP_VIEW_PROPERTY(editable, backedTextInputView.editable, BOOL)
RCT_REMAP_VIEW_PROPERTY(enablesReturnKeyAutomatically, backedTextInputView.enablesReturnKeyAutomatically, BOOL)
+RCT_REMAP_VIEW_PROPERTY(fontSize, fontAttributes.fontSize, NSNumber)
+RCT_REMAP_VIEW_PROPERTY(fontWeight, fontAttributes.fontWeight, NSString)
+RCT_REMAP_VIEW_PROPERTY(fontStyle, fontAttributes.fontStyle, NSString)
+RCT_REMAP_VIEW_PROPERTY(fontFamily, fontAttributes.fontFamily, NSString)
RCT_REMAP_VIEW_PROPERTY(keyboardAppearance, backedTextInputView.keyboardAppearance, UIKeyboardAppearance)
RCT_REMAP_VIEW_PROPERTY(keyboardType, backedTextInputView.keyboardType, UIKeyboardType)
RCT_REMAP_VIEW_PROPERTY(placeholder, backedTextInputView.placeholder, NSString)
@@ -61,22 +66,7 @@ RCT_EXPORT_VIEW_PROPERTY(text, NSString)
RCT_REMAP_VIEW_PROPERTY(caretHidden, backedTextInputView.caretHidden, BOOL)
RCT_REMAP_VIEW_PROPERTY(clearButtonMode, backedTextInputView.clearButtonMode, UITextFieldViewMode)
RCT_EXPORT_VIEW_PROPERTY(onSelectionChange, RCTDirectEventBlock)
-RCT_CUSTOM_VIEW_PROPERTY(fontSize, NSNumber, RCTTextField)
-{
- view.backedTextInputView.font = [RCTFont updateFont:view.backedTextInputView.font withSize:json ?: @(defaultView.backedTextInputView.font.pointSize)];
-}
-RCT_CUSTOM_VIEW_PROPERTY(fontWeight, NSString, __unused RCTTextField)
-{
- view.backedTextInputView.font = [RCTFont updateFont:view.backedTextInputView.font withWeight:json]; // defaults to normal
-}
-RCT_CUSTOM_VIEW_PROPERTY(fontStyle, NSString, __unused RCTTextField)
-{
- view.backedTextInputView.font = [RCTFont updateFont:view.backedTextInputView.font withStyle:json]; // defaults to normal
-}
-RCT_CUSTOM_VIEW_PROPERTY(fontFamily, NSString, RCTTextField)
-{
- view.backedTextInputView.font = [RCTFont updateFont:view.backedTextInputView.font withFamily:json ?: defaultView.backedTextInputView.font.familyName];
-}
+
RCT_EXPORT_VIEW_PROPERTY(mostRecentEventCount, NSInteger)
- (RCTViewManagerUIBlock)uiBlockToAmendWithShadowView:(RCTShadowView *)shadowView
diff --git a/Libraries/Text/RCTTextInput.h b/Libraries/Text/RCTTextInput.h
index 5531fca4e..47fcf4263 100644
--- a/Libraries/Text/RCTTextInput.h
+++ b/Libraries/Text/RCTTextInput.h
@@ -12,12 +12,14 @@
#import
#import "RCTBackedTextInputViewProtocol.h"
+#import "RCTFontAttributes.h"
+#import "RCTFontAttributesDelegate.h"
@class RCTBridge;
@class RCTEventDispatcher;
@class RCTTextSelection;
-@interface RCTTextInput : RCTView {
+@interface RCTTextInput : RCTView {
@protected
RCTBridge *_bridge;
RCTEventDispatcher *_eventDispatcher;
@@ -41,12 +43,16 @@
@property (nonatomic, copy) RCTDirectEventBlock onContentSizeChange;
@property (nonatomic, copy) RCTDirectEventBlock onSelectionChange;
+@property (nonatomic, readonly, strong) RCTFontAttributes *fontAttributes;
+
@property (nonatomic, assign) NSInteger mostRecentEventCount;
@property (nonatomic, assign) BOOL blurOnSubmit;
@property (nonatomic, assign) BOOL selectTextOnFocus;
@property (nonatomic, assign) BOOL clearTextOnFocus;
@property (nonatomic, copy) RCTTextSelection *selection;
+- (void)setFont:(UIFont *)font;
+
- (void)invalidateContentSize;
// Temporary exposure of particial `RCTBackedTextInputDelegate` support.
diff --git a/Libraries/Text/RCTTextInput.m b/Libraries/Text/RCTTextInput.m
index ed7bade62..d949437a4 100644
--- a/Libraries/Text/RCTTextInput.m
+++ b/Libraries/Text/RCTTextInput.m
@@ -9,11 +9,12 @@
#import "RCTTextInput.h"
+#import
#import
#import
#import
-#import
#import
+#import
#import
#import "RCTTextSelection.h"
@@ -29,6 +30,8 @@
if (self = [super initWithFrame:CGRectZero]) {
_bridge = bridge;
_eventDispatcher = bridge.eventDispatcher;
+ _fontAttributes = [[RCTFontAttributes alloc] initWithAccessibilityManager:bridge.accessibilityManager];
+ _fontAttributes.delegate = self;
}
return self;
@@ -44,6 +47,17 @@ RCT_NOT_IMPLEMENTED(- (instancetype)initWithFrame:(CGRect)frame)
return nil;
}
+- (void)setFont:(UIFont *)font
+{
+ self.backedTextInputView.font = font;
+ [self invalidateContentSize];
+}
+
+- (void)fontAttributesDidChangeWithFont:(UIFont *)font
+{
+ self.font = font;
+}
+
#pragma mark - Properties
- (void)setReactPaddingInsets:(UIEdgeInsets)reactPaddingInsets
diff --git a/Libraries/Text/RCTTextView.m b/Libraries/Text/RCTTextView.m
index 3342e445e..f3f19067c 100644
--- a/Libraries/Text/RCTTextView.m
+++ b/Libraries/Text/RCTTextView.m
@@ -11,6 +11,7 @@
#import
#import
+#import
#import
#import
#import
@@ -54,8 +55,8 @@
_backedTextInput.scrollsToTop = NO;
#endif
_backedTextInput.scrollEnabled = YES;
-
_backedTextInput.textInputDelegate = self;
+ _backedTextInput.font = self.fontAttributes.font;
[self addSubview:_backedTextInput];
}
diff --git a/Libraries/Text/RCTTextViewManager.m b/Libraries/Text/RCTTextViewManager.m
index 5f0fa6de9..814f2070f 100644
--- a/Libraries/Text/RCTTextViewManager.m
+++ b/Libraries/Text/RCTTextViewManager.m
@@ -35,11 +35,16 @@ RCT_EXPORT_MODULE()
#pragma mark - Unified properties
+RCT_REMAP_VIEW_PROPERTY(allowFontScaling, fontAttributes.allowFontScaling, BOOL)
RCT_REMAP_VIEW_PROPERTY(autoCapitalize, backedTextInputView.autocapitalizationType, UITextAutocapitalizationType)
RCT_REMAP_VIEW_PROPERTY(autoCorrect, backedTextInputView.autocorrectionType, UITextAutocorrectionType)
RCT_REMAP_VIEW_PROPERTY(color, backedTextInputView.textColor, UIColor)
RCT_REMAP_VIEW_PROPERTY(editable, backedTextInputView.editable, BOOL)
RCT_REMAP_VIEW_PROPERTY(enablesReturnKeyAutomatically, backedTextInputView.enablesReturnKeyAutomatically, BOOL)
+RCT_REMAP_VIEW_PROPERTY(fontSize, fontAttributes.fontSize, NSNumber)
+RCT_REMAP_VIEW_PROPERTY(fontWeight, fontAttributes.fontWeight, NSString)
+RCT_REMAP_VIEW_PROPERTY(fontStyle, fontAttributes.fontStyle, NSString)
+RCT_REMAP_VIEW_PROPERTY(fontFamily, fontAttributes.fontFamily, NSString)
RCT_REMAP_VIEW_PROPERTY(keyboardAppearance, backedTextInputView.keyboardAppearance, UIKeyboardAppearance)
RCT_REMAP_VIEW_PROPERTY(keyboardType, backedTextInputView.keyboardType, UIKeyboardType)
RCT_REMAP_VIEW_PROPERTY(placeholder, backedTextInputView.placeholder, NSString)
@@ -64,22 +69,6 @@ RCT_EXPORT_VIEW_PROPERTY(onSelectionChange, RCTDirectEventBlock)
RCT_EXPORT_VIEW_PROPERTY(onScroll, RCTDirectEventBlock)
RCT_EXPORT_VIEW_PROPERTY(onTextInput, RCTDirectEventBlock)
-RCT_CUSTOM_VIEW_PROPERTY(fontSize, NSNumber, RCTTextView)
-{
- view.font = [RCTFont updateFont:view.font withSize:json ?: @(defaultView.font.pointSize)];
-}
-RCT_CUSTOM_VIEW_PROPERTY(fontWeight, NSString, __unused RCTTextView)
-{
- view.font = [RCTFont updateFont:view.font withWeight:json]; // defaults to normal
-}
-RCT_CUSTOM_VIEW_PROPERTY(fontStyle, NSString, __unused RCTTextView)
-{
- view.font = [RCTFont updateFont:view.font withStyle:json]; // defaults to normal
-}
-RCT_CUSTOM_VIEW_PROPERTY(fontFamily, NSString, RCTTextView)
-{
- view.font = [RCTFont updateFont:view.font withFamily:json ?: defaultView.font.familyName];
-}
RCT_EXPORT_VIEW_PROPERTY(mostRecentEventCount, NSInteger)
#if !TARGET_OS_TV