Estoy tratando de crear un inicio de sesión para una aplicación. Sin embargo, tengo un problema.
Este es mi código:
package com.forgetmenot.loginregister; import java.util.ArrayList; import java.util.List; import org.apache.http.NameValuePair; import org.apache.http.message.BasicNameValuePair; import org.json.JSONArray; import org.json.JSONException; import org.json.JSONObject; import android.app.Activity; import android.content.Intent; import android.os.AsyncTask; import android.os.Bundle; import android.util.Log; import android.view.Menu; import android.view.MenuItem; import android.view.View; import android.widget.Button; import android.widget.EditText; public class MainActivity extends Activity { EditText uname, password; Button submit; // Creating JSON Parser object JSONParser jParser = new JSONParser(); private static final String TAG = "Login"; JSONObject json; private static String url_login = "http://localhost:8080/ForgetMeNotApplication/Login"; //JSONArray incoming_msg = null; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); findViewsById(); submit.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View arg0) { // execute method invokes doInBackground() where we open a Http URL connection using the given Servlet URL //and get output response from InputStream and return it. new Login().execute(); } }); } private void findViewsById() { uname = (EditText) findViewById(R.id.txtUser); password = (EditText) findViewById(R.id.txtPass); submit = (Button) findViewById(R.id.login); } private class Login extends AsyncTask{ @Override protected String doInBackground(String... args) { // Getting username and password from user input String username = uname.getText().toString(); String pass = password.getText().toString(); List params = new ArrayList(); params.add(new BasicNameValuePair("u",username)); params.add(new BasicNameValuePair("p",pass)); json = jParser.makeHttpRequest(url_login, "GET", params); String s=null; try { s= json.getString("info"); Log.d("Msg", json.getString("info")); if(s.equals("success")){ Intent login = new Intent(getApplicationContext(), home.class); login.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); startActivity(login); finish(); } } catch (JSONException e) { // TODO Auto-generated catch block e.printStackTrace(); } return null; } } @Override public boolean onCreateOptionsMenu(Menu menu) { // Inflate the menu; this adds items to the action bar if it is present. getMenuInflater().inflate(R.menu.menu_main, menu); return true; } @Override public boolean onOptionsItemSelected(MenuItem item) { // Handle action bar item clicks here. The action bar will // automatically handle clicks on the Home/Up button, so long // as you specify a parent activity in AndroidManifest.xml. int id = item.getItemId(); if (id == R.id.action_settings) { return true; } return super.onOptionsItemSelected(item); } }
El estudio de Android dice que se debe llamar al método getText()
desde el subproceso UI en las instrucciones: uname.getText().toString();
y password.getText().toString();
¿¿Soluciones posibles??
Intente pasar Sus valores a Login AsyncTask
mediante el Login AsyncTask
execute(param1, param1, ..., paramN)
:
submit.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View arg0) { String username = uname.getText().toString(); String pass = password.getText().toString(); new Login().execute(username, pass); } }); } private void findViewsById() { uname = (EditText) findViewById(R.id.txtUser); password = (EditText) findViewById(R.id.txtPass); submit = (Button) findViewById(R.id.login); } private class Login extends AsyncTask{ @Override protected String doInBackground(String... args) { // Getting username and password from user input String username = args[0]; String pass = args[1];
hacer username
y pass
variable de clase de login
y anular onPreExcecute()
y hacer esto:
@Override protected void onPreExecute() { username = uname.getText().toString(); pass = password.getText().toString(); }
Está accediendo al hilo de la interfaz de usuario de un hilo de fondo aquí:
String username = uname.getText().toString(); String pass = password.getText().toString();
Lo que quiere hacer es pasar las cadenas de nombre de usuario / contraseña a su constructor de tareas en segundo plano o puede pasarlas directamente al método de ejecución. Prefiero definirlos en el constructor si van a ser necesarios (como los tuyos).
Defina su LoginTask como
String uname; String password; public Login(String username, String password({ this.uname = username; this.password = password; }
Luego, en doInBackground () usa los miembros en su lugar.
List params = new ArrayList (); params.add(new BasicNameValuePair("u",this.username)); params.add(new BasicNameValuePair("p",this.pass)); json = jParser.makeHttpRequest(url_login, "GET", params);
Editar – entonces su nueva llamada a Login (). Execute () se vería más como esto
new Login(uname.getText().toString(), password.getText().toString()).execute();
A menos que haya cambiado algo que yo no sepa, eso no debería ser un problema. Los elementos de la IU no se pueden actualizar desde el fondo, pero acceder a sus captadores nunca ha sido un problema.
De todos modos, puedes evitar esto agregando un constructor a tu AsyncTask
que tomaría las dos AsyncTask
y luego las enviaría al crear tu tarea.
private class Login extends AsyncTask{ // member variables of the task class String uName, pwd public Login(String userName, String password) { uName = userName; pwd = password; } @Override protected String doInBackground(String... args) {...}
y pasarlos en su onClick()
@Override public void onClick(View arg0) { // execute method invokes doInBackground() where we open a Http URL connection using the given Servlet URL //and get output response from InputStream and return it. // pass them here new Login(uname.getText().toString(), password.getText().toString()).execute(); }
La excepción se produce porque doInBackground()
se invoca desde un hilo de fondo. Agregaría dos parámetros de cadena al constructor de su clase de Login
de Login
.
Me gustaría aconsejarle que obtenga más conocimiento sobre AsyncTasks
y Threading en Android. Por ejemplo, hay una página en los documentos oficiales: http://developer.android.com/guide/components/processes-and-threads.html .
También puede echar un vistazo a este curso: https://www.udacity.com/course/developing-android-apps–ud853 . Puede aprender muchos conceptos básicos del marco Android.