OLD | NEW |
1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this | 1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this |
2 // source code is governed by a BSD-style license that can be found in the | 2 // source code is governed by a BSD-style license that can be found in the |
3 // LICENSE file. | 3 // LICENSE file. |
4 | 4 |
5 #include "chrome/browser/views/autocomplete/autocomplete_popup_contents_view.h" | 5 #include "chrome/browser/views/autocomplete/autocomplete_popup_contents_view.h" |
6 | 6 |
7 #include <objidl.h> | |
8 #include <commctrl.h> | |
9 #include <dwmapi.h> | |
10 | |
11 #include "app/gfx/canvas.h" | 7 #include "app/gfx/canvas.h" |
12 #include "app/gfx/color_utils.h" | 8 #include "app/gfx/color_utils.h" |
13 #include "app/gfx/insets.h" | 9 #include "app/gfx/insets.h" |
14 #include "app/gfx/path.h" | 10 #include "app/gfx/path.h" |
15 #include "app/l10n_util.h" | 11 #include "app/l10n_util.h" |
16 #include "app/resource_bundle.h" | 12 #include "app/resource_bundle.h" |
17 #include "app/theme_provider.h" | 13 #include "app/theme_provider.h" |
18 #include "app/win_util.h" | |
19 #include "base/compiler_specific.h" | 14 #include "base/compiler_specific.h" |
20 #include "chrome/browser/autocomplete/autocomplete_edit_view_win.h" | 15 #include "chrome/browser/autocomplete/autocomplete_edit_view.h" |
21 #include "chrome/browser/autocomplete/autocomplete_popup_model.h" | 16 #include "chrome/browser/autocomplete/autocomplete_popup_model.h" |
22 #include "chrome/browser/views/autocomplete/autocomplete_popup_win.h" | |
23 #include "grit/generated_resources.h" | 17 #include "grit/generated_resources.h" |
24 #include "grit/theme_resources.h" | 18 #include "grit/theme_resources.h" |
25 #include "third_party/skia/include/core/SkShader.h" | 19 #include "third_party/skia/include/core/SkShader.h" |
26 #include "third_party/icu38/public/common/unicode/ubidi.h" | 20 #include "third_party/icu38/public/common/unicode/ubidi.h" |
27 #include "views/widget/widget.h" | 21 #include "views/widget/widget.h" |
28 | 22 |
| 23 #if defined(OS_WIN) |
| 24 #include <objidl.h> |
| 25 #include <commctrl.h> |
| 26 #include <dwmapi.h> |
| 27 |
| 28 #include "app/win_util.h" |
| 29 #include "chrome/browser/views/autocomplete/autocomplete_popup_win.h" |
| 30 #else |
| 31 #include "chrome/browser/views/autocomplete/autocomplete_popup_gtk.h" |
| 32 #endif |
| 33 |
29 // Colors for various components of the view. | 34 // Colors for various components of the view. |
| 35 #if defined(OS_WIN) |
30 static const SkColor kBackgroundColor = | 36 static const SkColor kBackgroundColor = |
31 color_utils::GetSysSkColor(COLOR_WINDOW); | 37 color_utils::GetSysSkColor(COLOR_WINDOW); |
32 static const SkColor kSelectedBackgroundColor = | 38 static const SkColor kSelectedBackgroundColor = |
33 color_utils::GetSysSkColor(COLOR_HIGHLIGHT); | 39 color_utils::GetSysSkColor(COLOR_HIGHLIGHT); |
34 static const SkColor kHoverBackgroundColor = | 40 static const SkColor kHoverBackgroundColor = |
35 SkColorSetA(kSelectedBackgroundColor, 127); | 41 SkColorSetA(kSelectedBackgroundColor, 127); |
36 static const SkColor kTextColor = | 42 static const SkColor kTextColor = |
37 color_utils::GetSysSkColor(COLOR_WINDOWTEXT); | 43 color_utils::GetSysSkColor(COLOR_WINDOWTEXT); |
38 static const SkColor kSelectedTextColor = | 44 static const SkColor kSelectedTextColor = |
39 color_utils::GetSysSkColor(COLOR_HIGHLIGHTTEXT); | 45 color_utils::GetSysSkColor(COLOR_HIGHLIGHTTEXT); |
40 static const SkColor kDimTextColor = | 46 static const SkColor kDimTextColor = |
41 color_utils::GetSysSkColor(COLOR_GRAYTEXT); | 47 color_utils::GetSysSkColor(COLOR_GRAYTEXT); |
42 static const SkColor kSelectedDimTextColor = | 48 static const SkColor kSelectedDimTextColor = |
43 color_utils::GetSysSkColor(COLOR_HIGHLIGHTTEXT); | 49 color_utils::GetSysSkColor(COLOR_HIGHLIGHTTEXT); |
| 50 #else |
| 51 // TODO(beng): source from theme provider. |
| 52 static const SkColor kBackgroundColor = SK_ColorWHITE; |
| 53 static const SkColor kSelectedBackgroundColor = SK_ColorBLUE; |
| 54 static const SkColor kHoverBackgroundColor = SK_ColorCYAN; |
| 55 static const SkColor kTextColor = SK_ColorBLACK; |
| 56 static const SkColor kSelectedTextColor = SK_ColorWHITE; |
| 57 static const SkColor kDimTextColor = SK_ColorGRAY; |
| 58 static const SkColor kSelectedDimTextColor = SK_ColorWHITE; |
| 59 #endif |
44 static const SkColor kStandardURLColor = SkColorSetRGB(0, 0x80, 0); | 60 static const SkColor kStandardURLColor = SkColorSetRGB(0, 0x80, 0); |
45 static const SkColor kHighlightURLColor = SkColorSetRGB(0xD0, 0xFF, 0xD0); | 61 static const SkColor kHighlightURLColor = SkColorSetRGB(0xD0, 0xFF, 0xD0); |
46 static const int kGlassPopupTransparency = 240; | 62 static const int kGlassPopupTransparency = 240; |
47 static const int kOpaquePopupTransparency = 255; | 63 static const int kOpaquePopupTransparency = 255; |
48 static const int kHoverRowAlpha = 0x40; | 64 static const int kHoverRowAlpha = 0x40; |
49 // The minimum distance between the top and bottom of the icon and the top or | 65 // The minimum distance between the top and bottom of the icon and the top or |
50 // bottom of the row. "Minimum" is used because the vertical padding may be | 66 // bottom of the row. "Minimum" is used because the vertical padding may be |
51 // larger, depending on the size of the text. | 67 // larger, depending on the size of the text. |
52 static const int kIconVerticalPadding = 2; | 68 static const int kIconVerticalPadding = 2; |
53 // The minimum distance between the top and bottom of the text and the top or | 69 // The minimum distance between the top and bottom of the text and the top or |
(...skipping 596 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
650 dropshadow_bottomleft_ = rb.GetBitmapNamed(IDR_OMNIBOX_POPUP_DS_BL); | 666 dropshadow_bottomleft_ = rb.GetBitmapNamed(IDR_OMNIBOX_POPUP_DS_BL); |
651 initialized = true; | 667 initialized = true; |
652 } | 668 } |
653 } | 669 } |
654 | 670 |
655 //////////////////////////////////////////////////////////////////////////////// | 671 //////////////////////////////////////////////////////////////////////////////// |
656 // AutocompletePopupContentsView, public: | 672 // AutocompletePopupContentsView, public: |
657 | 673 |
658 AutocompletePopupContentsView::AutocompletePopupContentsView( | 674 AutocompletePopupContentsView::AutocompletePopupContentsView( |
659 const gfx::Font& font, | 675 const gfx::Font& font, |
660 AutocompleteEditViewWin* edit_view, | 676 AutocompleteEditView* edit_view, |
661 AutocompleteEditModel* edit_model, | 677 AutocompleteEditModel* edit_model, |
662 Profile* profile, | 678 Profile* profile, |
663 AutocompletePopupPositioner* popup_positioner) | 679 AutocompletePopupPositioner* popup_positioner) |
| 680 #if defined(OS_WIN) |
664 : popup_(new AutocompletePopupWin(this)), | 681 : popup_(new AutocompletePopupWin(this)), |
| 682 #else |
| 683 : popup_(new AutocompletePopupGtk(this)), |
| 684 #endif |
665 model_(new AutocompletePopupModel(this, edit_model, profile)), | 685 model_(new AutocompletePopupModel(this, edit_model, profile)), |
666 edit_view_(edit_view), | 686 edit_view_(edit_view), |
667 popup_positioner_(popup_positioner), | 687 popup_positioner_(popup_positioner), |
668 result_font_(font.DeriveFont(kEditFontAdjust)), | 688 result_font_(font.DeriveFont(kEditFontAdjust)), |
669 ALLOW_THIS_IN_INITIALIZER_LIST(size_animation_(this)) { | 689 ALLOW_THIS_IN_INITIALIZER_LIST(size_animation_(this)) { |
670 set_border(new PopupBorder); | 690 set_border(new PopupBorder); |
671 } | 691 } |
672 | 692 |
673 gfx::Rect AutocompletePopupContentsView::GetPopupBounds() const { | 693 gfx::Rect AutocompletePopupContentsView::GetPopupBounds() const { |
674 if (!size_animation_.IsAnimating()) | 694 if (!size_animation_.IsAnimating()) |
675 return target_bounds_; | 695 return target_bounds_; |
676 | 696 |
677 gfx::Rect current_frame_bounds = start_bounds_; | 697 gfx::Rect current_frame_bounds = start_bounds_; |
678 int total_height_delta = target_bounds_.height() - start_bounds_.height(); | 698 int total_height_delta = target_bounds_.height() - start_bounds_.height(); |
679 // Round |current_height_delta| instead of truncating so we won't leave single | 699 // Round |current_height_delta| instead of truncating so we won't leave single |
680 // white pixels at the bottom of the popup as long when animating very small | 700 // white pixels at the bottom of the popup as long when animating very small |
681 // height differences. | 701 // height differences. |
682 int current_height_delta = static_cast<int>( | 702 int current_height_delta = static_cast<int>( |
683 size_animation_.GetCurrentValue() * total_height_delta - 0.5); | 703 size_animation_.GetCurrentValue() * total_height_delta - 0.5); |
684 current_frame_bounds.set_height( | 704 current_frame_bounds.set_height( |
685 current_frame_bounds.height() + current_height_delta); | 705 current_frame_bounds.height() + current_height_delta); |
686 return current_frame_bounds; | 706 return current_frame_bounds; |
687 } | 707 } |
688 | 708 |
689 //////////////////////////////////////////////////////////////////////////////// | 709 //////////////////////////////////////////////////////////////////////////////// |
690 // AutocompletePopupContentsView, AutocompletePopupView overrides: | 710 // AutocompletePopupContentsView, AutocompletePopupView overrides: |
691 | 711 |
692 bool AutocompletePopupContentsView::IsOpen() const { | 712 bool AutocompletePopupContentsView::IsOpen() const { |
693 return popup_->IsWindow() && popup_->IsVisible(); | 713 return popup_->IsOpen(); |
694 } | 714 } |
695 | 715 |
696 void AutocompletePopupContentsView::InvalidateLine(size_t line) { | 716 void AutocompletePopupContentsView::InvalidateLine(size_t line) { |
697 GetChildViewAt(static_cast<int>(line))->SchedulePaint(); | 717 GetChildViewAt(static_cast<int>(line))->SchedulePaint(); |
698 } | 718 } |
699 | 719 |
700 void AutocompletePopupContentsView::UpdatePopupAppearance() { | 720 void AutocompletePopupContentsView::UpdatePopupAppearance() { |
701 if (model_->result().empty()) { | 721 if (model_->result().empty()) { |
702 // No matches, close any existing popup. | 722 // No matches, close any existing popup. |
703 if (popup_->IsWindow()) { | 723 if (popup_->IsCreated()) { |
704 size_animation_.Stop(); | 724 size_animation_.Stop(); |
705 popup_->Hide(); | 725 popup_->Hide(); |
706 } | 726 } |
707 return; | 727 return; |
708 } | 728 } |
709 | 729 |
710 // Update the match cached by each row, in the process of doing so make sure | 730 // Update the match cached by each row, in the process of doing so make sure |
711 // we have enough row views. | 731 // we have enough row views. |
712 int total_child_height = 0; | 732 int total_child_height = 0; |
713 size_t child_view_count = GetChildViewCount(); | 733 size_t child_view_count = GetChildViewCount(); |
(...skipping 18 matching lines...) Expand all Loading... |
732 -insets.bottom()); | 752 -insets.bottom()); |
733 | 753 |
734 // If we're animating and our target height changes, reset the animation. | 754 // If we're animating and our target height changes, reset the animation. |
735 // NOTE: If we just reset blindly on _every_ update, then when the user types | 755 // NOTE: If we just reset blindly on _every_ update, then when the user types |
736 // rapidly we could get "stuck" trying repeatedly to animate shrinking by the | 756 // rapidly we could get "stuck" trying repeatedly to animate shrinking by the |
737 // last few pixels to get to one visible result. | 757 // last few pixels to get to one visible result. |
738 if (new_target_bounds.height() != target_bounds_.height()) | 758 if (new_target_bounds.height() != target_bounds_.height()) |
739 size_animation_.Reset(); | 759 size_animation_.Reset(); |
740 target_bounds_ = new_target_bounds; | 760 target_bounds_ = new_target_bounds; |
741 | 761 |
742 if (!popup_->IsWindow()) { | 762 if (!popup_->IsCreated()) { |
743 // If we've never been shown, we need to create the window. | 763 // If we've never been shown, we need to create the window. |
744 popup_->Init(edit_view_, this); | 764 popup_->Init(edit_view_, this); |
745 } else { | 765 } else { |
746 // Animate the popup shrinking, but don't animate growing larger (or | 766 // Animate the popup shrinking, but don't animate growing larger (or |
747 // appearing for the first time) since that would make the popup feel less | 767 // appearing for the first time) since that would make the popup feel less |
748 // responsive. | 768 // responsive. |
749 GetWidget()->GetBounds(&start_bounds_, true); | 769 GetWidget()->GetBounds(&start_bounds_, true); |
750 if (popup_->IsVisible() && | 770 if (popup_->IsVisible() && |
751 (target_bounds_.height() < start_bounds_.height())) | 771 (target_bounds_.height() < start_bounds_.height())) |
752 size_animation_.Show(); | 772 size_animation_.Show(); |
(...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
890 rect.set(SkIntToScalar(bounding_rect.x()), | 910 rect.set(SkIntToScalar(bounding_rect.x()), |
891 SkIntToScalar(bounding_rect.y()), | 911 SkIntToScalar(bounding_rect.y()), |
892 SkIntToScalar(bounding_rect.right()), | 912 SkIntToScalar(bounding_rect.right()), |
893 SkIntToScalar(bounding_rect.bottom())); | 913 SkIntToScalar(bounding_rect.bottom())); |
894 | 914 |
895 SkScalar radius = SkIntToScalar(PopupBorder::GetBorderRadius()); | 915 SkScalar radius = SkIntToScalar(PopupBorder::GetBorderRadius()); |
896 path->addRoundRect(rect, radius, radius); | 916 path->addRoundRect(rect, radius, radius); |
897 } | 917 } |
898 | 918 |
899 void AutocompletePopupContentsView::UpdateBlurRegion() { | 919 void AutocompletePopupContentsView::UpdateBlurRegion() { |
| 920 #if defined(OS_WIN) |
900 // We only support background blurring on Vista with Aero-Glass enabled. | 921 // We only support background blurring on Vista with Aero-Glass enabled. |
901 if (!win_util::ShouldUseVistaFrame() || !GetWidget()) | 922 if (!win_util::ShouldUseVistaFrame() || !GetWidget()) |
902 return; | 923 return; |
903 | 924 |
904 // Provide a blurred background effect within the contents region of the | 925 // Provide a blurred background effect within the contents region of the |
905 // popup. | 926 // popup. |
906 DWM_BLURBEHIND bb = {0}; | 927 DWM_BLURBEHIND bb = {0}; |
907 bb.dwFlags = DWM_BB_ENABLE | DWM_BB_BLURREGION; | 928 bb.dwFlags = DWM_BB_ENABLE | DWM_BB_BLURREGION; |
908 bb.fEnable = true; | 929 bb.fEnable = true; |
909 | 930 |
910 // Translate the contents rect into widget coordinates, since that's what | 931 // Translate the contents rect into widget coordinates, since that's what |
911 // DwmEnableBlurBehindWindow expects a region in. | 932 // DwmEnableBlurBehindWindow expects a region in. |
912 gfx::Rect contents_rect = GetLocalBounds(false); | 933 gfx::Rect contents_rect = GetLocalBounds(false); |
913 gfx::Point origin(contents_rect.origin()); | 934 gfx::Point origin(contents_rect.origin()); |
914 views::View::ConvertPointToWidget(this, &origin); | 935 views::View::ConvertPointToWidget(this, &origin); |
915 contents_rect.set_origin(origin); | 936 contents_rect.set_origin(origin); |
916 | 937 |
917 gfx::Path contents_path; | 938 gfx::Path contents_path; |
918 MakeContentsPath(&contents_path, contents_rect); | 939 MakeContentsPath(&contents_path, contents_rect); |
919 ScopedGDIObject<HRGN> popup_region; | 940 ScopedGDIObject<HRGN> popup_region; |
920 popup_region.Set(contents_path.CreateHRGN()); | 941 popup_region.Set(contents_path.CreateHRGN()); |
921 bb.hRgnBlur = popup_region.Get(); | 942 bb.hRgnBlur = popup_region.Get(); |
922 DwmEnableBlurBehindWindow(GetWidget()->GetNativeView(), &bb); | 943 DwmEnableBlurBehindWindow(GetWidget()->GetNativeView(), &bb); |
| 944 #endif |
923 } | 945 } |
924 | 946 |
925 void AutocompletePopupContentsView::MakeCanvasTransparent( | 947 void AutocompletePopupContentsView::MakeCanvasTransparent( |
926 gfx::Canvas* canvas) { | 948 gfx::Canvas* canvas) { |
927 // Allow the window blur effect to show through the popup background. | 949 // Allow the window blur effect to show through the popup background. |
928 SkPaint paint; | 950 SkPaint paint; |
929 SkColor transparency = GetThemeProvider()->ShouldUseNativeFrame() ? | 951 SkColor transparency = GetThemeProvider()->ShouldUseNativeFrame() ? |
930 kGlassPopupTransparency : kOpaquePopupTransparency; | 952 kGlassPopupTransparency : kOpaquePopupTransparency; |
931 paint.setColor(SkColorSetARGB(transparency, 255, 255, 255)); | 953 paint.setColor(SkColorSetARGB(transparency, 255, 255, 255)); |
932 paint.setXfermodeMode(SkXfermode::kDstIn_Mode); | 954 paint.setXfermodeMode(SkXfermode::kDstIn_Mode); |
933 paint.setStyle(SkPaint::kFill_Style); | 955 paint.setStyle(SkPaint::kFill_Style); |
934 canvas->FillRectInt(0, 0, canvas->getDevice()->width(), | 956 canvas->FillRectInt(0, 0, canvas->getDevice()->width(), |
935 canvas->getDevice()->height(), paint); | 957 canvas->getDevice()->height(), paint); |
936 } | 958 } |
| 959 |
| 960 // static |
| 961 AutocompletePopupView* AutocompletePopupView::CreatePopupView( |
| 962 const gfx::Font& font, |
| 963 AutocompleteEditView* edit_view, |
| 964 AutocompleteEditModel* edit_model, |
| 965 Profile* profile, |
| 966 AutocompletePopupPositioner* popup_positioner) { |
| 967 return new AutocompletePopupContentsView(font, edit_view, edit_model, |
| 968 profile, popup_positioner); |
| 969 } |
OLD | NEW |