Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1207)

Side by Side Diff: chrome/browser/autocomplete/autocomplete_edit_view_gtk.cc

Issue 5698006: Fix Instant suggest issues in Linux Views port. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Update according to review feedback. Created 10 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « no previous file | chrome/browser/ui/views/location_bar/location_bar_view.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/autocomplete/autocomplete_edit_view_gtk.h" 5 #include "chrome/browser/autocomplete/autocomplete_edit_view_gtk.h"
6 6
7 #include <gtk/gtk.h> 7 #include <gtk/gtk.h>
8 #include <gdk/gdkkeysyms.h> 8 #include <gdk/gdkkeysyms.h>
9 9
10 #include <algorithm> 10 #include <algorithm>
(...skipping 415 matching lines...) Expand 10 before | Expand all | Expand 10 after
426 GdkRectangle first_char_bounds, last_char_bounds; 426 GdkRectangle first_char_bounds, last_char_bounds;
427 gtk_text_buffer_get_start_iter(text_buffer_, &start); 427 gtk_text_buffer_get_start_iter(text_buffer_, &start);
428 428
429 // Use the real end iterator here to take the width of instant suggestion 429 // Use the real end iterator here to take the width of instant suggestion
430 // text into account, so that location bar can layout its children correctly. 430 // text into account, so that location bar can layout its children correctly.
431 gtk_text_buffer_get_end_iter(text_buffer_, &end); 431 gtk_text_buffer_get_end_iter(text_buffer_, &end);
432 gtk_text_view_get_iter_location(GTK_TEXT_VIEW(text_view_), 432 gtk_text_view_get_iter_location(GTK_TEXT_VIEW(text_view_),
433 &start, &first_char_bounds); 433 &start, &first_char_bounds);
434 gtk_text_view_get_iter_location(GTK_TEXT_VIEW(text_view_), 434 gtk_text_view_get_iter_location(GTK_TEXT_VIEW(text_view_),
435 &end, &last_char_bounds); 435 &end, &last_char_bounds);
436 return ((last_char_bounds.x > first_char_bounds.x) ? 436
437 (last_char_bounds.x + last_char_bounds.width - first_char_bounds.x) : 437 gint first_char_start = first_char_bounds.x;
438 (first_char_bounds.x - last_char_bounds.x + last_char_bounds.width)) + 438 gint first_char_end = first_char_start + first_char_bounds.width;
439 horizontal_border_size; 439 gint last_char_start = last_char_bounds.x;
440 gint last_char_end = last_char_start + last_char_bounds.width;
441
442 // bounds width could be negative for RTL text.
443 if (first_char_start > first_char_end)
444 std::swap(first_char_start, first_char_end);
445 if (last_char_start > last_char_end)
446 std::swap(last_char_start, last_char_end);
447
448 gint text_width = first_char_start < last_char_start ?
449 last_char_end - first_char_start : first_char_end - last_char_start;
450
451 return text_width + horizontal_border_size;
440 } 452 }
441 453
442 int AutocompleteEditViewGtk::WidthOfTextAfterCursor() { 454 int AutocompleteEditViewGtk::WidthOfTextAfterCursor() {
443 // Not used. 455 // Not used.
444 return -1; 456 return -1;
445 } 457 }
446 458
447 gfx::Font AutocompleteEditViewGtk::GetFont() { 459 gfx::Font AutocompleteEditViewGtk::GetFont() {
448 GtkRcStyle* rc_style = gtk_widget_get_modifier_style(text_view_); 460 GtkRcStyle* rc_style = gtk_widget_get_modifier_style(text_view_);
449 return gfx::Font((rc_style && rc_style->font_desc) ? 461 return gfx::Font((rc_style && rc_style->font_desc) ?
(...skipping 391 matching lines...) Expand 10 before | Expand all | Expand 10 after
841 853
842 g_object_set(faded_text_tag_, "foreground", kTextBaseColor, NULL); 854 g_object_set(faded_text_tag_, "foreground", kTextBaseColor, NULL);
843 g_object_set(normal_text_tag_, "foreground", "#000000", NULL); 855 g_object_set(normal_text_tag_, "foreground", "#000000", NULL);
844 } 856 }
845 857
846 AdjustVerticalAlignmentOfInstantView(); 858 AdjustVerticalAlignmentOfInstantView();
847 UpdateInstantViewColors(); 859 UpdateInstantViewColors();
848 } 860 }
849 861
850 void AutocompleteEditViewGtk::UpdateInstantViewColors() { 862 void AutocompleteEditViewGtk::UpdateInstantViewColors() {
851 #if !defined(TOOLKIT_VIEWS)
852 SkColor selection_text, selection_bg; 863 SkColor selection_text, selection_bg;
853 GdkColor faded_text, normal_bg; 864 GdkColor faded_text, normal_bg;
854 865
855 if (theme_provider_->UseGtkTheme()) { 866 #if defined(TOOLKIT_VIEWS)
856 GtkStyle* style = gtk_rc_get_style(text_view_); 867 bool use_gtk = false;
868 #else
869 bool use_gtk = theme_provider_->UseGtkTheme();
870 #endif
871
872 if (use_gtk) {
873 GtkStyle* style = gtk_rc_get_style(instant_view_);
857 874
858 faded_text = gtk_util::AverageColors( 875 faded_text = gtk_util::AverageColors(
859 style->text[GTK_STATE_NORMAL], style->base[GTK_STATE_NORMAL]); 876 style->text[GTK_STATE_NORMAL], style->base[GTK_STATE_NORMAL]);
860 normal_bg = style->base[GTK_STATE_NORMAL]; 877 normal_bg = style->base[GTK_STATE_NORMAL];
861 878
862 selection_text = gfx::GdkColorToSkColor(style->text[GTK_STATE_SELECTED]); 879 selection_text = gfx::GdkColorToSkColor(style->text[GTK_STATE_SELECTED]);
863 selection_bg = gfx::GdkColorToSkColor(style->base[GTK_STATE_SELECTED]); 880 selection_bg = gfx::GdkColorToSkColor(style->base[GTK_STATE_SELECTED]);
864 } else { 881 } else {
865 gdk_color_parse(kTextBaseColor, &faded_text); 882 gdk_color_parse(kTextBaseColor, &faded_text);
883
884 #if defined(TOOLKIT_VIEWS)
885 normal_bg = gfx::SkColorToGdkColor(
886 LocationBarView::GetColor(ToolbarModel::NONE,
887 LocationBarView::BACKGROUND));
888 selection_text = LocationBarView::GetColor(
889 ToolbarModel::NONE, LocationBarView::SELECTED_TEXT);
890
891 GtkStyle* style = gtk_rc_get_style(instant_view_);
892 selection_bg = gfx::GdkColorToSkColor(style->base[GTK_STATE_SELECTED]);
893 #else
866 normal_bg = LocationBarViewGtk::kBackgroundColor; 894 normal_bg = LocationBarViewGtk::kBackgroundColor;
867
868 selection_text = 895 selection_text =
869 theme_provider_->get_active_selection_fg_color(); 896 theme_provider_->get_active_selection_fg_color();
870 selection_bg = 897 selection_bg =
871 theme_provider_->get_active_selection_bg_color(); 898 theme_provider_->get_active_selection_bg_color();
899 #endif
872 } 900 }
873 901
874 double alpha = instant_animation_->is_animating() ? 902 double alpha = instant_animation_->is_animating() ?
875 instant_animation_->GetCurrentValue() : 0.0; 903 instant_animation_->GetCurrentValue() : 0.0;
876 GdkColor text = gfx::SkColorToGdkColor(color_utils::AlphaBlend( 904 GdkColor text = gfx::SkColorToGdkColor(color_utils::AlphaBlend(
877 selection_text, 905 selection_text,
878 gfx::GdkColorToSkColor(faded_text), 906 gfx::GdkColorToSkColor(faded_text),
879 alpha * 0xff)); 907 alpha * 0xff));
880 GdkColor bg = gfx::SkColorToGdkColor(color_utils::AlphaBlend( 908 GdkColor bg = gfx::SkColorToGdkColor(color_utils::AlphaBlend(
881 selection_bg, 909 selection_bg,
882 gfx::GdkColorToSkColor(normal_bg), 910 gfx::GdkColorToSkColor(normal_bg),
883 alpha * 0xff)); 911 alpha * 0xff));
884 912
885 if (alpha > 0.0) { 913 if (alpha > 0.0) {
886 gtk_label_select_region(GTK_LABEL(instant_view_), 0, -1); 914 gtk_label_select_region(GTK_LABEL(instant_view_), 0, -1);
887 // ACTIVE is the state for text that is selected, but not focused. 915 // ACTIVE is the state for text that is selected, but not focused.
888 gtk_widget_modify_text(instant_view_, GTK_STATE_ACTIVE, &text); 916 gtk_widget_modify_text(instant_view_, GTK_STATE_ACTIVE, &text);
889 gtk_widget_modify_base(instant_view_, GTK_STATE_ACTIVE, &bg); 917 gtk_widget_modify_base(instant_view_, GTK_STATE_ACTIVE, &bg);
890 } else { 918 } else {
891 // When the text is unselected, fg is used for text color, the state 919 // When the text is unselected, fg is used for text color, the state
892 // is NORMAL, and the background is transparent. 920 // is NORMAL, and the background is transparent.
893 gtk_widget_modify_fg(instant_view_, GTK_STATE_NORMAL, &text); 921 gtk_widget_modify_fg(instant_view_, GTK_STATE_NORMAL, &text);
894 } 922 }
895 #else // defined(TOOLKIT_VIEWS)
896 // We don't worry about views because it doesn't use the instant view.
897 #endif
898 } 923 }
899 924
900 void AutocompleteEditViewGtk::HandleBeginUserAction(GtkTextBuffer* sender) { 925 void AutocompleteEditViewGtk::HandleBeginUserAction(GtkTextBuffer* sender) {
901 OnBeforePossibleChange(); 926 OnBeforePossibleChange();
902 } 927 }
903 928
904 void AutocompleteEditViewGtk::HandleEndUserAction(GtkTextBuffer* sender) { 929 void AutocompleteEditViewGtk::HandleEndUserAction(GtkTextBuffer* sender) {
905 OnAfterPossibleChange(); 930 OnAfterPossibleChange();
906 } 931 }
907 932
(...skipping 257 matching lines...) Expand 10 before | Expand all | Expand 10 after
1165 } 1190 }
1166 1191
1167 void AutocompleteEditViewGtk::HandleViewMoveCursor( 1192 void AutocompleteEditViewGtk::HandleViewMoveCursor(
1168 GtkWidget* sender, 1193 GtkWidget* sender,
1169 GtkMovementStep step, 1194 GtkMovementStep step,
1170 gint count, 1195 gint count,
1171 gboolean extend_selection) { 1196 gboolean extend_selection) {
1172 GtkTextIter sel_start, sel_end; 1197 GtkTextIter sel_start, sel_end;
1173 gboolean has_selection = 1198 gboolean has_selection =
1174 gtk_text_buffer_get_selection_bounds(text_buffer_, &sel_start, &sel_end); 1199 gtk_text_buffer_get_selection_bounds(text_buffer_, &sel_start, &sel_end);
1200 bool handled = false;
1175 1201
1176 bool handled = true; 1202 if (step == GTK_MOVEMENT_VISUAL_POSITIONS && !extend_selection &&
1203 (count == 1 || count == -1)) {
1204 gint cursor_pos;
1205 g_object_get(G_OBJECT(text_buffer_), "cursor-position", &cursor_pos, NULL);
1177 1206
1178 // We want the GtkEntry behavior when you move the cursor while you have a 1207 // We need to take the content direction into account when handling cursor
1179 // selection. GtkTextView just drops the selection and moves the cursor, but 1208 // movement, because the behavior of Left and Right key will be inverted if
1180 // instead we want to move the cursor to the appropiate end of the selection. 1209 // the direction is RTL. Although we should check the direction around the
1181 if (step == GTK_MOVEMENT_VISUAL_POSITIONS && !extend_selection) { 1210 // input caret, it's much simpler and good enough to check whole content's
1182 if ((count == 1 || count == -1) && has_selection) { 1211 // direction.
1212 PangoDirection content_dir = GetContentDirection();
1213 gint count_towards_end = content_dir == PANGO_DIRECTION_RTL ? -1 : 1;
1214
1215 // We want the GtkEntry behavior when you move the cursor while you have a
1216 // selection. GtkTextView just drops the selection and moves the cursor,
1217 // but instead we want to move the cursor to the appropiate end of the
1218 // selection.
1219 if (has_selection) {
1183 // We have a selection and start / end are in ascending order. 1220 // We have a selection and start / end are in ascending order.
1184 // Cursor placement will remove the selection, so we need inform |model_| 1221 // Cursor placement will remove the selection, so we need inform
1185 // about this change by calling On{Before|After}PossibleChange() methods. 1222 // |model_| about this change by
1223 // calling On{Before|After}PossibleChange() methods.
1186 OnBeforePossibleChange(); 1224 OnBeforePossibleChange();
1187 gtk_text_buffer_place_cursor(text_buffer_, 1225 gtk_text_buffer_place_cursor(
1188 count == 1 ? &sel_end : &sel_start); 1226 text_buffer_, count == count_towards_end ? &sel_end : &sel_start);
1189 OnAfterPossibleChange(); 1227 OnAfterPossibleChange();
1190 } else if (count == 1 && !has_selection) { 1228 handled = true;
1191 gint cursor_pos; 1229 } else if (count == count_towards_end && cursor_pos == GetTextLength()) {
1192 g_object_get(G_OBJECT(text_buffer_), "cursor-position", &cursor_pos, 1230 handled = controller_->OnCommitSuggestedText(GetText());
1193 NULL);
1194 if (cursor_pos == GetTextLength())
1195 controller_->OnCommitSuggestedText(GetText());
1196 else
1197 handled = false;
1198 } else {
1199 handled = false;
1200 } 1231 }
1201 } else if (step == GTK_MOVEMENT_PAGES) { // Page up and down. 1232 } else if (step == GTK_MOVEMENT_PAGES) { // Page up and down.
1202 // Multiply by count for the direction (if we move too much that's ok). 1233 // Multiply by count for the direction (if we move too much that's ok).
1203 model_->OnUpOrDownKeyPressed(model_->result().size() * count); 1234 model_->OnUpOrDownKeyPressed(model_->result().size() * count);
1235 handled = true;
1204 } else if (step == GTK_MOVEMENT_DISPLAY_LINES) { // Arrow up and down. 1236 } else if (step == GTK_MOVEMENT_DISPLAY_LINES) { // Arrow up and down.
1205 model_->OnUpOrDownKeyPressed(count); 1237 model_->OnUpOrDownKeyPressed(count);
1206 } else { 1238 handled = true;
1207 handled = false;
1208 } 1239 }
1209 1240
1210 if (!handled) { 1241 if (!handled) {
1211 // Cursor movement may change the selection, we need to record the change 1242 // Cursor movement may change the selection, we need to record the change
1212 // and report it to |model_|. 1243 // and report it to |model_|.
1213 if (has_selection || extend_selection) 1244 if (has_selection || extend_selection)
1214 OnBeforePossibleChange(); 1245 OnBeforePossibleChange();
1215 1246
1216 // Propagate into GtkTextView 1247 // Propagate into GtkTextView
1217 GtkTextViewClass* klass = GTK_TEXT_VIEW_GET_CLASS(text_view_); 1248 GtkTextViewClass* klass = GTK_TEXT_VIEW_GET_CLASS(text_view_);
(...skipping 245 matching lines...) Expand 10 before | Expand all | Expand 10 after
1463 // prevent the focus from being moved. 1494 // prevent the focus from being moved.
1464 bool handled = false; 1495 bool handled = false;
1465 1496
1466 // Trigger Tab to search behavior only when Tab key is pressed. 1497 // Trigger Tab to search behavior only when Tab key is pressed.
1467 if (model_->is_keyword_hint() && !model_->keyword().empty()) { 1498 if (model_->is_keyword_hint() && !model_->keyword().empty()) {
1468 if (enable_tab_to_search_) { 1499 if (enable_tab_to_search_) {
1469 model_->AcceptKeyword(); 1500 model_->AcceptKeyword();
1470 handled = true; 1501 handled = true;
1471 } 1502 }
1472 } else { 1503 } else {
1473 // TODO(estade): this only works for linux/gtk; linux/views doesn't use
1474 // |instant_view_| so its visibility is not an indicator of whether we
1475 // have a suggestion.
1476 if (GTK_WIDGET_VISIBLE(instant_view_)) { 1504 if (GTK_WIDGET_VISIBLE(instant_view_)) {
1477 controller_->OnCommitSuggestedText(GetText()); 1505 controller_->OnCommitSuggestedText(GetText());
1478 handled = true; 1506 handled = true;
1479 } else { 1507 } else {
1480 handled = controller_->AcceptCurrentInstantPreview(); 1508 handled = controller_->AcceptCurrentInstantPreview();
1481 } 1509 }
1482 } 1510 }
1483 1511
1484 if (handled) { 1512 if (handled) {
1485 static guint signal_id = g_signal_lookup("move-focus", GTK_TYPE_WIDGET); 1513 static guint signal_id = g_signal_lookup("move-focus", GTK_TYPE_WIDGET);
(...skipping 578 matching lines...) Expand 10 before | Expand all | Expand 10 after
2064 // baseline, so we need to move the |instant_view_| down to make sure it 2092 // baseline, so we need to move the |instant_view_| down to make sure it
2065 // has the same baseline as the |text_view_|. 2093 // has the same baseline as the |text_view_|.
2066 PangoLayout* layout = gtk_label_get_layout(GTK_LABEL(instant_view_)); 2094 PangoLayout* layout = gtk_label_get_layout(GTK_LABEL(instant_view_));
2067 int height; 2095 int height;
2068 pango_layout_get_size(layout, NULL, &height); 2096 pango_layout_get_size(layout, NULL, &height);
2069 PangoLayoutIter* iter = pango_layout_get_iter(layout); 2097 PangoLayoutIter* iter = pango_layout_get_iter(layout);
2070 int baseline = pango_layout_iter_get_baseline(iter); 2098 int baseline = pango_layout_iter_get_baseline(iter);
2071 pango_layout_iter_free(iter); 2099 pango_layout_iter_free(iter);
2072 g_object_set(instant_anchor_tag_, "rise", baseline - height, NULL); 2100 g_object_set(instant_anchor_tag_, "rise", baseline - height, NULL);
2073 } 2101 }
OLDNEW
« no previous file with comments | « no previous file | chrome/browser/ui/views/location_bar/location_bar_view.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698