Форум программистов, компьютерный форум, киберфорум
Наши страницы
Программирование Android
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.67/3: Рейтинг темы: голосов - 3, средняя оценка - 4.67
Serbis
8 / 8 / 2
Регистрация: 13.07.2012
Сообщений: 133
1

Вызов диалога с ожиданием реакции - мьютекс лочит UI поток

13.02.2015, 14:08. Просмотров 625. Ответов 5
Метки нет (Все метки)

Необходимо решить классическую задачу - вызвать диалог, дождаться действия пользователя и на их основе сделать что-то. Естественно нужно это все сделать выполнив останов главного потока не затронув UI поток. Решение взял такое. Из активности вызывается функция вспомогательного класса, который сформировав первый асинхронный поток, вызывает из другого класса конструктор диалога который в свою очередь запускается как ответвление UI потока, первый поток блокируется мьютексом и и ждет реакции от диалога. При этом по логике UI поток должен быть свободен. Но получается так, что по непонятным мне причинам мьютекс лочит как раз его, программа виснет впав в бесконечное ожидание.

MainActivity
Java
1
2
DialogGrouper dialogConstructor = new DialogGrouper(this, MainActivity.this);
Boolean result = dialogConstructor.createDeleteDialog();
DialogGrouper
Java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
public Boolean createDeleteDialog() {
        class DialogTask extends AsyncTask<Void, Void, Boolean> {
            boolean response;
 
            @Override
            protected Boolean doInBackground(Void... params) {
                mainActivity.runOnUiThread(new Runnable() {                
                    public void run() {
                        deleteDialog.show();
                    }
                });
 
                try {
                    deleteDialog.waitForResponse();            
                    response = deleteDialog.getResult();
                } catch (InterruptedException e) {
                    //response
                }
 
                return response;
            }
        }
 
        DialogTask dialog = new DialogTask();
        dialog.execute();
 
        try {
            return dialog.get();
        } catch (InterruptedException e) {
            return false;
        } catch (ExecutionException e){ return false; }
 
    }
DeleteDialog
Java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
public class DeleteDialog {
    private AlertDialog.Builder builder;
    private Mutex mMutex;
    private boolean mResult;
 
    public DeleteDialog(Context context) {
        mMutex = new Mutex();
        builder = new AlertDialog.Builder(context);
        mResult = false;
 
        builder.setTitle(R.string.dialog_TitleDelete);
        builder.setCancelable(true);
 
        builder.setPositiveButton(R.string.dialog_yes, new DialogInterface.OnClickListener() {
 
            @Override
            public void onClick(DialogInterface dialog, int which) {
                mResult = true;
                mMutex.unlock();
            }
        });
        builder.setNegativeButton(R.string.dialog_no, new DialogInterface.OnClickListener() {
            @Override
            public void onClick(DialogInterface dialog, int which) {
                mResult = false;
                mMutex.unlock();
                dialog.cancel();
            }
        });
 
 
    }
 
    public void show() {
        builder.show();
    }
 
    public boolean getResult() {
        return mResult;
    }
 
    public void waitForResponse() throws InterruptedException {    
        mMutex.lock();
    }
}
Mutex
Java
1
2
3
4
5
6
7
8
public class Mutex {
    public synchronized void lock() throws InterruptedException {
        this.wait();
    }
    public synchronized void unlock() {
        this.notify();
    }
}
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
13.02.2015, 14:08
Ответы с готовыми решениями:

Вызов диалога из диалога
Есть диалог, как сделать чтобы при выборе определенной позиции в это диалоге...

Вызов диалога из кнопки в action bar-е
Закинул кнопочку в action bar при нажатии на которую должен создаваться диалог,...

Как правильно завершить поток, который лочит мьютекс в цикле?
Есть поток, созданный посредствам CreateThread, который в цикле лочит именной...

Вызов с ожиданием завершения
Проблема не раз обсуждалась и имеет решения на разных форумах Однако...

Вызов диалога
Хотел вызывать окно по нажатию на кнопку. Вот код: var button:btn1 = new...

5
Armagedo
13.02.2015, 15:14
  #2

Не по теме:

Какой-то сюр...или я ничего не понял 8-)

0
Pablito
2731 / 2166 / 735
Регистрация: 12.05.2014
Сообщений: 7,579
Завершенные тесты: 1
13.02.2015, 19:40 3
Java
1
2
3
4
5
6
protected Boolean doInBackground(Void... params) {
                mainActivity.runOnUiThread(new Runnable() {                
                    public void run() {
                        deleteDialog.show();
                    }
                });
фу так делать, я бы ВСЕ вытер и сел думать над новой структурой программы
0
Serbis
8 / 8 / 2
Регистрация: 13.07.2012
Сообщений: 133
13.02.2015, 21:54  [ТС] 4
Паблито, ваши предложения по реализации данного механизма? Я бьюсь над этим вопросом третий день, пытаясь найти хотя бы просто работающее решение не говоря уж о его красоте. Вся проблема в том, что "великие" программисты из гугл как-то подслили этот момент, а когда поняли это, было уже поздно что либо переделывать. В начале я решил прощупать почву так сказать, сделал функцию с передачей параметров диалога, но каково было мое разочарование, когда я понял, что onCяlickListener диалога ограничен только его собственным пространством имен а любая попытка "подождать" появления флага завершения приводила к повисанию. Тогда я решил запустить диалог в отдельном потоке и вызвать wait, но и тут получил по ушам - все опять повисло. Поиск по просторам сети привел вот к такому корявому решению из нескольких потоков. Желание лезть в такие некрасивые решения, обусловлен тем, что в программе есть десять функций делающих разные вещи, но использующих в каркасе один и тот же диалог. Это образует строк 200 практически идентичного кода, который "если бы не криворукие из гагла" можно было бы очень просто и удобно упаковать в одну функцию, но увы нельзя...
0
Nixy
ComfyMobile
400 / 281 / 34
Регистрация: 24.07.2012
Сообщений: 916
14.02.2015, 11:38 5
Java
1
2
3
4
5
6
7
@Override
            protected Boolean doInBackground(Void... params) {
                mainActivity.runOnUiThread(new Runnable() {                
                    public void run() {
                        deleteDialog.show();
                    }
                });
Вы в корне не понимаете задачи AsyncTaska. Погуглите чуть-чуть, если не справитесь то пишите еще раз, постараемся помочь.
0
Armagedo
209 / 209 / 60
Регистрация: 22.08.2014
Сообщений: 644
14.02.2015, 12:04 6
Вы хоть один читали ТЗ?

Естественно нужно это все сделать выполнив останов главного потока не затронув UI поток.

...
0
14.02.2015, 12:04
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
14.02.2015, 12:04

Вызов диалога из потока
В потоке нужно вызвать QDialog и ждать нажатия кнопки пользователем, т.е. поток...

Вызов диалога из потока
Вопрос нубский скажем так, но как вызвать алерт из не GUI потока, подождать...

Вызов диалога из case
привет. есть массив case (в dialog), как сделать, что бы заместо &quot;'0')sudo...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
6
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.
Рейтинг@Mail.ru