Я хочу проверить URL-адрес в тексте редактирования и, если он действителен, добавить элемент в режиме ресайклера. Поэтому для этой цели я запустил поток для проверки HTTP-соединения.

 thread = new Thread(new Runnable() {
                    @Override
                    public void run() {

                        String link = edt.getText().toString();
                        URL url = null;
                        try {
                            url = new URL(link);
                            HttpURLConnection connection = (HttpURLConnection) url.openConnection();
                            int code = connection.getResponseCode();

                            if(code == 200) {
                                Log.d(TAG, "reachable");
                                InsertItem(url,adapter);
                            } else {
                                Log.d(TAG, "in catch: not reachable");
                            }
                        }  catch (IOException e) {
                            e.printStackTrace();
                        }
                    }
                });
                thread.start();

Проблема в том, что я получаю ошибку при попытке добавить элемент

 private void InsertItem(URL url, MyAdapter adapter) {
        thread.currentThread().interrupt();
        arrayList.add(0,new file(url.toString()));
        adapter.notifyItemChanged(0);
};

И ошибка:

android.view.ViewRootImpl$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.
0
ghazalia 27 Ноя 2021 в 09:48

1 ответ

Лучший ответ

android.view.ViewRootImpl $ CalledFromWrongThreadException: только исходный поток, создавший иерархию представлений, может касаться его представлений.

Похоже, внутри вашего нового потока вы вызываете InsertItem (url, adapter) (должен начинаться с буквы «I» в нижнем регистре), который пытается выполнить некоторую работу с элементом пользовательского интерфейса.

В сообщении об ошибке вы не можете касаться представлений за пределами потока пользовательского интерфейса. Вы можете попробовать добавить runOnUiThread (() -> insertItems (url, adapter) внутри вашего потока, чтобы опубликовать действие в потоке пользовательского интерфейса.

1
R Millaci 27 Ноя 2021 в 10:01
Спасибо. как я могу остановить все потоки, которые я запускаю? (новый поток, runOnUiThread)
 – 
ghazalia
27 Ноя 2021 в 10:27
RunOnUiThread, которым вам не нужно управлять, это просто способ выполнить некоторые действия в основном потоке Android. Вы можете вызвать прерывание в своем новом потоке так же, как и раньше, если вы переместите свой блок runOnUiThread в метод insertItem () и перед вызовом thread.interrupt ()
 – 
R Millaci
27 Ноя 2021 в 10:35