2012-02-09 9 views
5

A similar question è stato chiesto un anno fa, e non è stato risolto, ma tenterò comunque la mia fortuna, forse qualcuno lo sa.Cercando di aprire il tag SELECT in Android WebView si blocca l'applicazione

Ho questa applicazione che esegue un paio di pagine HTML in una WebView. Tutto sembra bello e funziona OK, finché non provi ad aprire un tag SELECT - boom, crash dell'applicazione. Ecco uno stack trace, se questo aiuta:

Discussione [< 1> principale] (sospeso (eccezione WindowManager $ BadTokenException)) AlertDialog (Dialog) .Show() Linea: 247
WebView $ InvokeListBox. run() linea: 7841
WebView $ PrivateHandler (Handler) .handleCallback (Messaggio) linea: 587
WebView $ PrivateHandler (Handler) .dispatchMessage (Messaggio) linea: ActivityThread 130 : 92
Looper.loop) linea (.main (String []) line: 3859
Met hod.invokeNative (Object, Object [], Class, Class [], Class, int, boolean) line: non disponibile [metodo nativo]
Method.invoke (Object, Object ...) line: 507
ZygoteInit $ MethodAndArgsCaller.run() linea: 840
ZygoteInit.main (String []) linea: 598 NativeStart.main (String []) la linea: non disponibile [metodo nativo]

(Cosa deve AlertDialog fare con l'apertura di una casella di selezione è oltre me. E no, non esiste uno script associato a SELECT che apre un avviso).

Ora, ecco la parte migliore. Sto testando l'app su 2 dispositivi, Samsung Galaxy S2 con OS 2.3.3 e Motorola RAZR XT910 con OS 2.3.5. Su Samsung tutto funziona alla grande. Su RAZR, tuttavia, succede quanto sopra.

Le pagine sono piuttosto pesanti con CSS e JavaScript, ma si bloccano anche se tutto viene rimosso. In effetti, un HTML vuoto con un solo controllo SELECT si blocca ancora. Un paio di cose di cui alla domanda di anno fa, che ho provato:

  • Rimozione di tutti gli elementi assoluti e fissi posizionati dal codice HTML (in realtà ho rimosso tutto il CSS solo per vedere se ha qualche effetto - è non lo fa).
  • Garantire che SELECT sia scritto dal libro, nessun attributo/tag falso.

Niente di utile.

Qualcuno ha la minima idea di cosa potrebbe causare questo?

+0

In Android, i menu a discesa non "scendono" (almeno prima di ICS), mostrano le opzioni in un elenco all'interno di un AlertDialog, quindi è da lì che proviene. Ahimè, non so perché il problema accade. – dmon

+0

Dovresti pubblicare il codice HTML (o un esempio) per vedere se qualcuno può individuare qualcosa che potrebbe causare un arresto anomalo. Hai provato con un SELECT più semplice? – dmon

+0

Sembra abbastanza semplice, quanto più semplice di un controllo deve funzionare un WebView? Voglio dire, lo stesso WebView ha gestito animazioni CSS e JS piuttosto pesanti e cosa no, e tutto era peachy. –

risposta

0

Dopo aver cercato su tutto il Web per oltre un mese, ho rinunciato e inoltrato tutti i SELECT al codice nativo.

Sostituire il SELECT con qualcosa che sembra SELECT, si legano click gestore che lancia un metodo su JavascriptInterface e passare i valori opzione seleziona ad esso, lasciare che il metodo di aprire un Dialog con un RadioGroup, riempire il gruppo con RadioButton s che rappresenta il opzioni. Quando è selezionato, risolvere l'indice e passarlo nuovamente al codice JavaScript (l'istanza SELECT che ha avviato il processo deve essere prima salvata in alcune var).

Questo è brutto da morire, ma purtroppo nessun altro sembrava funzionare.

+0

puoi fornire un codice funzionante? –

+0

Vorrei. Questa è stata una vita fa e il codice è di proprietà della società a cui non lavoro più. –

+0

Devo capire che quella schifezza è ANCORA successa dopo tutti questi anni ?! –

1

Si arresta in modo anomalo perché è stato assegnato ApplicationContext alla visualizzazione Web. Quando si fa clic su un tag SELECT, Android visualizza internamente le sue opzioni utilizzando un codice nativo AlertDialog.
La Webview deve essere creata con un contesto di attività perché l'istanza AlertDialog richiede un contesto Activity.

2

In realtà quello che hai fatto è che hai passato il Contesto di applicazione alla visualizzazione web. Un tag SELECT visualizza fondamentalmente le sue opzioni utilizzando il codice nativo di Android AlertDialog che necessita di un Contesto attività .

Per risolvere il problema è possibile passare il Contesto attività tramite il file di layout (XML) come mostrato di seguito.

<LinearLayout 
    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:layout_width="match_parent" 
    android:layout_height="match_parent" 
    android:orientation="vertical" 
    android:fitsSystemWindows="true" 
    tools:context="com.myApp.Activities.WebViewActivity"> 

    <WebView 
      tools:context="com.myApp.Activities.WebViewActivity" 
      android:layout_width="match_parent" 
      android:id="@+id/webView" 
      android:layout_height="match_parent"/> 

</LinearLayout> 

strumenti: context = "com.myApp.Activities.WebViewActivity"

+0

Dove eri 6 anni fa? :) –

0

ritardo al gioco, ma che ho letto per una mezza giornata di lavoro, e cercando soluzioni diverse per diversi giorni lavorativi, e tornò a questo thread più e più volte. Ho avuto un frammento con una Webview al suo interno, e le versioni di Android precedenti Oreo (28) si sono bloccate quando si seleziona una selezione in HTML mentre 28+ lo ha semplicemente ignorato.

E 'quello che ha detto Diffy e Igor_K detto (anche se la soluzione di Diffy non ha funzionato): è il contesto sbagliato. Quello che mi ha fatto risolvere è stato this thread. Copia e incolla la risposta qui sotto:

Heaps of love a Manish Sharma per questa risposta.

Per passare nuovo contesto per WebView è possibile creare un metodo per inizializzare WebView, passando un argomento di contesto come illustrato di seguito:

public static Webview initializeWebView(Context context) 
{ 

    myWebView = new WebView(); 
    return myWebView; 

} 

E dopo questo è possibile chiamare questo metodo ovunque tu voglia e quando vuoi. È possibile chiamare questo come illustrato di seguito:

myWebView = initializeWebView(YourActivityName.this); 
//this way whatever Context you will pass your webview will be initialized that way 
//for example you can also pass getApplicationContext() as an Argument 
myWebView = initializeWebView(getApplicationContext()); 
//or 
myWebView = initializeWebView(customContext); 

questo customContext può essere qualsiasi contesto che viene ereditato da altri contesto che si voleva utilizzare.