aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--test/MessageNumbers.py63
-rw-r--r--test/XiteMenu.py26
-rw-r--r--test/XiteWin.py650
-rw-r--r--test/examples/x.asp12
-rw-r--r--test/examples/x.asp.styled12
-rw-r--r--test/examples/x.cxx4
-rw-r--r--test/examples/x.cxx.styled4
-rw-r--r--test/examples/x.html7
-rw-r--r--test/examples/x.html.styled7
-rw-r--r--test/examples/x.php6
-rw-r--r--test/examples/x.php.styled6
-rw-r--r--test/examples/x.py11
-rw-r--r--test/examples/x.py.styled11
-rw-r--r--test/examples/x.vb9
-rw-r--r--test/examples/x.vb.styled9
-rw-r--r--test/lexTests.py106
-rw-r--r--test/performanceTests.py84
-rw-r--r--test/simpleTests.py897
-rw-r--r--test/xite.py6
19 files changed, 1930 insertions, 0 deletions
diff --git a/test/MessageNumbers.py b/test/MessageNumbers.py
new file mode 100644
index 000000000..782027069
--- /dev/null
+++ b/test/MessageNumbers.py
@@ -0,0 +1,63 @@
+# List many windows message numbers
+
+msgs = {
+"WM_ACTIVATE":6,
+"WM_ACTIVATEAPP":28,
+"WM_CAPTURECHANGED":533,
+"WM_CHAR":258,
+"WM_CLOSE":16,
+"WM_CREATE":1,
+"WM_COMMAND":273,
+"WM_DESTROY":2,
+"WM_ENTERSIZEMOVE":561,
+"WM_ERASEBKGND":20,
+"WM_EXITSIZEMOVE":562,
+"WM_GETMINMAXINFO":36,
+"WM_GETTEXT":13,
+"WM_IME_SETCONTEXT":0x0281,
+"WM_IME_NOTIFY":0x0282,
+"WM_KEYDOWN":256,
+"WM_KEYUP":257,
+"WM_KILLFOCUS":8,
+"WM_LBUTTONDOWN":513,
+"WM_LBUTTONUP":514,
+"WM_MBUTTONDOWN":519,
+"WM_MBUTTONUP":520,
+"WM_MBUTTONDBLCLK":521,
+"WM_MOUSEACTIVATE":33,
+"WM_MOUSEMOVE":512,
+"WM_MOVE":3,
+"WM_MOVING":534,
+"WM_NCACTIVATE":134,
+"WM_NCCALCSIZE":131,
+"WM_NCCREATE":129,
+"WM_NCDESTROY":130,
+"WM_NCHITTEST":132,
+"WM_NCLBUTTONDBLCLK":163,
+"WM_NCLBUTTONDOWN":161,
+"WM_NCLBUTTONUP":162,
+"WM_NCMOUSEMOVE":160,
+"WM_NCPAINT":133,
+"WM_PAINT":15,
+"WM_PARENTNOTIFY":528,
+"WM_SETCURSOR":32,
+"WM_SETFOCUS":7,
+"WM_SETFONT":48,
+"WM_SETTEXT":12,
+"WM_SHOWWINDOW":24,
+"WM_SIZE":5,
+"WM_SIZING":532,
+"WM_SYNCPAINT":136,
+"WM_SYSCOMMAND":274,
+"WM_SYSKEYDOWN":260,
+"WM_TIMER":275,
+"WM_USER":1024,
+"WM_USER+1":1025,
+"WM_WINDOWPOSCHANGED":71,
+"WM_WINDOWPOSCHANGING":70,
+}
+
+sgsm={}
+for k,v in msgs.items():
+ sgsm[v] = k
+
diff --git a/test/XiteMenu.py b/test/XiteMenu.py
new file mode 100644
index 000000000..f265387cb
--- /dev/null
+++ b/test/XiteMenu.py
@@ -0,0 +1,26 @@
+# -*- coding: utf-8 -*-
+
+""" Define the menu structure used by the Pentacle applications """
+
+MenuStructure = [
+ ["&File", [
+ ["&New", "<control>N"],
+ ["&Open...", "<control>O"],
+ ["&Save", "<control>S"],
+ ["Save &As...", "<control><shift>S"],
+ ["Test", ""],
+ ["Exercised", ""],
+ ["Uncalled", ""],
+ ["-", ""],
+ ["&Exit", ""]]],
+ [ "&Edit", [
+ ["&Undo", "<control>Z"],
+ ["&Redo", "<control>Y"],
+ ["-", ""],
+ ["Cu&t", "<control>X"],
+ ["&Copy", "<control>C"],
+ ["&Paste", "<control>V"],
+ ["&Delete", "Del"],
+ ["Select &All", "<control>A"],
+ ]],
+]
diff --git a/test/XiteWin.py b/test/XiteWin.py
new file mode 100644
index 000000000..71234cbd6
--- /dev/null
+++ b/test/XiteWin.py
@@ -0,0 +1,650 @@
+# -*- coding: utf-8 -*-
+
+from __future__ import with_statement
+
+import os, sys, unittest
+
+import ctypes
+from ctypes import wintypes
+from ctypes import c_int, c_ulong, c_char_p, c_wchar_p, c_ushort
+user32=ctypes.windll.user32
+gdi32=ctypes.windll.gdi32
+kernel32=ctypes.windll.kernel32
+from MessageNumbers import msgs, sgsm
+
+import XiteMenu
+
+scintillaDirectory = ".."
+scintillaIncludeDirectory = os.path.join(scintillaDirectory, "include")
+sys.path.append(scintillaIncludeDirectory)
+import Face
+
+scintillaBinDirectory = os.path.join(scintillaDirectory, "bin")
+os.environ['PATH'] = os.environ['PATH'] + ";" + scintillaBinDirectory
+#print(os.environ['PATH'])
+
+WFUNC = ctypes.WINFUNCTYPE(c_int, c_int, c_int, c_int, c_int)
+
+WS_CHILD = 0x40000000
+WS_CLIPCHILDREN = 0x2000000
+WS_OVERLAPPEDWINDOW = 0xcf0000
+WS_VISIBLE = 0x10000000
+WS_HSCROLL = 0x100000
+WS_VSCROLL = 0x200000
+WA_INACTIVE = 0
+MF_POPUP = 16
+MF_SEPARATOR = 0x800
+IDYES = 6
+OFN_HIDEREADONLY = 4
+MB_OK = 0
+MB_YESNOCANCEL = 3
+MF_CHECKED = 8
+MF_UNCHECKED = 0
+SW_SHOW = 5
+PM_REMOVE = 1
+
+VK_SHIFT = 16
+VK_CONTROL = 17
+VK_MENU = 18
+
+class OPENFILENAME(ctypes.Structure):
+ _fields_ = (("lStructSize", c_int),
+ ("hwndOwner", c_int),
+ ("hInstance", c_int),
+ ("lpstrFilter", c_wchar_p),
+ ("lpstrCustomFilter", c_char_p),
+ ("nMaxCustFilter", c_int),
+ ("nFilterIndex", c_int),
+ ("lpstrFile", c_wchar_p),
+ ("nMaxFile", c_int),
+ ("lpstrFileTitle", c_wchar_p),
+ ("nMaxFileTitle", c_int),
+ ("lpstrInitialDir", c_wchar_p),
+ ("lpstrTitle", c_wchar_p),
+ ("flags", c_int),
+ ("nFileOffset", c_ushort),
+ ("nFileExtension", c_ushort),
+ ("lpstrDefExt", c_char_p),
+ ("lCustData", c_int),
+ ("lpfnHook", c_char_p),
+ ("lpTemplateName", c_char_p),
+ ("pvReserved", c_char_p),
+ ("dwReserved", c_int),
+ ("flagsEx", c_int))
+
+ def __init__(self, win, title):
+ ctypes.Structure.__init__(self)
+ self.lStructSize = ctypes.sizeof(OPENFILENAME)
+ self.nMaxFile = 1024
+ self.hwndOwner = win
+ self.lpstrTitle = title
+ self.Flags = OFN_HIDEREADONLY
+
+trace = False
+#~ trace = True
+
+def WindowSize(w):
+ rc = ctypes.wintypes.RECT()
+ user32.GetClientRect(w, ctypes.byref(rc))
+ return rc.right - rc.left, rc.bottom - rc.top
+
+def IsKeyDown(key):
+ return (user32.GetKeyState(key) & 0x8000) != 0
+
+def KeyTranslate(w):
+ tr = { 9: "Tab", 0xD:"Enter", 0x1B: "Esc" }
+ if w in tr:
+ return tr[w]
+ elif ord("A") <= w <= ord("Z"):
+ return chr(w)
+ elif 0x70 <= w <= 0x7b:
+ return "F" + str(w-0x70+1)
+ else:
+ return "Unknown_" + hex(w)
+
+class WNDCLASS(ctypes.Structure):
+ _fields_= (\
+ ('style', c_int),
+ ('lpfnWndProc', WFUNC),
+ ('cls_extra', c_int),
+ ('wnd_extra', c_int),
+ ('hInst', c_int),
+ ('hIcon', c_int),
+ ('hCursor', c_int),
+ ('hbrBackground', c_int),
+ ('menu_name', c_wchar_p),
+ ('lpzClassName', c_wchar_p),
+ )
+
+class XTEXTRANGE(ctypes.Structure):
+ _fields_= (\
+ ('cpMin', c_int),
+ ('cpMax', c_int),
+ ('lpstrText', c_char_p),
+ )
+
+class TEXTRANGE(ctypes.Structure):
+ _fields_= (\
+ ('cpMin', c_int),
+ ('cpMax', c_int),
+ ('lpstrText', ctypes.POINTER(ctypes.c_char)),
+ )
+
+class FINDTEXT(ctypes.Structure):
+ _fields_= (\
+ ('cpMin', c_int),
+ ('cpMax', c_int),
+ ('lpstrText', c_char_p),
+ ('cpMinText', c_int),
+ ('cpMaxText', c_int),
+ )
+
+hinst = ctypes.windll.kernel32.GetModuleHandleW(0)
+
+def RegisterClass(name, func, background = 0):
+ # register a window class for toplevel windows.
+ wc = WNDCLASS()
+ wc.style = 0
+ wc.lpfnWndProc = func
+ wc.cls_extra = 0
+ wc.wnd_extra = 0
+ wc.hInst = hinst
+ wc.hIcon = 0
+ wc.hCursor = 0
+ wc.hbrBackground = background
+ wc.menu_name = 0
+ wc.lpzClassName = name
+ user32.RegisterClassW(ctypes.byref(wc))
+
+class SciCall:
+ def __init__(self, fn, ptr, msg):
+ self._fn = fn
+ self._ptr = ptr
+ self._msg = msg
+ def __call__(self, w=0, l=0):
+ return self._fn(self._ptr, self._msg, w, l)
+
+class Scintilla:
+ def __init__(self, face, hwndParent, hinstance):
+ self.__dict__["face"] = face
+ self.__dict__["used"] = set()
+ self.__dict__["all"] = set()
+ # The k member is for accessing constants as a dictionary
+ self.__dict__["k"] = {}
+ for f in face.features:
+ self.all.add(f)
+ if face.features[f]["FeatureType"] == "val":
+ self.k[f] = int(self.face.features[f]["Value"], 0)
+ elif face.features[f]["FeatureType"] == "evt":
+ self.k["SCN_"+f] = int(self.face.features[f]["Value"], 0)
+ # Get the function first as that also loads the DLL
+ self.__dict__["_scifn"] = ctypes.windll.SciLexer.Scintilla_DirectFunction
+ self.__dict__["_hwnd"] = user32.CreateWindowExW(0,
+ "Scintilla", "Source",
+ WS_CHILD | WS_VSCROLL | WS_HSCROLL | WS_CLIPCHILDREN,
+ 0, 0, 100, 100, hwndParent, 0, hinstance, 0)
+ self.__dict__["_sciptr"] = user32.SendMessageW(self._hwnd,
+ int(self.face.features["GetDirectPointer"]["Value"], 0), 0,0)
+ user32.ShowWindow(self._hwnd, SW_SHOW)
+ def __getattr__(self, name):
+ if name in self.face.features:
+ self.used.add(name)
+ feature = self.face.features[name]
+ value = int(feature["Value"], 0)
+ #~ print("Feature", name, feature)
+ if feature["FeatureType"] == "val":
+ self.__dict__[name] = value
+ return value
+ else:
+ return SciCall(self._scifn, self._sciptr, value)
+ elif ("Get" + name) in self.face.features:
+ self.used.add("Get" + name)
+ feature = self.face.features["Get" + name]
+ value = int(feature["Value"], 0)
+ if feature["FeatureType"] == "get" and \
+ not name.startswith("Get") and \
+ not feature["Param1Type"] and \
+ not feature["Param2Type"] and \
+ feature["ReturnType"] in ["bool", "int", "position"]:
+ #~ print("property", feature)
+ return self._scifn(self._sciptr, value, 0, 0)
+ elif name.startswith("SCN_") and name in self.k:
+ self.used.add(name)
+ feature = self.face.features[name[4:]]
+ value = int(feature["Value"], 0)
+ #~ print("Feature", name, feature)
+ if feature["FeatureType"] == "val":
+ return value
+ raise AttributeError(name)
+ def __setattr__(self, name, val):
+ if ("Set" + name) in self.face.features:
+ self.used.add("Set" + name)
+ feature = self.face.features["Set" + name]
+ value = int(feature["Value"], 0)
+ #~ print("setproperty", feature)
+ if feature["FeatureType"] == "set" and not name.startswith("Set"):
+ if feature["Param1Type"] in ["bool", "int", "position"]:
+ return self._scifn(self._sciptr, value, val, 0)
+ elif feature["Param2Type"] in ["string"]:
+ return self._scifn(self._sciptr, value, 0, val)
+ raise AttributeError(name)
+ raise AttributeError(name)
+ def getvalue(self, name):
+ if name in self.face.features:
+ feature = self.face.features[name]
+ if feature["FeatureType"] != "evt":
+ try:
+ return int(feature["Value"], 0)
+ except ValueError:
+ return -1
+ return -1
+
+
+ def ByteRange(self, start, end):
+ tr = TEXTRANGE()
+ tr.cpMin = start
+ tr.cpMax = end
+ length = end - start
+ tr.lpstrText = ctypes.create_string_buffer(length + 1)
+ self.GetTextRange(0, ctypes.byref(tr))
+ text = tr.lpstrText[:length]
+ text += b"\0" * (length - len(text))
+ return text
+ def StyledTextRange(self, start, end):
+ tr = TEXTRANGE()
+ tr.cpMin = start
+ tr.cpMax = end
+ length = 2 * (end - start)
+ tr.lpstrText = ctypes.create_string_buffer(length + 2)
+ self.GetStyledText(0, ctypes.byref(tr))
+ styledText = tr.lpstrText[:length]
+ styledText += b"\0" * (length - len(styledText))
+ return styledText
+ def FindBytes(self, start, end, s, flags):
+ ft = FINDTEXT()
+ ft.cpMin = start
+ ft.cpMax = end
+ ft.lpstrText = s
+ ft.cpMinText = 0
+ ft.cpMaxText = 0
+ pos = self.FindText(flags, ctypes.byref(ft))
+ #~ print(start, end, ft.cpMinText, ft.cpMaxText)
+ return pos
+
+ def Contents(self):
+ return self.ByteRange(0, self.Length)
+ def SizeTo(self, width, height):
+ user32.SetWindowPos(self._hwnd, 0, 0, 0, width, height, 0)
+ def FocusOn(self):
+ user32.SetFocus(self._hwnd)
+
+class XiteWin():
+ def __init__(self, test=""):
+ self.face = Face.Face()
+ self.face.ReadFromFile(os.path.join(scintillaIncludeDirectory, "Scintilla.iface"))
+
+ self.titleDirty = True
+ self.fullPath = ""
+ self.test = test
+
+ self.appName = "xite"
+
+ self.cmds = {}
+ self.windowName = "XiteWindow"
+ self.wfunc = WFUNC(self.WndProc)
+ RegisterClass(self.windowName, self.wfunc)
+ user32.CreateWindowExW(0, self.windowName, self.appName, \
+ WS_VISIBLE | WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN, \
+ 0, 0, 500, 700, 0, 0, hinst, 0)
+
+ args = sys.argv[1:]
+ self.SetMenus()
+ if args:
+ self.GrabFile(args[0])
+ self.ed.FocusOn()
+ self.ed.GotoPos(self.ed.Length)
+
+ print(self.test)
+ if self.test:
+ for k in self.cmds:
+ if self.cmds[k] == "Test":
+ user32.PostMessageW(self.win, msgs["WM_COMMAND"], k, 0)
+
+ def OnSize(self):
+ width, height = WindowSize(self.win)
+ self.ed.SizeTo(width, height)
+ user32.InvalidateRect(self.win, 0, 0)
+
+ def OnCreate(self, hwnd):
+ self.win = hwnd
+ self.ed = Scintilla(self.face, hwnd, hinst)
+ self.ed.FocusOn()
+
+
+ def Invalidate(self):
+ user32.InvalidateRect(self.win, 0, 0)
+
+ def WndProc(self, h, m, w, l):
+ ms = sgsm.get(m, "XXX")
+ if trace:
+ print("%s %s %s %s" % (hex(h)[2:],ms,w,l))
+ if ms == "WM_CLOSE":
+ user32.PostQuitMessage(0)
+ elif ms == "WM_CREATE":
+ self.OnCreate(h)
+ return 0
+ elif ms == "WM_SIZE":
+ # Work out size
+ if w != 1:
+ self.OnSize()
+ return 0
+ elif ms == "WM_COMMAND":
+ cmdCode = w & 0xffff
+ if cmdCode in self.cmds:
+ self.Command(self.cmds[cmdCode])
+ return 0
+ elif ms == "WM_ACTIVATE":
+ if w != WA_INACTIVE:
+ self.ed.FocusOn()
+ return 0
+ else:
+ return user32.DefWindowProcW(h, m, w, l)
+ return 0
+
+ def Command(self, name):
+ name = name.replace(" ", "")
+ method = "Cmd" + name
+ cmd = None
+ try:
+ cmd = getattr(self, method)
+ except AttributeError:
+ return
+ if cmd:
+ cmd()
+
+ def KeyDown(self, w, prefix = ""):
+ keyName = prefix
+ if IsKeyDown(VK_CONTROL):
+ keyName += "<control>"
+ if IsKeyDown(VK_SHIFT):
+ keyName += "<shift>"
+ keyName += KeyTranslate(w)
+ if trace:
+ print("Key:", keyName)
+ if keyName in self.keys:
+ method = "Cmd" + self.keys[keyName]
+ getattr(self, method)()
+ return True
+ #~ print("UKey:", keyName)
+ return False
+
+ def Accelerator(self, msg):
+ ms = sgsm.get(msg.message, "XXX")
+ if ms == "WM_KEYDOWN":
+ return self.KeyDown(msg.wParam)
+ elif ms == "WM_SYSKEYDOWN":
+ return self.KeyDown(msg.wParam, "<alt>")
+ return False
+
+ def AppLoop(self):
+ msg = ctypes.wintypes.MSG()
+ lpmsg = ctypes.byref(msg)
+ while user32.GetMessageW(lpmsg, 0, 0, 0):
+ if trace and msg.message != msgs["WM_TIMER"]:
+ print('mm', hex(msg.hWnd)[2:],sgsm.get(msg.message, "XXX"))
+ if not self.Accelerator(msg):
+ user32.TranslateMessage(lpmsg)
+ user32.DispatchMessageW(lpmsg)
+
+ def DoEvents(self):
+ msg = ctypes.wintypes.MSG()
+ lpmsg = ctypes.byref(msg)
+ cont = True
+ while cont:
+ cont = user32.PeekMessageW(lpmsg, 0, 0, 0, PM_REMOVE)
+ if cont:
+ if not self.Accelerator(msg):
+ user32.TranslateMessage(lpmsg)
+ user32.DispatchMessageW(lpmsg)
+
+ def SetTitle(self, changePath):
+ if changePath or self.titleDirty != self.ed.Modify:
+ self.titleDirty = self.ed.Modify
+ self.title = self.fullPath
+ if self.titleDirty:
+ self.title += " * "
+ else:
+ self.title += " - "
+ self.title += self.appName
+ if self.win:
+ user32.SetWindowTextW(self.win, self.title)
+
+ def Open(self):
+ ofx = OPENFILENAME(self.win, "Open File")
+ opath = "\0" * 1024
+ ofx.lpstrFile = opath
+ filters = ["Python (.py;.pyw)|*.py;*.pyw|All|*.*"]
+ filterText = "\0".join([f.replace("|", "\0") for f in filters])+"\0\0"
+ ofx.lpstrFilter = filterText
+ if ctypes.windll.comdlg32.GetOpenFileNameW(ctypes.byref(ofx)):
+ absPath = opath.replace("\0", "")
+ self.GrabFile(absPath)
+ self.ed.FocusOn()
+ self.ed.LexerLanguage = "python"
+ self.ed.Lexer = self.ed.SCLEX_PYTHON
+ self.ed.SetKeyWords(0, "class def else for if import print return while")
+ for style in [k for k in self.ed.k if k.startswith("SCE_P_")]:
+ self.ed.StyleSetFont(self.ed.k[style], "Verdana")
+ if "COMMENT" in style:
+ self.ed.StyleSetFore(self.ed.k[style], 127 * 256)
+ self.ed.StyleSetFont(self.ed.k[style], "Comic Sans MS")
+ elif "OPERATOR" in style:
+ print(style, self.ed.k[style])
+ self.ed.StyleSetBold(self.ed.k[style], 1)
+ self.ed.StyleSetFore(self.ed.k[style], 127 * 256 * 256)
+ elif "WORD" in style:
+ print(style, self.ed.k[style])
+ self.ed.StyleSetItalic(self.ed.k[style], 255)
+ self.ed.StyleSetFore(self.ed.k[style], 255 * 256 * 256)
+ else:
+ self.ed.StyleSetFore(self.ed.k[style], 0)
+
+ def SaveAs(self):
+ ofx = OPENFILENAME(self.win, "Save File")
+ opath = "\0" * 1024
+ ofx.lpstrFile = opath
+ if ctypes.windll.comdlg32.GetSaveFileNameW(ctypes.byref(ofx)):
+ self.fullPath = opath.replace("\0", "")
+ self.Save()
+ self.SetTitle(1)
+ self.ed.FocusOn()
+
+ def SetMenus(self):
+ ui = XiteMenu.MenuStructure
+ self.cmds = {}
+ self.keys = {}
+
+ cmdId = 0
+ self.menuBar = user32.CreateMenu()
+ for name, contents in ui:
+ cmdId += 1
+ menu = user32.CreateMenu()
+ for item in contents:
+ text, key = item
+ cmdText = text.replace("&", "")
+ cmdText = cmdText.replace("...", "")
+ cmdText = cmdText.replace(" ", "")
+ cmdId += 1
+ if key:
+ keyText = key.replace("<control>", "Ctrl+")
+ keyText = keyText.replace("<shift>", "Shift+")
+ text += "\t" + keyText
+ if text == "-":
+ user32.AppendMenuW(menu, MF_SEPARATOR, cmdId, text)
+ else:
+ user32.AppendMenuW(menu, 0, cmdId, text)
+ self.cmds[cmdId] = cmdText
+ self.keys[key] = cmdText
+ #~ print(cmdId, item)
+ user32.AppendMenuW(self.menuBar, MF_POPUP, menu, name)
+ user32.SetMenu(self.win, self.menuBar)
+ self.CheckMenuItem("Wrap", True)
+ user32.ShowWindow(self.win, SW_SHOW)
+
+ def CheckMenuItem(self, name, val):
+ #~ print(name, val)
+ if self.cmds:
+ for k,v in self.cmds.items():
+ if v == name:
+ #~ print(name, k)
+ user32.CheckMenuItem(user32.GetMenu(self.win), \
+ k, [MF_UNCHECKED, MF_CHECKED][val])
+
+ def Exit(self):
+ sys.exit(0)
+
+ def DisplayMessage(self, msg, ask):
+ return IDYES == user32.MessageBoxW(self.win, \
+ msg, self.appName, [MB_OK, MB_YESNOCANCEL][ask])
+
+ def NewDocument(self):
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+ self.ed.SetSavePoint()
+
+ def SaveIfUnsure(self):
+ if self.ed.Modify:
+ msg = "Save changes to \"" + self.fullPath + "\"?"
+ print(msg)
+ decision = self.DisplayMessage(msg, True)
+ if decision:
+ self.CmdSave()
+ return decision
+ return True
+
+ def New(self):
+ if self.SaveIfUnsure():
+ self.fullPath = ""
+ self.overrideMode = None
+ self.NewDocument()
+ self.SetTitle(1)
+ self.Invalidate()
+
+ def CheckMenus(self):
+ pass
+
+ def MoveSelection(self, caret, anchor=-1):
+ if anchor == -1:
+ anchor = caret
+ self.ed.SetSelectionStart(caret)
+ self.ed.SetSelectionEnd(anchor)
+ self.ed.ScrollCaret()
+ self.Invalidate()
+
+ def GrabFile(self, name):
+ self.fullPath = name
+ self.overrideMode = None
+ self.NewDocument()
+ fsr = open(name, "rb")
+ data = fsr.read()
+ fsr.close()
+ self.ed.AddText(len(data), data)
+ self.ed.EmptyUndoBuffer()
+ self.MoveSelection(0)
+ self.SetTitle(1)
+
+ def Save(self):
+ fos = open(self.fullPath, "wb")
+ blockSize = 1024
+ length = self.ed.Length
+ i = 0
+ while i < length:
+ grabSize = length - i
+ if grabSize > blockSize:
+ grabSize = blockSize
+ #~ print(i, grabSize, length)
+ data = self.ed.ByteRange(i, i + grabSize)
+ fos.write(data)
+ i += grabSize
+ fos.close()
+ self.ed.SetSavePoint()
+ self.SetTitle(0)
+
+ # Command handlers are called by menu actions
+
+ def CmdNew(self):
+ self.New()
+
+ def CmdOpen(self):
+ self.Open()
+
+ def CmdSave(self):
+ if (self.fullPath == None) or (len(self.fullPath) == 0):
+ self.SaveAs()
+ else:
+ self.Save()
+
+ def CmdSaveAs(self):
+ self.SaveAs()
+
+ def CmdTest(self):
+ runner = unittest.TextTestRunner()
+ if self.test:
+ tests = unittest.defaultTestLoader.loadTestsFromName(self.test)
+ else:
+ tests = unittest.defaultTestLoader.loadTestsFromName("simpleTests")
+ results = runner.run(tests)
+ #~ print(results)
+ if self.test:
+ user32.PostQuitMessage(0)
+
+ def CmdExercised(self):
+ print()
+ unused = sorted(self.ed.all.difference(self.ed.used))
+ print("Unused", len(unused))
+ print()
+ print("\n".join(unused))
+ print()
+ print("Used", len(self.ed.used))
+ print()
+ print("\n".join(sorted(self.ed.used)))
+
+ def CmdUncalled(self):
+ print()
+ unused = sorted(self.ed.all.difference(self.ed.used))
+ uu = {}
+ for u in unused:
+ v = self.ed.getvalue(u)
+ if v > 2000:
+ uu[v] = u
+ for x in sorted(uu.keys())[150:]:
+ print(x, uu[x])
+ print()
+
+ def CmdExit(self):
+ self.Exit()
+
+ def CmdUndo(self):
+ self.ed.Undo()
+
+ def CmdRedo(self):
+ self.ed.Redo()
+
+ def CmdCut(self):
+ self.ed.Cut()
+
+ def CmdCopy(self):
+ self.ed.Copy()
+
+ def CmdPaste(self):
+ self.ed.Paste()
+
+ def CmdDelete(self):
+ self.ed.Clear()
+
+xiteFrame = None
+
+def main(test):
+ global xiteFrame
+ xiteFrame = XiteWin(test)
+ xiteFrame.AppLoop()
diff --git a/test/examples/x.asp b/test/examples/x.asp
new file mode 100644
index 000000000..a78acdc34
--- /dev/null
+++ b/test/examples/x.asp
@@ -0,0 +1,12 @@
+<%@language=javas%>
+<%
+#include
+function x() {
+}
+%>
+<%@language=vbscript%>
+<%
+sub x 'comment
+%>
+<head>
+<body></body>
diff --git a/test/examples/x.asp.styled b/test/examples/x.asp.styled
new file mode 100644
index 000000000..920c6380d
--- /dev/null
+++ b/test/examples/x.asp.styled
@@ -0,0 +1,12 @@
+{15}<%@{16}language=javas{15}%>{0}
+{15}<%{56}
+#{61}include{56}
+{62}function{56} {61}x{65}(){56} {65}{{56}
+{65}}{56}
+{15}%>{0}
+{15}<%@{16}language=vbscript{15}%>{0}
+{15}<%{81}
+{84}sub{81} {86}x{81} {82}'comment {81}
+{15}%>{0}
+{1}<head>{0}
+{1}<body></body>{0}
diff --git a/test/examples/x.cxx b/test/examples/x.cxx
new file mode 100644
index 000000000..255a70e7c
--- /dev/null
+++ b/test/examples/x.cxx
@@ -0,0 +1,4 @@
+// A demonstration program
+int main() {
+ printf("hello world %d\n", 9);
+}
diff --git a/test/examples/x.cxx.styled b/test/examples/x.cxx.styled
new file mode 100644
index 000000000..223ee0760
--- /dev/null
+++ b/test/examples/x.cxx.styled
@@ -0,0 +1,4 @@
+{2}// A demonstration program
+{5}int{0} {11}main{10}(){0} {10}{{0}
+ {11}printf{10}({6}"hello world %d\n"{10},{0} {4}9{10});{0}
+{10}}{0}
diff --git a/test/examples/x.html b/test/examples/x.html
new file mode 100644
index 000000000..1d325dc76
--- /dev/null
+++ b/test/examples/x.html
@@ -0,0 +1,7 @@
+<html xmlns="http://www.w3.org/1999/xhtml">
+<head>
+ <meta name="Date.Modified" content="20010515" />
+ <title>SinkWorld - Portability</title>
+ <unknown>SinkWorld - Portability</unknown>
+ <link rel="stylesheet" type="text/css" href="SW.css">
+</head>
diff --git a/test/examples/x.html.styled b/test/examples/x.html.styled
new file mode 100644
index 000000000..3bcb7bca1
--- /dev/null
+++ b/test/examples/x.html.styled
@@ -0,0 +1,7 @@
+{1}<html{8} {3}xmlns{8}={6}"http://www.w3.org/1999/xhtml"{1}>{0}
+{1}<head>{0}
+ {1}<meta{8} {3}name{8}={6}"Date.Modified"{8} {3}content{8}={6}"20010515"{8} {11}/>{0}
+ {1}<title>{0}SinkWorld - Portability{1}</title>{0}
+ {2}<unknown>{0}SinkWorld - Portability{2}</unknown>{0}
+ {1}<link{8} {3}rel{8}={6}"stylesheet"{8} {3}type{8}={6}"text/css"{8} {3}href{8}={6}"SW.css"{1}>{0}
+{1}</head>{0}
diff --git a/test/examples/x.php b/test/examples/x.php
new file mode 100644
index 000000000..bc7302d85
--- /dev/null
+++ b/test/examples/x.php
@@ -0,0 +1,6 @@
+<head> <!-- About to script -->
+<?php
+echo "<!-- -->\n";
+/* ?> */
+?>
+<strong>for</strong><b>if</b>
diff --git a/test/examples/x.php.styled b/test/examples/x.php.styled
new file mode 100644
index 000000000..fb90ba06e
--- /dev/null
+++ b/test/examples/x.php.styled
@@ -0,0 +1,6 @@
+{1}<head>{0} {9}<!-- About to script -->{0}
+{18}<?php{118}
+echo {119}"<!-- -->\n"{127};{118}
+{124}/* ?> */{118}
+{18}?>{0}
+{1}<strong>{0}for{1}</strong><b>{0}if{1}</b>{0}
diff --git a/test/examples/x.py b/test/examples/x.py
new file mode 100644
index 000000000..12c4b71df
--- /dev/null
+++ b/test/examples/x.py
@@ -0,0 +1,11 @@
+# Convert all punctuation characters except '_', '*', and '.' into spaces.
+def depunctuate(s):
+ '''A docstring'''
+ """Docstring 2"""
+ d = ""
+ for ch in s:
+ if ch in 'abcde':
+ d = d + ch
+ else:
+ d = d + " "
+ return d
diff --git a/test/examples/x.py.styled b/test/examples/x.py.styled
new file mode 100644
index 000000000..02f94a923
--- /dev/null
+++ b/test/examples/x.py.styled
@@ -0,0 +1,11 @@
+{1}# Convert all punctuation characters except '_', '*', and '.' into spaces.{0}
+{5}def{0} {9}depunctuate{10}({11}s{10}):{0}
+ {6}'''A docstring'''{0}
+ {7}"""Docstring 2"""{0}
+ {11}d{0} {10}={0} {3}""{0}
+ {5}for{0} {11}ch{0} {5}in{0} {11}s{10}:{0}
+ {5}if{0} {11}ch{0} {5}in{0} {4}'abcde'{10}:{0}
+ {11}d{0} {10}={0} {11}d{0} {10}+{0} {11}ch{0}
+ {5}else{10}:{0}
+ {11}d{0} {10}={0} {11}d{0} {10}+{0} {3}" "{0}
+ {5}return{0} {11}d{0}
diff --git a/test/examples/x.vb b/test/examples/x.vb
new file mode 100644
index 000000000..a4503704b
--- /dev/null
+++ b/test/examples/x.vb
@@ -0,0 +1,9 @@
+' String"
+Dim a As String = "hello, world"
+Dim b As String = "hello world"
+Dim c As String = "Joe said ""Hello"" to me"
+Dim d As String = "\\\\server\\share\\file.txt"
+' Character
+""C "c"C "cc"C
+' Date
+d = #5/31/1993# or # 01/01/0001 12:00:00AM #
diff --git a/test/examples/x.vb.styled b/test/examples/x.vb.styled
new file mode 100644
index 000000000..e0c86f918
--- /dev/null
+++ b/test/examples/x.vb.styled
@@ -0,0 +1,9 @@
+{1}' String"
+{3}Dim{0} {7}a{0} {3}As{0} {3}String{0} {6}={0} {4}"hello, world"{0}
+{3}Dim{0} {7}b{0} {3}As{0} {3}String{0} {6}={0} {4}"hello world"{0}
+{3}Dim{0} {7}c{0} {3}As{0} {3}String{0} {6}={0} {4}"Joe said ""Hello"" to me"{0}
+{3}Dim{0} {7}d{0} {3}As{0} {3}String{0} {6}={0} {4}"\\\\server\\share\\file.txt"{0}
+{1}' Character
+{4}""C{0} {4}"c"C{0} {4}"cc"C{0}
+{1}' Date
+{7}d{0} {6}={0} {8}#5/31/1993#{0} {3}or{0} {8}# 01/01/0001 12:00:00AM #{0}
diff --git a/test/lexTests.py b/test/lexTests.py
new file mode 100644
index 000000000..b4caa95f6
--- /dev/null
+++ b/test/lexTests.py
@@ -0,0 +1,106 @@
+# -*- coding: utf-8 -*-
+
+from __future__ import with_statement
+
+import io
+import os
+import unittest
+
+import XiteWin
+
+keywordsHTML = [
+b"b body content head href html link meta "
+ b"name rel script strong title type xmlns",
+b"function",
+b"sub"
+]
+
+class TestLexers(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+
+ def AsStyled(self):
+ data = io.StringIO()
+ len = 0
+ prevStyle = -1
+ for o in range(self.ed.Length):
+ styleNow = self.ed.GetStyleAt(len)
+ if styleNow != prevStyle:
+ styleBuf = "{%0d}" % styleNow
+ data.write(styleBuf)
+ prevStyle = styleNow
+ data.write(chr(self.ed.GetCharAt(len)))
+ len += 1
+ return data.getvalue( )
+
+ def LexExample(self, name, lexerName, keywords=None):
+ if keywords is None:
+ keywords = []
+ self.ed.LexerLanguage = lexerName
+ bits = self.ed.StyleBitsNeeded
+ mask = 2 << bits - 1
+ self.ed.StyleBits = bits
+ for i in range(len(keywords)):
+ self.ed.SetKeyWords(i, keywords[i])
+
+ nameExample = os.path.join("examples", name)
+ namePrevious = nameExample +".styled"
+ nameNew = nameExample +".new"
+ with open(nameExample, "rb") as f:
+ prog = f.read()
+ lenDocument = len(prog)
+ self.ed.AddText(lenDocument, prog)
+ self.ed.Colourise(0, lenDocument)
+ self.assertEquals(self.ed.EndStyled, lenDocument)
+ with open(namePrevious, "rb") as f:
+ prevStyled = f.read()
+ progStyled = self.AsStyled().encode('utf-8')
+ if progStyled != prevStyled:
+ with open(nameNew, "wb") as f:
+ f.write(progStyled)
+ print(progStyled)
+ print(prevStyled)
+ self.assertEquals(progStyled, prevStyled)
+ # The whole file doesn't parse like it did before so don't try line by line
+ # as that is likely to fail many times.
+ return
+
+ # Try partial lexes from the start of every line which should all be identical.
+ for line in range(self.ed.LineCount):
+ lineStart = self.ed.PositionFromLine(line)
+ self.ed.StartStyling(lineStart, mask)
+ self.assertEquals(self.ed.EndStyled, lineStart)
+ self.ed.Colourise(0, lenDocument)
+ progStyled = self.AsStyled().encode('utf-8')
+ if progStyled != prevStyled:
+ with open(nameNew, "wb") as f:
+ f.write(progStyled)
+ assertEquals(progStyled, prevStyled)
+ # Give up after one failure
+ return
+
+ def testCXX(self):
+ self.LexExample("x.cxx", b"cpp", [b"int"])
+
+ def testPython(self):
+ self.LexExample("x.py", b"python",
+ [b"class def else for if import in print return while"])
+
+ def testHTML(self):
+ self.LexExample("x.html", b"hypertext", keywordsHTML)
+
+ def testASP(self):
+ self.LexExample("x.asp", b"hypertext", keywordsHTML)
+
+ def testPHP(self):
+ self.LexExample("x.php", b"hypertext", keywordsHTML)
+
+ def testVB(self):
+ self.LexExample("x.vb", b"vb", [b"as dim or string"])
+
+if __name__ == '__main__':
+ XiteWin.main("lexTests")
diff --git a/test/performanceTests.py b/test/performanceTests.py
new file mode 100644
index 000000000..ed0550558
--- /dev/null
+++ b/test/performanceTests.py
@@ -0,0 +1,84 @@
+# -*- coding: utf-8 -*-
+
+from __future__ import with_statement
+
+import os, string, time, unittest
+
+import XiteWin
+
+class TestPerformance(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+
+ def testAddLine(self):
+ data = (string.ascii_letters + string.digits + "\n").encode('utf-8')
+ start = time.time()
+ for i in range(500):
+ self.ed.AddText(len(data), data)
+ self.assertEquals(self.ed.LineCount, i + 2)
+ end = time.time()
+ duration = end - start
+ print("%6.3f testAddLine" % duration)
+ self.xite.DoEvents()
+ self.assert_(self.ed.Length > 0)
+
+ def testAddLineMiddle(self):
+ data = (string.ascii_letters + string.digits + "\n").encode('utf-8')
+ start = time.time()
+ for i in range(500):
+ self.ed.AddText(len(data), data)
+ self.assertEquals(self.ed.LineCount, i + 2)
+ end = time.time()
+ duration = end - start
+ print("%6.3f testAddLineMiddle" % duration)
+ self.xite.DoEvents()
+ self.assert_(self.ed.Length > 0)
+
+ def testHuge(self):
+ data = (string.ascii_letters + string.digits + "\n").encode('utf-8')
+ data = data * 100000
+ print("len is", len(data))
+ start = time.time()
+ self.ed.AddText(len(data), data)
+ end = time.time()
+ duration = end - start
+ print("%6.3f testHuge" % duration)
+ self.xite.DoEvents()
+ self.assert_(self.ed.Length > 0)
+
+ def testHugeInserts(self):
+ data = (string.ascii_letters + string.digits + "\n").encode('utf-8')
+ data = data * 100000
+ insert = (string.digits + "\n").encode('utf-8')
+ self.ed.AddText(len(data), data)
+ start = time.time()
+ for i in range(500):
+ self.ed.InsertText(0, insert)
+ end = time.time()
+ duration = end - start
+ print("%6.3f testHugeInserts" % duration)
+ self.xite.DoEvents()
+ self.assert_(self.ed.Length > 0)
+
+ def testHugeReplace(self):
+ oneLine = (string.ascii_letters + string.digits + "\n").encode('utf-8')
+ data = oneLine * 100000
+ insert = (string.digits + "\n").encode('utf-8')
+ self.ed.AddText(len(data), data)
+ start = time.time()
+ for i in range(500):
+ self.ed.TargetStart = i * len(insert)
+ self.ed.TargetEnd = self.ed.TargetStart + len(oneLine)
+ self.ed.ReplaceTarget(len(insert), insert)
+ end = time.time()
+ duration = end - start
+ print("%6.3f testHugeReplace" % duration)
+ self.xite.DoEvents()
+ self.assert_(self.ed.Length > 0)
+
+if __name__ == '__main__':
+ XiteWin.main("performanceTests")
diff --git a/test/simpleTests.py b/test/simpleTests.py
new file mode 100644
index 000000000..3697e93f2
--- /dev/null
+++ b/test/simpleTests.py
@@ -0,0 +1,897 @@
+# -*- coding: utf-8 -*-
+
+from __future__ import with_statement
+
+import ctypes, os, unittest
+
+import XiteWin
+
+class TestSimple(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+
+ def testLength(self):
+ self.assertEquals(self.ed.Length, 0)
+
+ def testAddText(self):
+ self.ed.AddText(1, "x")
+ self.assertEquals(self.ed.Length, 1)
+ self.assertEquals(self.ed.GetCharAt(0), ord("x"))
+ self.assertEquals(self.ed.GetStyleAt(0), 0)
+ self.ed.ClearAll()
+ self.assertEquals(self.ed.Length, 0)
+
+ def testAddStyledText(self):
+ self.assertEquals(self.ed.EndStyled, 0)
+ self.ed.AddStyledText(2, b"x\002")
+ self.assertEquals(self.ed.Length, 1)
+ self.assertEquals(self.ed.GetCharAt(0), ord("x"))
+ self.assertEquals(self.ed.GetStyleAt(0), 2)
+ self.assertEquals(self.ed.StyledTextRange(0, 1), b"x\002")
+ self.ed.ClearDocumentStyle()
+ self.assertEquals(self.ed.Length, 1)
+ self.assertEquals(self.ed.GetCharAt(0), ord("x"))
+ self.assertEquals(self.ed.GetStyleAt(0), 0)
+ self.assertEquals(self.ed.StyledTextRange(0, 1), b"x\0")
+
+ def testStyling(self):
+ self.assertEquals(self.ed.EndStyled, 0)
+ self.ed.AddStyledText(4, b"x\002y\003")
+ self.assertEquals(self.ed.StyledTextRange(0, 2), b"x\002y\003")
+ self.ed.StartStyling(0,0xf)
+ self.ed.SetStyling(1, 5)
+ self.assertEquals(self.ed.StyledTextRange(0, 2), b"x\005y\003")
+ # Set the mask so 0 bit changed but not 2 bit
+ self.ed.StartStyling(0,0x1)
+ self.ed.SetStyling(1, 0)
+ self.assertEquals(self.ed.StyledTextRange(0, 2), b"x\004y\003")
+
+ self.ed.StartStyling(0,0xff)
+ self.ed.SetStylingEx(2, b"\100\101")
+ self.assertEquals(self.ed.StyledTextRange(0, 2), b"x\100y\101")
+
+ def testPosition(self):
+ self.assertEquals(self.ed.CurrentPos, 0)
+ self.assertEquals(self.ed.Anchor, 0)
+ self.ed.AddText(1, "x")
+ # Caret has automatically moved
+ self.assertEquals(self.ed.CurrentPos, 1)
+ self.assertEquals(self.ed.Anchor, 1)
+ self.ed.SelectAll()
+ self.assertEquals(self.ed.CurrentPos, 0)
+ self.assertEquals(self.ed.Anchor, 1)
+ self.ed.Anchor = 0
+ self.assertEquals(self.ed.Anchor, 0)
+ # Check line positions
+ self.assertEquals(self.ed.PositionFromLine(0), 0)
+ self.assertEquals(self.ed.GetLineEndPosition(0), 1)
+ self.assertEquals(self.ed.PositionFromLine(1), 1)
+
+ self.ed.CurrentPos = 1
+ self.assertEquals(self.ed.Anchor, 0)
+ self.assertEquals(self.ed.CurrentPos, 1)
+
+ def testSelection(self):
+ self.assertEquals(self.ed.CurrentPos, 0)
+ self.assertEquals(self.ed.Anchor, 0)
+ self.assertEquals(self.ed.SelectionStart, 0)
+ self.assertEquals(self.ed.SelectionEnd, 0)
+ self.ed.AddText(1, "x")
+ self.ed.SelectionStart = 0
+ self.assertEquals(self.ed.CurrentPos, 1)
+ self.assertEquals(self.ed.Anchor, 0)
+ self.assertEquals(self.ed.SelectionStart, 0)
+ self.assertEquals(self.ed.SelectionEnd, 1)
+ self.ed.SelectionStart = 1
+ self.assertEquals(self.ed.CurrentPos, 1)
+ self.assertEquals(self.ed.Anchor, 1)
+ self.assertEquals(self.ed.SelectionStart, 1)
+ self.assertEquals(self.ed.SelectionEnd, 1)
+
+ self.ed.SelectionEnd = 0
+ self.assertEquals(self.ed.CurrentPos, 0)
+ self.assertEquals(self.ed.Anchor, 0)
+
+ def testSetSelection(self):
+ self.ed.AddText(4, b"abcd")
+ self.ed.SetSel(1, 3)
+ self.assertEquals(self.ed.SelectionStart, 1)
+ self.assertEquals(self.ed.SelectionEnd, 3)
+ result = b"\0" * 5
+ length = self.ed.GetSelText(0, result)
+ self.assertEquals(length, 3)
+ self.assertEquals(result[:length], b"bc\0")
+ self.ed.ReplaceSel(0, b"1234")
+ self.assertEquals(self.ed.Length, 6)
+ self.assertEquals(self.ed.Contents(), b"a1234d")
+
+ def testReadOnly(self):
+ self.ed.AddText(1, b"x")
+ self.assertEquals(self.ed.ReadOnly, 0)
+ self.assertEquals(self.ed.Contents(), b"x")
+ self.ed.ReadOnly = 1
+ self.assertEquals(self.ed.ReadOnly, 1)
+ self.ed.AddText(1, b"x")
+ self.assertEquals(self.ed.Contents(), b"x")
+ self.ed.ReadOnly = 0
+ self.ed.AddText(1, b"x")
+ self.assertEquals(self.ed.Contents(), b"xx")
+ self.ed.Null()
+ self.assertEquals(self.ed.Contents(), b"xx")
+
+ def testAddLine(self):
+ data = b"x" * 70 + b"\n"
+ for i in range(5):
+ self.ed.AddText(len(data), data)
+ self.xite.DoEvents()
+ self.assertEquals(self.ed.LineCount, i + 2)
+ self.assert_(self.ed.Length > 0)
+
+ def testInsertText(self):
+ data = b"xy"
+ self.ed.InsertText(0, data)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(data, self.ed.ByteRange(0,2))
+
+ self.ed.InsertText(1, data)
+ # Should now be "xxyy"
+ self.assertEquals(self.ed.Length, 4)
+ self.assertEquals(b"xxyy", self.ed.ByteRange(0,4))
+
+ def testInsertNul(self):
+ data = b"\0"
+ self.ed.AddText(1, data)
+ self.assertEquals(self.ed.Length, 1)
+ self.assertEquals(data, self.ed.ByteRange(0,1))
+
+ def testUndoRedo(self):
+ data = b"xy"
+ self.assertEquals(self.ed.Modify, 0)
+ self.assertEquals(self.ed.UndoCollection, 1)
+ self.assertEquals(self.ed.CanRedo(), 0)
+ self.assertEquals(self.ed.CanUndo(), 0)
+ self.ed.InsertText(0, data)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.ed.Modify, 1)
+ self.assertEquals(self.ed.CanRedo(), 0)
+ self.assertEquals(self.ed.CanUndo(), 1)
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 0)
+ self.assertEquals(self.ed.Modify, 0)
+ self.assertEquals(self.ed.CanRedo(), 1)
+ self.assertEquals(self.ed.CanUndo(), 0)
+ self.ed.Redo()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.ed.Modify, 1)
+ self.assertEquals(data, self.ed.Contents())
+ self.assertEquals(self.ed.CanRedo(), 0)
+ self.assertEquals(self.ed.CanUndo(), 1)
+
+ def testUndoSavePoint(self):
+ data = b"xy"
+ self.assertEquals(self.ed.Modify, 0)
+ self.ed.InsertText(0, data)
+ self.assertEquals(self.ed.Modify, 1)
+ self.ed.SetSavePoint()
+ self.assertEquals(self.ed.Modify, 0)
+ self.ed.InsertText(0, data)
+ self.assertEquals(self.ed.Modify, 1)
+
+ def testUndoCollection(self):
+ data = b"xy"
+ self.assertEquals(self.ed.UndoCollection, 1)
+ self.ed.UndoCollection = 0
+ self.assertEquals(self.ed.UndoCollection, 0)
+ self.ed.InsertText(0, data)
+ self.assertEquals(self.ed.CanRedo(), 0)
+ self.assertEquals(self.ed.CanUndo(), 0)
+ self.ed.UndoCollection = 1
+
+ def testGetColumn(self):
+ self.ed.AddText(1, b"x")
+ self.assertEquals(self.ed.GetColumn(0), 0)
+ self.assertEquals(self.ed.GetColumn(1), 1)
+ # Next line caused infinite loop in 1.71
+ self.assertEquals(self.ed.GetColumn(2), 1)
+ self.assertEquals(self.ed.GetColumn(3), 1)
+
+ def testTabWidth(self):
+ self.assertEquals(self.ed.TabWidth, 8)
+ self.ed.AddText(3, b"x\tb")
+ self.assertEquals(self.ed.GetColumn(0), 0)
+ self.assertEquals(self.ed.GetColumn(1), 1)
+ self.assertEquals(self.ed.GetColumn(2), 8)
+ for col in range(10):
+ if col == 0:
+ self.assertEquals(self.ed.FindColumn(0, col), 0)
+ elif col == 1:
+ self.assertEquals(self.ed.FindColumn(0, col), 1)
+ elif col == 9:
+ self.assertEquals(self.ed.FindColumn(0, col), 3)
+ else:
+ self.assertEquals(self.ed.FindColumn(0, col), 2)
+ self.ed.TabWidth = 4
+ self.assertEquals(self.ed.TabWidth, 4)
+ self.assertEquals(self.ed.GetColumn(0), 0)
+ self.assertEquals(self.ed.GetColumn(1), 1)
+ self.assertEquals(self.ed.GetColumn(2), 4)
+
+ def testIndent(self):
+ self.assertEquals(self.ed.Indent, 0)
+ self.assertEquals(self.ed.UseTabs, 1)
+ self.ed.Indent = 8
+ self.ed.UseTabs = 0
+ self.assertEquals(self.ed.Indent, 8)
+ self.assertEquals(self.ed.UseTabs, 0)
+ self.ed.AddText(3, b"x\tb")
+ self.assertEquals(self.ed.GetLineIndentation(0), 0)
+ self.ed.InsertText(0, b" ")
+ self.assertEquals(self.ed.GetLineIndentation(0), 1)
+ self.assertEquals(self.ed.GetLineIndentPosition(0), 1)
+ self.assertEquals(self.ed.Contents(), b" x\tb")
+ self.ed.SetLineIndentation(0,2)
+ self.assertEquals(self.ed.Contents(), b" x\tb")
+ self.assertEquals(self.ed.GetLineIndentPosition(0), 2)
+ self.ed.UseTabs = 1
+ self.ed.SetLineIndentation(0,8)
+ self.assertEquals(self.ed.Contents(), b"\tx\tb")
+ self.assertEquals(self.ed.GetLineIndentPosition(0), 1)
+
+ def testGetCurLine(self):
+ self.ed.AddText(1, b"x")
+ data = b"\0" * 100
+ caret = self.ed.GetCurLine(len(data), data)
+ data = data.rstrip(b"\0")
+ self.assertEquals(caret, 1)
+ self.assertEquals(data, b"x")
+
+ def testGetLine(self):
+ self.ed.AddText(1, b"x")
+ data = b"\0" * 100
+ length = self.ed.GetLine(0, data)
+ self.assertEquals(length, 1)
+ data = data[:length]
+ self.assertEquals(data, b"x")
+
+ def testLineEnds(self):
+ self.ed.AddText(3, b"x\ny")
+ self.assertEquals(self.ed.GetLineEndPosition(0), 1)
+ self.assertEquals(self.ed.GetLineEndPosition(1), 3)
+ self.assertEquals(self.ed.LineLength(0), 2)
+ self.assertEquals(self.ed.LineLength(1), 1)
+ self.assertEquals(self.ed.EOLMode, self.ed.SC_EOL_CRLF)
+ lineEnds = [b"\r\n", b"\r", b"\n"]
+ for lineEndType in [self.ed.SC_EOL_CR, self.ed.SC_EOL_LF, self.ed.SC_EOL_CRLF]:
+ self.ed.EOLMode = lineEndType
+ self.assertEquals(self.ed.EOLMode, lineEndType)
+ self.ed.ConvertEOLs(lineEndType)
+ self.assertEquals(self.ed.Contents(), b"x" + lineEnds[lineEndType] + b"y")
+ self.assertEquals(self.ed.LineLength(0), 1 + len(lineEnds[lineEndType]))
+
+ def testGoto(self):
+ self.ed.AddText(5, b"a\nb\nc")
+ self.assertEquals(self.ed.CurrentPos, 5)
+ self.ed.GotoLine(1)
+ self.assertEquals(self.ed.CurrentPos, 2)
+ self.ed.GotoPos(4)
+ self.assertEquals(self.ed.CurrentPos, 4)
+
+ def testCutCopyPaste(self):
+ self.ed.AddText(5, b"a1b2c")
+ self.ed.SetSel(1,3)
+ self.ed.Cut()
+ self.assertEquals(self.ed.CanPaste(), 1)
+ self.ed.SetSel(0, 0)
+ self.ed.Paste()
+ self.assertEquals(self.ed.Contents(), b"1ba2c")
+ self.ed.SetSel(4,5)
+ self.ed.Copy()
+ self.ed.SetSel(1,3)
+ self.ed.Paste()
+ self.assertEquals(self.ed.Contents(), b"1c2c")
+ self.ed.SetSel(2,4)
+ self.ed.Clear()
+ self.assertEquals(self.ed.Contents(), b"1c")
+
+ def testGetSet(self):
+ self.ed.SetText(0, b"abc")
+ self.assertEquals(self.ed.TextLength, 3)
+ result = b"\0" * 5
+ length = self.ed.GetText(4, result)
+ result = result[:length]
+ self.assertEquals(result, b"abc")
+
+ def testAppend(self):
+ self.ed.SetText(0, b"abc")
+ self.assertEquals(self.ed.SelectionStart, 0)
+ self.assertEquals(self.ed.SelectionEnd, 0)
+ text = b"12"
+ self.ed.AppendText(len(text), text)
+ self.assertEquals(self.ed.SelectionStart, 0)
+ self.assertEquals(self.ed.SelectionEnd, 0)
+ self.assertEquals(self.ed.Contents(), b"abc12")
+
+ def testTarget(self):
+ self.ed.SetText(0, b"abcd")
+ self.ed.TargetStart = 1
+ self.ed.TargetEnd = 3
+ self.assertEquals(self.ed.TargetStart, 1)
+ self.assertEquals(self.ed.TargetEnd, 3)
+ rep = b"321"
+ self.ed.ReplaceTarget(len(rep), rep)
+ self.assertEquals(self.ed.Contents(), b"a321d")
+ self.ed.SearchFlags = self.ed.SCFIND_REGEXP
+ self.assertEquals(self.ed.SearchFlags, self.ed.SCFIND_REGEXP)
+ searchString = b"\([1-9]+\)"
+ pos = self.ed.SearchInTarget(len(searchString), searchString)
+ self.assertEquals(1, pos)
+ rep = b"\\1"
+ self.ed.TargetStart = 0
+ self.ed.TargetEnd = 0
+ self.ed.ReplaceTargetRE(len(rep), rep)
+ self.assertEquals(self.ed.Contents(), b"321a321d")
+ self.ed.SetSel(4,5)
+ self.ed.TargetFromSelection()
+ self.assertEquals(self.ed.TargetStart, 4)
+ self.assertEquals(self.ed.TargetEnd, 5)
+
+ def testPointsAndPositions(self):
+ self.ed.AddText(1, b"x")
+ # Start of text
+ self.assertEquals(self.ed.PositionFromPoint(0,0), 0)
+ # End of text
+ self.assertEquals(self.ed.PositionFromPoint(0,100), 1)
+
+ def testLinePositions(self):
+ text = b"ab\ncd\nef"
+ self.ed.AddText(len(text), text)
+ self.assertEquals(self.ed.LineFromPosition(-1), 0)
+ line = 0
+ for pos in range(len(text)+1):
+ self.assertEquals(self.ed.LineFromPosition(pos), line)
+ if pos < len(text) and text[pos] == ord("\n"):
+ line += 1
+
+ def testWordPositions(self):
+ text = b"ab cd\tef"
+ self.ed.AddText(len(text), text)
+ self.assertEquals(self.ed.WordStartPosition(3, 0), 2)
+ self.assertEquals(self.ed.WordStartPosition(4, 0), 3)
+ self.assertEquals(self.ed.WordStartPosition(5, 0), 3)
+ self.assertEquals(self.ed.WordStartPosition(6, 0), 5)
+
+ self.assertEquals(self.ed.WordEndPosition(2, 0), 3)
+ self.assertEquals(self.ed.WordEndPosition(3, 0), 5)
+ self.assertEquals(self.ed.WordEndPosition(4, 0), 5)
+ self.assertEquals(self.ed.WordEndPosition(5, 0), 6)
+ self.assertEquals(self.ed.WordEndPosition(6, 0), 8)
+
+MODI = 1
+UNDO = 2
+REDO = 4
+
+class TestContainerUndo(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+ self.data = b"xy"
+
+ def UndoState(self):
+ return (MODI if self.ed.Modify else 0) | \
+ (UNDO if self.ed.CanUndo() else 0) | \
+ (REDO if self.ed.CanRedo() else 0)
+
+ def testContainerActNoCoalesce(self):
+ self.ed.InsertText(0, self.data)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.AddUndoAction(5, 0)
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO | REDO)
+ self.ed.Redo()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.Undo()
+
+ def testContainerActCoalesce(self):
+ self.ed.InsertText(0, self.data)
+ self.ed.AddUndoAction(5, 1)
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 0)
+ self.assertEquals(self.UndoState(), REDO)
+ self.ed.Redo()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+
+ def testContainerMultiStage(self):
+ self.ed.InsertText(0, self.data)
+ self.ed.AddUndoAction(5, 1)
+ self.ed.AddUndoAction(5, 1)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 0)
+ self.assertEquals(self.UndoState(), REDO)
+ self.ed.Redo()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.AddUndoAction(5, 1)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 0)
+ self.assertEquals(self.UndoState(), REDO)
+
+ def testContainerMultiStageNoText(self):
+ self.ed.AddUndoAction(5, 1)
+ self.ed.AddUndoAction(5, 1)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.Undo()
+ self.assertEquals(self.UndoState(), REDO)
+ self.ed.Redo()
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.AddUndoAction(5, 1)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.Undo()
+ self.assertEquals(self.UndoState(), REDO)
+
+ def testContainerActCoalesceEnd(self):
+ self.ed.AddUndoAction(5, 1)
+ self.assertEquals(self.ed.Length, 0)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.InsertText(0, self.data)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 0)
+ self.assertEquals(self.UndoState(), REDO)
+ self.ed.Redo()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+
+ def testContainerBetweenInsertAndInsert(self):
+ self.assertEquals(self.ed.Length, 0)
+ self.ed.InsertText(0, self.data)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.AddUndoAction(5, 1)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.InsertText(2, self.data)
+ self.assertEquals(self.ed.Length, 4)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ # Undoes both insertions and the containerAction in the middle
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 0)
+ self.assertEquals(self.UndoState(), REDO)
+
+ def testContainerNoCoalesceBetweenInsertAndInsert(self):
+ self.assertEquals(self.ed.Length, 0)
+ self.ed.InsertText(0, self.data)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.AddUndoAction(5, 0)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.InsertText(2, self.data)
+ self.assertEquals(self.ed.Length, 4)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ # Undo last insertion
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO | REDO)
+ # Undo container
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO | REDO)
+ # Undo first insertion
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 0)
+ self.assertEquals(self.UndoState(), REDO)
+
+ def testContainerBetweenDeleteAndDelete(self):
+ self.ed.InsertText(0, self.data)
+ self.ed.EmptyUndoBuffer()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), 0)
+ self.ed.SetSel(2,2)
+ self.ed.DeleteBack()
+ self.assertEquals(self.ed.Length, 1)
+ self.ed.AddUndoAction(5, 1)
+ self.ed.DeleteBack()
+ self.assertEquals(self.ed.Length, 0)
+ # Undoes both deletions and the containerAction in the middle
+ self.ed.Undo()
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), REDO)
+
+ def testContainerBetweenInsertAndDelete(self):
+ self.assertEquals(self.ed.Length, 0)
+ self.ed.InsertText(0, self.data)
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.AddUndoAction(5, 1)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.SetSel(0,1)
+ self.ed.Cut()
+ self.assertEquals(self.ed.Length, 1)
+ self.assertEquals(self.UndoState(), MODI | UNDO)
+ self.ed.Undo() # Only undoes the deletion
+ self.assertEquals(self.ed.Length, 2)
+ self.assertEquals(self.UndoState(), MODI | UNDO | REDO)
+
+class TestKeyCommands(unittest.TestCase):
+ """ These commands are normally assigned to keys and take no arguments """
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+
+ def selRange(self):
+ return self.ed.CurrentPos, self.ed.Anchor
+
+ def testLineMove(self):
+ self.ed.AddText(8, b"x1\ny2\nz3")
+ self.ed.SetSel(0,0)
+ self.ed.ChooseCaretX()
+ self.ed.LineDown()
+ self.ed.LineDown()
+ self.assertEquals(self.selRange(), (6, 6))
+ self.ed.LineUp()
+ self.assertEquals(self.selRange(), (3, 3))
+ self.ed.LineDownExtend()
+ self.assertEquals(self.selRange(), (6, 3))
+ self.ed.LineUpExtend()
+ self.ed.LineUpExtend()
+ self.assertEquals(self.selRange(), (0, 3))
+
+ def testCharMove(self):
+ self.ed.AddText(8, b"x1\ny2\nz3")
+ self.ed.SetSel(0,0)
+ self.ed.CharRight()
+ self.ed.CharRight()
+ self.assertEquals(self.selRange(), (2, 2))
+ self.ed.CharLeft()
+ self.assertEquals(self.selRange(), (1, 1))
+ self.ed.CharRightExtend()
+ self.assertEquals(self.selRange(), (2, 1))
+ self.ed.CharLeftExtend()
+ self.ed.CharLeftExtend()
+ self.assertEquals(self.selRange(), (0, 1))
+
+ def testWordMove(self):
+ self.ed.AddText(10, b"a big boat")
+ self.ed.SetSel(3,3)
+ self.ed.WordRight()
+ self.ed.WordRight()
+ self.assertEquals(self.selRange(), (10, 10))
+ self.ed.WordLeft()
+ self.assertEquals(self.selRange(), (6, 6))
+ self.ed.WordRightExtend()
+ self.assertEquals(self.selRange(), (10, 6))
+ self.ed.WordLeftExtend()
+ self.ed.WordLeftExtend()
+ self.assertEquals(self.selRange(), (2, 6))
+
+ def testHomeEndMove(self):
+ self.ed.AddText(10, b"a big boat")
+ self.ed.SetSel(3,3)
+ self.ed.Home()
+ self.assertEquals(self.selRange(), (0, 0))
+ self.ed.LineEnd()
+ self.assertEquals(self.selRange(), (10, 10))
+ self.ed.SetSel(3,3)
+ self.ed.HomeExtend()
+ self.assertEquals(self.selRange(), (0, 3))
+ self.ed.LineEndExtend()
+ self.assertEquals(self.selRange(), (10, 3))
+
+ def testStartEndMove(self):
+ self.ed.AddText(10, b"a\nbig\nboat")
+ self.ed.SetSel(3,3)
+ self.ed.DocumentStart()
+ self.assertEquals(self.selRange(), (0, 0))
+ self.ed.DocumentEnd()
+ self.assertEquals(self.selRange(), (10, 10))
+ self.ed.SetSel(3,3)
+ self.ed.DocumentStartExtend()
+ self.assertEquals(self.selRange(), (0, 3))
+ self.ed.DocumentEndExtend()
+ self.assertEquals(self.selRange(), (10, 3))
+
+
+class TestMarkers(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+ self.ed.AddText(5, b"x\ny\nz")
+
+ def testMarker(self):
+ handle = self.ed.MarkerAdd(1,1)
+ self.assertEquals(self.ed.MarkerLineFromHandle(handle), 1)
+ self.ed.MarkerDelete(1,1)
+ self.assertEquals(self.ed.MarkerLineFromHandle(handle), -1)
+
+ def testMarkerDeleteAll(self):
+ h1 = self.ed.MarkerAdd(0,1)
+ h2 = self.ed.MarkerAdd(1,2)
+ self.assertEquals(self.ed.MarkerLineFromHandle(h1), 0)
+ self.assertEquals(self.ed.MarkerLineFromHandle(h2), 1)
+ self.ed.MarkerDeleteAll(1)
+ self.assertEquals(self.ed.MarkerLineFromHandle(h1), -1)
+ self.assertEquals(self.ed.MarkerLineFromHandle(h2), 1)
+ self.ed.MarkerDeleteAll(-1)
+ self.assertEquals(self.ed.MarkerLineFromHandle(h1), -1)
+ self.assertEquals(self.ed.MarkerLineFromHandle(h2), -1)
+
+ def testMarkerDeleteHandle(self):
+ handle = self.ed.MarkerAdd(0,1)
+ self.assertEquals(self.ed.MarkerLineFromHandle(handle), 0)
+ self.ed.MarkerDeleteHandle(handle)
+ self.assertEquals(self.ed.MarkerLineFromHandle(handle), -1)
+
+ def testMarkerBits(self):
+ self.assertEquals(self.ed.MarkerGet(0), 0)
+ self.ed.MarkerAdd(0,1)
+ self.assertEquals(self.ed.MarkerGet(0), 2)
+ self.ed.MarkerAdd(0,2)
+ self.assertEquals(self.ed.MarkerGet(0), 6)
+
+ def testMarkerAddSet(self):
+ self.assertEquals(self.ed.MarkerGet(0), 0)
+ self.ed.MarkerAddSet(0,5)
+ self.assertEquals(self.ed.MarkerGet(0), 5)
+ self.ed.MarkerDeleteAll(-1)
+
+ def testMarkerNext(self):
+ h1 = self.ed.MarkerAdd(0,1)
+ h2 = self.ed.MarkerAdd(2,1)
+ self.assertEquals(self.ed.MarkerNext(0, 2), 0)
+ self.assertEquals(self.ed.MarkerNext(1, 2), 2)
+ self.assertEquals(self.ed.MarkerNext(2, 2), 2)
+ self.assertEquals(self.ed.MarkerPrevious(0, 2), 0)
+ self.assertEquals(self.ed.MarkerPrevious(1, 2), 0)
+ self.assertEquals(self.ed.MarkerPrevious(2, 2), 2)
+
+ def testLineState(self):
+ self.assertEquals(self.ed.MaxLineState, 0)
+ self.assertEquals(self.ed.GetLineState(0), 0)
+ self.assertEquals(self.ed.GetLineState(1), 0)
+ self.assertEquals(self.ed.GetLineState(2), 0)
+ self.ed.SetLineState(1, 100)
+ self.assertNotEquals(self.ed.MaxLineState, 0)
+ self.assertEquals(self.ed.GetLineState(0), 0)
+ self.assertEquals(self.ed.GetLineState(1), 100)
+ self.assertEquals(self.ed.GetLineState(2), 0)
+
+ def testSymbolRetrieval(self):
+ self.ed.MarkerDefine(1,3)
+ self.assertEquals(self.ed.MarkerSymbolDefined(1), 3)
+
+class TestIndicators(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+
+ def testSetIndicator(self):
+ self.assertEquals(self.ed.IndicGetStyle(0), 1)
+ self.assertEquals(self.ed.IndicGetFore(0), 0x007f00)
+ self.ed.IndicSetStyle(0, 2)
+ self.ed.IndicSetFore(0, 0xff0080)
+ self.assertEquals(self.ed.IndicGetStyle(0), 2)
+ self.assertEquals(self.ed.IndicGetFore(0), 0xff0080)
+
+class TestSearch(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+ self.ed.InsertText(0, b"a\tbig boat\t")
+
+ def testFind(self):
+ pos = self.ed.FindBytes(0, self.ed.Length, b"zzz", 0)
+ self.assertEquals(pos, -1)
+ pos = self.ed.FindBytes(0, self.ed.Length, b"big", 0)
+ self.assertEquals(pos, 2)
+
+ def testCaseFind(self):
+ self.assertEquals(self.ed.FindBytes(0, self.ed.Length, b"big", 0), 2)
+ self.assertEquals(self.ed.FindBytes(0, self.ed.Length, b"bIg", 0), 2)
+ self.assertEquals(self.ed.FindBytes(0, self.ed.Length, b"bIg",
+ self.ed.SCFIND_MATCHCASE), -1)
+
+ def testWordFind(self):
+ self.assertEquals(self.ed.FindBytes(0, self.ed.Length, b"bi", 0), 2)
+ self.assertEquals(self.ed.FindBytes(0, self.ed.Length, b"bi",
+ self.ed.SCFIND_WHOLEWORD), -1)
+
+ def testWordStartFind(self):
+ self.assertEquals(self.ed.FindBytes(0, self.ed.Length, b"bi", 0), 2)
+ self.assertEquals(self.ed.FindBytes(0, self.ed.Length, b"bi",
+ self.ed.SCFIND_WORDSTART), 2)
+ self.assertEquals(self.ed.FindBytes(0, self.ed.Length, b"ig", 0), 3)
+ self.assertEquals(self.ed.FindBytes(0, self.ed.Length, b"ig",
+ self.ed.SCFIND_WORDSTART), -1)
+
+ def testREFind(self):
+ flags = self.ed.SCFIND_REGEXP
+ self.assertEquals(-1, self.ed.FindBytes(0, self.ed.Length, b"b.g", 0))
+ self.assertEquals(2, self.ed.FindBytes(0, self.ed.Length, b"b.g", flags))
+ self.assertEquals(2, self.ed.FindBytes(0, self.ed.Length, b"\<b.g\>", flags))
+ self.assertEquals(-1, self.ed.FindBytes(0, self.ed.Length, b"b[A-Z]g",
+ flags | self.ed.SCFIND_MATCHCASE))
+ self.assertEquals(2, self.ed.FindBytes(0, self.ed.Length, b"b[a-z]g", flags))
+ self.assertEquals(6, self.ed.FindBytes(0, self.ed.Length, b"b[a-z]*t", flags))
+ self.assertEquals(0, self.ed.FindBytes(0, self.ed.Length, b"^a", flags))
+ self.assertEquals(10, self.ed.FindBytes(0, self.ed.Length, b"\t$", flags))
+ self.assertEquals(0, self.ed.FindBytes(0, self.ed.Length, b"\([a]\).*\0", flags))
+
+ def testPosixREFind(self):
+ flags = self.ed.SCFIND_REGEXP | self.ed.SCFIND_POSIX
+ self.assertEquals(-1, self.ed.FindBytes(0, self.ed.Length, b"b.g", 0))
+ self.assertEquals(2, self.ed.FindBytes(0, self.ed.Length, b"b.g", flags))
+ self.assertEquals(2, self.ed.FindBytes(0, self.ed.Length, b"\<b.g\>", flags))
+ self.assertEquals(-1, self.ed.FindBytes(0, self.ed.Length, b"b[A-Z]g",
+ flags | self.ed.SCFIND_MATCHCASE))
+ self.assertEquals(2, self.ed.FindBytes(0, self.ed.Length, b"b[a-z]g", flags))
+ self.assertEquals(6, self.ed.FindBytes(0, self.ed.Length, b"b[a-z]*t", flags))
+ self.assertEquals(0, self.ed.FindBytes(0, self.ed.Length, b"^a", flags))
+ self.assertEquals(10, self.ed.FindBytes(0, self.ed.Length, b"\t$", flags))
+ self.assertEquals(0, self.ed.FindBytes(0, self.ed.Length, b"([a]).*\0", flags))
+
+ def testPhilippeREFind(self):
+ # Requires 1.,72
+ flags = self.ed.SCFIND_REGEXP
+ self.assertEquals(0, self.ed.FindBytes(0, self.ed.Length, "\w", flags))
+ self.assertEquals(1, self.ed.FindBytes(0, self.ed.Length, "\W", flags))
+ self.assertEquals(-1, self.ed.FindBytes(0, self.ed.Length, "\d", flags))
+ self.assertEquals(0, self.ed.FindBytes(0, self.ed.Length, "\D", flags))
+ self.assertEquals(1, self.ed.FindBytes(0, self.ed.Length, "\s", flags))
+ self.assertEquals(0, self.ed.FindBytes(0, self.ed.Length, "\S", flags))
+ self.assertEquals(2, self.ed.FindBytes(0, self.ed.Length, "\x62", flags))
+
+class TestProperties(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+
+ def testSet(self):
+ self.ed.SetProperty(b"test", b"12")
+ self.assertEquals(self.ed.GetPropertyInt(b"test"), 12)
+ result = b"\0" * 10
+ length = self.ed.GetProperty(b"test", result)
+ result = result[:length]
+ self.assertEquals(result, b"12")
+ self.ed.SetProperty(b"test.plus", b"[$(test)]")
+ result = b"\0" * 10
+ length = self.ed.GetPropertyExpanded(b"test.plus", result)
+ result = result[:length]
+ self.assertEquals(result, b"[12]")
+
+class TestTextMargin(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+ self.txt = b"abcd"
+ self.ed.AddText(1, b"x")
+
+ def testAscent(self):
+ lineHeight = self.ed.TextHeight(0)
+ self.ed.ExtraAscent
+ self.assertEquals(self.ed.ExtraAscent, 0)
+ self.assertEquals(self.ed.ExtraDescent, 0)
+ self.ed.ExtraAscent = 1
+ self.assertEquals(self.ed.ExtraAscent, 1)
+ self.ed.ExtraDescent = 2
+ self.assertEquals(self.ed.ExtraDescent, 2)
+ # Allow line height to recalculate
+ self.xite.DoEvents()
+ lineHeightIncreased = self.ed.TextHeight(0)
+ self.assertEquals(lineHeightIncreased, lineHeight + 2 + 1)
+
+ def testTextMargin(self):
+ self.ed.MarginSetText(0, self.txt)
+ result = b"\0" * 10
+ length = self.ed.MarginGetText(0, result)
+ result = result[:length]
+ self.assertEquals(result, self.txt)
+ self.ed.MarginTextClearAll()
+
+ def testTextMarginStyle(self):
+ self.ed.MarginSetText(0, self.txt)
+ self.ed.MarginSetStyle(0, 33)
+ self.assertEquals(self.ed.MarginGetStyle(0), 33)
+ self.ed.MarginTextClearAll()
+
+ def testTextMarginStyles(self):
+ styles = b"\001\002\003\004"
+ self.ed.MarginSetText(0, self.txt)
+ self.ed.MarginSetStyles(0, styles)
+ result = b"\0" * 10
+ length = self.ed.MarginGetStyles(0, result)
+ result = result[:length]
+ self.assertEquals(result, styles)
+ self.ed.MarginTextClearAll()
+
+ def testTextMarginStyleOffset(self):
+ self.ed.MarginSetStyleOffset(300)
+ self.assertEquals(self.ed.MarginGetStyleOffset(), 300)
+
+class TestAnnotation(unittest.TestCase):
+
+ def setUp(self):
+ self.xite = XiteWin.xiteFrame
+ self.ed = self.xite.ed
+ self.ed.ClearAll()
+ self.ed.EmptyUndoBuffer()
+ self.txt = b"abcd"
+ self.ed.AddText(1, b"x")
+
+ def testTextAnnotation(self):
+ self.assertEquals(self.ed.AnnotationGetLines(), 0)
+ self.ed.AnnotationSetText(0, self.txt)
+ self.assertEquals(self.ed.AnnotationGetLines(), 1)
+ result = b"\0" * 10
+ length = self.ed.AnnotationGetText(0, result)
+ self.assertEquals(length, 4)
+ result = result[:length]
+ self.assertEquals(result, self.txt)
+ self.ed.AnnotationClearAll()
+
+ def testTextAnnotationStyle(self):
+ self.ed.AnnotationSetText(0, self.txt)
+ self.ed.AnnotationSetStyle(0, 33)
+ self.assertEquals(self.ed.AnnotationGetStyle(0), 33)
+ self.ed.AnnotationClearAll()
+
+ def testTextAnnotationStyles(self):
+ styles = b"\001\002\003\004"
+ self.ed.AnnotationSetText(0, self.txt)
+ self.ed.AnnotationSetStyles(0, styles)
+ result = b"\0" * 10
+ length = self.ed.AnnotationGetStyles(0, result)
+ result = result[:length]
+ self.assertEquals(result, styles)
+ self.ed.AnnotationClearAll()
+
+ def testTextAnnotationStyleOffset(self):
+ self.ed.AnnotationSetStyleOffset(300)
+ self.assertEquals(self.ed.AnnotationGetStyleOffset(), 300)
+
+ def testTextAnnotationVisible(self):
+ self.assertEquals(self.ed.AnnotationGetVisible(), 0)
+ self.ed.AnnotationSetVisible(2)
+ self.assertEquals(self.ed.AnnotationGetVisible(), 2)
+ self.ed.AnnotationSetVisible(0)
+
+#~ import os
+#~ for x in os.getenv("PATH").split(";"):
+ #~ n = "scilexer.dll"
+ #~ nf = x + "\\" + n
+ #~ print os.access(nf, os.R_OK), nf
+if __name__ == '__main__':
+ XiteWin.main("simpleTests")
diff --git a/test/xite.py b/test/xite.py
new file mode 100644
index 000000000..399c79544
--- /dev/null
+++ b/test/xite.py
@@ -0,0 +1,6 @@
+# -*- coding: utf-8 -*-
+
+import XiteWin
+
+if __name__ == "__main__":
+ XiteWin.main("")