Как остановить прокрутку в виджете галереи? - PullRequest
29 голосов
/ 03 марта 2010

Я загрузил несколько изображений в галерею. Теперь я могу прокручивать, но как только прокрутка началась, прокрутка не остановится. Я бы хотел, чтобы галерея просто прокрутила до следующего изображения и затем остановилась, пока пользователь снова не сделает жест прокрутки.

это мой код

import android.widget.ImageView;
import android.widget.Toast;
 import android.widget.AdapterView.OnItemClickListener;

public class GalleryExample extends Activity {

private Gallery gallery;

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);

     gallery = (Gallery) findViewById(R.id.examplegallery);
     gallery.setAdapter(new AddImgAdp(this));

     gallery.setOnItemClickListener(new OnItemClickListener() {
        public void onItemClick(AdapterView parent, View v, int position, long id) {

            Toast.makeText(GalleryExample.this, "Position=" + position, Toast.LENGTH_SHORT).show();
        }
    });

}

public class AddImgAdp extends BaseAdapter {
    int GalItemBg;
    private Context cont;


    private Integer[] Imgid = {
            R.drawable.a_1, R.drawable.a_2, R.drawable.a_3, R.drawable.a_4, R.drawable.a_5, R.drawable.a_6, R.drawable.a_7
    };

    public AddImgAdp(Context c) {
        cont = c;
        TypedArray typArray = obtainStyledAttributes(R.styleable.GalleryTheme);
        GalItemBg = typArray.getResourceId(R.styleable.GalleryTheme_android_galleryItemBackground, 0);
        typArray.recycle();
    }

    public int getCount() {
        return Imgid.length;
    }

    public Object getItem(int position) {
        return position;
    }

    public long getItemId(int position) {
        return position;
    }

    public View getView(int position, View convertView, ViewGroup parent) {
        ImageView imgView = new ImageView(cont);

        imgView.setImageResource(Imgid[position]);

        i.setScaleType(ImageView.ScaleType.FIT_CENTER);
        imgView.setBackgroundResource(GalItemBg);

        return imgView;
    }
}

}

и файл xmlLayout

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout android:id="@+id/LinearLayout01"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
xmlns:android="http://schemas.android.com/apk/res/android" >
<Gallery xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/examplegallery"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent" />
</LinearLayout>

Ответы [ 7 ]

48 голосов
/ 20 августа 2010

Мне кажется, я нашел способ добиться как прокрутки по одному представлению за раз в галерее, так и иметь минимальную длину пролистывания для запуска анимации.

Переопределите метод onFling виджета галереи и вместо вызова super.onFling, проверьте, был ли пролистывание слева направо или справа налево, и вызовите соответствующее событие dpad, как показано ниже:

private boolean isScrollingLeft(MotionEvent e1, MotionEvent e2){
  return e2.getX() > e1.getX();
}

@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY){
  int kEvent;
  if(isScrollingLeft(e1, e2)){ //Check if scrolling left
    kEvent = KeyEvent.KEYCODE_DPAD_LEFT;
  }
  else{ //Otherwise scrolling right
    kEvent = KeyEvent.KEYCODE_DPAD_RIGHT;
  }
  onKeyDown(kEvent, null);
  return true;  
}
12 голосов
/ 03 марта 2011

Это код, который работал для меня.

Решение Nadewad + некоторые настройки скорости анимации:

Создание класса, расширяющего Gallery, и переопределение этих методов:

  @Override
  public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
    setAnimationDuration(600);
    return super.onScroll(e1, e2, distanceX, distanceY);
  }

  @Override
  public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
    float velMax = 2500f;
    float velMin = 1000f;
    float velX = Math.abs(velocityX);
    if (velX > velMax) {
      velX = velMax;
    } else if (velX < velMin) {
      velX = velMin;
    }
    velX -= 600;
    int k = 500000;
    int speed = (int) Math.floor(1f / velX * k);
    setAnimationDuration(speed);

    int kEvent;
    if (isScrollingLeft(e1, e2)) {
      // Check if scrolling left
      kEvent = KeyEvent.KEYCODE_DPAD_LEFT;
    } else {
      // Otherwise scrolling right
      kEvent = KeyEvent.KEYCODE_DPAD_RIGHT;
    }
    onKeyDown(kEvent, null);

    return true;
  }

Наслаждайтесь!

3 голосов
/ 08 мая 2011

Простой способ заключается в следующем:

@Override
    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
            float velocityY) {
        return super.onFling(e1, e2, 0, velocityY);
    }

Вы также можете проверить здесь: Галерея бесконечных циклов Android

2 голосов
/ 23 мая 2012

не нужно ничего делать, просто вернуть false

private boolean isScrollingLeft(MotionEvent e1, MotionEvent e2){
  return e2.getX() > e1.getX();
}

@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY){
  return false;  
}

это сработало для меня

2 голосов
/ 04 октября 2010

Я обнаружил, что следующее переопределение onFling сработало достаточно для небольших перелистываний и разбиения на страницы на одну страницу:

@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) 
{
    boolean leftScroll = isScrollingLeft(e1, e2);

    float velX;
    if(leftScroll)
    {
        velX=500;
    }
    else
    {
        velX=-500;
    }

    return super.onFling(e1, e2, velX, velocityY);
}

Значение velX + -500, по-видимому, дает достаточно хороший результат, но его можно настроить в соответствии с вашими предпочтениями.

(Примечание: здесь используется метод isScrollingLeft, представленный в ответе @ Nadewad )

2 голосов
/ 29 марта 2010

Я нашел самый простой способ сделать это, переопределив метод Gallery onFling и предоставив мое собственное значение speedX:

@Override
    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
            float velocityY) {
        return super.onFling(e1, e2, 10, velocityY);
    }

Это не идеально, но это делает работу. В идеале вы могли бы написать что-то нестандартное для onFling, чтобы оно работало именно так, как вам нравится.

1 голос
/ 27 февраля 2012

СПАСИБО БОГУ !!! О боже, я буквально включил это в какой-то код, и он сработал! тьфу, 48 часов подряд и думаю, что мне нужно было только сделать идеальный поиск в Google для моего ответа. Буквально подключи и играй. Спасибо.

новый код

public class CustomGallery extends Gallery {

public CustomGallery(Context context) {
    super(context);
}

public CustomGallery(Context context, AttributeSet attrs) {
    super(context, attrs);
}

public CustomGallery(Context context, AttributeSet attrs, int defStyle) {
    super(context, attrs, defStyle);
}

private boolean isScrollingLeft(MotionEvent e1, MotionEvent e2){
  return e2.getX() > e1.getX();
}

@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY){
  int kEvent;
  if(isScrollingLeft(e1, e2)){ //Check if scrolling left
    kEvent = KeyEvent.KEYCODE_DPAD_LEFT;
  }
  else{ //Otherwise scrolling right
    kEvent = KeyEvent.KEYCODE_DPAD_RIGHT;
  }
  onKeyDown(kEvent, null);
  return true;  
}
}

старый код: только для сравнения

 public class CustomGallery extends Gallery {

public CustomGallery(Context context) {
    super(context);
}

public CustomGallery(Context context, AttributeSet attrs) {
    super(context, attrs);
}

public CustomGallery(Context context, AttributeSet attrs, int defStyle) {
    super(context, attrs, defStyle);
}

@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX,
        float distanceY) {
    //Do something specific here.
    return super.onScroll(e1, e2, distanceX, distanceY);
}
}
...