iMessage 扩展:子视图控制器中的 UITextView,滚动行为有多个问题
iMessage Extension: UITextView in Child View Controller, scrolling behaviour has multiple issues
我在 iMessage 扩展中有一个非常基本的视图控制器。 (当然是扩展视图)。我知道您不能在精简视图中使用键盘输入...
UITextView 被限制在其上方和下方的元素中。它有一个设定的高度和宽度。约束都井井有条,没有被打破。
界面生成器中文本视图的所有选项都保留为默认值。
UITextView 出现以下问题:
当我开始编辑时,光标几乎看不见。 (在场地的底部,垂直切断的一半)。
键入第一个字母会将光标置于文本视图的垂直中心。
换行,然后输入一个字符,光标再次向下。
然后在此之后键入后续字符将使光标再次回到垂直中心。并且每隔一个字符再次将整个文本视图滚动到底部。所以每次击键都会出现这种奇怪的上下弹跳行为。
当我滚动时,右侧的滚动条视觉提示没有反映文本视图的正确高度。 (滚动条只下降到文本视图高度的一半。)
我希望 UITextView 默认像这样工作:
激活和编辑时,光标应移至文本视图的顶部。
在换行后键入键时,文本视图不应跳转。
垂直滚动条指示器应显示文本字段的整个范围,而不是一半。
因此,显然文本视图中的内部滚动视图在确定事物的大小方面存在问题。
有谁知道,如果这是 iMessage 特有的问题,或者是否有人在 iMessage 之外也遇到过这个问题,以及如何解决?
我的IB约束(倒数第二个视图是文本视图):
问题视频演示:
https://youtu.be/1bkvHnkXLWM
更新:我正在使用子视图控制器将我的视图控制器嵌入到根控制器中。我尝试了一个空白的 Hello World 应用程序,默认情况下 UITextView 正常工作。因此,这个问题与我嵌入子视图控制器的方式有关。
这是我用来嵌入我的子视图控制器的代码:
- (void)showViewController:(UIViewController*)vcToShow isPop:(BOOL)isPop
{
NSLog(@"Presenting Controller: %@", vcToShow);
[self.activeVC willMoveToParentViewController:nil];
[self addChildViewController:vcToShow];
vcToShow.view.translatesAutoresizingMaskIntoConstraints = NO;
vcToShow.view.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
[self.rootView addControls:@[vcToShow.view]
align:VerticalAlignStretchToFullHeight];
UIViewController* currentVC = self.activeVC;
self.activeVC = vcToShow;
vcToShow.view.alpha = 0.0f;
[self transitionFromViewController:currentVC
toViewController:vcToShow
duration:0.3
options:UIViewAnimationOptionTransitionNone
animations:^{
vcToShow.view.alpha = 1.0f;
}
completion:^(BOOL finished) {
[currentVC removeFromParentViewController];
[vcToShow didMoveToParentViewController:self];
[self updateScreenState];
if (isPop) {
[self removeReferenceToController:currentVC];
}
}];
}
我有办法。
我没有使用 Interface Builder 来放置我的 UITextView,而是使用我自己的编程约束生成方法来创建和放置 UITextView,仅在 ViewDidAppear 之后。
我怀疑在界面生成器呈现子视图 VC 时,它没有填充 UITextView 的内部滚动视图所需的所有内容。因此,滚动视图使用错误的维度值进行了初始化,因此会在任何与滚动相关的内容上出现故障。在以编程方式(在 Child VC 中)完成 viewDidAppear 中的所有操作后,文本视图现在可以正确滚动,并且光标始终位于开头,按预期工作。
更新码:
将 UITextView 完全从界面生成器中移除。
以编程方式添加(从 viewDidAppear 调用):
self.textView = [[UITextView alloc] init];
self.textView.translatesAutoresizingMaskIntoConstraints = NO;
CGFloat topPadding = self.instructionLabel.frame.origin.y + self.instructionLabel.frame.size.height + TEXT_VIEW_TOP_PADDING;
// This custom method generates Visual Constraint format for me
// so i don't have to write manual individual constraint syntax.
[self.rootView addControls:@[self.textView]
align:VerticalAlignTop
withHeight:TEXT_VIEW_HEIGHT
verticalPadding: 0
horizontalPadding: 20
topPadding: topPadding];
我在 iMessage 扩展中有一个非常基本的视图控制器。 (当然是扩展视图)。我知道您不能在精简视图中使用键盘输入...
UITextView 被限制在其上方和下方的元素中。它有一个设定的高度和宽度。约束都井井有条,没有被打破。
界面生成器中文本视图的所有选项都保留为默认值。
UITextView 出现以下问题:
当我开始编辑时,光标几乎看不见。 (在场地的底部,垂直切断的一半)。
键入第一个字母会将光标置于文本视图的垂直中心。
换行,然后输入一个字符,光标再次向下。
然后在此之后键入后续字符将使光标再次回到垂直中心。并且每隔一个字符再次将整个文本视图滚动到底部。所以每次击键都会出现这种奇怪的上下弹跳行为。
当我滚动时,右侧的滚动条视觉提示没有反映文本视图的正确高度。 (滚动条只下降到文本视图高度的一半。)
我希望 UITextView 默认像这样工作:
激活和编辑时,光标应移至文本视图的顶部。
在换行后键入键时,文本视图不应跳转。
垂直滚动条指示器应显示文本字段的整个范围,而不是一半。
因此,显然文本视图中的内部滚动视图在确定事物的大小方面存在问题。
有谁知道,如果这是 iMessage 特有的问题,或者是否有人在 iMessage 之外也遇到过这个问题,以及如何解决?
我的IB约束(倒数第二个视图是文本视图):
问题视频演示: https://youtu.be/1bkvHnkXLWM
更新:我正在使用子视图控制器将我的视图控制器嵌入到根控制器中。我尝试了一个空白的 Hello World 应用程序,默认情况下 UITextView 正常工作。因此,这个问题与我嵌入子视图控制器的方式有关。
这是我用来嵌入我的子视图控制器的代码:
- (void)showViewController:(UIViewController*)vcToShow isPop:(BOOL)isPop
{
NSLog(@"Presenting Controller: %@", vcToShow);
[self.activeVC willMoveToParentViewController:nil];
[self addChildViewController:vcToShow];
vcToShow.view.translatesAutoresizingMaskIntoConstraints = NO;
vcToShow.view.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
[self.rootView addControls:@[vcToShow.view]
align:VerticalAlignStretchToFullHeight];
UIViewController* currentVC = self.activeVC;
self.activeVC = vcToShow;
vcToShow.view.alpha = 0.0f;
[self transitionFromViewController:currentVC
toViewController:vcToShow
duration:0.3
options:UIViewAnimationOptionTransitionNone
animations:^{
vcToShow.view.alpha = 1.0f;
}
completion:^(BOOL finished) {
[currentVC removeFromParentViewController];
[vcToShow didMoveToParentViewController:self];
[self updateScreenState];
if (isPop) {
[self removeReferenceToController:currentVC];
}
}];
}
我有办法。
我没有使用 Interface Builder 来放置我的 UITextView,而是使用我自己的编程约束生成方法来创建和放置 UITextView,仅在 ViewDidAppear 之后。
我怀疑在界面生成器呈现子视图 VC 时,它没有填充 UITextView 的内部滚动视图所需的所有内容。因此,滚动视图使用错误的维度值进行了初始化,因此会在任何与滚动相关的内容上出现故障。在以编程方式(在 Child VC 中)完成 viewDidAppear 中的所有操作后,文本视图现在可以正确滚动,并且光标始终位于开头,按预期工作。
更新码:
将 UITextView 完全从界面生成器中移除。
以编程方式添加(从 viewDidAppear 调用):
self.textView = [[UITextView alloc] init]; self.textView.translatesAutoresizingMaskIntoConstraints = NO; CGFloat topPadding = self.instructionLabel.frame.origin.y + self.instructionLabel.frame.size.height + TEXT_VIEW_TOP_PADDING; // This custom method generates Visual Constraint format for me // so i don't have to write manual individual constraint syntax. [self.rootView addControls:@[self.textView] align:VerticalAlignTop withHeight:TEXT_VIEW_HEIGHT verticalPadding: 0 horizontalPadding: 20 topPadding: topPadding];