Como crear una Galería de Imágenes usando "GridView" y "Swipe"
(How create image gallery using gridview and swipe)
Intentaremos crear una galería de imagen bastante sencilla, con la funcionalidad de:
- Mostrar la miniaturas en un "GridView".
- Seleccionar una imagen para verla en tamaño original.
- una vez seleccionada una imagen podremos hacer "swipe" a la derecha o a la izquierda para continuar viendo las imágenes de la galería en tamaño original.
- Al volver a la galería de miniaturas, siempre tendremos seleccionada la ultima imagen que vimos en tamaño original.
Para ello crearemos solamente tres activities.
- MainActivity (Se crea por defecto cuando creamos el proyecto)
- ShowGalleryActivity
- SwipeImageActivity
Y ademas crearemos cuatro layouts.
- activity_main (Se crea por defecto cuando creamos el proyecto)
- images_gallery (Contiene el GridView)
- show_image (Es el contenedor de la imagen original, con algunos textos de ayuda)
- swipe_image_layout (Contiene el componente ViewPager, donde cargaremos el layout show_image, con las imágenes originales para hacer el efecto de "swipe").
Las imágenes que utilizaremos para esta galería las colocaremos, en una de nuestras carpetas de recursos, en nuestro caso drawable-xhdpi
Para este tutorial hemos usado Android Studio (I/O Preview) 0.2.5
1.- Después de haber creado un nuevo projecto, copiaremos nuestras imágenes a la carpeta de recursos drawable-xhdpi.
2.- A continuación creamos un layout llamado images_gallery
3.- Creamos una Activity llamada ShowGalleryActivity y la enlazamos con el images_gallery layout (setContentView(R.layout.images_gallery);)
A continuación el código con los comentarios suficientes para que se pueda entender.
public class ShowGalleryActivity extends Activity {
public static int mSelected = 0;
private GridView gridview;
// Hacemos referencia a nuestras imagenes en miniatura de la carpeta de recursos
public static Integer[] mImagesIds = {
R.drawable.i1_thumb, R.drawable.i2_thumb,
R.drawable.i3_thumb, R.drawable.i4_thumb,
R.drawable.i5_thumb, R.drawable.i6_thumb,
R.drawable.i7_thumb, R.drawable.i8_thumb,
R.drawable.i9_thumb, R.drawable.i10_thumb,
R.drawable.i11_thumb, R.drawable.i12_thumb,
R.drawable.i13_thumb, R.drawable.i14_thumb,
R.drawable.i15_thumb, R.drawable.i16_thumb,
R.drawable.i17_thumb, R.drawable.i18_thumb,
R.drawable.i10_thumb, R.drawable.i20_thumb,
R.drawable.i21_thumb, R.drawable.i22_thumb,
R.drawable.i23_thumb, R.drawable.i24_thumb,
R.drawable.i25_thumb, R.drawable.i26_thumb,
R.drawable.i27_thumb, R.drawable.i28_thumb,
R.drawable.i29_thumb, R.drawable.i30_thumb,
R.drawable.i31_thumb
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.images_gallery);
//Hacemos referncia nuestro GridView
gridview = (GridView) findViewById(R.id.gridview);
//Asignamos el ImageAdapter que hemos creado en esta misma clase al GridView
gridview.setAdapter(new ImageAdapter(this));
//Nos movemos al elemento seleccionado del GridView
gridview.setSelection(mSelected);
}
@Override
protected void onStart() {
super.onStart();
gridview = (GridView) findViewById(R.id.gridview);
gridview.setAdapter(new ImageAdapter(this));
gridview.setSelection(mSelected);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.show_gallery_activity, menu);
return true;
}
//ImageAdapter para almacenar las imagemes en el GridView
public class ImageAdapter extends BaseAdapter {
private Context mContext;
public ImageAdapter(Context c) {
mContext = c;
}
public int getCount() {
return mImagesIds.length;
}
public Object getItem(int position) {
return null;
}
public long getItemId(int position) {
return 0;
}
// Creamos un ImageView por cada imagen miniatura referenciada en nuestro ImageAdapter
public View getView(final int position, View convertView, ViewGroup parent) {
ImageView imageView;
if (convertView == null) { // if it's not recycled, initialize some attributes
imageView = new ImageView(mContext);
imageView.setLayoutParams(new GridView.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, 130));
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
imageView.setCropToPadding(true);
} else {
imageView.setScaleType(ImageView.ScaleType.FIT_XY);
}
imageView.setPadding(2, 2, 2, 2);
} else {
imageView = (ImageView) convertView;
}
//Asignamos a cada ImageView una imagen de nuestro "Array" de recursos
//utilizamos "setImageResource" ya que nuestras imagenes estan almacenadas en una
//carpeta de recursos en nuestro proyecto.
// "mImagesIds" es un Array de enteros, ya que almacena el Id del recurso, no la imagen en si.
imageView.setImageResource(mImagesIds[position]);
//En el evento click del ImageView obtenemos el indice de la imagen seleccionada
imageView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
mSelected = (Integer) view.getTag();
notifyDataSetChanged();
String index = String.valueOf(position);
Bundle extras = new Bundle();
//Pasamos el indice de la imagen seleccionada a la activity que se encarga de mostrar la image Original
//y hacer el "swipe"
extras.putString("position", index);
startActivity(new Intent(ShowGalleryActivity.this, SwipeImageActivity.class).putExtras(extras).addFlags(Intent.FLAG_ACTIVITY_NEW_TASK));
}
});
try {
imageView.setTag(position);
//Ponemos un borde de color naranja a la imagen en miniatura seleccionada en el GrisView
if (position == mSelected) {
imageView.setBackgroundColor(Color.parseColor("#ff6203"));
} else {
imageView.setBackgroundColor(Color.TRANSPARENT);
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return imageView;
}
}
}
5.- A continuación creamos un layout llamado swipe_images_layout que servirá de contenedor de la colección de imágenes
6.- Creamos otro layout con la estructura de cada elemento de la colección de imágenes.
Nota: Aquí usamos el componente <android.support.v4.view.ViewPager> por esta razón, debemos copiar en la carpeta lib de nuestro proyecto la librearía: android-support-v4.jar
6.- Creamos una activity llamada SwipeImageActivity. A continuación les dejo el código con los comentarios suficientes para que se pueda entender.
public class SwipeImageActivity extends Activity {
//Hacemos referencia a nuestras imagenes originales de la carpeta de recursos
public static Integer[] mImagesIds = {
R.drawable.i1, R.drawable.i2,
R.drawable.i3, R.drawable.i4,
R.drawable.i5, R.drawable.i6,
R.drawable.i7, R.drawable.i8,
R.drawable.i9, R.drawable.i10,
R.drawable.i11, R.drawable.i12,
R.drawable.i13, R.drawable.i14,
R.drawable.i15, R.drawable.i16,
R.drawable.i17, R.drawable.i18,
R.drawable.i10, R.drawable.i20,
R.drawable.i21, R.drawable.i22,
R.drawable.i23, R.drawable.i24,
R.drawable.i25, R.drawable.i26,
R.drawable.i27, R.drawable.i28,
R.drawable.i29, R.drawable.i30,
R.drawable.i31
};
private boolean hideSwipeText;
private String[] imagesDescriptions;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.swipe_images_layout);
//Optenenos del GridView de la activity anterior el indice de la imagen que hemos
//seleccionado
String i = getIntent().getStringExtra("position");
//Lo convertimos a entero
int index = Integer.parseInt(i);
//Obtenemos la decripcion de la imagen seleccionada de una lista en la carpeta values\arrays.xml
imagesDescriptions = getResources().getStringArray(R.array.images_descriptions);
SwipeImagePagerAdapter swipeNewsAdapter = new SwipeImagePagerAdapter();
ViewPager newsPager = (ViewPager) findViewById(R.id.swipe_pager);
newsPager.setAdapter(swipeNewsAdapter);
newsPager.setCurrentItem(index);
newsPager.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {
@Override
public void onPageScrolled(int i, float v, int i2) {
ShowGalleryActivity.mSelected = i;
}
@Override
public void onPageSelected(int i) {
}
@Override
public void onPageScrollStateChanged(int i) {
}
});
}
//Creamos el SwipeImagePagerAdapter. Donde utilizaremos el layout "show_images"
//para cargar la imagen original y los textos de descripcion de la imagen
private class SwipeImagePagerAdapter extends PagerAdapter {
@Override
public int getCount() {
return ShowGalleryActivity.mImagesIds.length;
}
/**
* Create the page for the given position. The adapter is responsible
* for adding the view to the container given here, although it only
* must ensure this is done by the time it returns from
* {@link #finishUpdate(android.view.ViewGroup)}.
*
* @param collection The containing View in which the page will be shown.
* @param position The page position to be instantiated.
* @return Returns an Object representing the new page. This does not
* need to be a View, but can be some other container of the page.
*/
@Override
public Object instantiateItem(ViewGroup collection, int position) {
LayoutInflater inflater = (LayoutInflater) collection.getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
//Refereciamos el show_images layout
View view = inflater.inflate(R.layout.show_images, null);
LinearLayout swipeDescription = (LinearLayout) view.findViewById(R.id.swipe_description);
if (hideSwipeText) {
swipeDescription.setVisibility(View.GONE);
}
hideSwipeText = true;
//Refereciamos el objeto ImageView del "show_images" layout
ImageView imageView = (ImageView) view.findViewById(R.id.gallery_image);
//Asignamos a cada ImageView una imagen de nuestro "Array" de recursos
//utilizamos "setImageResource" ya que nuestras imagenes estan almacenadas en una
//carpeta de recursos en nuestro proyecto.
// "mImagesIds" es un Array de enteros, ya que almacena el Id del recurso, no la imagen en si.
imageView.setImageResource(mImagesIds[position]);
//Refereciamos el objeto TextView del "show_images" layout, para colocar la descripcion de la imagen
TextView imageDescription = (TextView) view.findViewById(R.id.image_description);
//Asignamos el test descriptivo de la imagen al objecto TextView.
imageDescription.setText(imagesDescriptions[position].toString());
//Adicionamos el "view" que hemos creado con los objectos ImageView y TextView a la coleccion ViewGroup
collection.addView(view, 0);
return view;
}
/**
* Remove a page for the given position. The adapter is responsible
* for removing the view from its container, although it only must ensure
* this is done by the time it returns from {@link #finishUpdate(android.view.ViewGroup)}.
*
* @param collection The containing View from which the page will be removed.
* @param position The page position to be removed.
* @param view The same object that was returned by
* {@link #instantiateItem(android.view.View, int)}.
*/
@Override
public void destroyItem(ViewGroup collection, int position, Object view) {
collection.removeView((View) view);
}
/**
* Determines whether a page View is associated with a specific key object
* as returned by instantiateItem(ViewGroup, int). This method is required
* for a PagerAdapter to function properly.
*
* @param view Page View to check for association with object
* @param object Object to check for association with view
* @return
*/
@Override
public boolean isViewFromObject(View view, Object object) {
return (view == object);
}
/**
* Called when the a change in the shown pages has been completed. At this
* point you must ensure that all of the pages have actually been added or
* removed from the container as appropriate.
*
* @param arg0 The containing View which is displaying this adapter's
* page views.
*/
@Override
public void finishUpdate(ViewGroup arg0) {
}
@Override
public void restoreState(Parcelable arg0, ClassLoader arg1) {
}
@Override
public Parcelable saveState() {
return null;
}
@Override
public void startUpdate(ViewGroup arg0) {
}
}
}
Nota: Las descripciones de las imagenes se encuentran en la carpeta res\values\arrays.xml
7. -Por ultimo modificaremos nuestro Main Activity para hacer el llamado nuestra galería de imágenes:
El layout associado a la Main Activity (activity_main) queda de la siguiente manera:
En la clase MainActivity, capturamos el evento del click del botón, para así mostrar la galería:
public class MainActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Button showGallery = (Button) findViewById(R.id.button);
showGallery.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
startActivity(new Intent(MainActivity.this, ShowGalleryActivity.class).addFlags(Intent.FLAG_ACTIVITY_NEW_TASK));
}
});
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
return true;
}
}
Así debería quedar nuestro proyecto:Y el resultado seria el siguiente:
Y después de seleccionar una imagen:
Puede descargar el código fuente en: ImageGallerySource











