2012-03-09 18 views
5

Sto tentando di implementare il metodo scrollViewWillBeginDragging. Quando si chiama questo metodo, controllo che l'utente abbia selezionato uno dei pulsanti che si trovano all'interno dello scrollview: stato selezionato. In caso contrario, visualizzo un UIAlert per informare l'utente.Controllare la direzione di scorrimento in UIScrollView

mio problema qui è che solo voglia di chiamare il pulsante selezionato il metodo (NextQuestion) se l'utente scorre da destra a sinistra (tirando la vista successiva da destra). Ma se stanno scorrendo da da sinistra a destra, allora voglio che scorra normalmente.

Attualmente il metodo viene chiamato correttore non importa quale direzione l'utente scorre in. Come posso che io chiamo un metodo quando si scorrono da destra a Sinistra?

Ecco come ho attualmente implementato è:

- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView 
{ 
    [self NextQuestion:scrollView]; 
} 

-(IBAction)NextQuestion:(id)sender 
{ 
    CGFloat pageWidth = scrollView.frame.size.width; 
    int page = floor((scrollView.contentOffset.x - pageWidth)/pageWidth) + 1; 
    NSInteger npage = 0; 
    CGRect frame = scrollView.frame; 

    // Check to see if the question has been answered. Call method from another class. 
    if([QuestionControl CheckQuestionWasAnswered:page]) 
    { 
     pageNumber++; 

     NSLog(@"Proceed"); 
     if(([loadedQuestionnaire count] - 1) != page) 
     { 
      [self loadScrollViewWithPage:page - 1]; 
      [self loadScrollViewWithPage:page]; 
      [self loadScrollViewWithPage:page + 1]; 
     } 

     // update the scroll view to the appropriate page 
     frame = scrollView.frame; 
     frame.origin.x = (frame.size.width * page) + frame.size.width; 
     frame.origin.y = 0; 
     [self.scrollView scrollRectToVisible:frame animated:YES]; 

    } 

    // If question has not been answered show a UIAlert with instructions. 
    else 
    { 
     UIAlertView *alertNotAnswered = [[UIAlertView alloc] initWithTitle:@"Question Not Answered" 
                   message:@"You must answer this question to continue the questionnaire." 
                   delegate:nil 
                 cancelButtonTitle:@"OK" 
                 otherButtonTitles:nil, nil]; 
     [alertNotAnswered show]; 
    } 
} 

Codice in materia Soluzione 1:

- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView 
{ 
    NSLog(@"%f",scrollView.contentOffset.x); 
    if (scrollView.contentOffset.x < lastOffset) // has scrolled left.. 
    { 
     lastOffset = scrollView.contentOffset.x; 
     [self NextQuestion:scrollView]; 
    } 
} 
+0

Date un'occhiata a questa risposta: http://stackoverflow.com/a/4073028/742298 –

risposta

0

Fai un CGFloat lastOffset come member variable nel vostro class.h file.

quindi impostare 0 in viewDidLoad.

poi il check-in

 - (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView 

    { 
    if (scrollView.contentOffset.x < lastOffset) // has scrolled left.. 
    { 
     lastOffset = scrollView.contentOffset.x; 
     [self NextQuestion:scrollView]; 
    } 

} 
+0

Purtroppo questo non ha funzionato. Il debugger mostra di saltare questa istruzione If. Ho impostato lastOffset su 0 in ViewDidLoad. E idee? – HGomez90

+0

NSLog scrollView.contentOffset.x poco prima se l'istruzione ..deve essere negativo per lo scorrimento a sinistra – Shubhank

+0

Lo scorrimento da destra a sinistra mostra scrollview.contentOffset.x a '0,000000' . Da sinistra a destra lo mostra a '768.000000' – HGomez90

0

è possibile mantenere un offset iniziale come un membro della vostra classe che si memorizza quando il delegato riceve il scrollViewDidBeginDragging: messaggio. Una volta ottenuto tale valore, è possibile confrontare il valore x dell'offset della vista a scorrimento con quello memorizzato e vedere se la vista è stata trascinata a sinistra oa destra.

Se la modifica della direzione del trascinamento è importante, è possibile ripristinare il punto di confronto nel metodo viewDidScroll: delegato. Quindi una soluzione più completa memorizzerebbe sia l'ultima direzione rilevata sia il punto di offset di base e aggiornerà lo stato ogni volta che viene trascinata una distanza ragionevole.

- (void) scrollViewDidScroll:(UIScrollView *)scrollView 
{ 
    CGFloat distance = lastScrollPoint.x - scrollView.contentOffset.x; 
    NSInteger direction = distance > 0 ? 1 : -1; 
    if (abs(distance) > kReasonableDistance && direction != lastDirection) { 
     lastDirection = direction; 
     lastScrollPoint = scrollView.contentOffset; 
    } 
} 

La 'distanza ragionevole' è ciò che è necessario per evitare che la direzione di scorrimento per capovolgere tra destra e sinistra in modo semplice, ma circa 10 punti dovrebbero essere abbastanza.

21

Nel scrollViewWillBeginDragging la vista di scorrimento non ha ancora mosso (o registrati movimento) e così contentOffset sarà per 0. Come di iOS 5 si può invece guardare in ScrollView del panGestureRecognizer per determinare la direzione e la grandezza del gesto scorrimento dell'utente.

- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView 
{ 
    CGPoint translation = [scrollView.panGestureRecognizer translationInView:scrollView.superview]; 

    if(translation.x > 0) 
    { 
     // react to dragging right 
    } else 
    { 
     // react to dragging left 
    } 
} 
+5

** Nota, la traduzione può restituire zero se il gesto è troppo sottile. ** Usa '' 'CGPoint velocity = [scrollView.panGestureRecognizer velocityInView: scrollView.superview]; '' 'invece. – Robert

+0

Inoltre, se si scorre un UIScrollView e si tocca e si tiene premuto mentre la vista sta ancora decelerando, scrollViewWillBeginDragging sarà chiamato con traduzione e velocità entrambi aventi x = y = 0. Quindi meglio non dare per scontato che '' 'else {...} '' 'sarebbe' '' trascinando a sinistra'''. Verificare i valori di traslazione/velocità di zero per essere sicuri. – Robert