2008年9月5日星期五

一个用手指波动指针调整的时钟的QT3实现


有一天OPPO的人拿来多普达的手机让我看一个触摸屏拖动指针来调时钟的功能。
看了以后觉得很NB, 不过一直不服, 就在想怎么自己写一个。

昨天看了atan2函数以后就想到了办法,
今天对时钟的稳定性做了调整。
这个程序即使把调整时间的API换成WIN的也不能正常在WIN下工作。 所以这个小程序就不支持win了。 在linux下正常。


这个程序直接:
qmake -project
qmake
make
就可以运行了。
不过要在ROOT权限下运行哦~

有啥BUG发给我哈。


#include <qapplication.h>
#include <qpushbutton.h>
#include <qslider.h>
#include <qlcdnumber.h>
#include <qfont.h>

#include <qpoint.h>
#include <qpainter.h>
#include <qdatetime.h>
#include <qtimer.h>

#include <qvbox.h>
#include <qwidget.h>
#include <cmath>
#include <qcanvas.h>
int degreen(double a) ;

class MyWidget : public QWidget
{
public:
MyWidget( QWidget *parent=0, const char *name=0 );

protected:
void paintEvent (QPaintEvent *);
void mouseMoveEvent (QMouseEvent *e);
void mouseReleaseEvent (QMouseEvent *) ;

private:

double rotate_angle_minute; // minute rotate angle
bool in_move;


};


MyWidget::MyWidget( QWidget *parent, const char *name )
: QWidget( parent, name )
{
bool in_move = false;
QTimer *timer = new QTimer (this);

connect ( timer, SIGNAL(timeout()), this, SLOT(update()));
timer->start(500);

resize(200, 200);
}

int degreen(double a) {
return a * 180 / M_PI;
}

#include <sys/time.h>
#include <time.h>
#include <errno.h>

void adjustTime (int , int min, int )
{
struct timeval cur_val;
struct timezone cur_zone;
int ret;
static int last_min = 0;
int delta = min - last_min;
qDebug("delta: %d", delta);
// ignore too large time adjust
if ( delta < -5 || delta > 10) {
last_min = min;
return;
} else {
delta = min - last_min;
last_min = min;
}

gettimeofday(&cur_val, &cur_zone);

time_t new_time;
new_time = delta * 60;
cur_val.tv_sec += new_time;

ret = settimeofday(&cur_val, &cur_zone);
qDebug( "time add %d seconds, ret is :%d ", (int)new_time, ret);
if (errno != 0)
perror("can't set time");
}

void
MyWidget::mouseMoveEvent( QMouseEvent *e) {
static int count = 0;
if (count++ < 5) // also for let adjust smoothly
return;
else
count = 0;


int angle;
angle = degreen(atan2(100 - e->pos().y() , 100 - e->pos().x() ));

qDebug(" X:%3d Y:%3d angle :%3d -- the minute angle :%d ",
e->pos().x(),
e->pos().y(),
angle,
(int)rotate_angle_minute);
if (!in_move)
angle = rotate_angle_minute; // for avoid minute pin jump
in_move = true;

int current_minute = (angle/ 6);

QString old_time = QTime::currentTime().toString();

adjustTime (0, current_minute - QTime::currentTime().minute(), 0);

QString new_time_str = QTime::currentTime().toString();
qDebug("old time: %s \n", old_time.latin1());
qDebug("new time: %s \n", new_time_str.latin1());
update();
}

void MyWidget::mouseReleaseEvent (QMouseEvent *) {
in_move = false; // just for minute pin don't jump
}


void MyWidget::paintEvent (QPaintEvent *) {
QPointArray hourhand(3);
QPointArray minutehand(3);

hourhand.putPoints (0, 3, 7, 8, -7, 8, 0, -40);
minutehand.putPoints (0, 3, 7, 8, -7, 8, 0, -70);


QPointArray secondhand(3);
secondhand.putPoints(0, 3, 3, 4, -3, -4, 0, -90);

QColor hourColor(127, 0, 127);
QColor minuteColor(0, 127, 127);
QColor secondColor (127, 127, 0);

int side = (width() < height()) ? width() : height() ;
QTime time = QTime::currentTime();

QPainter painter(this);
painter.translate(width() / 2, height() / 2);
painter.scale(side / 200.0, side / 200.0);

painter.setPen(Qt::NoPen);
painter.setBrush(hourColor);

painter.save();
painter.rotate(30.0 * ((time.hour() + time.minute() / 60.0)));
painter.drawConvexPolygon(hourhand);
painter.restore();

painter.setPen(hourColor);

for (int i = 0; i < 12; ++i) {
painter.drawLine(88, 0, 96, 0);
painter.rotate(30.0);
}

painter.setPen(Qt::NoPen);
painter.setBrush(minuteColor);

painter.save();
rotate_angle_minute = ( 6.0 * (time.minute() + time.second() / 60.0));
painter.rotate(rotate_angle_minute);

painter.drawConvexPolygon(minutehand);
painter.restore();

painter.save();
painter.setPen(secondColor);
painter.rotate( 6.0 * (time.second() + time.msec() / 1000));
painter.drawConvexPolygon(secondhand);
painter.restore();

painter.setPen(minuteColor);

for (int j = 0; j < 60; ++j) {
if ((j % 5) != 0)
painter.drawLine(92, 0, 96, 0);
painter.rotate(6.0);
}

}

int main( int argc, char **argv )
{
QApplication a( argc, argv );

MyWidget w;
a.setMainWidget( &w );
w.show();
return a.exec();
}

没有评论: