텍스트를 변경할 때마다 UITextView를 맨 위로 스크롤하려면 어떻게해야합니까?
OK, 나는 몇 가지 문제가 있어요 UITextView
. 문제는 다음과 같습니다.
나는 UITextView
. 그런 다음 사용자는 두 번 클릭하여 항목을 선택합니다. 그런 다음 UITextView
(위와 같이 프로그래밍 방식으로) 텍스트를 변경하고 UITextView
커서가있는 페이지 하단으로 스크롤합니다.
그러나 그것은 사용자가 클릭 한 곳이 아닙니다. UITextView
사용자가 클릭 한 위치에 관계없이 항상 맨 아래로 스크롤됩니다 .
그래서 여기에 내 질문이 UITextView
있습니다. 텍스트를 변경할 때마다 어떻게 강제로 맨 위로 스크롤합니까? 나는 해봤 contentOffset
하고 scrollRangeToVisible
. 둘 다 작동하지 않습니다.
모든 제안을 주시면 감사하겠습니다.
UITextView*note;
[note setContentOffset:CGPointZero animated:YES];
이것은 나를 위해 그것을합니다.
Swift 버전 (Xcode 9.3에서 iOS 11이 설치된 Swift 4.1) :
note.setContentOffset(.zero, animated: true)
사람이 아이폰 OS 8에서이 문제가 있다면, 그건 바로 설정을 발견 UITextView's
한 후 호출, 텍스트 속성을 scrollRangeToVisible
로 NSRange
와 location:0
, length:0
,했다. 내 텍스트보기는 편집 할 수 없었고 선택 가능과 선택 불가능을 테스트했습니다 (두 설정 모두 결과에 영향을주지 않음). 다음은 Swift의 예입니다.
myTextView.text = "Text that is long enough to scroll"
myTextView.scrollRangeToVisible(NSRange(location:0, length:0))
그리고 여기 내 해결책이 있습니다 ...
override func viewDidLoad() {
textView.scrollEnabled = false
textView.text = "your text"
}
override func viewDidAppear(animated: Bool) {
textView.scrollEnabled = true
}
부름
scrollRangeToVisible(NSMakeRange(0, 0))
작동하지만 전화
override func viewDidAppear(animated: Bool)
HTML에서 편집 할 수없는 텍스트보기로 attributeString을 사용하고있었습니다. 콘텐츠 오프셋 설정도 나에게 효과적이지 않았습니다. 이것은 나를 위해 일했습니다 : 스크롤 활성화를 비활성화하고 텍스트를 설정 한 다음 스크롤을 다시 활성화하십시오.
[yourTextView setScrollEnabled:NO];
yourTextView.text = yourtext;
[yourTextView setScrollEnabled:YES];
이러한 솔루션 중 어느 것도 저에게 효과가 없었고 솔루션을 결합하는 데 너무 많은 시간을 낭비했기 때문에 마침내 해결되었습니다.
override func viewWillAppear(animated: Bool) {
dispatch_async(dispatch_get_main_queue(), {
let desiredOffset = CGPoint(x: 0, y: -self.textView.contentInset.top)
self.textView.setContentOffset(desiredOffset, animated: false)
})
}
이 컨트롤의 기본 동작이 아니라는 것은 정말 어리석은 일입니다.
이 정보가 다른 사람에게 도움이되기를 바랍니다.
질문을 이해했는지 확실하지 않지만 단순히보기를 맨 위로 스크롤하려고합니까? 만약 그렇다면
[textview scrollRectToVisible:CGRectMake(0,0,1,1) animated:YES];
iOS 10 및 Swift 3의 경우 다음을 수행했습니다.
override func viewDidLoad() {
super.viewDidLoad()
textview.isScrollEnabled = false
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
textView.isScrollEnabled = true
}
나를 위해 일했지만 최신 버전의 Swift 및 iOS에 문제가 있는지 확실하지 않습니다.
사용자가 스크롤 애니메이션을 경험하지 않고 textview가 올바르게 표시되도록 업데이트 된 답변이 있습니다.
override func viewWillAppear(animated: Bool) {
dispatch_async(dispatch_get_main_queue(), {
self.introductionText.scrollRangeToVisible(NSMakeRange(0, 0))
})
이것은 화면에 나타나기 전에 textView가 맨 위로 스크롤되도록 iOS 9 Release에서 작동 한 방식입니다.
- (void)viewDidLoad
{
[super viewDidLoad];
textView.scrollEnabled = NO;
}
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
textView.scrollEnabled = YES;
}
그렇게 했어요
스위프트 4 :
extension UITextView {
override open func draw(_ rect: CGRect)
{
super.draw(rect)
setContentOffset(CGPoint.zero, animated: false)
}
}
커서를 텍스트의 맨 위로 이동하려면 이것을 시도하십시오.
NSRange r = {0,0};
[yourTextView setSelectedRange:r];
어떻게되는지보세요. 모든 이벤트가 시작되었거나 수행중인 모든 작업이 완료된 후에 이것을 호출해야합니다.
이전 답변을 결합하면 이제 작동합니다.
talePageText.scrollEnabled = false
talePageText.textColor = UIColor.blackColor()
talePageText.font = UIFont(name: "Bradley Hand", size: 24.0)
talePageText.contentOffset = CGPointZero
talePageText.scrollRangeToVisible(NSRange(location:0, length:0))
talePageText.scrollEnabled = true
[txtView setContentOffset:CGPointMake(0.0, 0.0) animated:YES];
이 코드 줄은 저에게 효과적입니다.
내 문제는 view가 나타날 때 textView를 맨 위로 스크롤하도록 설정하는 것입니다. iOS 10.3.2 및 Swift 3.
해결책 1 :
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
// It doesn't work. Very strange.
self.textView.setContentOffset(CGPoint.zero, animated: false)
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
// It works, but with an animation effection.
self.textView.setContentOffset(CGPoint.zero, animated: false)
}
해결책 2 :
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
// It works.
self.textView.contentOffset = CGPoint.zero
}
Swift 2 답변 :
textView.scrollEnabled = false
/* Set the content of your textView here */
textView.scrollEnabled = true
이렇게하면 설정 후 textView가 텍스트 끝으로 스크롤되는 것을 방지 할 수 있습니다.
Swift 3 :
viewWillLayoutSubviews 는 변경할 수있는 곳입니다. viewWillAppear도 작동해야하지만 논리적으로 레이아웃 은 viewWillLayoutSubviews 에서 수행되어야합니다 .
메서드와 관련하여 scrollRangeToVisible 과 setContentOffset 이 모두 작동합니다. 그러나 setContentOffset을 사용하면 애니메이션을 끄거나 켤 수 있습니다.
UITextView 이름이 yourUITextView 라고 가정합니다 . 코드는 다음과 같습니다.
// Connects to the TextView in the interface builder.
@IBOutlet weak var yourUITextView: UITextView!
/// Overrides the viewWillLayoutSubviews of the super class.
override func viewWillLayoutSubviews() {
// Ensures the super class is happy.
super.viewWillLayoutSubviews()
// Option 1:
// Scrolls to a range of text, (0,0) in this very case, animated.
yourUITextView.scrollRangeToVisible(NSRange(location: 0, length: 0))
// Option 2:
// Sets the offset directly, optional animation.
yourUITextView.setContentOffset(CGPoint(x: 0, y: 0), animated: false)
}
이것은 나를 위해 일했습니다. RyanTCB의 답변을 기반으로하지만 동일한 솔루션의 Objective-C 변형입니다.
- (void) viewWillAppear:(BOOL)animated {
// For some reason the text view, which is a scroll view, did scroll to the end of the text which seems to hide the imprint etc at the beginning of the text.
// On some devices it is not obvious that there is more text when the user scrolls up.
// Therefore we need to scroll textView to the top.
[self.textView scrollRangeToVisible:NSMakeRange(0, 0)];
}
-(void) viewDidAppear:(BOOL)animated{
[mytextView scrollRangeToVisible:NSMakeRange(0,0)];}
- (void)viewWillAppear:(BOOL)animated{
[mytextView scrollRangeToVisible:NSMakeRange(0,0)];}
ViewWillappear
will do it instantly before user can notice, butViewDidDisappear
section will animate it lazily.[mytextView setContentOffset:CGPointZero animated:YES];
does NOT work sometimes(I don't know why), so use scrollrangetovisible rather.
Problem solved: iOS = 10.2 Swift 3 UITextView
I just used the following line:
displayText.contentOffset.y = 0
just you can use this code
override func viewDidLayoutSubviews() {
super.viewDidLayoutSubviews()
textView.scrollRangeToVisible(NSMakeRange(0, 0))
}
This worked for me
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
DispatchQueue.main.async {
self.textView.scrollRangeToVisible(NSRange(location: 0, length: 0))
}
}
[self.textView scrollRectToVisible:CGRectMake(0, 0, 320, self.textView.frame.size.height) animated:NO];
-(void)viewWillLayoutSubviews{
[super viewWillLayoutSubviews];
[textview setContentOffset:CGPointZero animated:NO];
}
I had the problem, but in my case textview is the subview of some custom view and added it to ViewController. None of the solution worked for me. To solve the problem added 0.1 sec delay and then enabled scroll. It worked for me.
textView.isScrollEnabled = false
..
textView.text = // set your text here
let dispatchTime = DispatchTime.now() + 0.1
DispatchQueue.main.asyncAfter(deadline: dispatchTime) {
self.textView.isScrollEnabled = true
}
For me fine works this code:
textView.attributedText = newText //or textView.text = ...
//this part of code scrolls to top
textView.contentOffset.y = -64
textView.scrollEnabled = false
textView.layoutIfNeeded() //if don't work, try to delete this line
textView.scrollEnabled = true
For scroll to exact position and show it on top of screen I use this code:
var scrollToLocation = 50 //<needed position>
textView.contentOffset.y = textView.contentSize.height
textView.scrollRangeToVisible(NSRange.init(location: scrollToLocation, length: 1))
Setting contentOffset.y scrolls to the end of text, and then scrollRangeToVisible scrolls up to value of scrollToLocation. Thereby, needed position appears in first line of scrollView.
For me in iOS 9 it stopped to work for me with attributed string with method scrollRangeToVisible (the 1 row was with bold font, other rows were with regular font)
So I had to use:
textViewMain.attributedText = attributedString
textViewMain.scrollRangeToVisible(NSRange(location:0, length:0))
delay(0.0, closure: {
self.textViewMain.scrollRectToVisible(CGRectMake(0, 0, 10, 10), animated: false)
})
where delay is:
func delay(delay:Double, closure:()->Void) {
dispatch_after(
dispatch_time(
DISPATCH_TIME_NOW,
Int64(delay * Double(NSEC_PER_SEC))
),
dispatch_get_main_queue(), closure)
}
Try to use this 2 lines solution:
view.layoutIfNeeded()
textView.contentOffset = CGPointMake(textView.contentInset.left, textView.contentInset.top)
Here are my codes. It works fine.
class MyViewController: ...
{
private offsetY: CGFloat = 0
@IBOutlet weak var textView: UITextView!
...
override viewWillAppear(...)
{
...
offsetY = self.textView.contentOffset.y
...
}
...
func refreshView() {
let offSetY = textView.contentOffset.y
self.textView.setContentOffset(CGPoint(x:0, y:0), animated: true)
DispatchQueue.main.asyncAfter(deadline: .now() + 0.3) {
[unowned self] in
self.textView.setContentOffset(CGPoint(x:0, y:self.offSetY),
animated: true)
self.textView.setNeedsDisplay()
}
}
Swift 3 version of drew_s answer earlier, which is the only thing that worked for me after trying most of the other answers.
override func viewWillAppear(_ animated: Bool) {
DispatchQueue.main.async{
let desiredOffset = CGPoint(x: 0, y: -self.person_description.contentInset.top)
self.person_description.setContentOffset(desiredOffset, animated: false)
}
}
This was a cut and paste of working code. Replace person_description with your textview variable.
'Programming' 카테고리의 다른 글
Android TextView에서 HTML 목록 태그가 작동하지 않습니다. (0) | 2020.08.25 |
---|---|
세 번째 변수를 사용하지 않고 두 변수 값 바꾸기셸에서 가비지 수집을 어떻게 강제합니까? (0) | 2020.08.25 |
Java에서 String []을 쉼표로 구분 된 문자열로 변환 (0) | 2020.08.25 |
단일 파일을 사용한 Python 로깅 (함수 이름, 파일 이름, 줄 번호) (0) | 2020.08.25 |
JQuery $ .scrollTo () 함수를 사용하여 창을 스크롤하는 방법 (0) | 2020.08.25 |