2015-06-29 9 views
10

Nella mia attività principale, ho un viewflipper con tre viste figlio. Dopo che l'app è stata avviata, quando eseguo il primo scorrimento da destra a sinistra, la vista cambia, ma non ha l'animazione della diapositiva. Dopo il primo scorrimento, l'animazione funziona come previsto durante lo scorrimento in entrambe le direzioni. Sto seguendo il tutorial this. Il codice che uso è:L'animazione di ViewFlipper non funziona sul primo scorrimento

public boolean onTouchEvent(MotionEvent touchevent) 
{ 
    switch (touchevent.getAction()) 
    { 
     // when user first touches the screen 
     case MotionEvent.ACTION_DOWN: 
     { 
      lastX = touchevent.getX(); 
      break; 
     } 
     case MotionEvent.ACTION_UP: 
     { 
      float currentX = touchevent.getX(); 

      // left to right swipe 
      if (lastX < currentX) 
      { 
       if (mViewFlipper.getDisplayedChild() == 0) 
        break; 

       mViewFlipper.setInAnimation(this, R.anim.in_from_left); 
       mViewFlipper.setOutAnimation(this, R.anim.out_to_right); 

       mViewFlipper.showPrevious(); 
      } 

      // right to left swipe 
      if (lastX > currentX) 
      { 
       if (mViewFlipper.getDisplayedChild() == mViewFlipper.getChildCount() - 1) 
        break; 

       mViewFlipper.setInAnimation(this, R.anim.in_from_right); 
       mViewFlipper.setOutAnimation(this, R.anim.out_to_left); 

       mViewFlipper.showNext(); 
      } 

      break; 
     } 
    } 

    return false; 
} 

Quando il debug del codice, non vedo alcuna differenza tra quando l'animazione è in funzione e quando non lo è. Inoltre, vedo questo comportamento su un dispositivo reale e sull'emulatore. Cosa mi sono perso? Posso pubblicare i file xml dell'animazione e la vista xml, se sono necessari.

EDIT:

L'unico modo sono in grado di farlo funzionare come ci si aspetta è quello di impostare la seguente nel metodo onCreate:

mViewFlipper.setInAnimation(this, R.anim.in_from_right); 
    mViewFlipper.setOutAnimation(this, R.anim.out_to_left); 
    mViewFlipper.setFlipInterval(10000); 
    mViewFlipper.startFlipping(); 

Ho poi chiamo stopFlipping() sul primo colpo. La cosa interessante per me è che l'animazione funziona al primo colpo con queste modifiche, anche se il primo auto-flip non si è verificato. Tuttavia, se imposto semplicemente l'animazione nel metodo onCreate senza chiamare il metodo startFlipping(), non ha ancora l'animazione sul primo scorrimento. Qualcuno può offrire una spiegazione del perché questo comportamento si verifica?

+0

Solo per verificare, guardando il [codice sorgente] (http://bit.ly/1dMu0dc) della classe ViewFlipper, quando si chiama ViewFlipper.showNext(), viene chiamato il metodo ViewAnimator.showOnly (int position) . Questa è la convalida eseguita all'interno di questo metodo: final boolean animate = (! MFirstTime || mAnimateFirstTime); showOnly (childIndex, animato) ;. Quindi, quello che potrebbe succedere è che l'animazione è semplicemente ignorata sul primo capovolgimento. Non sono al 100% su questo, ma puoi verificarlo aggiungendo mViewFlipper.setAnimateFirstView (true) nel onCreate (invece delle righe che hai nella modifica) – mmark

+0

Farò un tentativo quando ne avrò la possibilità. –

+0

@mmark Che ha funzionato. Pubblicalo come risposta e lo accetterò. Grazie! –

risposta

1

Guardando attraverso il codice sorgente della classe ViewFlipper, il ViewFlipper.showNext() chiama internamente il metodo ViewAnimator.showOnly (int position) .

Questa è la convalida eseguita all'interno di quel metodo:

void showOnly(int childIndex) { 
     final boolean animate = (!mFirstTime || mAnimateFirstTime); 
     showOnly(childIndex, animate); 
    } 

Così, al fine di ottenere ciò che si vuole, è necessario dire al ViewFlipper per animare il primo flip all'interno del vostro Activity.onCreate:

@Override 
    void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 

     setContentView(R.layout.my_activity); 
     mViewFlipper = (ViewFlipper) findViewById(R.id.viewflipper); 
     mViewFlipper.setAnimateFirstView(true); 
    } 

NOTA:

sono stato in grado di raggiungere questo obiettivo senza chiamare mViewFlipper.setAnimateFirst Visualizza (true) utilizzando il livello API 22. Ma non sembra funzionare allo stesso modo nelle versioni precedenti.

+0

non funziona per me –

2

In un primo momento, non si ha l'algoritmo del proprio onTouchEvent. Ora ottieni qualcosa come inversione con l'impostazione errata dell'ordine di animazione.

Cercate di usare la mia onTouchEvent, questo è un lavoro per me come un fascino:

public boolean onTouchEvent(MotionEvent touchevent) 
    { 
     switch (touchevent.getAction()) 
     { 
      // when user first touches the screen to swap 
      case MotionEvent.ACTION_DOWN: 
      { 
       lastX = touchevent.getX(); 
       break; 
      } 
      case MotionEvent.ACTION_UP: 
      { 
       float currentX = touchevent.getX(); 

       // if left to right swipe on screen 
       if (lastX < currentX) 
       { 
        // If no more View/Child to flip 
        if (viewFlipper.getDisplayedChild() == 0) 
         break; 

        // set the required Animation type to ViewFlipper 
        // The Next screen will come in form Left and current Screen will go OUT from Right 
        viewFlipper.setInAnimation(this, R.anim.in_from_left); 
        viewFlipper.setOutAnimation(this, R.anim.out_to_right); 
        // Show the next Screen 
        viewFlipper.showNext(); 
       } 

       // if right to left swipe on screen 
       if (lastX > currentX) 
       { 
        if (viewFlipper.getDisplayedChild() == 1) 
         break; 
        // set the required Animation type to ViewFlipper 
        // The Next screen will come in form Right and current Screen will go OUT from Left 
        viewFlipper.setInAnimation(this, R.anim.in_from_right); 
        viewFlipper.setOutAnimation(this, R.anim.out_to_left); 
        // Show The Previous Screen 
        viewFlipper.showPrevious(); 
       } 
       break; 
      } 
     } 
     return true; 
    } 
+0

Ho apportato le modifiche, ma il risultato è lo stesso. Al primo passaggio, non c'è animazione. Ogni volta che si fa scorrere, l'animazione funziona come previsto. –

+1

Forse i file di animazione non sono corretti. – GIGAMOLE

+1

Non penso, dal momento che l'animazione funziona, non solo al primo passaggio. Vedi la mia modifica. –

0
Try to use this gesture for swipe with animation just get animation swipe left to right and right to left and put inside this: 

    final GestureDetector gesture = new GestureDetector(getActivity(), 
       new GestureDetector.SimpleOnGestureListener() { 

        @Override 
        public boolean onDown(MotionEvent e) { 
         return true; 
        } 

        @Override 
        public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, 
          float velocityY) { 
         Log.i("null", "onFling has been called!"); 
         final int SWIPE_MIN_DISTANCE = 80; 
         final int SWIPE_MAX_OFF_PATH = 150; 
         final int SWIPE_THRESHOLD_VELOCITY = 100; 
         try { 
          if (Math.abs(e1.getY() - e2.getY()) > SWIPE_MAX_OFF_PATH) 
           return false; 
          if (e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE 
            && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) { 
           try { 

            //your swipe code 
           } catch (Exception e) { 
            n = -1; 
           } 

          } else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE 
            && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) { 
           try { 

//your swipe code 
         } catch (Exception e) { 

           } 

          } 
         } catch (Exception e) { 
         } 
         return super.onFling(e1, e2, velocityX, velocityY); 
        } 
       }); 
     yourFullRelativeLayout.setOnTouchListener(new View.OnTouchListener() { 

      @Override 
      public boolean onTouch(View v, MotionEvent event) { 
       return gesture.onTouchEvent(event); 
      } 
     }); 
     yourView.setOnTouchListener(new View.OnTouchListener() { 
      @Override 
      public boolean onTouch(View v, MotionEvent event) { 
       return gesture.onTouchEvent(event); 
      } 
     }); 
Problemi correlati