static void gtk_text_layout_real_free_line_data (GtkTextLayout *layout,
GtkTextLine *line,
GtkTextLineData *line_data);
+static void gtk_text_layout_emit_changed (GtkTextLayout *layout,
+ gint y,
+ gint old_height,
+ gint new_height);
static void gtk_text_layout_invalidate_all (GtkTextLayout *layout);
LAST_ARG
};
+#define PIXEL_BOUND(d) (((d) + PANGO_SCALE - 1) / PANGO_SCALE)
+
static void gtk_text_layout_init (GtkTextLayout *text_layout);
static void gtk_text_layout_class_init (GtkTextLayoutClass *klass);
static void gtk_text_layout_finalize (GObject *object);
gtk_text_buffer_get_mark (layout->buffer, "insert"));
gtk_text_layout_get_line_yrange (layout, &iter, &y, &height);
- gtk_text_layout_changed (layout, y, height, height);
+ gtk_text_layout_emit_changed (layout, y, height, height);
gtk_text_layout_invalidate_cache (layout, _gtk_text_iter_get_text_line (&iter));
}
g_signal_emit (layout, signals[INVALIDATED], 0);
}
+static void
+gtk_text_layout_emit_changed (GtkTextLayout *layout,
+ gint y,
+ gint old_height,
+ gint new_height)
+{
+ g_signal_emit (layout, signals[CHANGED], 0, y, old_height, new_height);
+}
+
void
gtk_text_layout_changed (GtkTextLayout *layout,
gint y,
gint old_height,
gint new_height)
{
- g_signal_emit (layout, signals[CHANGED], 0, y, old_height, new_height);
+ /* Check if the range intersects our cached line display,
+ * and invalidate the cached line if so.
+ */
+ if (layout->one_display_cache)
+ {
+ GtkTextLine *line = layout->one_display_cache->line;
+ gint cache_y = _gtk_text_btree_find_line_top (_gtk_text_buffer_get_btree (layout->buffer),
+ line, layout);
+ gint cache_height = layout->one_display_cache->height;
+
+ if (cache_y + cache_height > y && cache_y < y + old_height)
+ gtk_text_layout_invalidate_cache (layout, line);
+ }
+
+ gtk_text_layout_emit_changed (layout, y, old_height, new_height);
}
void
/* Validate backwards from the anchor line to y0
*/
line = _gtk_text_iter_get_text_line (anchor);
+ line = _gtk_text_line_previous (line);
seen = 0;
while (line && seen < -y0)
{
delta_height += line_data->height - old_height;
first_line = line;
- first_line_y = -seen;
+ first_line_y = -seen - line_data->height;
if (!last_line)
{
last_line = line;
- last_line_y = -seen + line_data->height;
+ last_line_y = -seen;
}
}
line_top = _gtk_text_btree_find_line_top (_gtk_text_buffer_get_btree (layout->buffer),
first_line, layout);
- gtk_text_layout_changed (layout,
- line_top,
- last_line_y - first_line_y - delta_height,
- last_line_y - first_line_y);
+ gtk_text_layout_emit_changed (layout,
+ line_top,
+ last_line_y - first_line_y - delta_height,
+ last_line_y - first_line_y);
}
}
max_pixels -= new_height;
update_layout_size (layout);
- gtk_text_layout_changed (layout, y, old_height, new_height);
+ gtk_text_layout_emit_changed (layout, y, old_height, new_height);
}
}
pango_layout_set_wrap (display->layout, PANGO_WRAP_WORD);
break;
+ case GTK_WRAP_WORD_CHAR:
+ layout_width = layout->screen_width - display->left_margin - display->right_margin;
+ pango_layout_set_width (display->layout, layout_width * PANGO_SCALE);
+ pango_layout_set_wrap (display->layout, PANGO_WRAP_WORD_CHAR);
+ break;
+
case GTK_WRAP_NONE:
break;
}
pango_layout_get_extents (display->layout, NULL, &extents);
- display->width = PANGO_PIXELS (extents.width) + display->left_margin + display->right_margin;
+ display->width = PIXEL_BOUND (extents.width) + display->left_margin + display->right_margin;
display->height += PANGO_PIXELS (extents.height);
/* Free this if we aren't in a loop */
GtkTextLineDisplay *display;
gint line_top;
gint index;
+ GtkTextIter insert_iter;
PangoRectangle pango_strong_pos;
PangoRectangle pango_weak_pos;
line_top = _gtk_text_btree_find_line_top (_gtk_text_buffer_get_btree (layout->buffer),
line, layout);
+ gtk_text_buffer_get_iter_at_mark (layout->buffer, &insert_iter,
+ gtk_text_buffer_get_mark (layout->buffer,
+ "insert"));
+
+ if (gtk_text_iter_equal (iter, &insert_iter))
+ index += layout->preedit_cursor - layout->preedit_len;
+
pango_layout_get_cursor_pos (display->layout, index,
strong_pos ? &pango_strong_pos : NULL,
weak_pos ? &pango_weak_pos : NULL);
line = _gtk_text_line_next_excluding_last (line);
}
+ if (!found_after)
+ gtk_text_buffer_get_end_iter (layout->buffer, iter);
+
return
!gtk_text_iter_equal (iter, &orig) &&
!gtk_text_iter_is_end (iter);