2016-04-12 7 views
1

, also habe ich das Android-Lernprogramm für Dialoge Link angeschaut. Und beschlossen, ein benutzerdefiniertes Dialogfeld zu erstellen, um einen Benutzer nach einem Host, Benutzernamen und Kennwort für die Verbindung zu fragen. Ich möchte nicht mit dem Host innerhalb der Dialog-Klasse verbinden, also muss ich die Strings zurück an die Hauptaktivität übergeben. Ich habe versucht, dies mit einer Schnittstelle wie im Tutorial, aber wenn ich das Ereignis in der Hauptaktivität auf den EditText zugreifen will, bekomme ich eine NullPointerException. Ich bin mir sicher, dass es einen einfachen Workaround gibt oder ich einen anderen dummen Fehler mache. Bitte helfen Sie!Android: Das Zurückgeben von Benutzereingaben von DialogFragment führt zu NullPointerException

Dialog Klasse:

public class ConnectionDialog extends DialogFragment { 

public interface NoticeDialogListener { 
    public void onDialogPositiveClick(DialogFragment dialog); 
    public void onDialogNegativeClick(DialogFragment dialog); 
} 

// Use this instance of the interface to deliver action events 
NoticeDialogListener mListener; 

// Override the Fragment.onAttach() method to instantiate the NoticeDialogListener 
@Override 
public void onAttach(Activity activity) { 
    super.onAttach(activity); 
    // Verify that the host activity implements the callback interface 
    try { 
     // Instantiate the NoticeDialogListener so we can send events to the host 
     mListener = (NoticeDialogListener) activity; 
    } catch (ClassCastException e) { 
     // The activity doesn't implement the interface, throw exception 
     throw new ClassCastException(activity.toString() 
       + " must implement NoticeDialogListener"); 
    } 
} 


@Override 
public Dialog onCreateDialog(Bundle savedInstanceState) { 
    AlertDialog.Builder builder = new AlertDialog.Builder(getActivity()); 
    // Get the layout inflater 
    final LayoutInflater inflater = getActivity().getLayoutInflater(); 
    // Inflate and set the layout for the dialog 
    // Pass null as the parent view because its going in the dialog layout 
    builder.setView(inflater.inflate(R.layout.connection_dialog, null)) 
      // Add action buttons 
      .setPositiveButton(R.string.connect, new DialogInterface.OnClickListener() { 
       @Override 
       public void onClick(DialogInterface dialog, int id) { 
        mListener.onDialogPositiveClick(ConnectionDialog.this); 
        // sign in the user ... 
       } 
      }) 
      .setNegativeButton(R.string.abort, new DialogInterface.OnClickListener() { 
       public void onClick(DialogInterface dialog, int id) { 
        mListener.onDialogNegativeClick(ConnectionDialog.this); 
        //LoginDialogFragment.this.getDialog().cancel(); 
       } 
      }); 
    return builder.create(); 

} 
} 

Und Hauptaktivität:

public class MainActivity extends FragmentActivity implements ConnectionDialog.NoticeDialogListener { 

public void showConnectionDialog() { 
    // Create an instance of the dialog fragment and show it 
    DialogFragment dialog = new ConnectionDialog(); 
    dialog.show(getFragmentManager(), "Connection Dialog"); 
} 

public void toast(String message){ 
    Context context = getApplicationContext(); 
    int duration = Toast.LENGTH_SHORT; 
    Toast toast = Toast.makeText(context, message, duration); 
    toast.show(); 
} 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_main); 

} 

@Override 
public void onDialogPositiveClick(DialogFragment dialog) { 
    EditText editHost = (EditText)dialog.getView().findViewById(R.id.dialog_host); 
    EditText editUser = (EditText)dialog.getView().findViewById(R.id.dialog_user); 
    EditText editPassword = (EditText)dialog.getView().findViewById(R.id.dialog_password); 
    String host = editHost.getText().toString(); 
    String user = editUser.getText().toString(); 
    String password = editPassword.getText().toString(); 

    dialog.dismiss(); 
} 

@Override 
public void onDialogNegativeClick(DialogFragment dialog) { 
    toast("cancled"); 
    dialog.dismiss(); 
    // User touched the dialog's negative button 
} 
public void connect(View view){ 
    showConnectionDialog(); 
} 
} 

Vielen Dank!

Edit:

Nullpointer

04-12 18:52:00.278 5216-5216/com.example.josias.myapplication E/AndroidRuntime: FATAL EXCEPTION: main 
                      Process: com.example.josias.myapplication, PID: 5216 
                      java.lang.NullPointerException: Attempt to invoke virtual method 'android.view.View android.view.View.findViewById(int)' on a null object reference 
                       at com.example.josias.myapplication.MainActivity.onDialogPositiveClick(MainActivity.java:44) 
                       at com.example.josias.myapplication.ConnectionDialog$2.onClick(ConnectionDialog.java:54) 
                       at android.support.v7.app.AlertController$ButtonHandler.handleMessage(AlertController.java:153) 
                       at android.os.Handler.dispatchMessage(Handler.java:102) 
                       at android.os.Looper.loop(Looper.java:148) 
                       at android.app.ActivityThread.main(ActivityThread.java:5417) 
                       at java.lang.reflect.Method.invoke(Native Method) 
                       at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726) 
                       at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616) 
+2

Auf einer anderen Anmerkung: Warum don‘ t übergeben Sie "String" -Werte über "interface" anstelle von dialog? –

+0

Sie müssen ein '' '' '' '' '' '' '' '' '' '' '' findViewById' 'darauf zeigen, sonst erhalten Sie' null' –

+0

@ cricket_007 ich mache. Ich habe nur vergessen, es in den Code aboce aufzunehmen. jetzt ist es da. Die Methode connect() wird ausgeführt, indem eine Taste gedrückt wird – Suppenkasper

Antwort

0

Schalten Sie Ihre Schnittstellen, um die String-Werte zu übergeben, statt entlang der gesamten Dialog zu übergeben.

Um Ihnen den Einstieg, so etwas wie dieses

public interface NoticeDialogListener { 
    public void onDialogPositiveClick(String host, String user, String pass); 
    public void onDialogNegativeClick(); 
} 
final LayoutInflater inflater = getActivity().getLayoutInflater(); 
// Inflate and set the layout for the dialog 
// Pass null as the parent view because its going in the dialog layout 
View dialogView = inflater.inflate(R.layout.connection_dialog, null); 

final EditText editHost = (EditText)dialogView.findViewById(R.id.dialog_host); 
final EditText editUser = (EditText)dialogView.findViewById(R.id.dialog_user); 
final EditText editPassword = (EditText)dialogView.findViewById(R.id.dialog_password); 

builder.setView(dialogView) 
     // Add action buttons 
     .setPositiveButton(R.string.connect, new DialogInterface.OnClickListener() { 
      @Override 
      public void onClick(DialogInterface dialog, int id) { 
       String host = editHost.getText().toString(); 
       String user = editUser.getText().toString(); 
       String pass = editPassword.getText().toString(); 

       mListener.onDialogPositiveClick(host, user, pass); 
      } 
     }) 
     // set null to dismiss dialog 
     .setNegativeButton(R.string.abort, null); 
return builder.create(); 
+0

Das ist genau das, was ich gesucht habe. Vielen Dank!Wenn ich es komplizierter machen wollte, konnte ich trotzdem das gesamte dialogView übergeben, oder? – Suppenkasper

+0

Sie könnten, aber es ist eine gute Angewohnheit, nur um die Variablen herumzugeben, die Sie tatsächlich benötigen. Wenn Sie etwas Kompliziertes benötigen, sollten Sie vielleicht eine Klasse erstellen, die alle Daten aus dem Dialog enthält und diese anstelle vieler Parameter verwendet. –

1

Ja, Sie können. Ihre Schnittstelle wird so aussehen,

public interface NoticeDialogListener { 
    public void onDialogPositiveClick(DialogFragment dialog); 
} 

Pass DialogFragment weise wie folgt auf die Schnittstelle, in positive Taste onClick() -Methode.

Weiter in Ihrer MainActivity - Sie können jedes Feld von DialogFragment, das Sie als Formulare angezeigt haben. In Interface-Methode, die Sie in MainActivity außer Kraft gesetzt werden, wie dies definieren,

@Override 
public void onSaveButtonClick(DialogFragment dialog) { 
...... 

    EditText field1= (EditText) dialog.getDialog().findViewById(R.id.field1); 
    EditText field2= (EditText) dialog.getDialog().findViewById(R.id.field2); 
.... 
} 

Dann Sie den Text und die Arbeit wie pro Ihre Anforderung erhalten. Für weitere Informationen können Sie Refre diese: https://www.youtube.com/watch?v=a0T--DfR48A Hier ist alles gut erklärt ...

0

sollten Sie verwenden:

dialog.getDialog() 

statt:

dialog.getView() 
+0

was diese Art von Unsinn beantworten. –

Verwandte Themen