##// END OF EJS Templates
color: port to using ctypes (issue2687)...
Adrian Buehlmann -
r13641:2420cb1e stable
parent child Browse files
Show More
@@ -203,7 +203,7 b' def uisetup(ui):'
203 if mode == 'win32':
203 if mode == 'win32':
204 if w32effects is None:
204 if w32effects is None:
205 # only warn if color.mode is explicitly set to win32
205 # only warn if color.mode is explicitly set to win32
206 ui.warn(_('win32console not found, please install pywin32\n'))
206 ui.warn(_('warning: failed to set color mode to %s\n') % mode)
207 return
207 return
208 _effects.update(w32effects)
208 _effects.update(w32effects)
209 elif mode != 'ansi':
209 elif mode != 'ansi':
@@ -231,52 +231,96 b' def extsetup(ui):'
231 _("when to colorize (boolean, always, auto, or never)"),
231 _("when to colorize (boolean, always, auto, or never)"),
232 _('TYPE')))
232 _('TYPE')))
233
233
234 try:
234 if os.name != 'nt':
235 import re, pywintypes, win32console as win32c
235 w32effects = None
236 else:
237 import re, ctypes
238
239 _kernel32 = ctypes.windll.kernel32
240
241 _WORD = ctypes.c_ushort
242
243 _INVALID_HANDLE_VALUE = -1
244
245 class _COORD(ctypes.Structure):
246 _fields_ = [('X', ctypes.c_short),
247 ('Y', ctypes.c_short)]
248
249 class _SMALL_RECT(ctypes.Structure):
250 _fields_ = [('Left', ctypes.c_short),
251 ('Top', ctypes.c_short),
252 ('Right', ctypes.c_short),
253 ('Bottom', ctypes.c_short)]
254
255 class _CONSOLE_SCREEN_BUFFER_INFO(ctypes.Structure):
256 _fields_ = [('dwSize', _COORD),
257 ('dwCursorPosition', _COORD),
258 ('wAttributes', _WORD),
259 ('srWindow', _SMALL_RECT),
260 ('dwMaximumWindowSize', _COORD)]
261
262 _STD_OUTPUT_HANDLE = 0xfffffff5L # (DWORD)-11
263 _STD_ERROR_HANDLE = 0xfffffff4L # (DWORD)-12
264
265 _FOREGROUND_BLUE = 0x0001
266 _FOREGROUND_GREEN = 0x0002
267 _FOREGROUND_RED = 0x0004
268 _FOREGROUND_INTENSITY = 0x0008
269
270 _BACKGROUND_BLUE = 0x0010
271 _BACKGROUND_GREEN = 0x0020
272 _BACKGROUND_RED = 0x0040
273 _BACKGROUND_INTENSITY = 0x0080
274
275 _COMMON_LVB_REVERSE_VIDEO = 0x4000
276 _COMMON_LVB_UNDERSCORE = 0x8000
236
277
237 # http://msdn.microsoft.com/en-us/library/ms682088%28VS.85%29.aspx
278 # http://msdn.microsoft.com/en-us/library/ms682088%28VS.85%29.aspx
238 w32effects = {
279 w32effects = {
239 'none': -1,
280 'none': -1,
240 'black': 0,
281 'black': 0,
241 'red': win32c.FOREGROUND_RED,
282 'red': _FOREGROUND_RED,
242 'green': win32c.FOREGROUND_GREEN,
283 'green': _FOREGROUND_GREEN,
243 'yellow': win32c.FOREGROUND_RED | win32c.FOREGROUND_GREEN,
284 'yellow': _FOREGROUND_RED | _FOREGROUND_GREEN,
244 'blue': win32c.FOREGROUND_BLUE,
285 'blue': _FOREGROUND_BLUE,
245 'magenta': win32c.FOREGROUND_BLUE | win32c.FOREGROUND_RED,
286 'magenta': _FOREGROUND_BLUE | _FOREGROUND_RED,
246 'cyan': win32c.FOREGROUND_BLUE | win32c.FOREGROUND_GREEN,
287 'cyan': _FOREGROUND_BLUE | _FOREGROUND_GREEN,
247 'white': (win32c.FOREGROUND_RED | win32c.FOREGROUND_GREEN |
288 'white': _FOREGROUND_RED | _FOREGROUND_GREEN | _FOREGROUND_BLUE,
248 win32c.FOREGROUND_BLUE),
289 'bold': _FOREGROUND_INTENSITY,
249 'bold': win32c.FOREGROUND_INTENSITY,
250 'black_background': 0x100, # unused value > 0x0f
290 'black_background': 0x100, # unused value > 0x0f
251 'red_background': win32c.BACKGROUND_RED,
291 'red_background': _BACKGROUND_RED,
252 'green_background': win32c.BACKGROUND_GREEN,
292 'green_background': _BACKGROUND_GREEN,
253 'yellow_background': win32c.BACKGROUND_RED | win32c.BACKGROUND_GREEN,
293 'yellow_background': _BACKGROUND_RED | _BACKGROUND_GREEN,
254 'blue_background': win32c.BACKGROUND_BLUE,
294 'blue_background': _BACKGROUND_BLUE,
255 'purple_background': win32c.BACKGROUND_BLUE | win32c.BACKGROUND_RED,
295 'purple_background': _BACKGROUND_BLUE | _BACKGROUND_RED,
256 'cyan_background': win32c.BACKGROUND_BLUE | win32c.BACKGROUND_GREEN,
296 'cyan_background': _BACKGROUND_BLUE | _BACKGROUND_GREEN,
257 'white_background': (win32c.BACKGROUND_RED | win32c.BACKGROUND_GREEN |
297 'white_background': (_BACKGROUND_RED | _BACKGROUND_GREEN |
258 win32c.BACKGROUND_BLUE),
298 _BACKGROUND_BLUE),
259 'bold_background': win32c.BACKGROUND_INTENSITY,
299 'bold_background': _BACKGROUND_INTENSITY,
260 'underline': win32c.COMMON_LVB_UNDERSCORE, # double-byte charsets only
300 'underline': _COMMON_LVB_UNDERSCORE, # double-byte charsets only
261 'inverse': win32c.COMMON_LVB_REVERSE_VIDEO, # double-byte charsets only
301 'inverse': _COMMON_LVB_REVERSE_VIDEO, # double-byte charsets only
262 }
302 }
263
303
264 passthrough = set([win32c.FOREGROUND_INTENSITY,
304 passthrough = set([_FOREGROUND_INTENSITY,
265 win32c.BACKGROUND_INTENSITY,
305 _BACKGROUND_INTENSITY,
266 win32c.COMMON_LVB_UNDERSCORE,
306 _COMMON_LVB_UNDERSCORE,
267 win32c.COMMON_LVB_REVERSE_VIDEO])
307 _COMMON_LVB_REVERSE_VIDEO])
268
308
269 try:
309 stdout = _kernel32.GetStdHandle(
270 stdout = win32c.GetStdHandle(win32c.STD_OUTPUT_HANDLE)
310 _STD_OUTPUT_HANDLE) # don't close the handle returned
271 if stdout is None:
311 if stdout is None or stdout == _INVALID_HANDLE_VALUE:
272 raise ImportError()
312 w32effects = None
273 origattr = stdout.GetConsoleScreenBufferInfo()['Attributes']
313 else:
274 except pywintypes.error:
314 csbi = _CONSOLE_SCREEN_BUFFER_INFO()
275 # stdout may be defined but not support
315 if not _kernel32.GetConsoleScreenBufferInfo(
276 # GetConsoleScreenBufferInfo(), when called from subprocess or
316 stdout, ctypes.byref(csbi)):
277 # redirected.
317 # stdout may not support GetConsoleScreenBufferInfo()
278 raise ImportError()
318 # when called from subprocess or redirected
279 ansire = re.compile('\033\[([^m]*)m([^\033]*)(.*)', re.MULTILINE | re.DOTALL)
319 w32effects = None
320 else:
321 origattr = csbi.wAttributes
322 ansire = re.compile('\033\[([^m]*)m([^\033]*)(.*)',
323 re.MULTILINE | re.DOTALL)
280
324
281 def win32print(text, orig, **opts):
325 def win32print(text, orig, **opts):
282 label = opts.get('label', '')
326 label = opts.get('label', '')
@@ -308,12 +352,9 b' try:'
308 for sattr in m.group(1).split(';'):
352 for sattr in m.group(1).split(';'):
309 if sattr:
353 if sattr:
310 attr = mapcolor(int(sattr), attr)
354 attr = mapcolor(int(sattr), attr)
311 stdout.SetConsoleTextAttribute(attr)
355 _kernel32.SetConsoleTextAttribute(stdout, attr)
312 orig(m.group(2), **opts)
356 orig(m.group(2), **opts)
313 m = re.match(ansire, m.group(3))
357 m = re.match(ansire, m.group(3))
314
358
315 # Explicity reset original attributes
359 # Explicity reset original attributes
316 stdout.SetConsoleTextAttribute(origattr)
360 _kernel32.SetConsoleTextAttribute(stdout, origattr)
317
318 except ImportError:
319 w32effects = None
General Comments 0
You need to be logged in to leave comments. Login now