QTableView中和horizo​​ntalHeader() - > restoreSta

2019-09-20 03:08发布

我不能缩小这个错误, 但是我似乎有以下问题:

  • saveState()一个的horizontalHeader()
  • 重新启动应用程序
  • 修改模型,使其少了一个列
  • restoreState()
  • 现在,出于某种原因,该headerview的状态是完全搞砸了。 我不能显示或隐藏任何新的栏目,我也不能永远得到一个合理的状态恢复

我知道,这是不是很描述性的,但我希望在别人面前也有这个问题。

Answer 1:

对于QMainWindow的,在save/restoreState需要一个版本号。 QTableView中的restoreState()没有,所以你需要自己管理这种情况。

如果你想恢复状态,即使模型不符,您有以下选择:

  • 与在后保存模型存在的列的列表存储在一起的状态,这样就可以避免从数据恢复如果列不匹配,并恢复到defualt情况
  • 执行该处理这种情况你自己保存/ restoreState功能(啊)
  • 添加具有提供状态正在恢复假/伪列的代理模型,然后删除这些列只是之后。


Answer 2:

我个人从来没有使用saveState() / restoreState()在任何Qt物件,因为它们只返回一个二进制的blob反正。 我想我的配置文件是人类可读的,用简单的类型。 这也摆脱这些那样的问题。

此外, QHeaderView有顽皮的问题restoreState()当模型已经设置,然后一段时间(或等价物)永远只为我工作。 我结束了连接到QHeaderView::sectionCountChanged()信号和设置从它称为插槽的状态。



Answer 3:

下面是我使用升压序列化制造解决方案。

它处理新的和删除列,或多或少。 适合我的使用情况。

  // Because QHeaderView sucks
  struct QHeaderViewState
  {
    explicit QHeaderViewState(ssci::CustomTreeView const & view):
      m_headers(view.header()->count())
    {
      QHeaderView const & headers(*view.header());
      // Stored in *visual index* order
      for(int vi = 0; vi < headers.count();++vi)
      {
        int           li     = headers.logicalIndex(vi);
        HeaderState & header = m_headers[vi];

        header.hidden               = headers.isSectionHidden(li);
        header.size                 = headers.sectionSize(li);
        header.logical_index        = li;
        header.visual_index         = vi;
        header.name                 = view.model()->headerData(li,Qt::Horizontal).toString();
        header.view                 = &view;
      }
      m_sort_indicator_shown   = headers.isSortIndicatorShown();
      if(m_sort_indicator_shown)
      {
        m_sort_indicator_section = headers.sortIndicatorSection();
        m_sort_order             = headers.sortIndicatorOrder();
      }
    }

    QHeaderViewState(){}

    template<typename Archive>
    void serialize(Archive & ar, unsigned int)
    {
      ar & m_headers;
      ar & m_sort_indicator_shown;
      if(m_sort_indicator_shown)
      {
        ar & m_sort_indicator_section;
        ar & m_sort_order;
      }
    }

    void
    restoreState(ssci::CustomTreeView & view) const
    {
      QHeaderView & headers(*view.header());

      const int max_columns = std::min(headers.count(),
                                       static_cast<int>(m_headers.size()));      

      std::vector<HeaderState> header_state(m_headers);
      std::map<QString,HeaderState *> map;
      for(std::size_t ii = 0; ii < header_state.size(); ++ii)
        map[header_state[ii].name] = &header_state[ii];

      // First set all sections to be hidden and update logical
      // indexes
      for(int li = 0; li < headers.count(); ++li)
      {
        headers.setSectionHidden(li,true);
        std::map<QString,HeaderState *>::iterator it =
          map.find(view.model()->headerData(li,Qt::Horizontal).toString());
        if(it != map.end())
          it->second->logical_index = li;
      }

      // Now restore
      for(int vi = 0; vi < max_columns; ++vi)
      {
        HeaderState const & header = header_state[vi];
        const int li = header.logical_index;
        SSCI_ASSERT_BUG(vi == header.visual_index);
        headers.setSectionHidden(li,header.hidden);
        headers.resizeSection(li,header.size);
        headers.moveSection(headers.visualIndex(li),vi);
      }
      if(m_sort_indicator_shown)
        headers.setSortIndicator(m_sort_indicator_section,
                                 m_sort_order);
    }

    struct HeaderState
    {
      initialize<bool,false>  hidden;
      initialize<int,0>       size;
      initialize<int,0>       logical_index;
      initialize<int,0>       visual_index;
      QString                 name;
      CustomTreeView const  *view;

      HeaderState():view(0){}

      template<typename Archive>
      void serialize(Archive & ar, unsigned int)
      {
        ar & hidden & size & logical_index & visual_index & name;
      }
    };

    std::vector<HeaderState> m_headers;
    bool                     m_sort_indicator_shown;
    int                      m_sort_indicator_section;
    Qt::SortOrder            m_sort_order; // iff m_sort_indicator_shown
  };


Answer 4:

我希望它打破,如果你改变模型! 这些功能保存和直接,没有任何完整性检查恢复私有类成员变量。 尝试恢复状态,然后改变模型。



Answer 5:

我试图解决这个问题,Qt的5.6.2,击中了同样的问题后。 见在审查一个Qt补丁这个环节 ,这使得restoreState()处理,其中部分(例如,列)中保存的状态数不会在当前视图部分的数量相匹配的情况。



文章来源: QTableView and horizontalHeader()->restoreState()
标签: qt qtableview