Coverage for pyilper/pilcore.py: 86%

Shortcuts on this page

r m x   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

104 statements  

1#!/usr/bin/python3 

2# -*- coding: utf-8 -*- 

3# 

4# pyILPER  

5# 

6# Python platform dependent classes and constants 

7# Copyright (c) 2016 J. Siebold 

8# 

9# This program is free software; you can redistribute it and/or 

10# modify it under the terms of the GNU General Public License 

11# as published by the Free Software Foundation; either version 2 

12# of the License, or (at your option) any later version. 

13# 

14# This program is distributed in the hope that it will be useful, 

15# but WITHOUT ANY WARRANTY; without even the implied warranty of 

16# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 

17# GNU General Public License for more details. 

18# 

19# You should have received a copy of the GNU General Public License 

20# along with this program; if not, write to the Free Software 

21# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 

22# 

23# pyILPER support and constants --------------------------------------------------- 

24# 

25# Changelog 

26# 08.07.16 - jsi: 

27# - initial release 

28# 25.07.2016 - jsi 

29# - set version to "production" 

30# 21.08.2016 - jsi 

31# - set version to 1.3.5 development 

32# 13.10.2016 - jsi 

33# - device tab constants and dictionary added 

34# 18.10.2016 - jsi 

35# - set version number to 1.4.0 development 

36# 23.10.2016 - jsi 

37# - EMU7470_VERSION added 

38# 25.10.2016 - jsi 

39# - decode_version moved from lifexec.py 

40# 26.10.2016 - jsi 

41# - version 1.4.0 beta1 

42# 04.11.2016 - jsi 

43# - version 1.4.0 beta2 

44# 01.01.2016 - jsi 

45# - version 1.4.0 

46# 07.01.2016 - jsi 

47# - add encode version function 

48# 03.01.2016 - jsi 

49# - version - 1.5.0beta1 development 

50# 16.03.2017 - jsi 

51# - version - 1.5.0 production 

52# 01.08.2017 - jsi 

53# - device HP82162A added 

54# 10.08.2017 jsi 

55# - version 1.6.0 development 

56# 11.08.2017 jsi 

57# - catch error in decode_version if no version information exists 

58# 18.08.2017 jsi 

59# - Tab name plotter renamed to HP7470A 

60# 21.08.2017 jsi 

61# - PDF and barcode constants added 

62# 31.08.2017 jsi 

63# - parameter TERMINAL_MINIMUM_ROWS added 

64# 03.09.2017 jsi 

65# - communication mode constants moved from pyilpermain.py 

66# 06.09.2017 jsi 

67# - restructured, assemble_frame and disassemble_frame added 

68# 07.09.2017 jsi 

69# - timeout constants for TCP, socket and pipe communication added 

70# 01.10.2017 jsi 

71# - 1.6.0 beta1 

72# 12.11.2017 jsi 

73# - 1.6.0 beta3 

74# 13.11.2017 jsi 

75# - make USE8BITS change depending on data returned by the PIL-Box 

76# 27.11.2017 jsi 

77# - version 1.6.0 production 

78# 04.12.2017 jsi 

79# - version 1.6.1 development 

80# 28.12.2017 jsi 

81# - AUTOSCROLL_RATE parameter introduced 

82# 16.01.2018 jsi 

83# - added config type parameters for cls_config_tool_button 

84# 17.01.2018 jsi 

85# - added color scheme constants 

86# - changed version to 1.7.0 because of major enhancements of the GUI 

87# 21.01.2018 jsi 

88# - moved cls_config_tool_button and color scheme constants to pilwidget.py 

89# 22.02.2018 jsi 

90# - 1.7.1 production 

91# 18.03.2018 jsi 

92# - 1.7.2 development, added Python minimum version requirements 

93# 04.08.2018 jsi 

94# - 1.7.2 beta1 

95# 11.08.2018 jsi 

96# - 1.7.2 beta2 

97# 20.08.2018 jsi 

98# - 1.7.2 production 

99# 12.12.2018 jsi 

100# - added HP2225B_LINEBUFFERSIZE 

101# - 1.8.0 development 

102# 18.12.2018 jsi 

103# - added HP2225B 

104# 10.01.2019 jsi 

105# - renamed Printer tab to Generic Printer 

106# - prepare Beta1 

107# 14.01.2019 jsi 

108# - added constants for keyboard type configuration 

109# - prepare Beta2 

110# 27.01.2019 jsi 

111# - introduced KEYBOARD_DELAY configuration parameter 

112# 09.01.2019 jsi 

113# - prepare release 

114# 31.05.2019 jsi 

115# - 1.8.1 development 

116# 05.06.2019 

117# - 1.8.1 production 

118# 06.11.2019 jsi 

119# - 1.8.2 development 

120# 03.02.2020 jsi 

121# - prepare release 

122# 29.04.2020 jsi 

123# - 1.8.3 development 

124# 10.01.2021 jsi 

125# - 1.8.3 release 

126# 01.03.2021 jsi 

127# - 1.8.4 development 

128# 16.11.2021 jsi 

129# - TAB_RAWDRIVE added 

130# 28.11.2021 jsi 

131# - prepare 1.8.5 beta 1 

132# 12.12.2021 jsi 

133# - function buildconfigfilename added 

134# 17.02.2022 jsi 

135# - 1.8.5 release 

136# - function to decode the pyILPER release number rewritten 

137# 18.04.22 jsi 

138# - 1.8.6 beta1  

139# - used raw string in re.compile to avoid DEPRECATED warning 

140# 

141import platform 

142import os 

143import re 

144# 

145# Program constants -------------------------------------------------- 

146# 

147# General constants: 

148# 

149PRODUCTION= False # Production/Development Version 

150VERSION="1.8.7b2" # pyILPR version number 

151CONFIG_VERSION="2" # Version number of pyILPER config file, must be string 

152# 

153# Python minimum version 

154# 

155PYTHON_REQUIRED_MAJOR=3 

156PYTHON_REQUIRED_MINOR=5 

157# 

158# Communication modes and classes 

159# 

160MODE_PILBOX=0 # connect to PIL-Box 

161MODE_TCPIP=1 # connect to virtual HP-IL over TCP/IP 

162MODE_SOCKET=2 # conect via Unix domain socket 

163 

164# 

165# PIL-Box communication 

166# 

167USE8BITS= True # use 8 bit data transfer to PIL-Box 

168TMOUTCMD=1 # time out for PIL-Box commands 

169TMOUTFRM=0.05 # time out for HP-IL frames 

170 

171# 

172# TCP/IP, socket and pipe communication 

173# 

174COMTMOUTREAD=0.1 # time out for read 

175COMTMOUTACK=1 # time out for receiving an acknowledge 

176COMTMOUTWRITE=1 # tine out for write 

177 

178# 

179# Drive tab - directory listing 

180# 

181REFRESH_RATE=1000 # period to check whether a drive was altered and is idle 

182NOT_TALKER_SPAN=3 # time (s) a drive must be inactive to be concidered as idle 

183# 

184# Terminal tab 

185# 

186UPDATE_TIMER=25 # Poll timer (ms) for terminal output queue 

187CURSOR_BLINK=500 # 500 ms cursor blink rate 

188CURSOR_BLINK_INTERVAL= CURSOR_BLINK / UPDATE_TIMER 

189AUTOSCROLL_RATE=100 # 500 ms cursor blink rate 

190TERMINAL_MINIMUM_ROWS=24 # can't get beyond that 

191KEYBOARD_DELAY=500 # autorepeat delay to prevent too fast kbd input 

192 

193# 

194# predefined baudrates 

195# the list controlles the baudrates that are supported by the application: 

196# - the first list element sets the text in the combobox 

197# - the second list element is the baud rate, a value of 0 means auto baud detection 

198# the baudrates must be defined in ascending order 

199BAUDRATES= [ ["Auto", 0], ["9600", 9600 ] , [ "115200", 115200 ], ["230400", 230400]] 

200 

201# 

202# plotter tab, required version of emu7470 

203# 

204EMU7470_VERSION=900 

205 

206# 

207# thermal printer tab 

208# 

209HP82162A_LINEBUFFERSIZE=2000 

210 

211# 

212# if Development Version append string to VERSION and "d" to config file name 

213# 

214if not PRODUCTION: 

215 VERSION=VERSION+" (Development)" 

216# 

217# Tab types 

218# 

219TAB_SCOPE=0 

220TAB_PRINTER=1 

221TAB_DRIVE=2 

222TAB_TERMINAL=3 

223TAB_PLOTTER=4 

224TAB_HP82162A=5 

225TAB_HP2225B=6 

226TAB_RAWDRIVE=7 

227# 

228TAB_NAMES={TAB_SCOPE:'Scope',TAB_PRINTER:'Generic Printer',TAB_DRIVE:'Drive',TAB_TERMINAL:'Terminal',TAB_PLOTTER:'HP7470A',TAB_HP82162A:'HP82162A', TAB_HP2225B: 'HP2225B', TAB_RAWDRIVE: 'Raw Drive'} 

229# 

230# PDF Constants in 1/10 mm 

231# 

232PDF_MARGINS=100 

233PDF_FORMAT_A4=0 

234PDF_FORMAT_LETTER=1 

235PDF_ORIENTATION_PORTRAIT=0 

236PDF_ORIENTATION_LANDSCAPE=1 

237# 

238# Barcode Constants in 1/10 mm 

239# 

240BARCODE_HEIGHT=100 

241BARCODE_NARROW_W= 5 

242BARCODE_WIDE_W= 10 

243BARCODE_SPACING= 5 

244 

245# 

246# utility functions -------------------------------------------------------------- 

247# 

248# get platform 

249# 

250def isLINUX(): 

251 return platform.system()=="Linux" 

252def isWINDOWS(): 

253 return platform.system()=="Windows" 

254def isMACOS(): 

255 return platform.system()=="Darwin" 

256# 

257# Standard FONT 

258# Note: It would be more elegant to use "Andale Mono" on Macos and "Consolas" on  

259# Windows. "Consolas" is not available on XP and older Windows versions. 

260# 

261if isLINUX(): 

262 FONT="Monospace" 

263else: 

264 FONT="Courier New" 

265# 

266# decode version number of lifutils or emu7470 

267# 

268def decode_version(version_number): 

269 if version_number==0: 

270 return "(unknown)" 

271 version=str(version_number) 

272 major=int(version[0]) 

273 minor=int(version[1:3]) 

274 subversion=int(version[3:5]) 

275 return "{:d}.{:d}.{:d}".format(major,minor,subversion) 

276# 

277# decode version number of pyilper as a list 

278# 

279def decode_pyILPERVersion(version_string): 

280# 

281# parse the pyILPER version string as a list: 

282# major version, minor version, subversion, a/b, devel-version 

283# only major version, minor version and subersion are returned as a 

284# single integer. Returns 0 if no valid release information was found. 

285# 

286# Fixed DEPRECATED escape sequence \. using raw string 

287 reg=re.compile(r'^([0-9]+)\.([0-9]+)\.([0-9]+)(?:(b)([0-9]+)?)?.*$') 

288 ret=reg.findall(version_string) 

289 try: 

290 major=int(ret[0][0]) 

291 minor=int(ret[0][1]) 

292 subversion=int(ret[0][2]) 

293 return major*10000+minor*100+subversion 

294 except ValueError: 

295 return 0 

296 except IndexError: 

297 return 0 

298# 

299# assemble frame from low and high byte according to 7- oder 8-bit format 

300# 

301def assemble_frame(hbyt,lbyt): 

302 global USE8BITS 

303 if( lbyt & 0x80 ): 

304 USE8BITS= True 

305 return ((hbyt & 0x1E) << 6) + (lbyt & 0x7F) 

306 else: 

307 USE8BITS= False 

308 return ((hbyt & 0x1F) << 6) + (lbyt & 0x3F) 

309# 

310# disassemble frame from low and high byte according to 7- oder 8-bit format 

311# 

312 

313def disassemble_frame(frame): 

314 if not USE8BITS : 

315 hbyt = ((frame >> 6) & 0x1F) | 0x20 

316 lbyt = (frame & 0x3F) | 0x40 

317 else: 

318 hbyt = ((frame >> 6) & 0x1E) | 0x20 

319 lbyt = (frame & 0x7F) | 0x80 

320 return(hbyt,lbyt) 

321# 

322# assemble file name of config file 

323# 

324def buildconfigfilename(progname,filename,configversion,instance,production): 

325# 

326# determine config file name 

327# 

328 fname=filename+instance+configversion 

329 if not production: 

330 fname+= "d" 

331# 

332# determine path (os dependend) 

333# 

334 userhome=os.path.expanduser("~") 

335 

336 if platform.system()=="Linux": 

337# 

338# LINUX 

339#  

340 configpath=os.path.join(userhome,".config",progname) 

341 elif platform.system()=="Windows": 

342# 

343# Windows 

344# 

345 configpath=os.path.join(os.environ['APPDATA'],progname) 

346 elif platform.system()=="Darwin": 

347# 

348# Mac OS X 

349# 

350 configpath=os.path.join(userhome,"Library","Application Support",progname) 

351# 

352 else: 

353# 

354# Fallback 

355# 

356 configpath=os.path.join(userhome,progname) 

357 configfilename=os.path.join(configpath,fname) 

358 

359 return configfilename,configpath