2012-04-17 2 views
50

내 앱에서 간단한 슬라이드 쇼보기를 만들고 있습니다. 내 UIPageControl을 UIScrollView에 연결하고 싶습니다. 너무 어렵지는 않지만 어디서나 간단한 솔루션을 찾을 수 없었습니다. 아래는 제 코드입니다.프로그래밍 방식으로 UIPageControl을 UIScrollView에 연결하기

HelpViewController.h

#import <UIKit/UIKit.h> 

@interface HelpViewController : UIViewController{ 
} 
@end 

#import "HelpViewController.h" 

@interface HelpViewController() 

@end 

@implementation HelpViewController 

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil 
{ 
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil]; 
    if (self) { 
     // Custom initialization 
    } 
    return self; 
} 

- (void)viewDidLoad 
{ 
    [super viewDidLoad]; 
    CGRect scrollViewFrame = CGRectMake(0, 62, 320, 404); 
    UIScrollView *scrollView = [[UIScrollView alloc] initWithFrame:scrollViewFrame]; 
    [self.view addSubview:scrollView]; 
    CGSize scrollViewContentSize = CGSizeMake(640, 404); 
    [scrollView setContentSize:scrollViewContentSize]; 
    UILabel *label = [[UILabel alloc] initWithFrame:CGRectMake(200, 200, 50, 21)]; 
    [label setText:@"Hello"]; 
    [scrollView addSubview:label]; 
    [scrollView setPagingEnabled:YES]; 
    scrollView.showsHorizontalScrollIndicator = NO; 
    UIPageControl *pageControl = [[UIPageControl alloc] init]; 
    pageControl.frame = CGRectMake(110,5,100,100); 
    pageControl.numberOfPages = 2; 
    pageControl.currentPage = 0; 
    [self.view addSubview:pageControl]; 
    pageControl.backgroundColor = [UIColor redColor]; 
} 

- (void)viewDidUnload 
{ 
    [super viewDidUnload]; 
    // Release any retained subviews of the main view. 
} 

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation 
{ 
    return (interfaceOrientation == UIInterfaceOrientationPortrait); 
} 

@end 
+0

정확하게 답변했습니다. https://stackoverflow.com/questions/3533047/how-do-you-combine-uiscrollview-with-uipagecontrol-to-show-different-views/14230698#14230698 답변이 더 좋습니다. 한 곳 ... 제안 된 변경 사항을 수정했습니다. – Renetik

답변

77

어쩌면 이것은 당신

합니다 (있는 UIScrollView의 위임 = 자신을 설정하는 것을 잊지 마십시오 당신은 어디든지 작동 HelpViewController.m 아래의 선택자). 코드에 대한

- (void)scrollViewDidScroll:(UIScrollView *)scrollView { 
    CGFloat pageWidth = self.scrollView.frame.size.width; // you need to have a **iVar** with getter for scrollView 
    float fractionalPage = self.scrollView.contentOffset.x/pageWidth; 
    NSInteger page = lround(fractionalPage); 
    self.pageControl.currentPage = page; // you need to have a **iVar** with getter for pageControl 
} 

은 다음과 같다 :

.H 파일

#import <UIKit/UIKit.h> 

@interface HelpViewController : UIViewController{ 
} 

@property (nonatomic, retain) UIScrollView *scrollView; 
@property (nonatomic, retain) UIPageControl * pageControl; 
@end 

하는 .m 파일

#import "HelpViewController.h" 

@interface HelpViewController() 

@end 

@implementation HelpViewController 
@synthesize scrollView=scrollView_; 
@synthesize pageControl=pageControl_; 

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil 
{ 
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil]; 
    if (self) { 
     // Custom initialization 
    } 
    return self; 
} 

- (void)viewDidLoad 
{ 
    [super viewDidLoad]; 
    CGRect scrollViewFrame = CGRectMake(0, 62, 320, 404); 
    self.scrollView = [[[UIScrollView alloc] initWithFrame:scrollViewFrame] autorelease]; 
    self.scrollView.delegate = self; 
    [self.view addSubview:self.scrollView]; 
    CGSize scrollViewContentSize = CGSizeMake(640, 404); 
    [self.scrollView setContentSize:scrollViewContentSize]; 
    UILabel *label = [[UILabel alloc] initWithFrame:CGRectMake(200, 200, 50, 21)]; 
    [label setText:@"Hello"]; 
    [self.scrollView addSubview:label]; 
    [self.scrollView setPagingEnabled:YES]; 
    self.scrollView.showsHorizontalScrollIndicator = NO; 
    self.pageControl = [[[UIPageControl alloc] init] autorelease]; 
    self.pageControl.frame = CGRectMake(110,5,100,100); 
    self.pageControl.numberOfPages = 2; 
    self.pageControl.currentPage = 0; 
    [self.view addSubview:self.pageControl]; 
    pageControl.backgroundColor = [UIColor redColor]; 
} 

- (void)viewDidUnload 
{ 
    [super viewDidUnload]; 
    // Release any retained subviews of the main view. 
} 

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation 
{ 
    return (interfaceOrientation == UIInterfaceOrientationPortrait); 
} 

- (void)scrollViewDidScroll:(UIScrollView *)scrollView { 
     CGFloat pageWidth = self.scrollView.frame.size.width; 
     float fractionalPage = self.scrollView.contentOffset.x/pageWidth; 
     NSInteger page = lround(fractionalPage); 
     self.pageControl.currentPage = page; 
    } 


@end 
+0

도움을 주셔서 감사합니다! 논리는 건전하지만 구현을 잘 이해하지 못합니다. 내 전체 .h 및 .m 파일을 포함하도록 게시를 업데이트했습니다. –

+0

업데이트 됨 단지 코드를 복사해라. .. :) .. 그것은 시험되지 않았다, theres는 아마 오타 일 것이다. 그러나 그것은 효과가있다. –

+0

정말 고마워요. 너는 나에게 많은 두통을 덜어 줬다.내 문제는 대의원과 끝났습니다. –

2

단순히 값을 반올림하지 않고 정확한 페이지 인덱스를 얻을 수 스크롤보기의 scrollViewDidEndDecelerating 대리자 메서드에서 pagecontrol.currentpage를 넣으십시오.이 기능은 나를 위해 작동합니다!

51

이것은 실제로 설정하는 것이 매우 간단합니다. 먼저 스크롤보기 및 페이지 컨트롤을 만들어야합니다. 클래스의 인터페이스에 UIScrollViewDelegate을 구현해야합니다.

UIScrollView * scrollView = [[UIScrollView alloc] initWithFrame:CGRectMake(0, 0, 100, 100)]; 
    scrollView.contentSize = CGSizeMake(scrollView.frame.size.width * 3, scrollView.frame.size.height); 
    scrollView.delegate = self; 

    UIPageControl * pageControl = [[UIPageControl alloc] initWithFrame:CGRectMake(0, 90, scrollView.frame.size.width, 20)]; 
    pageControl.numberOfPages = scrollView.contentSize.width/scrollView.frame.size.width; 
    [pageControl addTarget:self action:@selector(changePage:) forControlEvents:UIControlEventValueChanged]; 

그런 다음 다음과 같은 두 가지 방법을 추가해야합니다

- (IBAction)changePage:(id)sender { 
    CGFloat x = pageControl.currentPage * scrollView.frame.size.width; 
    [scrollView setContentOffset:CGPointMake(x, 0) animated:YES]; 
} 

-(void) scrollViewDidEndDecelerating:(UIScrollView *)scrollView { 
    NSInteger pageNumber = roundf(scrollView.contentOffset.x/(scrollView.frame.size.width)); 
    pageControl.currentPage = pageNumber; 
} 

이러한 방법은 페이지 컨트롤과 스크롤 뷰 사이에 필요한 통신을 추가 할 수 있습니다.

+0

pageControl.numberOfPages로 여러 번 지정할 pageNumber를 올바르게 결정하려면 –

0

이 모든 답변은 훌륭하지만 ReactiveCocoa을 사용하는 대안 솔루션을 제안하고 싶습니다.

다음 코드는 scrollView이라는 속성과 pageControl이라는 속성이 있다고 가정합니다. 모든 것은 여기에 무슨

[RACObserve(self.scrollView, contentOffset) 
    subscribeNext:^(NSValue* value){ 
     CGPoint offset = [value CGPointValue]; 
     CGFloat fractional = offset.x/self.scrollView.width; 
     [self.pageControl setCurrentPage:lroundf(fractional)]; 
    }]; 

당신이있는 ScrollView의 contentOffset 속성에 변화를 관찰하고 모든 다음 이벤트의 페이지 인덱스 (즉 때마다 속성 값이 변경)을 계산하는 것입니다.

유일한 단점은 CGPoint의 편지함을 열어야한다는 것입니다. 그러나 위쪽에는 전혀 UIScrollViewDelegate 코드가 필요하지 않습니다!

관련 문제