Russian Qt Forum
Октябрь 01, 2024, 07:22 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: 1 2 3 [4] 5 6   Вниз
  Печать  
Автор Тема: Создание/вызов методов в разных потоках.  (Прочитано 44785 раз)
spectre71
Гость
« Ответ #45 : Ноябрь 29, 2009, 14:33 »

Тут у меня один вопрос (наверное, ввиду моей неопытности при работе с сигналами/слотами): как указать слот, чтобы сигнал типа qwebview слался в run() дочернего потока??

Смотри:
int QThread::exec ();
Записан
serg_hd
Хакер
*****
Offline Offline

Сообщений: 668



Просмотр профиля
« Ответ #46 : Ноябрь 29, 2009, 14:34 »

п.с. сил больше нет бороться с этим qwebview((
Я это уже предлагал, но повторюсь.
А ты не пробовал использовать вместо QWebView объекты классов QWebPage/QWebFrame.
Это не GUI-классы и думаю спокойно смогут работать в других потоках.

У QWebPage нет метода load()
Записан

kubuntu/Win7/x64/NetBeans
BRE
Гость
« Ответ #47 : Ноябрь 29, 2009, 14:34 »

У QWebPage нет метода load()
А у QWebFrame есть.  Улыбающийся
Записан
spectre71
Гость
« Ответ #48 : Ноябрь 29, 2009, 14:38 »

У QWebPage нет метода load()
А у QWebFrame есть.  Улыбающийся

QWebFrame * QWebPage::currentFrame () const
Предаем его в другой поток
void QWebFrame::load ( const QUrl & url)

Видимо так.
Записан
zenden
Гость
« Ответ #49 : Ноябрь 29, 2009, 14:49 »

Конкретную задачу решили, а общую - нет.
Записан
serg_hd
Хакер
*****
Offline Offline

Сообщений: 668



Просмотр профиля
« Ответ #50 : Ноябрь 29, 2009, 14:50 »

конкретную это какую?
Записан

kubuntu/Win7/x64/NetBeans
niXman
Гость
« Ответ #51 : Ноябрь 29, 2009, 15:14 »

Цитировать
this.wv.load(this.url);
Так делать нельзя. ВебВью создан в одном потоке, ты вызываешь его метод из другого потока. Шли ему сигнал:
Код
C++ (Qt)
class RunThreads extends QSignalEmitter implements Runnable
{
//сигнал для метода load(QUrl) -> QWebView
public Signal1<QUrl> signalOut3 = new Signal1<QUrl>();
...
...
public void run()
{
 for (int i = 0; i <= _thCount; i ++)
 {
  //при получении ответа от главного потока использовать объект QWebView в методе xxx2() этого класса
  _form.signalOut1.connect(this, "xxx2(QWebView)", ConnectionType.QueuedConnection);
  //испустить сигнал, чтобы главный поток создал экземпляр QWebView
  this.signalOut2.emit(1); /** политика сигнала(почему-то) QueuedConnection.
                                        это означает что сигнал будет класться в очередь.
                                        допустим(возможно это qt-jambi specific. т.к. в с++ этого аргумента указывать не нужно),
                                        сигнал стоит в очереди, и еще не обработан.
                                        но код в цикле его не ждет. и при попытке использовать созданный объект
                                        (который еще не создался), краш.
  */

  /** а вот собственно и испускание сигнала */
  signalOut3.emit(this.url);
 }
}
 
public void xxx2(QWebView v)
{
 this.wv = v;
 /** соединяем только что созданный объект с нашим сигналом */
 signalOut3.connect(this.wv, "load(QUrl)");
}
 
Т.е. я это реализовал именно так. Один поток! Шлет сигналы на создание вьюшек, в слоте получает указатель на созданный объект. пихает его массив указателей.
Еще поправка. Так как все созданные объекты конектятся к одному сигналу, то при его испускании, они все получают один УРЛ. А этого нам не нужно Подмигивающий Чтоб этого избежать, я унаследовался от QWebView, добавил метод load(QWidget*, const QUrl&). В этом методе я проверяю, этому ли объекту предназначается посланный сигнал. Да, это кривой костыль, знаю. Но нужно написать QSignalMapper, только наоборот.
И еще в унаследованный класс добавил метод bool isFree() const. При получении СВОЕГО урл, этот флаг ставится в false. Когда же QWebView, заканчивает загрузку, этот флаг ставиться в true, и цикл, перебирающий объекты, видя что "этот" свободен, испускает сигнал.
Все.
« Последнее редактирование: Ноябрь 29, 2009, 15:17 от niXman » Записан
niXman
Гость
« Ответ #52 : Ноябрь 29, 2009, 15:36 »

Полез во внутренности QWebView, и заблудился.
Одно что я понял, это то, что QWebView создает отдельный поток. Так как когда я закачиваю файл, прогресс операции обновляется без задержек, и обработчики всяких кнопок работают.
Записан
spectre71
Гость
« Ответ #53 : Ноябрь 29, 2009, 15:51 »

Цитировать
this.wv.load(this.url);
Так делать нельзя. ВебВью создан в одном потоке, ты вызываешь его метод из другого потока. Шли ему сигнал:
Код
C++ (Qt)
 
Т.е. я это реализовал именно так. Один поток! Шлет сигналы на создание вьюшек, в слоте получает указатель на созданный объект. пихает его массив указателей.
Еще поправка. Так как все созданные объекты конектятся к одному сигналу, то при его испускании, они все получают один УРЛ. А этого нам не нужно Подмигивающий Чтоб этого избежать, я унаследовался от QWebView, добавил метод load(QWidget*, const QUrl&). В этом методе я проверяю, этому ли объекту предназначается посланный сигнал. Да, это кривой костыль, знаю. Но нужно написать QSignalMapper, только наоборот.
И еще в унаследованный класс добавил метод bool isFree() const. При получении СВОЕГО урл, этот флаг ставится в false. Когда же QWebView, заканчивает загрузку, этот флаг ставиться в true, и цикл, перебирающий объекты, видя что "этот" свободен, испускает сигнал.
Все.

Что к чему. Что-то намудрил.
Я согласен что как я написал нельзя, но это общая схема.
Чуть более подробно.

В главном потоке:
- QWebPage* WebPage = new QWebPage(NULL);
- QWebFrame* WebFrame = WebPage->mainFrame();
- Cоздаем новый поток и передаем ему WebFrame или предаем каким либо образом(можно и через сигнал)  WebFrame в уже существующий поток
Во второстепенном потоке:
- WebFrame::load (const QUrl & url)
- Испускаем сигнал после загрузки
В главном потоке:
WebView->setPage(WebPage)

============
Остальное технические детали, главное чтобы WebFrame::load (const QUrl & url) делался в другом потоке.
============
Но есть проблема!
Может этого и нельзя сделать!  Непонимающий

WebPage - обязан создаваться в главном потоке, поскольку его родителем будет QWebView

Цитировать
The child of a QObject must always be created in the thread where the parent was created.

Родителем WebFrame является WebPage, все нормально.
Предаем его в другой поток, вызываем там WebFrame::load.
И наш WebFrame при загрузке создает у себя дочерние QWebFrame !!! Что недопустимо, они должны быть созданы в главном потоке!
Записан
niXman
Гость
« Ответ #54 : Ноябрь 29, 2009, 16:08 »

Цитировать
Что к чему
это вопрос?

Цитировать
Что-то намудрил
Жду пояснений.

Цитировать
Я согласен что как я написал нельзя, но это общая схема
так я не вас цитировал Подмигивающий

Что-то вы намудрили Подмигивающий
Записан
spectre71
Гость
« Ответ #55 : Ноябрь 29, 2009, 16:17 »

Цитировать
Что к чему
это вопрос?

Цитировать
Что-то намудрил
Жду пояснений.

Цитировать
Я согласен что как я написал нельзя, но это общая схема
так я не вас цитировал Подмигивающий

Что-то вы намудрили Подмигивающий

Ты привел какой-то абсрактный код, неизвестно что делающий. Он не работоспосбен поскольку повыдерганы куски. По нему ничего понять нельзя. Привел примерно такое же объяснение. Вот я и написал  - "Что к чему".
Если уж хочешь рассказать и показать свой вариант, делай это так что бы было понятно не только тебе. Улыбающийся
Записан
niXman
Гость
« Ответ #56 : Ноябрь 29, 2009, 16:20 »

Цитировать
Ты привел какой-то абсрактный код, неизвестно что делающий. Он не работоспосбен поскольку повыдерганы куски. По нему ничего понять нельзя. Привел примерно такое же объяснение. Вот я и написал  - "Что к чему".
Если уж хочешь рассказать и показать свой вариант, делай это так что бы было понятно не только тебе. Улыбающийся
Все нормально описал. Если не достаточно букав, вот, посмотрите: http://rghost.ru/655431
Записан
spectre71
Гость
« Ответ #57 : Ноябрь 29, 2009, 16:39 »

Цитировать
Ты привел какой-то абсрактный код, неизвестно что делающий. Он не работоспосбен поскольку повыдерганы куски. По нему ничего понять нельзя. Привел примерно такое же объяснение. Вот я и написал  - "Что к чему".
Если уж хочешь рассказать и показать свой вариант, делай это так что бы было понятно не только тебе. Улыбающийся
Все нормально описал. Если не достаточно букав, вот, посмотрите: http://rghost.ru/655431

Описал нормально для себя! Что ты там описал понимаешь только ты.
Вообще даже не до конца понятно какую ты решал задачу, а без этого невозможно понять как ты ее решал.
Цитировать
Т.е. я это реализовал именно так.
Что реализавал, опиши задачу. Мы много чего обсуждали в данной теме.

Видео посмотрел. Чего-то там дергается и прыгает, весело так прыгает; Улыбающийся
Записан
serg_hd
Хакер
*****
Offline Offline

Сообщений: 668



Просмотр профиля
« Ответ #58 : Ноябрь 29, 2009, 16:42 »

niXman, в run()'e у тебя только испускание сигналов и коннекты, это только частичная многопоточность. А то что на видео - просто демонстрация асинхронной работы load(), не многопоточность это. А ведь работать может понадобиться с каждой загруженной страницей отдельно и методы работы с ними будут разные, 100% не асинхронные грубо говоря.
Записан

kubuntu/Win7/x64/NetBeans
niXman
Гость
« Ответ #59 : Ноябрь 29, 2009, 16:43 »

Код
C++ (Qt)
Видео посмотрел. Чего-то там дергается и прыгает, весело так прыгает
так это и решал. скучно было Подмигивающий
Записан
Страниц: 1 2 3 [4] 5 6   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.13 секунд. Запросов: 22.