// Copyright (c) 2012 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "ui/views/bubble/tray_bubble_view.h"

#include <algorithm>

#include "third_party/skia/include/core/SkCanvas.h"
#include "third_party/skia/include/core/SkColor.h"
#include "third_party/skia/include/core/SkPaint.h"
#include "third_party/skia/include/core/SkPath.h"
#include "third_party/skia/include/effects/SkBlurImageFilter.h"
#include "ui/accessibility/ax_view_state.h"
#include "ui/aura/window.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/layer_delegate.h"
#include "ui/events/event.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/insets.h"
#include "ui/gfx/path.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/skia_util.h"
#include "ui/views/bubble/bubble_frame_view.h"
#include "ui/views/bubble/bubble_window_targeter.h"
#include "ui/views/layout/box_layout.h"
#include "ui/views/widget/widget.h"

namespace {

// Inset the arrow a bit from the edge.
const int kArrowMinOffset = 20;
const int kBubbleSpacing = 20;

// The new theme adjusts the menus / bubbles to be flush with the shelf when
// there is no bubble. These are the offsets which need to be applied.
const int kArrowOffsetTopBottom = 4;
const int kArrowOffsetLeft = 9;
const int kArrowOffsetRight = -5;
const int kOffsetLeftRightForTopBottomOrientation = 5;

// The sampling time for mouse position changes in ms - which is roughly a frame
// time.
const int kFrameTimeInMS = 30;
}  // namespace

namespace views {

namespace internal {

// Detects any mouse movement. This is needed to detect mouse movements by the
// user over the bubble if the bubble got created underneath the cursor.
class MouseMoveDetectorHost : public MouseWatcherHost {
 public:
  MouseMoveDetectorHost();
  virtual ~MouseMoveDetectorHost();

  virtual bool Contains(const gfx::Point& screen_point,
                        MouseEventType type) OVERRIDE;
 private:
  DISALLOW_COPY_AND_ASSIGN(MouseMoveDetectorHost);
};

MouseMoveDetectorHost::MouseMoveDetectorHost() {
}

MouseMoveDetectorHost::~MouseMoveDetectorHost() {
}

bool MouseMoveDetectorHost::Contains(const gfx::Point& screen_point,
                                     MouseEventType type) {
  return false;
}

// Custom border for TrayBubbleView. Contains special logic for GetBounds()
// to stack bubbles with no arrows correctly. Also calculates the arrow offset.
class TrayBubbleBorder : public BubbleBorder {
 public:
  TrayBubbleBorder(View* owner,
                   View* anchor,
                   TrayBubbleView::InitParams params)
      : BubbleBorder(params.arrow, params.shadow, params.arrow_color),
        owner_(owner),
        anchor_(anchor),
        tray_arrow_offset_(params.arrow_offset),
        first_item_has_no_margin_(params.first_item_has_no_margin) {
    set_alignment(params.arrow_alignment);
    set_background_color(params.arrow_color);
    set_paint_arrow(params.arrow_paint_type);
  }

  virtual ~TrayBubbleBorder() {}

  // Overridden from BubbleBorder.
  // Sets the bubble on top of the anchor when it has no arrow.
  virtual gfx::Rect GetBounds(const gfx::Rect& position_relative_to,
                              const gfx::Size& contents_size) const OVERRIDE {
    if (has_arrow(arrow())) {
      gfx::Rect rect =
          BubbleBorder::GetBounds(position_relative_to, contents_size);
      if (first_item_has_no_margin_) {
        if (arrow() == BubbleBorder::BOTTOM_RIGHT ||
            arrow() == BubbleBorder::BOTTOM_LEFT) {
          rect.set_y(rect.y() + kArrowOffsetTopBottom);
          int rtl_factor = base::i18n::IsRTL() ? -1 : 1;
          rect.set_x(rect.x() +
                     rtl_factor * kOffsetLeftRightForTopBottomOrientation);
        } else if (arrow() == BubbleBorder::LEFT_BOTTOM) {
          rect.set_x(rect.x() + kArrowOffsetLeft);
        } else if (arrow() == BubbleBorder::RIGHT_BOTTOM) {
          rect.set_x(rect.x() + kArrowOffsetRight);
        }
      }
      return rect;
    }

    gfx::Size border_size(contents_size);
    gfx::Insets insets = GetInsets();
    border_size.Enlarge(insets.width(), insets.height());
    const int x = position_relative_to.x() +
        position_relative_to.width() / 2 - border_size.width() / 2;
    // Position the bubble on top of the anchor.
    const int y = position_relative_to.y() - border_size.height() +
        insets.height() - kBubbleSpacing;
    return gfx::Rect(x, y, border_size.width(), border_size.height());
  }

  void UpdateArrowOffset() {
    int arrow_offset = 0;
    if (arrow() == BubbleBorder::BOTTOM_RIGHT ||
        arrow() == BubbleBorder::BOTTOM_LEFT) {
      // Note: tray_arrow_offset_ is relative to the anchor widget.
      if (tray_arrow_offset_ ==
          TrayBubbleView::InitParams::kArrowDefaultOffset) {
        arrow_offset = kArrowMinOffset;
      } else {
        const int width = owner_->GetWidget()->GetContentsView()->width();
        gfx::Point pt(tray_arrow_offset_, 0);
        View::ConvertPointToScreen(anchor_->GetWidget()->GetRootView(), &pt);
        View::ConvertPointFromScreen(owner_->GetWidget()->GetRootView(), &pt);
        arrow_offset = pt.x();
        if (arrow() == BubbleBorder::BOTTOM_RIGHT)
          arrow_offset = width - arrow_offset;
        arrow_offset = std::max(arrow_offset, kArrowMinOffset);
      }
    } else {
      if (tray_arrow_offset_ ==
          TrayBubbleView::InitParams::kArrowDefaultOffset) {
        arrow_offset = kArrowMinOffset;
      } else {
        gfx::Point pt(0, tray_arrow_offset_);
        View::ConvertPointToScreen(anchor_->GetWidget()->GetRootView(), &pt);
        View::ConvertPointFromScreen(owner_->GetWidget()->GetRootView(), &pt);
        arrow_offset = pt.y();
        arrow_offset = std::max(arrow_offset, kArrowMinOffset);
      }
    }
    set_arrow_offset(arrow_offset);
  }

 private:
  View* owner_;
  View* anchor_;
  const int tray_arrow_offset_;

  // If true the first item should not get any additional spacing against the
  // anchor (without the bubble tip the bubble should be flush to the shelf).
  const bool first_item_has_no_margin_;

  DISALLOW_COPY_AND_ASSIGN(TrayBubbleBorder);
};

// This mask layer clips the bubble's content so that it does not overwrite the
// rounded bubble corners.
// TODO(miket): This does not work on Windows. Implement layer masking or
// alternate solutions if the TrayBubbleView is needed there in the future.
class TrayBubbleContentMask : public ui::LayerDelegate {
 public:
  explicit TrayBubbleContentMask(int corner_radius);
  virtual ~TrayBubbleContentMask();

  ui::Layer* layer() { return &layer_; }

  // Overridden from LayerDelegate.
  virtual void OnPaintLayer(gfx::Canvas* canvas) OVERRIDE;
  virtual void OnDelegatedFrameDamage(
      const gfx::Rect& damage_rect_in_dip) OVERRIDE {}
  virtual void OnDeviceScaleFactorChanged(float device_scale_factor) OVERRIDE;
  virtual base::Closure PrepareForLayerBoundsChange() OVERRIDE;

 private:
  ui::Layer layer_;
  int corner_radius_;

  DISALLOW_COPY_AND_ASSIGN(TrayBubbleContentMask);
};

TrayBubbleContentMask::TrayBubbleContentMask(int corner_radius)
    : layer_(ui::LAYER_TEXTURED),
      corner_radius_(corner_radius) {
  layer_.set_delegate(this);
}

TrayBubbleContentMask::~TrayBubbleContentMask() {
  layer_.set_delegate(NULL);
}

void TrayBubbleContentMask::OnPaintLayer(gfx::Canvas* canvas) {
  SkPaint paint;
  paint.setAlpha(255);
  paint.setStyle(SkPaint::kFill_Style);
  gfx::Rect rect(layer()->bounds().size());
  canvas->DrawRoundRect(rect, corner_radius_, paint);
}

void TrayBubbleContentMask::OnDeviceScaleFactorChanged(
    float device_scale_factor) {
  // Redrawing will take care of scale factor change.
}

base::Closure TrayBubbleContentMask::PrepareForLayerBoundsChange() {
  return base::Closure();
}

// Custom layout for the bubble-view. Does the default box-layout if there is
// enough height. Otherwise, makes sure the bottom rows are visible.
class BottomAlignedBoxLayout : public BoxLayout {
 public:
  explicit BottomAlignedBoxLayout(TrayBubbleView* bubble_view)
      : BoxLayout(BoxLayout::kVertical, 0, 0, 0),
        bubble_view_(bubble_view) {
  }

  virtual ~BottomAlignedBoxLayout() {}

 private:
  virtual void Layout(View* host) OVERRIDE {
    if (host->height() >= host->GetPreferredSize().height() ||
        !bubble_view_->is_gesture_dragging()) {
      BoxLayout::Layout(host);
      return;
    }

    int consumed_height = 0;
    for (int i = host->child_count() - 1;
        i >= 0 && consumed_height < host->height(); --i) {
      View* child = host->child_at(i);
      if (!child->visible())
        continue;
      gfx::Size size = child->GetPreferredSize();
      child->SetBounds(0, host->height() - consumed_height - size.height(),
          host->width(), size.height());
      consumed_height += size.height();
    }
  }

  TrayBubbleView* bubble_view_;

  DISALLOW_COPY_AND_ASSIGN(BottomAlignedBoxLayout);
};

}  // namespace internal

using internal::TrayBubbleBorder;
using internal::TrayBubbleContentMask;
using internal::BottomAlignedBoxLayout;

// static
const int TrayBubbleView::InitParams::kArrowDefaultOffset = -1;

TrayBubbleView::InitParams::InitParams(AnchorType anchor_type,
                                       AnchorAlignment anchor_alignment,
                                       int min_width,
                                       int max_width)
    : anchor_type(anchor_type),
      anchor_alignment(anchor_alignment),
      min_width(min_width),
      max_width(max_width),
      max_height(0),
      can_activate(false),
      close_on_deactivate(true),
      arrow_color(SK_ColorBLACK),
      first_item_has_no_margin(false),
      arrow(BubbleBorder::NONE),
      arrow_offset(kArrowDefaultOffset),
      arrow_paint_type(BubbleBorder::PAINT_NORMAL),
      shadow(BubbleBorder::BIG_SHADOW),
      arrow_alignment(BubbleBorder::ALIGN_EDGE_TO_ANCHOR_EDGE) {
}

// static
TrayBubbleView* TrayBubbleView::Create(gfx::NativeView parent_window,
                                       View* anchor,
                                       Delegate* delegate,
                                       InitParams* init_params) {
  // Set arrow here so that it can be passed to the BubbleView constructor.
  if (init_params->anchor_type == ANCHOR_TYPE_TRAY) {
    if (init_params->anchor_alignment == ANCHOR_ALIGNMENT_BOTTOM) {
      init_params->arrow = base::i18n::IsRTL() ?
          BubbleBorder::BOTTOM_LEFT : BubbleBorder::BOTTOM_RIGHT;
    } else if (init_params->anchor_alignment == ANCHOR_ALIGNMENT_TOP) {
      init_params->arrow = BubbleBorder::TOP_LEFT;
    } else if (init_params->anchor_alignment == ANCHOR_ALIGNMENT_LEFT) {
      init_params->arrow = BubbleBorder::LEFT_BOTTOM;
    } else {
      init_params->arrow = BubbleBorder::RIGHT_BOTTOM;
    }
  } else {
    init_params->arrow = BubbleBorder::NONE;
  }

  return new TrayBubbleView(parent_window, anchor, delegate, *init_params);
}

TrayBubbleView::TrayBubbleView(gfx::NativeView parent_window,
                               View* anchor,
                               Delegate* delegate,
                               const InitParams& init_params)
    : BubbleDelegateView(anchor, init_params.arrow),
      params_(init_params),
      delegate_(delegate),
      preferred_width_(init_params.min_width),
      bubble_border_(NULL),
      is_gesture_dragging_(false),
      mouse_actively_entered_(false) {
  set_parent_window(parent_window);
  set_notify_enter_exit_on_child(true);
  set_close_on_deactivate(init_params.close_on_deactivate);
  set_margins(gfx::Insets());
  bubble_border_ = new TrayBubbleBorder(this, GetAnchorView(), params_);
  SetPaintToLayer(true);
  SetFillsBoundsOpaquely(true);

  bubble_content_mask_.reset(
      new TrayBubbleContentMask(bubble_border_->GetBorderCornerRadius()));
}

TrayBubbleView::~TrayBubbleView() {
  mouse_watcher_.reset();
  // Inform host items (models) that their views are being destroyed.
  if (delegate_)
    delegate_->BubbleViewDestroyed();
}

void TrayBubbleView::InitializeAndShowBubble() {
  // Must occur after call to BubbleDelegateView::CreateBubble().
  SetAlignment(params_.arrow_alignment);
  bubble_border_->UpdateArrowOffset();

  layer()->parent()->SetMaskLayer(bubble_content_mask_->layer());

  GetWidget()->Show();
  GetWidget()->GetNativeWindow()->SetEventTargeter(
      scoped_ptr<ui::EventTargeter>(new BubbleWindowTargeter(this)));
  UpdateBubble();
}

void TrayBubbleView::UpdateBubble() {
  SizeToContents();
  bubble_content_mask_->layer()->SetBounds(layer()->bounds());
  GetWidget()->GetRootView()->SchedulePaint();
}

void TrayBubbleView::SetMaxHeight(int height) {
  params_.max_height = height;
  if (GetWidget())
    SizeToContents();
}

void TrayBubbleView::SetWidth(int width) {
  width = std::max(std::min(width, params_.max_width), params_.min_width);
  if (preferred_width_ == width)
    return;
  preferred_width_ = width;
  if (GetWidget())
    SizeToContents();
}

void TrayBubbleView::SetArrowPaintType(
    views::BubbleBorder::ArrowPaintType paint_type) {
  bubble_border_->set_paint_arrow(paint_type);
  UpdateBubble();
}

gfx::Insets TrayBubbleView::GetBorderInsets() const {
  return bubble_border_->GetInsets();
}

void TrayBubbleView::Init() {
  BoxLayout* layout = new BottomAlignedBoxLayout(this);
  layout->SetDefaultFlex(1);
  SetLayoutManager(layout);
}

gfx::Rect TrayBubbleView::GetAnchorRect() const {
  if (!delegate_)
    return gfx::Rect();
  return delegate_->GetAnchorRect(anchor_widget(),
                                  params_.anchor_type,
                                  params_.anchor_alignment);
}

bool TrayBubbleView::CanActivate() const {
  return params_.can_activate;
}

NonClientFrameView* TrayBubbleView::CreateNonClientFrameView(Widget* widget) {
  BubbleFrameView* frame = new BubbleFrameView(margins());
  frame->SetBubbleBorder(scoped_ptr<views::BubbleBorder>(bubble_border_));
  return frame;
}

bool TrayBubbleView::WidgetHasHitTestMask() const {
  return true;
}

void TrayBubbleView::GetWidgetHitTestMask(gfx::Path* mask) const {
  DCHECK(mask);
  mask->addRect(gfx::RectToSkRect(GetBubbleFrameView()->GetContentsBounds()));
}

gfx::Size TrayBubbleView::GetPreferredSize() const {
  return gfx::Size(preferred_width_, GetHeightForWidth(preferred_width_));
}

gfx::Size TrayBubbleView::GetMaximumSize() const {
  gfx::Size size = GetPreferredSize();
  size.set_width(params_.max_width);
  return size;
}

int TrayBubbleView::GetHeightForWidth(int width) const {
  int height = GetInsets().height();
  width = std::max(width - GetInsets().width(), 0);
  for (int i = 0; i < child_count(); ++i) {
    const View* child = child_at(i);
    if (child->visible())
      height += child->GetHeightForWidth(width);
  }

  return (params_.max_height != 0) ?
      std::min(height, params_.max_height) : height;
}

void TrayBubbleView::OnMouseEntered(const ui::MouseEvent& event) {
  mouse_watcher_.reset();
  if (delegate_ && !(event.flags() & ui::EF_IS_SYNTHESIZED)) {
    // Coming here the user was actively moving the mouse over the bubble and
    // we inform the delegate that we entered. This will prevent the bubble
    // to auto close.
    delegate_->OnMouseEnteredView();
    mouse_actively_entered_ = true;
  } else {
    // Coming here the bubble got shown and the mouse was 'accidentally' over it
    // which is not a reason to prevent the bubble to auto close. As such we
    // do not call the delegate, but wait for the first mouse move within the
    // bubble. The used MouseWatcher will notify use of a movement and call
    // |MouseMovedOutOfHost|.
    mouse_watcher_.reset(new MouseWatcher(
        new views::internal::MouseMoveDetectorHost(),
        this));
    // Set the mouse sampling frequency to roughly a frame time so that the user
    // cannot see a lag.
    mouse_watcher_->set_notify_on_exit_time(
        base::TimeDelta::FromMilliseconds(kFrameTimeInMS));
    mouse_watcher_->Start();
  }
}

void TrayBubbleView::OnMouseExited(const ui::MouseEvent& event) {
  // If there was a mouse watcher waiting for mouse movements we disable it
  // immediately since we now leave the bubble.
  mouse_watcher_.reset();
  // Do not notify the delegate of an exit if we never told it that we entered.
  if (delegate_ && mouse_actively_entered_)
    delegate_->OnMouseExitedView();
}

void TrayBubbleView::GetAccessibleState(ui::AXViewState* state) {
  if (delegate_ && params_.can_activate) {
    state->role = ui::AX_ROLE_WINDOW;
    state->name = delegate_->GetAccessibleNameForBubble();
  }
}

void TrayBubbleView::MouseMovedOutOfHost() {
  // The mouse was accidentally over the bubble when it opened and the AutoClose
  // logic was not activated. Now that the user did move the mouse we tell the
  // delegate to disable AutoClose.
  delegate_->OnMouseEnteredView();
  mouse_actively_entered_ = true;
  mouse_watcher_->Stop();
}

void TrayBubbleView::ChildPreferredSizeChanged(View* child) {
  SizeToContents();
}

void TrayBubbleView::ViewHierarchyChanged(
    const ViewHierarchyChangedDetails& details) {
  if (details.is_add && details.child == this) {
    details.parent->SetPaintToLayer(true);
    details.parent->SetFillsBoundsOpaquely(true);
    details.parent->layer()->SetMasksToBounds(true);
  }
}

}  // namespace views
