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

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

Страниц: 1 [2]   Вниз
  Печать  
Автор Тема: Выпадающее меню на HeaderView с перечнем чекбоксов с названиями колонок  (Прочитано 13760 раз)
stealth
Гость
« Ответ #15 : Октябрь 23, 2007, 19:02 »

Не подскажешь как ты этого добился?
Записан
ритт
Гость
« Ответ #16 : Октябрь 23, 2007, 21:08 »

чего добился? дерева? или меню с тиарОфф'ом?

у тебя вьюха родная или унаследованная?
Записан
stealth
Гость
« Ответ #17 : Октябрь 23, 2007, 22:28 »

я не особо понял, что такое ТиарОФФ? Улыбающийся
Интересует как сделал выпадающее меню с чекбоксами, чтобы они отрабатывали скрытие и открытие - аналогично тому, как это в виндовом експлорере сделано (при обзоре файлов и нажатии правой кнопкой по заголовку).
А с listView впринципе всё понятно...
Вьюха стандартная.
Записан
fox
Гость
« Ответ #18 : Октябрь 24, 2007, 13:46 »

Доброго дня!
Собственно сабж! Как делается на TableView такая штука, чтобы пользователь мог влючить или отключить показ колонок в таблице?
Делал подобную вещь но меню выпадала только при клике по последней колонке таблицы
Если такой вариант устроит приведу код Улыбающийся
Записан
ритт
Гость
« Ответ #19 : Октябрь 24, 2007, 17:07 »

Код:
...

void TableView::setModel(QAbstractItemModel* model)
{
QTableView::setModel(model);


QSignalMapper* signalMapper = new QSignalMapper(this);
for(int i = 0; i < model->columnCount(); i++)
{
QAction* action = new QAction(model->headerData(i, Qt::Horizontal).toString(), this);
action->setCheckable(true);
action->setChecked(!isColumnHidden(i));
action->setData(i);
connect(action, SIGNAL(triggered()), signalMapper, SLOT(map()));
signalMapper->setMapping(action, action);

horizontalHeader()->addAction(action);
}
connect(signalMapper, SIGNAL(mapped(QObject*)), this, SLOT(showHideColumnsMenuTriggered(QObject*)));

horizontalHeader()->setContextMenuPolicy(Qt::ActionsContextMenu);
}

...

void TableView::showHideColumnsMenuTriggered(QAction* action)
{
setColumnHidden(action->data().toInt(), !action->isChecked());
}

//данный слот для совместимости с сигналмаппером
void TableView::showHideColumnsMenuTriggered(QObject* obj)
{
QAction* action = qobject_cast<QAction*>(obj);
if(action)
showHideColumnsMenuTriggered(action);
}

...

5 рублей (или пИво)
« Последнее редактирование: Октябрь 24, 2007, 17:28 от xep » Записан
stealth
Гость
« Ответ #20 : Октябрь 24, 2007, 18:10 »

хер, с меня теперь точно 5 рублей или пиво! Улыбающийся
Спасибо за действительно рабочий вариант этой штуки.
Но опять же это нужно наследовать TableView, а я, как писал выше, добиваюсь сделать функцию, которая бы возвращала QMenu (получая на входе модель и вью), который уже вешается на любой TableView. Наследоваться не всегда есть возможность - например при использовании форм, сделанных в QtDesigner.

Радует, конечно, create more, но еще хотелось бы и code less Улыбающийся

to fox - приведи пожалуйста, чем больше вариантов, тем тема будет больше раскрыта!
Записан
fox
Гость
« Ответ #21 : Октябрь 24, 2007, 18:37 »

to fox - приведи пожалуйста, чем больше вариантов, тем тема будет больше раскрыта!
Вообщем хотел сделать почти то же самое только для управления показом/скрытием колонок использовал отдельную колонку
По умолчанию последние где в заголовке нет текста только иконка

Соответственно для начала сигнал
Код:
  QHeaderView * head = horizontalHeader();
  connect(head, SIGNAL(sectionClicked(int)), this, SLOT(sectionClicked(int)));

а уже в обработчике проверка на то что клацнули на нужную мне колонку

Код:
  if(logicalIndex == Observer::MenuTerminalSection){
    QMenu menuSection(tr("Columns"), this);
    QHeaderView * head = horizontalHeader();
    int c = head->count();
    for(int i=0;i<c;++i){
      if(i == Observer::MenuTerminalSection){
        continue;
      }
      QAction * action = menuSection.addAction(model()->headerData(i, Qt::Horizontal, Qt::DisplayRole).toString());
      action->setCheckable(true);
      action->setChecked(!head->isSectionHidden(i));
      action->setData(i);
    }
    QAction * action = menuSection.exec(QCursor::pos());
    if(action){
      int index = action->data().toInt();
      head->setSectionHidden(index, !action->isChecked());
      if(action->isChecked()) resizeColumnToContents(index);
    }
  }
Записан
ритт
Гость
« Ответ #22 : Октябрь 24, 2007, 19:05 »

стэлз, смотри код внимательно - все используемые методы публичные. код можно использовать как внутри вьюхи, так и снаружи
Записан
stealth
Гость
« Ответ #23 : Октябрь 25, 2007, 21:50 »

to fox - хороший вариант, особенно хорошо, что достаточно просто реализуется
to xep - спасибо! угу, чёт я название класса просто увидел TableView и подумал, что ты его наследуешь от QTableView.
Всё заработало!

Вот что получилось в итоге (по большей части код от "xep" Улыбающийся ):
Код:
//
//service.cpp
//
#include "service.h"
#include <QMessageBox>

QMenu *MenuForHeaderView::createMenu(QWidget *parent, QSqlRelationalTableModel *model, QTableView *view) {

    QMenu *columnsMenu= new QMenu(tr("Колонки"));
    columnsMenu->setIcon(QIcon(":images/images/configure.png"));

    QSignalMapper* signalMapper = new QSignalMapper(parent);

    for (int i = 0; i < model->columnCount(); i++) {
        QAction* action = new QAction(model->headerData(i, Qt::Horizontal).toString(), view);
        action->setCheckable(true);
        action->setChecked(!view->isColumnHidden(i));
        action->setData(i);
        signalMapper->setMapping(action, action);
        connect(action, SIGNAL(triggered()), signalMapper, SLOT(map()));
        columnsMenu->addAction(action);
    }
    connect(signalMapper, SIGNAL(mapped(QObject*)), this, SLOT(showHideColumnsMenuTriggered(QObject*)));
    v = new QTableView;
    v=view;

    return columnsMenu;
}

void MenuForHeaderView::showHideColumnsMenuTriggered(QAction* action) {
    v->setColumnHidden(action->data().toInt(), !action->isChecked());
    v->resizeColumnsToContents();
}

//данный слот для совместимости с сигналмаппером
void MenuForHeaderView::showHideColumnsMenuTriggered(QObject* obj) {
    QAction* action = qobject_cast<QAction*>(obj);
    if (action)
        showHideColumnsMenuTriggered(action);
}



Заголовочный файл
Код:
//
//service.h
//
#ifndef __SERVICE_H__
#define __SERVICE_H__
#include <QtGui>
#include <QtSql>

class MenuForHeaderView:public QObject {
    Q_OBJECT
public:
MenuForHeaderView(QObject *parent = 0): QObject(parent) {}

    QTableView *v;
    QMenu *createMenu(QWidget *parent=0, QSqlRelationalTableModel *model=0, QTableView *view=0);
public slots:
    void showHideColumnsMenuTriggered(QAction* action);
    void showHideColumnsMenuTriggered(QObject* obj);

};
#endif // __SERVICE_H__


А так вот использовать в программе:
Код:
...
//соответсвенно
//QSqlRelationalTableModel *model, QTableView *tableView

    MenuForHeaderView *mm = new MenuForHeaderView(this);
    QMenu *headerMenu= new QMenu;
    tableView->horizontalHeader()->addAction(headerMenu->addMenu(mm->createMenu(this, model, View) ));
    tableView->horizontalHeader()->setContextMenuPolicy(Qt::ActionsContextMenu);
...

Большое спасибо всем, кто принял участие в данном обсуждении!
Записан
Страниц: 1 [2]   Вверх
  Печать  
 
Перейти в:  


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