安卓在子线程传值给主线程,通过Handler传值

2022-07-14 13:56:51 浏览数 (1)

昨晚上在进行http请求获取数据并修改listview的时候遇到了一个问题Only the original thread that created a view hierarchy can touch its views

大概意思就是:只有创建了视图层级的原始线程才可以修改这个视图

于是我百度了一下,然后大概解决方案是这样子的,子线程通过handler传值给主线程,主线程接收后,再进行修改listview。

代码语言:javascript复制
Handler handler = new Handler() {
    @Override
    public void handleMessage(Message msg) {
       super.handleMessage(msg);
       if (msg.what == 1) {
         Bundle data = msg.getData();
         String val = data.getString("value");
         //设置UI
         tvCode.setText(val);
         Log.i(TAG, "请求结果:"   val);
       } else if (msg.what ==0) {
         Toast.makeText(getApplicationContext(),"请求资源不成功",Toast.LENGTH_LONG).show();
       }
  }
};
 
/**
 * 处理网络请求的线程
 */
private class RequestThread extends Thread {
  @Override
  public void run() {
     
     //网络请求
     String string = 请求结果
     Message msg = new Message();
     Bundle data = new Bundle();
 
    //将获取到的String装载到msg中
     data.putString("value", string);
     msg.setData(data);
     msg.what = 1;
     //发消息到主线程
     handler.sendMessage(msg);           
    }
}
 
//点击事件启动新线程
public void test(View v){
   new RequestThread().start();
}

解决方法原链接:https://blog.csdn.net/LJX_ahut/article/details/89432576

经过实践着实有用。

获取前:

获取后:

MainActivity.java代码

代码语言:javascript复制
package ink.cik.logininfoapp;

import androidx.appcompat.app.ActionBar;
import androidx.appcompat.app.AppCompatActivity;

import android.annotation.SuppressLint;
import android.net.wifi.aware.DiscoverySession;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.view.Menu;
import android.view.View;
import android.widget.Adapter;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.ListView;
import android.widget.Toast;

import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;

import java.util.ArrayList;
import java.util.List;

import ink.cik.logininfoapp.eneity.userInfo;
import ink.cik.logininfoapp.help.httpHelper;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;

public class MainActivity extends AppCompatActivity {
    private final Gson gson = new Gson();
    @SuppressLint("HandlerLeak")
    Handler handler = new Handler() {
        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            if (msg.what == 1) {
                Bundle data = msg.getData();
                String val = data.getString("value");
                List<userInfo> userInfoList = parseJson(val);
                ListView listView = (ListView) findViewById(R.id.listInfo);
                ArrayList<String> list = new ArrayList<String>();//数据源集合创建
                for (userInfo userInfo : userInfoList) {
                    list.add(userInfo.getUserName());
                }
                ArrayAdapter<String> adapter = new ArrayAdapter<String>(
                        MainActivity.this, android.R.layout.simple_list_item_1, list
                );
                listView.setAdapter(adapter);
            } else if (msg.what == 0) {
                Toast.makeText(MainActivity.this, "数据获取失败,请检查网络!", Toast.LENGTH_SHORT);
            }
        }
    };

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Button button = (Button) findViewById(R.id.searchButton);
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                getAll();
            }
        });


    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.menu, menu);
        return true;
    }

    private void getAll() {
        final httpHelper httpHelper = new httpHelper();
        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    String res = httpHelper.httpGet("https://api.565.ink/login/getAll?passwd=lanol666");
                    Log.d("结果:", res);
                    Message msg = new Message();
                    Bundle data = new Bundle();
                    //将获取到的String装载到msg中
                    data.putString("value", res);
                    msg.setData(data);
                    msg.what = 1;
                    handler.sendMessage(msg);
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }).start();
    }

    private List<userInfo> parseJson(String JsonData) {
        Gson gson = new Gson();
        List<userInfo> userInfoList = gson.fromJson(JsonData, new TypeToken<List<userInfo>>() {
        }.getType());
        return userInfoList;
    }
}

0 人点赞