2010-12-01 7 views
36

Я пытаюсь создать тот же эффект, что и в приложении AppStore для просмотра скриншотов: внутри UITableView у меня есть пользовательские подклассы UITableViewCell. Один из них предназначен для показа предварительного просмотра какого-либо продукта, скажем, 4 изображений. Я хочу, чтобы они отображались так же, как AppStore представляет скриншоты приложения: внутри горизонтального UIScrollView с его подключенным UIPageControl.Горизонтальный UIScrollView внутри UITableViewCell

Так что я добавить мой UIScrollView и мой UIPageControl к моему UITableViewCell, просто так:

@implementation phVolumePreviewCell 
- (id)init { 
    if (self = [super initWithStyle:UITableViewCellStyleDefault reuseIdentifier:kVolumePreviewCellIdentifier]) { 
     [self setAccessoryType:UITableViewCellAccessoryDisclosureIndicator]; 
     [self setSelectionStyle:UITableViewCellSeparatorStyleNone]; 

     previews = [[NSMutableArray alloc] initWithCapacity:4]; 
     for (int i = 0; i < 4; i++) { 
      [previews addObject:@"dummy"]; 
     } 

     scrollView = [[UIScrollView alloc] initWithFrame:CGRectZero]; 
     [scrollView setPagingEnabled:YES]; 
     [scrollView setBackgroundColor:[UIColor grayColor]]; 
     [scrollView setIndicatorStyle:UIScrollViewIndicatorStyleBlack]; 
     [scrollView setShowsHorizontalScrollIndicator:YES]; 
     [scrollView setBounces:YES]; 
     [scrollView setScrollEnabled:YES]; 
     [scrollView setDelegate:self]; 
     [self.contentView addSubview:scrollView]; 
     [scrollView release]; 

     pageControl = [[UIPageControl alloc] initWithFrame:CGRectZero]; 
     [pageControl setNumberOfPages:[previews count]]; 
     [pageControl setBackgroundColor:[UIColor grayColor]]; 
     [self.contentView addSubview:pageControl]; 
     [pageControl release]; 
    } 
    return self; 
} 

(примечание: Я заселение «превью» с фиктивными данными здесь, только для того, чтобы иметь [предварительные просмотры count], я хочу просмотреть индикатор прокрутки scrollView только для тестовых целей, позже я их скрою).

Моя проблема в том, что я могу прокрутить весь UITableView, содержащий этот phVolumePreviewCell (подкласс UITableViewCell), но я не могу прокрутить UIScrollView. Как я могу это достичь?

Единственная информация, которую я нашел, есть: http://theexciter.com/articles/touches-and-uiscrollview-inside-a-uitableview.html Но это говорит о старых SDK (а именно 2.2), и я уверен, что для этого существует более «недавний» подход.

Некоторые уточнения:

  • Я пролистывания UIScrollView с двумя пальцами. Это не то, что я хочу, я хочу, чтобы он мог прокручивать только одним пальцем.
  • Когда я прокручиваю двумя пальцами, TableView по-прежнему перехватывает штрихи и немного прокручивается в верхнюю или нижнюю часть. Я бы хотел, чтобы TableView придерживался своего положения, когда касался ScrollView.

Я считаю, что я должен работать, как перехватывать штрихи на мой TableView, и если касание на phVolumePreviewCell (пользовательские UITableViewCell подкласса), передать его в камеру вместо того, чтобы обрабатывать его на TableView.

Для записи, мой TableView создается программно в UITableViewController подкласса:

@interface phVolumeController : UITableViewController <UITableViewDelegate> { 
    LocalLibrary *lib; 
     NSString *volumeID; 
     LLVolume *volume; 
} 

- (id)initWithLibrary:(LocalLibrary *)newLib andVolumeID:(NSString *)newVolumeID; 
@end 

@implementation phVolumeController 

#pragma mark - 
#pragma mark Initialization 

- (id)initWithLibrary:(LocalLibrary *)newLib andVolumeID:(NSString *)newVolumeID { 
    if (self = [super initWithStyle:UITableViewStylePlain]) { 
     lib   = [newLib retain]; 
     volumeID  = newVolumeID; 
     volume  = [(LLVolume *)[LLVolume alloc] initFromLibrary:lib forID:volumeID]; 
     [[self navigationItem] setTitle:[volume title]]; 
    } 
    return self; 
} 

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView { 
    return 1; 
} 

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section { 
    return 1; 
} 

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { 
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:kVolumePreviewCellIdentifier]; 
    if (cell == nil) { 
     cell = [[[phVolumePreviewCell alloc] init] autorelease]; 
    } 

    [(phVolumePreviewCell *)cell setVolume:volume]; 
    return (UITableViewCell *)cell; 
} 

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath { 
    return kVolumePreviewCellHeight; 
} 

Спасибо за любую помощь!

ответ

21

Я нашел обходное решение.

Восстанавливая с нуля очень простой UITableView (8 строк) и вставляя UIScrollView только во вторую строку, отлично работает. Вложенные представления прокрутки (TableView и ScrollView) прокручиваются независимо, как и ожидалось. Все, что было сделано в однофайльном тестовом проекте, в AppDelegate.

Итак, сначала я подумал: «Это может быть проблема делегирования», поэтому я сказал scrollView, что его делегатом был TableView, а не мой собственный подкласс TableViewCell. Но безрезультатно.

Затем вместо использования специального подкласса TableViewCell, который просто добавляет ScrollView и PageControl, я прибегал к созданию простого TableViewCell в методе cellForRowAtIndexPath: TableView. Затем я создаю UIScrollView сразу после инициализации TableViewCell, а затем добавляю его в TableViewCell и shazam ... он работает!

До:

UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:kVolumePreviewCellIdentifier]; 
if (cell == nil) { 
    cell = [[[phVolumePreviewCell alloc] init] autorelease]; 
} 

[(phVolumePreviewCell *)cell setVolume:volume]; 
// That does the job of creating the cell's scrollView and pageControl 

return (UITableViewCell *)cell 

После:

UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:kvcPreviewRowIdentifier]; 
if (cell == nil) { 
    cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:kvcPreviewRowIdentifier] autorelease]; 

    previewScrollView = [[UIScrollView alloc] initWithFrame:CGRectMake(0, 0, tableView.frame.size.width, kvcPreviewScrollViewHeight)]; 
    [previewScrollView setContentSize:CGSizeMake(1000, kvcPreviewScrollViewHeight)]; 
    [[cell contentView] addSubview:previewScrollView]; 

    previewPageControl = [[UIPageControl alloc] initWithFrame:CGRectMake(0, kvcPreviewScrollViewHeight, tableView.frame.size.width, kvcPreviewPageControlHeight)]; 
    [previewPageControl setNumberOfPages:4]; 
    [[cell contentView] addSubview:previewPageControl]; 
} 

return (UITableViewCell *)cell; 

Как щеколда приходит, что когда я создаю мой Scrollview из подкласса TVcell, он не играет хорошо; но когда я создаю scrollView из TableView сразу после создания «классического» TVCell, он работает?

Возможно, я нашел решение, но я все еще озадачен причиной.

+0

Thanks Cyrille !! Та же проблема здесь. Ваше решение сэкономило мне много часов в отчаянии! :-) – 2011-07-10 07:40:41