You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android Socket接收树莓派温湿度数据调用TextView.setText报错如何解决?

错误根因

  • Android系统规定所有UI控件的更新操作必须在主线程(UI线程)执行,你的StartThread是自定义子线程,直接在子线程调用temphum.setText()会直接触发CalledFromWrongThreadException崩溃
  • 你当前转字符串的方式会残留无效内容:每次创建的64字节buffer如果没有被数据填满,未填充的字节会被转成乱码/空白字符,导致TextView显示冗余旧内容

修复方案

1. 修正StartThread的循环逻辑,切主线程更新UI+清理无效字符

直接替换你的StartThread类代码即可:

class StartThread extends Thread{
    int bytes;
    // 增加退出标记,避免线程一直运行导致内存泄漏
    private boolean isRunning = true;

    public StartThread(){
    }

    // 点击停止按钮时调用该方法终止接收循环
    public void stopReceive() {
        isRunning = false;
    }

    public void run(){
        try {
            Log.d(TAG, "데이터 수신 준비");
            // 把流初始化移到循环外,避免重复创建对象
            InputStream input = socket.getInputStream();
            byte[] buffer = new byte[64];
            while (isRunning) {
                bytes = input.read(buffer);
                if(bytes <= 0) break; // 连接断开/读取结束直接退出循环
                // 只转换实际读取到的字节长度,trim去掉首尾空白/换行符,避免残留无效内容
                String sensor = new String(buffer, 0, bytes).trim();
                Log.d(TAG, "data = " + sensor);
                // 切换到主线程更新UI
                runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        // setText会直接覆盖旧内容,无需额外清理
                        temphum.setText("data = " + sensor);
                    }
                });
            }
        }catch(IOException e){
            e.printStackTrace();
            Log.e(TAG,"수신 에러");
        }
    }
}

2. 修正按钮逻辑,增加线程控制

先把StartThread声明为全局变量,方便停止时调用:

// 加到成员变量声明区域
private StartThread sthread;

修改StartButton和StopButton的点击逻辑:

StartButton.setOnClickListener(new Button.OnClickListener() {
    @Override
    public void onClick(View view) {
        sthread = new StartThread();
        StartButton.setEnabled(false);
        StopButton.setEnabled(true);
        sthread.start();
    }
});

StopButton.setOnClickListener(new Button.OnClickListener() {
    @Override
    public void onClick(View view) {
        // 先终止接收线程
        if(sthread != null) {
            sthread.stopReceive();
        }
        StopThread spthread = new StopThread();
        StartButton.setEnabled(true);
        StopButton.setEnabled(false);
        spthread.start();
    }
});

补充说明

setText()方法本身会直接覆盖TextView的原有内容,只要传入的sensor字符串清理掉了冗余无效字符,就会自动展示最新的传感器数据,不需要额外做刷新/删除旧数据操作。

内容的提问来源于stack exchange,提问作者user17135507

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.30 10:54:01