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

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

Страниц: [1]   Вниз
  Печать  
Автор Тема: Странное поведение QTimeLine  (Прочитано 3851 раз)
lighting
Гость
« : Октябрь 09, 2009, 13:36 »

Пробовал создать анимацию, и столкнулся с весьма странным поведением QTimeLine. Догадываюсь что на 99,999% ошибка в моем коде, но что-то никак ее не могу обнаружить.
mainwindow.h
Код
C++ (Qt)
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
 
#include <QtGui/QMainWindow>
#include <QWidget>
#include <QtGui/QGraphicsView>
#include <QFileDialog>
 
class QTimeLine;
class QPushButton;
class QFileDialog;
 
class MainWindow : public QMainWindow
{
   Q_OBJECT
 
public:
   MainWindow(QWidget *parent = 0);
   ~MainWindow();
 
private slots:
   void dialogAppear();
   void dialogDisappear();
   void TimerNextFrame();
 
private:
   QGraphicsView *graphicsView;
   QGraphicsScene *scene;
   QPushButton *btnClose;
   QPushButton *btnShow;
   QFileDialog *fileDialog;
   QTimeLine *dialogAnimTimer;
   QGraphicsProxyWidget *item;
   QTransform transform;
 
};
 
#endif // MAINWINDOW_H
 

mainwindow.cpp
Код
C++ (Qt)
#include "mainwindow.h"
#include <QGraphicsScene>
#include <QGraphicsProxyWidget>
#include <QPushButton>
#include <QTimeLine>
 
MainWindow::MainWindow(QWidget *parent)
   : QMainWindow(parent)
{  
   this->setGeometry(200,200, 800, 600);
   graphicsView = new QGraphicsView(this);
   graphicsView->setGeometry(0,0,800,600);
   graphicsView->setRenderHint(QPainter::Antialiasing);
   scene = new QGraphicsScene(this);
   scene->setSceneRect(0,0,790,590);    
   graphicsView->setScene(scene);
   dialogAnimTimer = new QTimeLine();
   dialogAnimTimer->setDuration(200);
   dialogAnimTimer->setFrameRange(1, 20);
   connect(dialogAnimTimer, SIGNAL(frameChanged(int)), this , SLOT(TimerNextFrame()));
   fileDialog = new QFileDialog(this);
   fileDialog->hide();
   btnClose = new QPushButton(tr("&Quit"));
   btnShow = new QPushButton(tr("Show dialog"));
   connect(btnClose, SIGNAL(clicked()), this, SLOT(close()));
   connect(btnShow, SIGNAL(clicked()), this, SLOT(dialogAppear()));
   connect(fileDialog, SIGNAL(finished(int)), this, SLOT(dialogDisappear()));
   btnClose->move(700, 500);
   scene->addWidget(btnClose);
   scene->addWidget(btnShow);
   item = new QGraphicsProxyWidget();
   item = scene->addWidget(fileDialog);
}
 
MainWindow::~MainWindow()
{
 
}
 
void MainWindow::dialogAppear()
{
   dialogAnimTimer->setDirection(QTimeLine::Forward);
   dialogAnimTimer->start();
}
 
void MainWindow::dialogDisappear()
{
   dialogAnimTimer->setDirection(QTimeLine::Backward);
   dialogAnimTimer->start();
}
 
void MainWindow::TimerNextFrame()
{
   int framenum = dialogAnimTimer->currentFrame();
     if (dialogAnimTimer->direction() == QTimeLine::Forward)
     {
       transform.scale(1.05, 1.05);
       if (framenum == 1)
       {
         fileDialog->show();
       }
     }
     else
     {
       transform.scale(1/1.05, 1/1.05);
     }
   item->setTransform(transform);
  fileDialog->update();
}
 
Суть проблемы - после запуска программы FileDialog появляется только после второго нажатия btnShow (при том что событие DialogAppear вызывается два раза). После этого повторные нажатия btnShow открывают FileDialog сразу.
Записан
kwisp
Гость
« Ответ #1 : Октябрь 09, 2009, 14:16 »

dialogAnimTimer->setDuration(200);
вот эта строчка смущает немного
общая длительность получается 0,2с.
это правильно?
Записан
lighting
Гость
« Ответ #2 : Октябрь 09, 2009, 14:51 »

kwisp Да, правильно.
Записан
Rcus
Гость
« Ответ #3 : Октябрь 09, 2009, 15:25 »

Тонко, красиво Улыбающийся сигнал frameChanged посылается только если текущий кадр изменился (внезапно да?) А поскольку при создании объекта время устанавливается в ноль то при первом запуске не произойдет смены кадра. Я бы не стал полагаться на это поведение, в данном случае больше подходит сигнал QTimeLine::stateChanged( QTimeLine::State newState );
Записан
lighting
Гость
« Ответ #4 : Октябрь 10, 2009, 10:33 »

Rcus получается при Direction = Forward и вызове start номер фрейма увеличивается, а время уменьшается и наоборот?
А вот stateChanged мне там ни к чему, frameCahged самое то. Добавил только строчку dialogAnimTimer->setCurrentTime(200); при создании таймлайна и все заработало как надо. Спасибо за подсказку, сам-бы я на это много времени убил Улыбающийся
Записан
Страниц: [1]   Вверх
  Печать  
 
Перейти в:  


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