This source file includes following definitions.
- CreateAndShowWidgetWithContent
- widget_closed_
- Close
- RemoveMessage
- OnPaint
- GetAccessibleState
- OnImplicitAnimationsCompleted
- AddLabel
- CloseMessage
- IsVisible
- GetShownTextForTest
- ShowMessage
#include "chrome/browser/chromeos/ui/idle_app_name_notification_view.h"
#include <string>
#include "ash/shell.h"
#include "ash/shell_delegate.h"
#include "ash/shell_window_ids.h"
#include "ash/wm/window_animations.h"
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
#include "base/time/time.h"
#include "base/timer/timer.h"
#include "extensions/common/extension.h"
#include "grit/generated_resources.h"
#include "ui/accessibility/ax_view_state.h"
#include "ui/aura/window.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/compositor/layer_animation_observer.h"
#include "ui/compositor/scoped_layer_animation_settings.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font_list.h"
#include "ui/gfx/text_utils.h"
#include "ui/views/controls/label.h"
#include "ui/views/layout/box_layout.h"
#include "ui/views/layout/fill_layout.h"
#include "ui/views/view.h"
#include "ui/views/widget/widget.h"
#include "ui/views/widget/widget_delegate.h"
namespace ui {
class LayerAnimationSequence;
}
namespace chromeos {
namespace {
const SkColor kTextColor = SK_ColorBLACK;
const SkColor kErrorTextColor = SK_ColorRED;
const SkColor kWindowBackgroundColor = SK_ColorWHITE;
const int kWindowCornerRadius = 4;
void CreateAndShowWidgetWithContent(views::WidgetDelegate* delegate,
views::View* view,
int animation_time_ms) {
aura::Window* root_window = ash::Shell::GetTargetRootWindow();
gfx::Size rs = root_window->bounds().size();
gfx::Size ps = view->GetPreferredSize();
gfx::Rect bounds((rs.width() - ps.width()) / 2,
-ps.height(),
ps.width(),
ps.height());
views::Widget::InitParams params;
params.type = views::Widget::InitParams::TYPE_POPUP;
params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW;
params.ownership = views::Widget::InitParams::NATIVE_WIDGET_OWNS_WIDGET;
params.accept_events = false;
params.can_activate = false;
params.keep_on_top = true;
params.remove_standard_frame = true;
params.delegate = delegate;
params.bounds = bounds;
params.parent = ash::Shell::GetContainer(
root_window, ash::kShellWindowId_SettingBubbleContainer);
views::Widget* widget = new views::Widget;
widget->Init(params);
widget->SetContentsView(view);
gfx::NativeView native_view = widget->GetNativeView();
native_view->SetName("KioskIdleAppNameNotification");
ui::LayerAnimator* animator = new ui::LayerAnimator(
base::TimeDelta::FromMilliseconds(animation_time_ms));
native_view->layer()->SetAnimator(animator);
widget->Show();
animator->StopAnimating();
bounds.set_y((rs.height() - ps.height()) / 20);
widget->SetBounds(bounds);
view->NotifyAccessibilityEvent(ui::AX_EVENT_ALERT, true);
}
}
class IdleAppNameNotificationDelegateView
: public views::WidgetDelegateView,
public ui::ImplicitAnimationObserver {
public:
IdleAppNameNotificationDelegateView(IdleAppNameNotificationView *owner,
const base::string16& app_name,
bool error,
int message_visibility_time_in_ms)
: owner_(owner),
widget_closed_(false) {
ui::ResourceBundle& rb = ui::ResourceBundle::GetSharedInstance();
AddLabel(app_name,
rb.GetFontList(ui::ResourceBundle::BoldFont),
error ? kErrorTextColor : kTextColor);
spoken_text_ = app_name;
SetLayoutManager(new views::FillLayout);
hide_timer_.Start(
FROM_HERE,
base::TimeDelta::FromMilliseconds(message_visibility_time_in_ms),
this,
&IdleAppNameNotificationDelegateView::RemoveMessage);
}
virtual ~IdleAppNameNotificationDelegateView() {
widget_closed_ = true;
Close();
}
void Close() {
hide_timer_.Stop();
if (owner_) {
IdleAppNameNotificationView* owner = owner_;
owner_ = NULL;
owner->CloseMessage();
}
if (!widget_closed_) {
widget_closed_ = true;
GetWidget()->Close();
}
}
void RemoveMessage() {
aura::Window* widget_view = GetWidget()->GetNativeView();
ui::Layer* layer = widget_view->layer();
ui::ScopedLayerAnimationSettings settings(layer->GetAnimator());
settings.AddObserver(this);
gfx::Rect rect = widget_view->bounds();
rect.set_y(-GetPreferredSize().height());
layer->SetBounds(rect);
}
virtual void OnPaint(gfx::Canvas* canvas) OVERRIDE {
SkPaint paint;
paint.setStyle(SkPaint::kFill_Style);
paint.setColor(kWindowBackgroundColor);
canvas->DrawRoundRect(GetLocalBounds(), kWindowCornerRadius, paint);
views::WidgetDelegateView::OnPaint(canvas);
}
virtual void GetAccessibleState(ui::AXViewState* state) OVERRIDE {
state->name = spoken_text_;
state->role = ui::AX_ROLE_ALERT;
}
virtual void OnImplicitAnimationsCompleted() OVERRIDE {
Close();
}
private:
void AddLabel(const base::string16& text,
const gfx::FontList& font,
SkColor text_color) {
views::Label* label = new views::Label;
label->SetText(text);
label->SetHorizontalAlignment(gfx::ALIGN_CENTER);
label->SetFontList(font);
label->SetEnabledColor(text_color);
label->SetDisabledColor(text_color);
label->SetAutoColorReadabilityEnabled(false);
AddChildView(label);
}
base::OneShotTimer<IdleAppNameNotificationDelegateView> hide_timer_;
IdleAppNameNotificationView* owner_;
base::string16 spoken_text_;
bool widget_closed_;
DISALLOW_COPY_AND_ASSIGN(IdleAppNameNotificationDelegateView);
};
IdleAppNameNotificationView::IdleAppNameNotificationView(
int message_visibility_time_in_ms,
int animation_time_ms,
const extensions::Extension* extension)
: view_(NULL) {
ShowMessage(message_visibility_time_in_ms, animation_time_ms, extension);
}
IdleAppNameNotificationView::~IdleAppNameNotificationView() {
CloseMessage();
}
void IdleAppNameNotificationView::CloseMessage() {
if (view_) {
IdleAppNameNotificationDelegateView* view = view_;
view_ = NULL;
view->Close();
}
}
bool IdleAppNameNotificationView::IsVisible() {
return view_ != NULL;
}
base::string16 IdleAppNameNotificationView::GetShownTextForTest() {
ui::AXViewState state;
DCHECK(view_);
view_->GetAccessibleState(&state);
return state.name;
}
void IdleAppNameNotificationView::ShowMessage(
int message_visibility_time_in_ms,
int animation_time_ms,
const extensions::Extension* extension) {
DCHECK(!view_);
base::string16 app_name;
bool error = false;
if (extension &&
!base::ContainsOnlyChars(extension->name(), base::kWhitespaceASCII)) {
app_name = base::UTF8ToUTF16(extension->name());
} else {
error = true;
app_name = l10n_util::GetStringUTF16(
IDS_IDLE_APP_NAME_UNKNOWN_APPLICATION_NOTIFICATION);
}
view_ = new IdleAppNameNotificationDelegateView(
this,
app_name,
error,
message_visibility_time_in_ms + animation_time_ms);
CreateAndShowWidgetWithContent(view_, view_, animation_time_ms);
}
}