热门关键字:
jquery > jquery教程 > html5 > QRowTable表格控件-支持hover整行、checked整行…

QRowTable表格控件-支持hover整行、checked整行…

328
作者:管理员
发布时间:2020/3/23 10:49:10
评论数:0
转载请自觉注明原文:http://www.jq-school.com/Show.aspx?id=1088

  QRowTable表格控件-支持hover整行、checked整行、指定列排序等

  目录

  一、开心一刻

  二、嘴一嘴

  三、效果展示

  四、浅谈实现

  五、自定义数据源

  1、data函数

  2、flags函数

  六、自定义视图

  1、目的

  2、问题分析

  七、测试

  八、相关文章

  原文链接:QRowTable表格控件-支持hover整行、checked整行、局部列排序等

  一、开心一刻

  老公和老婆晚上回家,路旁突然跳出三个持刀蒙面大汉:“绑架!你俩可以走一个,回家等消息。”

  老公一把将老婆推开:“老婆快走!”待老婆走远后,三个蒙面人摘下面具:“尼玛现在找你打个麻将这么费劲?”

  五分钟后老公致电老婆:"往卡里打五千块,别报警,他们说关我一夜明早放人。"十分钟后老公从卡里取走五千块战斗到天明。

  次日老公回家,老婆扑上来含泪说:“关键时候才能看出老公对我的好,老公以后我啥都听你的!

  二、嘴一嘴

  看完笑话,我们进入正题。

  本篇文章我们带来的是一个表格的简单使用,主要是把表格的hover、checked进行了重新定制,支持用户自己去设置相关颜色,并且可以对指定列进行放大缩小等。

  为什么会写这篇文章呢?博主自己使用Qt也好几年了,对于Qt的使用算是比较有心得了吧。最近在做表格的一些相关东西,发现网上的很多文章讲的不是特别好,因此将自己做的一个简单事例做一分享,希望能帮到有需要的同学。

  本篇文章我们主要对表格的以下内容进行了封装,内容比较有限,有深度定制需求的同学可以加我QQ详谈。

  hover行背景色

  checked行背景色

  列宽是否可排序

  列宽允许拖动范围

  准确定位hover状态

  三、效果展示

  如下图所示,一个简单的gif效果展示。

  配色时博主自己随便搞的,配色只能说很一般,大家主要看效果和实现思路。

  四、浅谈实现

  使用过QTableView或者了解控件的同学应该都很清楚,表格是一个很强大的控件,支持我们做各种各样的功能,博主之前也想过几篇相关的文章,都是讲述表格控件的。

  Qt实现表格控件-支持多级列表头、多级行表头、单元格合并、字体设置等

  Qt高仿Excel表格组件-支持冻结列、冻结行、内容自适应和合并单元格

  属性浏览器控件QtTreePropertyBrowser编译成动态库(设计师插件)

  超级实用的属性浏览器控件--QtTreePropertyBrowser

  Qt之表格控件蚂蚁线

  当然了表格控件的使用远远不止于此,后续有时间和精力我会陆续推出更多有用好玩儿的功能。

  本篇文章的功能实现也比较简单,写这个demo我大概用了大半天的时间,代码量其实不多,大部分的时间主要用来设计接口和重构逻辑功能了。

  如下图所示,是整个工程目录结构,这里主要重写了数据源model和view

  下面我们就分别讲述model和view都干了些什么

  五、自定义数据源

  所谓数据源,其实主要就是给view提供数据的地方,这里我们取了一个巧,数据源直接继承自QStandarItemModel,这样的话数据的存储和获取大部分的工作都不需要我们去关心,因为QStandarItemModel这个类已经做的很完善。

  这里我们主要从写了两个接口

  virtualQVariantdata(constQModelIndex&index,introle=Qt::DisplayRole)constoverride;

  virtualQt::ItemFlagsflags(constQModelIndex&index)constoverride;

  1、data函数

  视图获取数据的接口就是data,因此这个接口我们必须重写,实现代码也很简单,主要是需要大家对Qt的MVC有一个基本的认识。

  QVariantQRowModel::data(constQModelIndex&index,introle/*=Qt::DisplayRole*/)const

  {

  if(Qt::BackgroundRole==role)

  {

  if(index.row()==m_iHoverRow)

  {

  returnm_HoverColor;

  }

  }

  elseif(role==Qt::ForegroundRole)

  {

  if(index.row()==m_iHoverRow)

  {

  returnm_HoverColor.lighter(255);

  }

  }

  returnQStandardItemModel::data(index,role);

  }

  看上述代码,当绘制视图的时候,hover一行时,我们需要返回自定义的颜色值,其他情况走默认处理即可,是不是很简单。

  关于checked的实现不能放在这里,因为当item被选中的时候,item的背景色不是取自Qt::BackgroundRole,同时前景色也不是取自Qt::ForegroundRole,因此这里处理不了。

  如果非要让checked状态在这里实现也是有办法的,我们可以重写flags函数,让item不能被选中,这个办法博主是试过的,没有问题。但是就存在一个隐,如果后期我们的item想被选中,就比较麻烦了。

  基于以上设想,我们只需要这样重写flags函数,然后在data函数中返回checked行的背景色和前景色即可。

  Qt::ItemFlagsQRowModel::flags(constQModelIndex&index)const

  {

  returnQt::ItemIsEnabled;

  }

  2、flags函数

  上一小节flags函数都已经展示出来了,item处于可用状态,这里还需要在添加上可选中状态,以免有其他坑

  Qt::ItemFlagsQRowModel::flags(constQModelIndex&index)const

  {

  returnQt::ItemIsEnabled|Qt::ItemIsSelectable;

  }

  以上就是model函数的重写了,比较简单,下面放出model的头文件

  /**

  *简介:主要提供接口提供hover行

  */

  classQRowModel:publicQStandardItemModel

  {

  Q_OBJECT

  public:

  explicitQRowModel(QObject*parent=0);

  ~QRowModel();

  private:

  //hover时背景色不建议外部直接调用

  voidSetHoverColor(constQColor&color);

  QColorGetHoverColor()const{returnm_HoverColor;}

  //设置当前hover行不建议外部直接调用

  voidSetHoverRow(introw);

  intGetHoverRow()const{returnm_iHoverRow;}

  protected:

  virtualQVariantdata(constQModelIndex&index,introle=Qt::DisplayRole)constoverride;

  virtualQt::ItemFlagsflags(constQModelIndex&index)constoverride;

  private:

  intm_iHoverRow=-1;//没有hover

  QColorm_HoverColor=QColor(20,22,23);

  friendclassQRowTable;

  };

  六、自定义视图

  下面讲述今天的重头戏view。

  首先需要搞清楚,重写视图需要完成哪些工作,才能更好的准备定位每个函数的意思。

  1、目的

  hover时,把hover行通知到数据源

  准确的hover和取消hover状态,这个问题确实搞了好久

  点击item时,设置行选中色

  指定列可排序

  有了以上目标之后,我们逐个问题解决。

  2、问题分析

  针对以上4个目的,我们逐个分析解决办法

  1、鼠标hover到这个比较简单,而且可以通过多种方式进行获取。

  想要拿到这个状态,有一个很重要的属性需要开启:setMouseTracking(true);

  a、如果我们重写的是QTableWidget这个类,那么可以去接收cellEntered这个信号

  b、如果重写跟本篇文章一样,重写的QTableView这个类,那么我们需要重写mouseMoveEvent这个函数,然后通过indexAt函数获取当前行。

  voidQRowTable::mouseMoveEvent(QMouseEvent*event)

  {

  QTableView::mouseMoveEvent(event);

  constQModelIndex&index=indexAt(event->pos());

  introw=-1;

  if(index.isValid())

  {

  row=index.row();

  }

  if(m_pModel->GetHoverRow()!=row)

  {

  m_pModel->SetHoverRow(index.row());

  viewport()->update();

  }

  }

  2、取消hover装态

  这个问题处理确实化了好长时间,主要还是想处理的办法更优雅,效率高一些。

  这里为了实现不在item上时立刻取消hover状态,主要做了2件事。

  第一件事

  重写leaveEvent函数,鼠标离开时,恢复hover行为-1

  voidQRowTable::leaveEvent(QEvent*e)

  {

  if(m_pModel->GetHoverRow()!=-1)

  {

  m_pModel->SetHoverRow(-1);

  viewport()->update();

  }

  QTableView::leaveEvent(e);

  }





如果您觉得本文的内容对您的学习有所帮助:支付鼓励



关键字:html
友荐云推荐