之前写过一篇文章: QT–实现滑动切换界面,但是感觉整体还是不够流畅,不能及时响应用户的滑动,动画会有一定的滞后性,最近看到了一种新的方式,可以实现ipad、手机的页面滑动效果。
下载地址: ipad滑屏工程
一、效果展示
二、原理详解
首先框体面板是自己绘制的,内容区域是继承自QTableWidget
实现的一个类。QTableWidget
往上索引祖先,它继承自QAbstractScrollArea
类,该类支持滚动区域,所以可以给它添加QScroller
,从而实现滑屏的效果。
如此分析,那么只要是QAbstractScrollArea
类的子类就可以,那为什么我又选择了QTableWidget
,因为它的cell中可以放在QWidget
部件,这样一来的话,就可以在一个格子里放置一个QWidget,例如上图,有四个页面,所以行数为1,列数为4,行高设置为内容区域高度,列宽设置为内容区域宽度,即可实现上述的效果。
三、关键代码
页面类: Page_ipad
Page_ipad::Page_ipad(QWidget *parent) : QTableWidget(parent)
{
this->setFocusPolicy(Qt::NoFocus);
this->setShowGrid(false);
this->setSelectionMode(QAbstractItemView::NoSelection);
this->setSelectionBehavior(QAbstractItemView::SelectItems);
this->setEditTriggers(QAbstractItemView::NoEditTriggers);
this->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
this->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
this->verticalHeader()->hide();
this->horizontalHeader()->hide();
this->setHorizontalScrollMode(QAbstractItemView::ScrollPerPixel);
Init_UI();
}
void Page_ipad::Init_UI()
{
this->setRowCount(1); //设置行数
this->setColumnCount(PAGE_NUM); //设置列数(页数)
QSize itemSize = QSize(SCREEN_WIDTH,SCREEN_HEIGHT);
for(int i=0; i<PAGE_NUM; i++) //设置列宽
{
this->setColumnWidth(i,itemSize.width());
}
this->setRowHeight(0,itemSize.height()); //设置行高
page1 = new Page;
page1->setFixedSize(SCREEN_WIDTH,SCREEN_HEIGHT);
page1->set_background_image(":/Icon/background1.jpg");
page2 = new Page;
page2->setFixedSize(SCREEN_WIDTH,SCREEN_HEIGHT);
page2->set_background_image(":/Icon/background2.jpg");
page3 = new Page;
page3->setFixedSize(SCREEN_WIDTH,SCREEN_HEIGHT);
page3->set_background_image(":/Icon/background3.jpg");
page4 = new Page;
page4->setFixedSize(SCREEN_WIDTH,SCREEN_HEIGHT);
page4->set_background_image(":/Icon/background4.jpg");
this->setCellWidget(0,0,page1);
this->setCellWidget(0,1,page2);
this->setCellWidget(0,2,page3);
this->setCellWidget(0,3,page4);
this->setContentsMargins(0,0,0,0);
}
面板类: Frame_ipad
Frame_ipad::Frame_ipad(QWidget *parent) : QWidget(parent)
{
QHBoxLayout* mainLayout = new QHBoxLayout(this);
mainLayout->setMargin(offset+border_weight);
mainLayout->setSpacing(0);
m_pStackedWidget = new QStackedWidget;
mainLayout->addWidget(m_pStackedWidget);
page_ipad = new Page_ipad;
m_pStackedWidget->addWidget(page_ipad);
//给页面添加滚动
//=================================================================================================================
QScroller* scroller = QScroller::scroller(page_ipad);
scroller->grabGesture(page_ipad,QScroller::LeftMouseButtonGesture);
QScrollerProperties properties = scroller->scrollerProperties();
properties.setScrollMetric(QScrollerProperties::MousePressEventDelay,0);
properties.setScrollMetric(QScrollerProperties::DragVelocitySmoothingFactor,1);
properties.setScrollMetric(QScrollerProperties::FrameRate,QScrollerProperties::Fps60);
scroller->setScrollerProperties(properties);
connect(scroller,SIGNAL(stateChanged(QScroller::State)),this,SLOT(slot_scroll_state_changed(QScroller::State)));
}