//---------------------------------------------------------------------------
void WtRubiksClockWidget::DrawRubiksClock(
  Wt::WPainter& painter,
  const int left, const int top,
  const int width, const int height,
  const RubiksClock * const clock,
  const bool front_side)
{
  //Draw main clock ring
  {
    Wt::WPen pen = painter.pen();
    pen.setColor(Wt::black);
    painter.setPen(pen);
  }
  {
    painter.setBrush(
      Wt::WBrush(
        Wt::WColor(
          front_side ? 127 : 96,
          front_side ? 127 : 96,
          196)));
  }
  painter.drawEllipse(
    static_cast<double>(left),
    static_cast<double>(top),
    static_cast<double>(width),
    static_cast<double>(height));



  //Draw the clocks and pegs
  {
    for (int y=0; y!=3; ++y)
    {
      for (int x=0; x!=3; ++x)
      {
        const boost::shared_ptr<RubiksClockDialWidget> w
          = (front_side ? clock->GetFrontTimes() : clock->GetBackTimes()).times[x][y];
        WtDialWidget::DrawDial(
          painter,
          w->GetGeometry().GetX(),
          w->GetGeometry().GetY(),
          w->GetGeometry().GetWidth(),
          w->GetGeometry().GetHeight(),
          w->GetRubiksClockDial()->GetDial());
      }
    }
    //Draw the pegs
    for (int y=0; y!=2; ++y)
    {
      for (int x=0; x!=2; ++x)
      {
        WtToggleButtonWidget::DrawToggleButton(
          painter,
          (front_side
            ? clock->GetFrontPegs()
            : clock->GetBackPegs()).pegs[x][y].get());
      }
    }
  }
}
void ribi::WtDialWidget::DrawDial(
  Wt::WPainter& painter,
  const int left, const int top,
  const int width, const int height,
  const Dial * const dial)
{
  const double position = dial->GetPosition();

  //Draw knob
  {
    Wt::WPen pen = painter.pen();
    pen.setWidth(1);
    pen.setColor(Wt::WColor(0,0,0));
    painter.setPen(pen);
  }

  painter.setBrush(Wt::WColor(
    dial->GetRed(),
    dial->GetGreen(),
    dial->GetBlue()));

  painter.drawEllipse(left+1,top+1,width-2,height-2);

  //Draw pointer
  const int midx = width / 2;
  const int midy = height / 2;
  const double ray = static_cast<double>(std::min( midx, midy ));
  const double two_pi = boost::math::constants::two_pi<double>();
  const double angle = position * two_pi;
  const int pointerX
    = static_cast<int>( static_cast<double>(midx) + (std::sin(angle) * ray) );
  const int pointerY
    = static_cast<int>( static_cast<double>(midy) - (std::cos(angle) * ray) );

  {
    Wt::WPen pen = painter.pen();
    pen.setWidth(4);
    painter.setPen(pen);
  }
  painter.drawLine(left+midx,top+midy,left+pointerX,top+pointerY);
}
void ribi::WtToggleButtonWidget::DrawToggleButton(
  Wt::WPainter& painter,
  const int left, const int top,
  const int width, const int height,
  const ToggleButton * const button)
{
  {
    Wt::WPen pen = painter.pen();
    pen.setWidth(1);
    pen.setColor(Wt::WColor(0,0,0));
    painter.setPen(pen);
  }
  painter.setBrush(Wt::WColor(
    button->GetRed(),
    button->GetGreen(),
    button->GetBlue()));
  //Draw base
  painter.drawArc(
    left + 0,
    top + (height * 1 / 3),
    width,
    height * 2 / 3,
    180 * 16,
    180 * 16);
  //Draw top
  painter.drawEllipse(
    left + 0,
    top + (button->IsPressed() ? (height * 1 / 3) - 2 : 0.0),
    width,
    height * 2 / 3);
  painter.drawLine(
    left + 1,
    top + (button->IsPressed() ? (height * 2 / 3) - 2 : (height * 1 / 3)),
    left + 1,
    top + (height * 2 / 3));
  painter.drawLine(
    left + (width - 1),
    top + (button->IsPressed() ? (height * 2 / 3) - 2 : (height * 1 / 3)),
    left + width - 1,
    top + (height * 2 / 3));
}