#include "multicookview.h" #include #include #include MultiCookView::MultiCookView(QWidget *parent) : QWidget(parent), timePosition(0) { barPixmap.load(":/images/multi/bar.png"); connect(&checkTimer, SIGNAL(timeout()), SLOT(check())); } void MultiCookView::setContainer(MultiCookContainer *container) { this->container = container; rects = calcRects(); checkTimer.start(33); } void MultiCookView::setTimeBar(MultiCookTimeBar *bar) { this->bar = bar; } void MultiCookView::showNow() { timePosition = 0; updateView(); bar->showNow(); } void MultiCookView::showNext() { if (timePosition < 0 || !nothingOnRight()) { timePosition++; updateView(); bar->showNext(); } } void MultiCookView::showPrev() { if (timePosition > 0) { timePosition--; updateView(); bar->showPrev(); } } void MultiCookView::updateView() { rects = calcRects(); update(); } void MultiCookView::mousePressEvent(QMouseEvent *event) { int x = event->x(); int y = event->y(); pressedSlot = calcSlot(x, y); } void MultiCookView::mouseReleaseEvent(QMouseEvent *event) { if (pressedSlot == -1) return; int x = event->x(); int y = event->y(); if (calcSlot(x, y) == pressedSlot) emit clicked(pressedSlot); } void MultiCookView::paintEvent(QPaintEvent */*event*/) { QPainter painter(this); paintGrids(painter); paintBars(painter); paintCurrentTime(painter); } void MultiCookView::resizeEvent(QResizeEvent *event) { rects = calcRects(); QWidget::resizeEvent(event); } void MultiCookView::check() { bool needUpdate = false; QList rects = calcRects(); for (int i = 0; i < 10; i++) { if (rects.at(i) != this->rects.at(i)) { needUpdate = true; break; } } if (needUpdate) { this->rects = rects; update(); } } QList MultiCookView::calcRects() { int w = width(); int h = height(); int x = w * (2-timePosition) / 10 + 1; int y = (h / 10 - 67) / 2; QList list; for (int i = 0; i < 10; i++) { MultiCook *cook = container->at(i); if (cook == Q_NULLPTR) { list.append(QRect()); continue; } int barY = y + h * i / 10; int barW = 0; // bar width = remaining time(ms) / 200s * width of a grid int remainingTime = cook->remainingTime(); if (remainingTime > 0) barW = qCeil(remainingTime / 2000000.0 * w); list.append(QRect(x, barY, barW, 67)); } return list; } int MultiCookView::calcSlot(int x, int y) { for (int i = 0; i < 10; i++) { const QRect &r = rects.at(i); if (r.isNull()) continue; if (r.contains(x, y)) return i; } return -1; } void MultiCookView::paintGrids(QPainter &painter) { static const int padding = 12; int w = width(); int h = height(); painter.setBrush(Qt::NoBrush); painter.setPen(QColor(70,70,70)); for (int i = 1; i < 10; i++) painter.drawLine(0, h * i / 10, w, h * i / 10); for (int i = 1; i < 10; i++) painter.drawLine(w * i / 10, padding, w * i / 10, h - padding); } void MultiCookView::paintBars(QPainter &painter) { for (int i = 0; i < 10; i++) { MultiCook *cook = container->at(i); if (cook == Q_NULLPTR) continue; QRect r = rects.at(i); if (!r.isNull()) paintBar(painter, r); r.translate(12, 0); if (r.left() < 12) r.moveLeft(12); painter.setBrush(Qt::NoBrush); painter.setPen(Qt::white); painter.drawText(r, Qt::AlignVCenter | Qt::TextDontClip, cook->name()); } } void MultiCookView::paintCurrentTime(QPainter &painter) { static const int padding = 12; int w = width(); int h = height(); int x = w * (2-timePosition) / 10; QPen pen(Qt::yellow); pen.setWidth(4); painter.setPen(pen); painter.setBrush(Qt::NoBrush); painter.drawLine(x, padding, x, h - padding); } void MultiCookView::paintBar(QPainter &painter, QRect r) { static const int fullWidth = 337; static const int headWidth = 8; static const int tailWidth = fullWidth - 306; static const int bodyWidth = fullWidth - headWidth - tailWidth; static const int height = 67; static const int bodyOffset = headWidth; static const int tailOffset = fullWidth - tailWidth; int w = r.width(); if (w < tailWidth) { // Clip tail QRect sourceRect(tailWidth - w + tailOffset, 0, w, height); painter.drawPixmap(r, barPixmap, sourceRect); } else if (w < headWidth + tailWidth) { // Full tail QRect sourceRect(tailOffset, 0, tailWidth, height); QRect targetRect(r.x() + w - tailWidth, r.y(), tailWidth, height); painter.drawPixmap(targetRect, barPixmap, sourceRect); // Clip head // sourceRect = QRect(0, 0, w - tailWidth, height); // targetRect = QRect(r.x(), r.y(), w - tailWidth, height); // painter.drawPixmap(targetRect, barPixmap, sourceRect); sourceRect = QRect(headWidth - (w - tailWidth), 0, w - tailWidth, height); targetRect = QRect(r.x(), r.y(), w - tailWidth, height); painter.drawPixmap(targetRect, barPixmap, sourceRect); } else { // Full tail QRect sourceRect(tailOffset, 0, tailWidth, height); QRect targetRect(r.x() + w - tailWidth, r.y(), tailWidth, height); painter.drawPixmap(targetRect, barPixmap, sourceRect); // Full head sourceRect = QRect(0, 0, headWidth, height); targetRect = QRect(r.x(), r.y(), headWidth, height); painter.drawPixmap(targetRect, barPixmap, sourceRect); // Stretch body sourceRect = QRect(bodyOffset, 0, bodyWidth, 0); targetRect = QRect(r.x() + bodyOffset, r.y(), w - headWidth - tailWidth, height); painter.drawPixmap(targetRect, barPixmap, sourceRect); } } bool MultiCookView::nothingOnRight() { int rightMost = width() * 2 / 3; foreach (QRect r, rects) if (r.right() > rightMost) return false; return true; }