Entonces tengo lo que parece ser un problema común, que es que EditText en mi cuadro de diálogo no aparece cuando se enfoca. He visto varias soluciones alternativas, como en este hilo , este y este (y muchos más), pero nunca he visto una explicación satisfactoria de por qué está sucediendo esto en primer lugar.
Preferiría que Android use su propio comportamiento predeterminado para EditTexts que para construir el mío, pero parece que todos (en esos hilos) han aceptado que el comportamiento predeterminado para EditTexts en Dialogs es simplemente dar un cursor y no un teclado. ¿Por qué sería eso?
Para que conste, ninguna de estas soluciones parece funcionar para mí; lo más cerca que he podido llegar es forzar que aparezca un teclado debajo del cuadro de diálogo (usando InputMethodManager.toggleSoftKeyboard (*)). Mi configuración particular es API15, EditText aparece en un pie de página en un ListView dentro de un AlertDialog. El Android EditText: focusable = "true" está configurado y onFocusChangeListener está recibiendo eventos de enfoque.
Editar:
Según lo solicitado, aquí está el fragmento de código específico con el que estoy trabajando. No me molestaré con el diseño completo, pero en esta aplicación específica, EditText aparece en respuesta a presionar un botón en el diálogo (similar a una vista de acción ). Está contenido en un RelativeLayout que, por defecto, tiene visibilidad "desaparecida":
<RelativeLayout
android:id="@+id/relLay"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:visibility="gone"
android:layout_marginTop="5dp"
android:layout_marginBottom="5dp">
<ImageButton
android:id="@+id/cancelBut"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:background="@color/transparent"
android:src="@drawable/cancelButton"
android:layout_margin="5dp"/>
<ImageButton
android:id="@+id/okBut"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_toLeftOf="@id/cancelBut"
android:background="@color/transparent"
android:src="@drawable/okButton"
android:layout_margin="5dp" />
<EditText
android:id="@+id/editText"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:inputType="text"
android:focusable="true"
android:layout_toLeftOf="@id/okBut"/>
</RelativeLayout>
El código que crea esto establece la visibilidad del relativo diseño en "Visible" (y oculta los otros elementos de la interfaz de usuario). Esto debería ser suficiente para levantar el teclado cuando EditText se enfoca, según mi experiencia con EditText. Sin embargo, por alguna razón, este no es el caso. Puedo configurar el siguiente onFocusChangeListener:
edit_text.setOnFocusChangeListener(new OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
// For whatever reason we need to request a soft keyboard.
InputMethodManager imm = (InputMethodManager)dlg.getWindow().getContext().getSystemService(_Context.INPUT_METHOD_SERVICE);
if(hasFocus)
imm.toggleSoftInput(InputMethodManager.SHOW_FORCED, 0);
Log.v("DialogProblem", "Focus requested, " + (hasFocus?"has focus.":"doesn't have focus."));
}
}
});
Usando esta configuración, cuando entro por primera vez el EditText, el onFocusChangedListener se activa y genera un registro que invariablemente se ve así:
Focus requested, has focus.
Focus requested, doesn't have focus.
Focus requested, has focus.
El teclado aparece y luego desaparece, probablemente porque lo alterno dos veces, pero incluso cuando me aseguro de que permanece arriba, está detrás de la ventana de diálogo (en un área atenuada), y no hay forma de acceder a él sin cerrar el diálogo. .
Dicho esto, me gustaría hacer hincapié en que a pesar de que puede ser capaz de conseguir este trabajo en torno al trabajo, estoy principalmente interesado en la búsqueda de una simple razón por qué la EditarTexto no está activando en primer lugar, y por qué esto parece ser tan común!
Respuestas:
Bien, después de leer mucho, he descubierto por qué esto es un problema y no necesito usar ninguna solución alternativa.
El problema parece ser (al menos en mi caso), que dado que el lugar donde ingresa el texto está oculto inicialmente (o anidado o algo así), AlertDialog está configurando automáticamente la marca WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM (o alguna combinación de eso y WindowManager .LayoutParams.FLAG_NOT_FOCUSABLE) para que las cosas no activen la aparición de una entrada suave.
La forma que encontré para solucionar esto es agregar la siguiente línea después de que se haya creado el cuadro de diálogo:
dialog.getWindow().clearFlags(WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE|WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM);
Una vez hecho esto, EditText actúa como un EditText normal, sin necesidad de errores ni soluciones.
fuente
clearFlags()
despuésshow()
, gracias @AlexanderFragotsisTengo el mismo problema en mi propia aplicación. Si está desarrollando para el nivel de API> = 8, puede usar este fragmento:
dialog.setOnShowListener(new OnShowListener() { @Override public void onShow(DialogInterface dialog) { InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE); imm.showSoftInput(textEdit, InputMethodManager.SHOW_IMPLICIT); } });
No he encontrado una solución para niveles de API más bajos ...
Por cierto: este fragmento no siempre funciona en el emulador. No sé por qué.
fuente
AlertDialog dialog = builder.create();
antes ydialog.show();
después de lo anterior si está usando AlertDialog.BuilderSi lee la documentación de AlertDialog, encontrará allí:
Tuve el problema que mencionaste con EditText en ListView dentro de un diálogo. Lo arreglé sobrescribiendo la clase de vista personalizada (en mi caso ListView) con mi propio FocusableListView, con solo un método sobrescrito:
public class FocusableListView extends ListView { public FocusableListView(Context context) { super(context); } public FocusableListView(Context context, AttributeSet attrs) { super(context, attrs); } public FocusableListView(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); } @Override public boolean onCheckIsTextEditor() { // this is where the magic happens return true; } }
Entonces lo estoy usando en el archivo de diseño como:
<?xml version="1.0" encoding="UTF-8"?> <com.myexample.wiget.FocusableListView xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:descendantFocusability="beforeDescendants" android:layout_height="wrap_content" />
Puede sobrescribir el RelativeLayout en su caso de la misma manera y debería funcionar.
fuente
Esto es lo que funcionó para mí. Cree el AlertDialog.Builder, establezca el título, positiveButton, negativeButton. Después de hacer esto:
AlertDialog dialog = builder.create(); dialog.getWindow().clearFlags( WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE |WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM); dialog.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE); dialog.show(); editText.requestFocus();
No necesitas usar
builder.show();
.fuente
El código anterior es muy útil. Pero debe llamar al método "show" después del método "create" (no sé por qué, pero solo esto funciona en mi diálogo con EditText en ListView). En el método onCreateDialog:
@Override protected Dialog onCreateDialog(int id) { switch (id) { case YOUR_DIALOG_ID: { //... AlertDialog a = new AlertDialog.Builder(this)./* ... set the properties here */ .create(); a.show(); //!!! this is very important to call the "show" method a.getWindow().clearFlags( WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE | WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM); return a; } //... } return null; }
fuente
¡Gracias! Tengo un TextEdit incrustado en la última fila de ListView incrustado en el fragmento de diálogo de alerta. Usé su solución de borrar las banderas como una publicación ejecutable y ahora funciona perfectamente.
@Override public Dialog onCreateDialog(Bundle savedInstanceState) { AlertDialog.Builder builder = new AlertDialog.Builder(getContext()); builder.setTitle("My Title"); m_adapter = new MyAdapter(getContext()); builder.setAdapter(m_adapter, new OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { // TODO Auto-generated method stub } }); final AlertDialog dialog = builder.create(); final ListView listView = dialog.getListView(); listView.setOnItemClickListener(new OnItemClickListener() { @Override public void onItemClick(AdapterView<?> parent, View view, int position, long id) { } }); listView.post(new Runnable() { @Override public void run() { dialog.getWindow().clearFlags( WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE | WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM); } }); return dialog; }
fuente
He aquí una forma de hacerlo:
final Window dialogWindow = dialog.getWindow(); dialogWindow.clearFlags(WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE | WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM); dialogWindow.setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE);
fuente
Me gustaría agregar algo a la respuesta de Paul y al comentario de Alexander .
Yo mismo tengo un cuadro de diálogo que se creó en el
onCreateDialog()
método, que (parece) requerir regresardialog.show();
, por lo que no puede agregar los parámetros de diseño al cuadro de diálogo donde se crea el cuadro de diálogo. Para solucionar esto, simplemente mantenga suonCreateDialog()
método igual y agregue unonResume()
método de la siguiente manera:@Override public void onResume() { super.onResume(); Dialog dialog = getDialog(); dialog.getWindow().clearFlags(WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE | WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM); dialog.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE); }
Esto debería funcionar, me funciona, afortunadamente. He estado en este caso durante bastante tiempo.
fuente
código completo para mostrar el teclado en el diálogo:
public void onFocusChange(View v, boolean hasFocus) { Log.v("onFocusChange", hasFocus + " " + showkeyboard); if (hasFocus) { if (showkeyboard++ == 0) { alertDialog.getWindow().clearFlags( WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE | WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM); alertDialog.getWindow().setSoftInputMode( WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE); } else { showkeyboard = 1; } } }
fuente
This worked for me ---- editText.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { //dialog.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE); //dialog.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE); //dialog.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE); //dialog.getWindow().clearFlags(WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE | WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM); InputMethodManager mgr = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE); mgr.showSoftInput(v, InputMethodManager.SHOW_FORCED); editText.setFocusable(true); } });
fuente
simplemente agregue debajo de codeLine:
// para mostrar el teclado automáticamente mientras editText está en dialog dialog.getWindow (). setSoftInputMode (WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE);
fuente