import gtk
import pango
import gobject
+import itertools
from FukuiNoNamariExt import thread_view_extend
return log[3] / pango.SCALE + 2
+class Rectangle:
+ def __init__(self, x, y, width, height):
+ self.x = x
+ self.y = y
+ self.width = width
+ self.height = height
+
+
class Line:
HEIGHT = 15
def build_line_list(self, x, y, width, left_margin):
self.initialize()
- line = Line(0, 0, gtk.gdk.Rectangle(
+ line = Line(0, 0, Rectangle(
x, y, width - x,
get_approximate_char_height(self.pango_layout.get_context())))
self.line_list.append(line)
class ElementText:
+ ch_width_dict = {} # key: char, value: width
+
def __init__(self, text, pango_layout):
self.text = text
self.pango_layout = pango_layout
- attrlist = self._get_attrs()
- self.widths = thread_view_extend.get_char_width(
- pango_layout.get_context(), text, attrlist)
+ self.recalc_char_widths()
self.line_list = []
def recalc_char_widths(self):
- attrlist = self._get_attrs()
- self.widths = thread_view_extend.get_char_width(
- self.pango_layout.get_context(), self.text, attrlist)
+ self.widths = [i for i in itertools.repeat(0, len(self.text))]
+
+ dict = self._get_ch_width_dict()
+ need_to_get = False
+ for index, ch in enumerate(self.text):
+ if ch not in dict:
+ need_to_get = True
+ break
+ else:
+ width = dict[ch]
+ self.widths[index] = width
+
+ if need_to_get:
+ attrlist = self._get_attrs()
+ self.widths = thread_view_extend.get_char_width(
+ self.pango_layout.get_context(), self.text, attrlist)
+ for index, width in enumerate(self.widths):
+ dict[self.text[index]] = self.widths[index]
+
+ def _get_ch_width_dict(self):
+ return ElementText.ch_width_dict
def _get_attrs(self):
attrs = pango.AttrList()
if current_line_x + current_line_width + ch_w > width:
line = Line(
current_line_start_index, index,
- gtk.gdk.Rectangle(
+ Rectangle(
current_line_x, current_line_y,
current_line_width, ch_h))
self.line_list.append(line)
if current_line_start_index < len(self.text):
line = Line(current_line_start_index, len(self.text),
- gtk.gdk.Rectangle(current_line_x,
+ Rectangle(current_line_x,
current_line_y,
current_line_width,
ch_h))
def draw(self, drawingarea, y_offset, pango_layout,
selection=False, start_index=0, end_index=0xffffff):
- selection_fg = drawingarea.style.fg[3]
- selection_bg = drawingarea.style.bg[3]
+ if drawingarea.get_property("has-focus"):
+ selection_fg = drawingarea.style.text[gtk.STATE_SELECTED]
+ selection_bg = drawingarea.style.base[gtk.STATE_SELECTED]
+ else:
+ selection_fg = drawingarea.style.text[gtk.STATE_ACTIVE]
+ selection_bg = drawingarea.style.base[gtk.STATE_ACTIVE]
for line in self.line_list:
text = self.text[line.start_index:line.end_index]
u_text = text.encode("utf8")
gc = drawingarea.window.new_gc()
+ gc.set_foreground(drawingarea.style.text[gtk.STATE_NORMAL])
+ gc.set_background(drawingarea.style.base[gtk.STATE_NORMAL])
attrs = self._get_attrs()
if selection:
pango_layout.set_text(u_text)
pango_layout.set_attributes(attrs)
drawingarea.window.draw_layout(
- gc, line.rectangle.x, line.rectangle.y + y_offset,
+ gc, int(line.rectangle.x), line.rectangle.y + y_offset,
pango_layout)
attrlist.insert(attr)
return attrlist
+ def recalc_char_widths(self):
+ attrlist = self._get_attrs()
+ self.widths = thread_view_extend.get_char_width(
+ self.pango_layout.get_context(), self.text, attrlist)
+
class ElementLink(ElementText):
selection_start, selection_end = self._get_selection_start_end()
-
top_layout = self.get_layout_on_y(view_y)
- index = 0
- if top_layout:
- index = top_layout.list_index
- while index < len(self.res_layout_list):
- layout = self.res_layout_list[index]
- w, h = layout.get_pixel_size()
- layout_top = layout.posY
- layout_bottom = layout.posY + h
- area_top = view_y + area.y
- area_bottom = view_y + area.y + area.height
- if layout_top <= area_bottom and layout_bottom >= area_top:
- layout.draw(self.drawingarea,
- 0, layout.posY - int(view_y),
- selection_start, selection_end)
- if layout_top > area_bottom:
- break
-
- index += 1
+ if top_layout is None:
+ return
+ #area_top = view_y + area.y
+ area_bottom = view_y + area.y + area.height
+
+ iter = range(top_layout.list_index, len(self.res_layout_list))
+ iter = itertools.imap(lambda index: self.res_layout_list[index], iter)
+ iter = itertools.takewhile(lambda lay: lay.posY <= area_bottom, iter)
+ for layout in iter:
+ layout.draw(self.drawingarea, 0, layout.posY - int(view_y),
+ selection_start, selection_end)
def transform_coordinate_gdk_to_adj(self, y):
return y + self.vscrollbar.get_value()