OnItemClickListener no funciona, pero OnItemLongClickListener está trabajando en GridView

Tengo un problema con un clickListener en mi gridview. El LongClickListener funciona sin problemas. Pero no puedo conseguir ninguna respuesta del oyente del tecleo.

Mi código está abajo.

Im confundido en cuanto a porqué el tecleo largo trabaja pero no el tecleo normal,

Cualquier indicador sería apreciada

Gracias

final GridView gridView = (GridView) findViewById(R.id.grid_view); gridView.setNumColumns(numOfColumns); gridView.getLayoutParams().width = (CELL_WIDTH * numOfColumns); gridView.getLayoutParams().height = (CELL_WIDTH * numOfRows); .... gridView.setOnItemClickListener(new AdapterView.OnItemClickListener() { public void onItemClick(AdapterView<?> parent, View v, int position, long id) { Log.d("ABCD", "Position Single Click is " + position); // Ideally in here I want to put to open a soft keyboard for the user to enter a value // InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE); // imm.showSoftInput(gridView, InputMethodManager.SHOW_IMPLICIT); } }); gridView.setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() { @Override public boolean onItemLongClick(AdapterView<?> parent, View view, int position, long id) { Log.d("ABCD", "Position Long Click is " + position); return true; } }); 

Grid_view es

 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:descendantFocusability="blocksDescendants" android:orientation="vertical"> <LinearLayout android:layout_width="match_parent" android:layout_height="0dp" android:layout_weight="1" android:gravity="center" android:orientation="horizontal"> <View android:layout_width="0dp" android:layout_height="wrap_content" android:layout_weight="2"/> <GridView xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/my_grid_view" android:layout_width="wrap_content" android:layout_height="wrap_content" android:clickable="true"/> <<--- I WANT THIS TO GET THE CLICK <View android:layout_width="0dp" android:layout_height="wrap_content" android:layout_weight="2"/> </LinearLayout> <ListView xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/listId" android:layout_weight="1" android:layout_width="match_parent" android:layout_height="0dp" /> </LinearLayout> 

GridCell en la vista de cuadrícula es

 <?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:padding="0dp" android:layout_margin="0dp" android:focusable="false" android:clickable="false" android:focusableInTouchMode="false" > <TextView android:id="@+id/grid_item_number" android:layout_width="wrap_content" android:layout_height="wrap_content" android:paddingLeft="1dp" android:paddingRight="0dp" android:paddingTop="0dp" android:paddingBottom="0dp" android:textSize="10px" android:focusable="false" android:clickable="false" android:focusableInTouchMode="false" > </TextView> <EditText xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/grid_item_label" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@+id/celllabel" android:background="@android:color/transparent" android:paddingLeft="5dp" android:paddingRight="0dp" android:paddingTop="0dp" android:paddingBottom="0dp" android:layout_margin="0dp" android:focusable="false" android:focusableInTouchMode="false" android:clickable="false" android:cursorVisible="false"> </EditText> </RelativeLayout> 

La clase del adaptador tiene un getView y es como abajo

 public View getView(final int position, View convertView, ViewGroup parent) { LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE); View gridView; MyObject obj = myObjects.get(position); if (convertView == null) { gridView = inflater.inflate(R.layout.grid_cell, null); String textColour = "#000000"; TextView textView = (TextView) gridView.findViewById(R.id.grid_item_label); textView.setText(Html.fromHtml(String.format("<font color='%s'>%s</font>", textColour, obj.getValue()))); TextView superScriptTv = (TextView) gridView.findViewById(R.id.grid_item_number); if (obj.getNumber() > 0) { superScriptTv.setText(Html.fromHtml(String.format("<font>%s</font>", cell.getNumber()))); } } else { gridView = convertView; } gridView.setBackgroundColor(obj.getBackgroundColour()); return gridView; } 

EDITAR Realmente golpear mi cabeza contra una pared aquí ahora 🙂 Im actualización de la muestra de código para tener más datos. Ive notado eso en mi adaptador si no fijo el texto en el textview con ID = R.id.grid_item_number entonces trabaja. Tan pronto como puse el texto en él entonces pierdo el oyente del tecleo.

La pregunta / respuesta relacionada no ayuda de lo que puedo ver. ¿Puede alguien ayudarme con mi estupidez?

EDIT Se ha añadido el código del adaptador.

Gracias por adelantado.

El problema es con el EditText dentro de la row_cell . Al hacer clic en el elemento, se centra y evita que todo el elemento se haga clic de nuevo. Como te has dado cuenta, solo funciona con un clic largo. Aquí tienes un problema similar.

Para resolver ese problema movería su OnItemClickListeners de la actividad / fragmento a su GridViewAdapter , así que en vez de:

 gridView.setOnItemClickListener(new AdapterView.OnItemClickListener() { public void onItemClick(AdapterView<?> parent, View v, int position, long id) { Log.d("ABCD", "Position Single Click is " + position); // Ideally in here I want to put to open a soft keyboard for the user to enter a value // InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE); // imm.showSoftInput(gridView, InputMethodManager.SHOW_IMPLICIT); } }); gridView.setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() { @Override public boolean onItemLongClick(AdapterView<?> parent, View view, int position, long id) { Log.d("ABCD", "Position Long Click is " + position); return true; } }); 

Yo haría algo así:

 @Override public View getView(int position, View convertView, ViewGroup parent) { LayoutInflater layoutInflater = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE); View gridViewItem; if (convertView == null) { gridViewItem = new View(mContext); gridViewItem = layoutInflater.inflate(R.layout.grid_cell, null); TextView textView = (TextView)gridViewItem.findViewById(R.id.grid_item_number); textView.setText(mValues[position]); EditText editText = (EditText)gridViewItem.findViewById(R.id.grid_item_label); } else { gridViewItem = (View) convertView; } gridViewItem.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { Log.e("GRID", "onClick: " ); } }); gridViewItem.setOnLongClickListener(new View.OnLongClickListener() { @Override public boolean onLongClick(View v) { Log.e("GRID", "onLongClick: " ); return true; } }); return gridViewItem; } 

Se evitará este comportamiento extraño que está luchando en este momento.

Por el bien de ese ejemplo por favor encuentre mi código abajo:

Disposición MainActivity:

 <?xml version="1.0" encoding="utf-8"?> <android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:id="@+id/activity_main" android:layout_width="match_parent" android:layout_height="match_parent" tools:context="io.github.mmbs.gridviewcheck.MainActivity" tools:layout_editor_absoluteX="0dp" tools:layout_editor_absoluteY="0dp"> <GridView android:id="@+id/gridView" android:numColumns="auto_fit" android:columnWidth="100dp" android:stretchMode="columnWidth" android:layout_width="match_parent" android:layout_height="match_parent" android:clickable="true"> </GridView> </android.support.constraint.ConstraintLayout> 

Diseño de la celda de cuadrícula:

 <?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_margin="0dp" android:clickable="false" android:focusable="false" android:focusableInTouchMode="false" android:padding="8dp"> <TextView android:id="@+id/grid_item_number" android:layout_width="match_parent" android:layout_height="wrap_content" android:paddingBottom="0dp" android:paddingLeft="1dp" android:paddingRight="0dp" android:paddingTop="0dp" android:textSize="20sp" android:text="TEXTVIEW"> </TextView> <EditText android:id="@+id/grid_item_label" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_margin="0dp" android:background="@android:color/transparent" android:cursorVisible="false" android:layout_below="@id/grid_item_number" android:text="EDITTEXT"> </EditText> </RelativeLayout> 

Tenga en cuenta, que he eliminado todos los atributos de los diseños responsables de la capacidad de focusability .

MyGridAdapter:

 public class MyGridViewAdapter extends BaseAdapter { private Context mContext; private final String[] mValues; public MyGridViewAdapter(String[] values, Context context) { mValues = values; mContext = context; } @Override public int getCount() { return mValues.length; } @Override public Object getItem(int position) { return null; } @Override public long getItemId(int position) { return position; } @Override public View getView(int position, View convertView, ViewGroup parent) { LayoutInflater layoutInflater = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE); View gridViewItem; if (convertView == null) { gridViewItem = new View(mContext); gridViewItem = layoutInflater.inflate(R.layout.grid_cell, null); TextView textView = (TextView)gridViewItem.findViewById(R.id.grid_item_number); textView.setText(mValues[position]); EditText editText = (EditText)gridViewItem.findViewById(R.id.grid_item_label); } else { gridViewItem = (View) convertView; } gridViewItem.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { Log.e("GRID", "onClick: " ); } }); gridViewItem.setOnLongClickListener(new View.OnLongClickListener() { @Override public boolean onLongClick(View v) { Log.e("GRID", "onLongClick: " ); return true; } }); return gridViewItem; } } 

Si lo desea, también puedo compartir este código en github, por lo que tendrá un ejemplo completamente operativo.

La segunda opción es dejar su implementación tal cual es y hacer hacks cuando el EditText se puede EditText y habilitar. Aquí tienes temas relacionados:

  1. Android: Force EditText para eliminar el enfoque?
  2. Comportamiento de enfoque de los elementos ListView
  3. Focusable EditText dentro de ListView
  4. Android: Force EditText para eliminar el enfoque?

Lo que es más, por favor tenga en cuenta que la respuesta:

No utilice objetos que se puedan hacer clic en la cuadrícula. En ese caso, Android no puede manejar el evento de clic de GridView.

En su lugar, utilice algo para mostrar una vista de interfaz de usuario similar. Luego maneje las acciones de clic de ese objeto.

No: Ponga el botón en el GridView para realizar algunas acciones de clic.

Hacer: poner un ImageView en lugar de ImageButton y manejar los eventos de clic de ImageView.

Edit: Por favor encuentre un enlace al proyecto en mi Github .

gridView.setOnItemClickListener(.....) ya su vista raíz agregue debajo de la línea

 android:descendantFocusability="blocksDescendants" 

ViewGroup bloqueará a sus descendientes de recibir el enfoque.

HappyCoding;

Trate de agregar

 android:focusable="false" android:focusableInTouchMode="false" 

En su GridCell -> TextView

Trate de usar la vista del reciclador si se siente cómodo con él.

No da ningún problema, además de esto tiene sus propias ventajas.

Siga el enlace para una explicación completa.

Si tiene alguna vista de enfoque en su diseño de fila, no se llamará onItemClickListener. Para este problema es necesario personalizar su código getView y establecer onClickListener () en convertView y pasar la devolución de llamada a la actividad mediante la interfaz. He actualizado el código de su adaptador como se muestra a continuación. Ahora debe implementar GridViewItemClickListener en su actividad y pasar la instancia mientras crea la instancia del adaptador.

  public class MyGridViewAdapter extends BaseAdapter { private Context mContext; private final String[] mValues; private GridViewItemClickListener mListener; public MyGridViewAdapter(String[] values, Context context,GridViewItemClickListener listener ) { mValues = values; mContext = context; mListener = listener; } @Override public int getCount() { return mValues.length; } @Override public Object getItem(int position) { return null; } @Override public long getItemId(int position) { return position; } @Override public View getView(final int position, View convertView, ViewGroup parent) { LayoutInflater layoutInflater = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE); View gridViewItem; if (convertView == null) { gridViewItem = new View(mContext); gridViewItem = layoutInflater.inflate(R.layout.grid_cell, null); TextView textView = (TextView)gridViewItem.findViewById(R.id.grid_item_number); textView.setText(mValues[position]); EditText editText = (EditText)gridViewItem.findViewById(R.id.grid_item_label); } else { gridViewItem = (View) convertView; } gridViewItem.setOnLongClickListener(new View.OnLongClickListener() { @Override public boolean onLongClick(View v) { Log.e("GRID", "onLongClick: " ); return true; } }); //Add an OnclickListener here gridViewItem.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { if(mListener != null){ mListener.onGridItemClick(v, position); } } }); return gridViewItem; } public interface GridViewItemClickListener{ void onGridItemClick(View v, int index); } } 

Usted puede hacer clic en los oyentes dentro del adaptador que funcionará, debe funcionar de esta manera

Public View getView (posición final int, View convertView, ViewGroup padre) {LayoutInflater inflater = (LayoutInflater) context.getSystemService (Context.LAYOUT_INFLATER_SERVICE);

  View gridView; MyObject obj = myObjects.get(position); if (convertView == null) { gridView = inflater.inflate(R.layout.grid_cell, null); String textColour = "#000000"; TextView textView = (TextView) gridView.findViewById(R.id.grid_item_label); textView.setText(Html.fromHtml(String.format("<font color='%s'>%s</font>", textColour, obj.getValue()))); TextView superScriptTv = (TextView) gridView.findViewById(R.id.grid_item_number); superScriptTv.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { // here you can use every item of grid acc to position } }); if (obj.getNumber() > 0) { superScriptTv.setText(Html.fromHtml(String.format("<font>%s</font>", cell.getNumber()))); } } else { gridView = convertView; } gridView.setBackgroundColor(obj.getBackgroundColour()); return gridView; } 

¿Cómo puede funcionar el oyente de clics si establece el elemento raíz en GridCell.java como no clicable?

 <?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:padding="0dp" android:layout_margin="0dp" android:focusable="false" android:clickable="false" android:focusableInTouchMode="false" 

Quite las líneas de cada uno de sus componentes en el GridCell.java

 android:focusable="false" android:clickable="false" android:focusableInTouchMode="false" 

No creo que esto sea necesario para GridView, pero a veces para RecyclerView es necesario tener android: clickable = "true" en el componente raíz de GridCell.java

  • Manejo de un elemento de menú Haga clic en Evento - Android
  • SetOnItemClickListener VS setOnItemSelectedListener en ListView.
  • ViewRootImpl: ViewPostImeInputStage processPointer 0 en OnItemClick de Listview en android
  • Haga clic en largo Haga clic en span no disparar hasta que se haga clic
  • OnItemClickListener (), cómo pasar los datos del elemento pulsado?
  • OnItemClickListener con adaptador personalizado y listview
  • Vista de lista personalizada no responde al evento de clic
  • ¿Cómo recuperar la cadena clicada de un listview usando OnItemClick?
  • El clic de Listitem no funciona con las casillas de verificación Android
  • Mostrar alertDialog con los botones de radio cuando haga clic en un listViewItem
  • Recyclerview addOnItemTouchListener obtiene la vista previa que se hace clic en la fila
  • FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.