blob: 06381ef0e5ca34d141363213a846e5a9baa5fd8a [file] [log] [blame]
// 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 <windows.h>
#include "chrome/browser/platform_util.h"
#include "chrome/browser/ui/browser_dialogs.h"
#include "chrome/browser/ui/views/color_chooser_dialog.h"
#include "content/public/browser/color_chooser.h"
#include "content/public/browser/render_view_host.h"
#include "content/public/browser/render_widget_host.h"
#include "content/public/browser/render_widget_host_view.h"
#include "content/public/browser/web_contents.h"
#include "ui/views/color_chooser/color_chooser_listener.h"
class ColorChooserWin : public content::ColorChooser,
public views::ColorChooserListener {
public:
static ColorChooserWin* Open(content::WebContents* web_contents,
SkColor initial_color);
ColorChooserWin(content::WebContents* web_contents,
SkColor initial_color);
~ColorChooserWin() override;
// content::ColorChooser overrides:
void End() override;
void SetSelectedColor(SkColor color) override {}
// views::ColorChooserListener overrides:
void OnColorChosen(SkColor color) override;
void OnColorChooserDialogClosed() override;
private:
static ColorChooserWin* current_color_chooser_;
// The web contents invoking the color chooser. No ownership. because it will
// outlive this class.
content::WebContents* web_contents_;
// The color chooser dialog which maintains the native color chooser UI.
scoped_refptr<ColorChooserDialog> color_chooser_dialog_;
};
ColorChooserWin* ColorChooserWin::current_color_chooser_ = NULL;
ColorChooserWin* ColorChooserWin::Open(content::WebContents* web_contents,
SkColor initial_color) {
if (current_color_chooser_)
return NULL;
current_color_chooser_ = new ColorChooserWin(web_contents, initial_color);
return current_color_chooser_;
}
ColorChooserWin::ColorChooserWin(content::WebContents* web_contents,
SkColor initial_color)
: web_contents_(web_contents) {
gfx::NativeWindow owning_window =
platform_util::GetTopLevel(web_contents->GetRenderViewHost()
->GetWidget()
->GetView()
->GetNativeView());
color_chooser_dialog_ = new ColorChooserDialog(this,
initial_color,
owning_window);
}
ColorChooserWin::~ColorChooserWin() {
// Always call End() before destroying.
DCHECK(!color_chooser_dialog_.get());
}
void ColorChooserWin::End() {
// The ColorChooserDialog's listener is going away. Ideally we'd
// programmatically close the dialog at this point. Since that's impossible,
// we instead tell the dialog its listener is going away, so that the dialog
// doesn't try to communicate with a destroyed listener later. (We also tell
// the renderer the dialog is closed, since from the renderer's perspective
// it effectively is.)
OnColorChooserDialogClosed();
}
void ColorChooserWin::OnColorChosen(SkColor color) {
if (web_contents_)
web_contents_->DidChooseColorInColorChooser(color);
}
void ColorChooserWin::OnColorChooserDialogClosed() {
if (color_chooser_dialog_.get()) {
color_chooser_dialog_->ListenerDestroyed();
color_chooser_dialog_ = NULL;
}
DCHECK(current_color_chooser_ == this);
current_color_chooser_ = NULL;
if (web_contents_)
web_contents_->DidEndColorChooser();
}
namespace chrome {
content::ColorChooser* ShowColorChooser(content::WebContents* web_contents,
SkColor initial_color) {
return ColorChooserWin::Open(web_contents, initial_color);
}
} // namespace chrome