180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru/*
380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * Copyright 2011 Google Inc.
480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru *
580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * Use of this source code is governed by a BSD-style license that can be
680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * found in the LICENSE file.
780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */
880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkWidget.h"
980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkCanvas.h"
1080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkMath.h"
1180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkShader.h"
1280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkInterpolator.h"
1380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkTime.h"
1480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
1580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste QueruSkProgressView::SkProgressView(uint32_t flags) : SkView(flags), fOnShader(NULL), fOffShader(NULL)
1680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru{
1780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    fValue = 0;
1880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    fMax = 0;
1980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    fInterp = NULL;
2080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    fDoInterp = false;
2180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
2280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
2380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste QueruSkProgressView::~SkProgressView()
2480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru{
2580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    delete fInterp;
2680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkSafeUnref(fOnShader);
2780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkSafeUnref(fOffShader);
2880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
2980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
3080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queruvoid SkProgressView::setMax(U16CPU max)
3180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru{
3280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    if (fMax != max)
3380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    {
3480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        fMax = SkToU16(max);
3580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        if (fValue > 0)
3680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            this->inval(NULL);
3780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
3880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
3980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
4080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queruvoid SkProgressView::setValue(U16CPU value)
4180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru{
4280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    if (fValue != value)
4380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    {
4480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        if (fDoInterp)
4580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        {
4680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            if (fInterp)
4780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                delete fInterp;
4880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            fInterp = new SkInterpolator(1, 2);
4980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            SkScalar x = (SkScalar)(fValue << 8);
5080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            fInterp->setKeyFrame(0, SkTime::GetMSecs(), &x, 0);
5180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            x = (SkScalar)(value << 8);
5280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            fInterp->setKeyFrame(1, SkTime::GetMSecs() + 333, &x);
5380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        }
5480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        fValue = SkToU16(value);
5580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        this->inval(NULL);
5680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
5780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
5880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
5980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queruvoid SkProgressView::onDraw(SkCanvas* canvas)
6080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru{
6180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    if (fMax == 0)
6280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        return;
6380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
6480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkFixed    percent;
6580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
6680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    if (fInterp)
6780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    {
6880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkScalar x;
6980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        if (fInterp->timeToValues(SkTime::GetMSecs(), &x) == SkInterpolator::kFreezeEnd_Result)
7080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        {
7180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            delete fInterp;
7280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            fInterp = NULL;
7380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        }
7480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        percent = (SkFixed)x;    // now its 16.8
7580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        percent = SkMax32(0, SkMin32(percent, fMax << 8));    // now its pinned
7680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        percent = SkFixedDiv(percent, fMax << 8);    // now its 0.16
7780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        this->inval(NULL);
7880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
7980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    else
8080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    {
8180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        U16CPU value = SkMax32(0, SkMin32(fValue, fMax));
8280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        percent = SkFixedDiv(value, fMax);
8380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
8480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
8580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
8680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkRect    r;
8780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkPaint    p;
8880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
8980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    r.set(0, 0, this->width(), this->height());
9080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    p.setAntiAlias(true);
9180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
9280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    r.fRight = r.fLeft + SkScalarMul(r.width(), SkFixedToScalar(percent));
9380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    p.setStyle(SkPaint::kFill_Style);
9480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
9580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    p.setColor(SK_ColorDKGRAY);
9680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    p.setShader(fOnShader);
9780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    canvas->drawRect(r, p);
9880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
9980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    p.setColor(SK_ColorWHITE);
10080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    p.setShader(fOffShader);
10180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    r.fLeft = r.fRight;
10280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    r.fRight = this->width() - SK_Scalar1;
10380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    if (r.width() > 0)
10480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        canvas->drawRect(r, p);
10580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
10680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
10780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkImageDecoder.h"
10880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
10980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic SkShader* inflate_shader(const char file[])
11080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru{
11180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkBitmap    bm;
11280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
11380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    return SkImageDecoder::DecodeFile(file, &bm) ?
11480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            SkShader::CreateBitmapShader(bm, SkShader::kRepeat_TileMode, SkShader::kRepeat_TileMode) :
11580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            NULL;
11680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
11780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
11880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queruvoid SkProgressView::onInflate(const SkDOM& dom, const SkDOM::Node* node)
11980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru{
12080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    this->INHERITED::onInflate(dom, node);
12180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
12280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    const char* s;
12380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
12480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkASSERT(fOnShader == NULL);
12580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkASSERT(fOffShader == NULL);
12680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
12780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    if ((s = dom.findAttr(node, "src-on")) != NULL)
12880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        fOnShader = inflate_shader(s);
12980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    if ((s = dom.findAttr(node, "src-off")) != NULL)
13080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        fOffShader = inflate_shader(s);
13180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    (void)dom.findBool(node, "do-interp", &fDoInterp);
13280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
133