]> jfr.im git - irc/weechat/qweechat.git/blob - qweechat/chat.py
5b4be597b925d4ea776265a1a3a4c3ee093db76a
[irc/weechat/qweechat.git] / qweechat / chat.py
1 #!/usr/bin/env python
2 # -*- coding: utf-8 -*-
3 #
4 # chat.py - chat area
5 #
6 # Copyright (C) 2011-2014 Sébastien Helleu <flashcode@flashtux.org>
7 #
8 # This file is part of QWeeChat, a Qt remote GUI for WeeChat.
9 #
10 # QWeeChat is free software; you can redistribute it and/or modify
11 # it under the terms of the GNU General Public License as published by
12 # the Free Software Foundation; either version 3 of the License, or
13 # (at your option) any later version.
14 #
15 # QWeeChat is distributed in the hope that it will be useful,
16 # but WITHOUT ANY WARRANTY; without even the implied warranty of
17 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 # GNU General Public License for more details.
19 #
20 # You should have received a copy of the GNU General Public License
21 # along with QWeeChat. If not, see <http://www.gnu.org/licenses/>.
22 #
23
24 import datetime
25 import qt_compat
26 QtCore = qt_compat.import_module('QtCore')
27 QtGui = qt_compat.import_module('QtGui')
28 import config
29 import weechat.color as color
30
31
32 class ChatTextEdit(QtGui.QTextEdit):
33 """Chat area."""
34
35 def __init__(self, debug, *args):
36 QtGui.QTextEdit.__init__(*(self,) + args)
37 self.debug = debug
38 self.readOnly = True
39 self.setFocusPolicy(QtCore.Qt.NoFocus)
40 self.setFontFamily('monospace')
41 self._textcolor = self.textColor()
42 self._bgcolor = QtGui.QColor('#FFFFFF')
43 self._setcolorcode = {
44 'F': (self.setTextColor, self._textcolor),
45 'B': (self.setTextBackgroundColor, self._bgcolor)
46 }
47 self._setfont = {
48 '*': self.setFontWeight,
49 '_': self.setFontUnderline,
50 '/': self.setFontItalic
51 }
52 self._fontvalues = {
53 False: {
54 '*': QtGui.QFont.Normal,
55 '_': False,
56 '/': False
57 },
58 True: {
59 '*': QtGui.QFont.Bold,
60 '_': True,
61 '/': True
62 }
63 }
64 self._color = color.Color(config.color_options(), self.debug)
65
66 def display(self, time, prefix, text, forcecolor=None):
67 if time == 0:
68 d = datetime.datetime.now()
69 else:
70 d = datetime.datetime.fromtimestamp(float(time))
71 self.setTextColor(QtGui.QColor('#999999'))
72 self.insertPlainText(d.strftime('%H:%M '))
73 prefix = self._color.convert(prefix)
74 text = self._color.convert(text)
75 if forcecolor:
76 if prefix:
77 prefix = '\x01(F%s)%s' % (forcecolor, prefix)
78 text = '\x01(F%s)%s' % (forcecolor, text)
79 if prefix:
80 self._display_with_colors(str(prefix).decode('utf-8') + ' ')
81 if text:
82 self._display_with_colors(str(text).decode('utf-8'))
83 if text[-1:] != '\n':
84 self.insertPlainText('\n')
85 else:
86 self.insertPlainText('\n')
87 self.scroll_bottom()
88
89 def _display_with_colors(self, string):
90 self.setTextColor(self._textcolor)
91 self.setTextBackgroundColor(self._bgcolor)
92 self._reset_attributes()
93 items = string.split('\x01')
94 for i, item in enumerate(items):
95 if i > 0 and item.startswith('('):
96 pos = item.find(')')
97 if pos >= 2:
98 action = item[1]
99 code = item[2:pos]
100 if action == '+':
101 # set attribute
102 self._set_attribute(code[0], True)
103 elif action == '-':
104 # remove attribute
105 self._set_attribute(code[0], False)
106 else:
107 # reset attributes and color
108 if code == 'r':
109 self._reset_attributes()
110 self._setcolorcode[action][0](
111 self._setcolorcode[action][1])
112 else:
113 # set attributes + color
114 while code.startswith(('*', '!', '/', '_', '|',
115 'r')):
116 if code[0] == 'r':
117 self._reset_attributes()
118 elif code[0] in self._setfont:
119 self._set_attribute(
120 code[0],
121 not self._font[code[0]])
122 code = code[1:]
123 if code:
124 self._setcolorcode[action][0](
125 QtGui.QColor(code))
126 item = item[pos+1:]
127 if len(item) > 0:
128 self.insertPlainText(item)
129
130 def _reset_attributes(self):
131 self._font = {}
132 for attr in self._setfont:
133 self._set_attribute(attr, False)
134
135 def _set_attribute(self, attr, value):
136 self._font[attr] = value
137 self._setfont[attr](self._fontvalues[self._font[attr]][attr])
138
139 def scroll_bottom(self):
140 bar = self.verticalScrollBar()
141 bar.setValue(bar.maximum())