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

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

Страниц: [1] 2   Вниз
  Печать  
Автор Тема: Список окон  (Прочитано 10452 раз)
kadr
Гость
« : Январь 22, 2010, 09:54 »

Привет всем, скажите как можно сделать так, что бы можно было видеть список всех открытых в данный момент окон!
Есть основное окно, в котором открываются окна, если окно открыто, но не в фокусе, то оно уходит на задний план, за основное окно, которое на весь экран и, которое нельзя свернуть(так надо), так вот надо сделать что бы при нажатии правой кнопкой мыши выпадало контекстное меню в котором был список всех открытых окон, и при нажатии на строку в меню с названием окна, оно становилось активным и соответственно получало фокус!
Что сделал: сделал контекстное меню!  
Записан
BRE
Гость
« Ответ #1 : Январь 22, 2010, 10:01 »

Если используется QMdiArea, то есть:
QList<QMdiSubWindow *> QMdiArea::subWindowList ( WindowOrder order = CreationOrder ) const

Если используются окна верхнего уровня, то:
QWidgetList QApplication::topLevelWidgets ()   [static]
Записан
kadr
Гость
« Ответ #2 : Январь 22, 2010, 10:26 »

Если используются окна верхнего уровня, то:
QWidgetList QApplication::topLevelWidgets ()   [static]
А можно поточнее, как этим пользоваться?
Записан
kadr
Гость
« Ответ #3 : Январь 22, 2010, 10:37 »

Я делаю вот так:
Код:
void nozologia::menu()
{
    int i = 0;
    QMenu *contextMenu = new QMenu;
    contextMenu->addAction("Ввод рецепта");
    contextMenu->addAction("РР-1 Отчет");
    contextMenu->addAction("РЛ-1 Отчет");
    contextMenu->addSeparator();
    contextMenu->addAction("Выход");
    contextMenu->addSeparator();  
    contextMenu->setGeometry(QCursor::pos().x(),QCursor::pos().y(),contextMenu->sizeHint().width(),contextMenu->sizeHint().height());
    contextMenu->show();
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(exit(QAction*)));
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(vvod(QAction*)));
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(pp1(QAction*)));
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(pl1(QAction*)));

    while (i != QApplication::topLevelWidgets().count())
    {
        if (QApplication::topLevelWidgets().value(i)->windowTitle() != "" && QApplication::topLevelWidgets().value(i)->windowTitle() != "7 Нозологий"  && QApplication::topLevelWidgets().value(i)->isVisible())
        {
             contextMenu->addAction(QApplication::topLevelWidgets().value(i)->windowTitle());
        }
        i++;
    }
}
В меню добавляются окна, которые не на переднем плане! Как теперь можно сделать так что бы при нажатии на его название оно переходило на передний план.
« Последнее редактирование: Январь 22, 2010, 10:41 от kadr » Записан
BRE
Гость
« Ответ #4 : Январь 22, 2010, 10:43 »

А что говорит поиск по форуму?  Подмигивающий
http://www.prog.org.ru/topic_7821_0.html
Записан
DS_tm
Гость
« Ответ #5 : Январь 22, 2010, 10:47 »

Переопределяете в виджите, на котором нужно контекстное меню функцию contextMenuEvent. В ней пишете что-то типа этого:

Код
C++ (Qt)
   QMenu menu;
   foreach (QWidget *w, QApplication::topLevelWidgets()) {
       menu.addAction(w.windowTitle(), this, SLOT(showWidget())).setData(w);
   }
   menu.exec();
 

Создаете приватный слот showWidget, в этом классе с текстом:

Код
C++ (Qt)
   QAction *action = static_const<QAction*> (sender);
   if (action) {
        QWidget *w= static_const<QWidget*>(action->data().toInt());
        if (w) w->show();
   }
 

Код не проверял, мог напартачить с привиденьями, будте внимательным.
Записан
kadr
Гость
« Ответ #6 : Январь 22, 2010, 11:17 »

Переопределяете в виджите, на котором нужно контекстное меню функцию contextMenuEvent. В ней пишете что-то типа этого:

Код
C++ (Qt)
   QMenu menu;
   foreach (QWidget *w, QApplication::topLevelWidgets()) {
       menu.addAction(w.windowTitle(), this, SLOT(showWidget())).setData(w);
   }
   menu.exec();
 

Создаете приватный слот showWidget, в этом классе с текстом:

Код
C++ (Qt)
   QAction *action = static_const<QAction*> (sender);
   if (action) {
        QWidget *w= static_const<QWidget*>(action->data().toInt());
        if (w) w->show();
   }
 

Код не проверял, мог напартачить с привиденьями, будте внимательным.
А что такое sender, где я должен его определить.
Код:
void nozologia::menu()
{
    int i = 0;


    QMenu *contextMenu = new QMenu;
    contextMenu->addAction("Ввод рецепта");
    contextMenu->addAction("РР-1 Отчет");
    contextMenu->addAction("РЛ-1 Отчет");
    contextMenu->addSeparator();
    contextMenu->addAction("Выход");
    contextMenu->addSeparator();  
    contextMenu->setGeometry(QCursor::pos().x(),QCursor::pos().y(),contextMenu->sizeHint().width(),contextMenu->sizeHint().height());
    contextMenu->show();
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(exit(QAction*)));
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(vvod(QAction*)));
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(pp1(QAction*)));
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(pl1(QAction*)));

    foreach (QWidget *m, QApplication::topLevelWidgets())
    {
        if (m->windowTitle() != "" && m->windowTitle() != "7 Нозологий" && m->isVisible())
        {
            contextMenu->addAction(m->windowTitle(), this, SLOT(showWidget()))->setData(m);
        }      
    }
    contextMenu->exec();

}
и приватный слот
Код:
void nozologia::showWidget(QString *act)
{
    QAction *action = static_cast<QAction*>(sender);

    if (action)
        {
             QWidget *m= static_cast<QWidget*>(action->data().toInt());
             if (m) m->show();
        }
}
Ошибки:
Код:
'QVariant::QVariant(void*)' is private
within this context
invalid static_cast from type '<unresolved overloaded function type>' to type 'QAction*'
nvalid static_cast from type 'int' to type 'QWidget*'
Записан
kadr
Гость
« Ответ #7 : Январь 22, 2010, 11:27 »

Добавил в
contextMenu->addAction(m->windowTitle(), this, SLOT(showWidget()))->setData(m);
windowTitle();
contextMenu->addAction(m->windowTitle(), this, SLOT(showWidget()))->setData(m->windowTitle());
И пропала ошибка:
QVariant::QVariant(void*)' is private
within this context
Остались две ошибки:

invalid static_cast from type '<unresolved overloaded function type>' to type 'QAction*'
nvalid static_cast from type 'int' to type 'QWidget*
Записан
DS_tm
Гость
« Ответ #8 : Январь 22, 2010, 11:31 »

Мой косяк). sender - это функция, которая возвращает указатель на объект (наследник QObject), инициализирующий сообщение, а я просто скобки забыл поставить. Если вы определяете слот с параметром QAction *, то вам эта строчка не нужна, используйте передаваемую переменую.
Вместо static_const<QWidget*>(action->data().toInt()) попробуйте (QWidget*)action->data().toInt(), но если кто спросит, я вам этого не советывал))
Записан
kadr
Гость
« Ответ #9 : Январь 22, 2010, 12:18 »

Вот:
Код:
void nozologia::menu()
{
    int i = 0;
    QMenu *contextMenu = new QMenu;
    contextMenu->addAction("Ввод рецепта");
    contextMenu->addAction("РР-1 Отчет");
    contextMenu->addAction("РЛ-1 Отчет");
    contextMenu->addSeparator();
    contextMenu->addAction("Выход");
    contextMenu->addSeparator();  
    contextMenu->setGeometry(QCursor::pos().x(),QCursor::pos().y(),contextMenu->sizeHint().width(),contextMenu->sizeHint().height());
    contextMenu->show();
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(exit(QAction*)));
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(vvod(QAction*)));
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(pp1(QAction*)));
    connect(contextMenu,SIGNAL(triggered(QAction*)),this,SLOT(pl1(QAction*)));

    foreach (QWidget *m, QApplication::topLevelWidgets())
    {
        if (m->windowTitle() != "" && m->windowTitle() != "7 Нозологий" && m->isVisible())
        {
            contextMenu->addAction(m->windowTitle(), this,SLOT(showWidget()))->setData(m->windowTitle());
        }      
    }
    contextMenu->exec();

}

void nozologia::showWidget()
{
    QAction *action =  (QAction*)sender();

    if (action)
        {
             QWidget *m = (QWidget*)action->data().toInt();
             if (m) m->show();
        }
}
не хочет работать.
Все компилиться без проблем, но окна не переносятся на передний план!
« Последнее редактирование: Январь 22, 2010, 12:23 от kadr » Записан
DS_tm
Гость
« Ответ #10 : Январь 22, 2010, 12:44 »

Попробуйте еще добавить вызов activateWindow() для виджета m. То есть:

Код
C++ (Qt)
   if (m) {
     m->show();
     m->activeWindow();
   }
 

Если не сработает, проверте, верно ли определяеться виджет m, к примеру вызовете m->hide(). Если определяеться правельно, но не появляеться, то читайте ссылку что дал Вам BRE!
Записан
SABROG
Гость
« Ответ #11 : Январь 22, 2010, 12:47 »

еще можно попробовать void QWidget::raise ()   [slot]

только в документации нигде не сказано работает он с top level окнами или нет.
Записан
kadr
Гость
« Ответ #12 : Январь 22, 2010, 14:28 »

По той ссылке я не вынес ничего полезного. Все попробовал не работает.
Вот что я сделал:
qDebug() << action->text();
    qDebug() << action->objectName();
    qDebug() << action;
qDebug() << m;


Код:
void nozologia::showWidget()
{
    QAction *action =  (QAction*)sender();

    qDebug() << action->text();
    qDebug() << action->objectName();
    qDebug() << action;
    if (action)
        {
             QWidget *m = (QWidget*)action->data().toInt();

             qDebug() << m;
             if (m)
             {
                 m->setWindowFlags(m->windowFlags() | Qt::WindowStaysOnTopHint);
                 m->raise();
                 m->show();
                 m->activateWindow();

             }
        }
}
Вывод:
Код:
"Отчет РЛ-1" 
""
QAction(0x1072c2c8)
QObject(0x0)
Передается только Заголовок окна! windowsTitle();
« Последнее редактирование: Январь 22, 2010, 14:49 от kadr » Записан
SABROG
Гость
« Ответ #13 : Январь 22, 2010, 15:29 »

Так у тебя возвращается пустой указатель тут:

Код
C++ (Qt)
           QWidget *m = (QWidget*)action->data().toInt();
           qDebug() << m;
 
Записан
BRE
Гость
« Ответ #14 : Январь 22, 2010, 16:06 »

... и все это из-за того, что в data запихиваем WindowTitle, а получить хотим указатель на виджет.
Записан
Страниц: [1] 2   Вверх
  Печать  
 
Перейти в:  


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