[Bf-committers] fully interactive python console

zippy trip at spymac.com
Thu Mar 24 22:36:11 CET 2005


ooo can you provide examples ?
like how could it make something different as in todays current scripts  
?

On Mar 24, 2005, at 2:15 PM, Campbell Barton wrote:

>  Hi All, I had another poke at a script I wrote a while back and  
> managed to get a interactice python console in python.
>  I think I have achieved my goal to have somthing like autocads  
> interactice console.
>
>  Features are..
>
> 	• 	Can run at the same time as blender!, and dosent forget variables  
> etc between usage. also dosent hog recources.
> 	• 	Works in many ways just like pythons interactice console.
>
> 	• 	Raises proper errors and dosent bail out of the console..
>
> 	• 	 Has a command history and colour coding for input/output/errors
> 	• 	Scripts can be saved to a text file.
> 	• 	easy to extend (python)
> 	• 	Commented out, but can use a file called 'console_autoexec.py' for  
> startup functions.
>  This is nice for user shoutcuts so lots of nifty functions could have  
> 3 letter names,
>
>  Somthing Id like to add is optional autocompleate (bash style?), for  
> variables and and Imported modules.
>  Its commented out.
>
>  -  Cam
>
>  #!BPY
>
> """ Registration info for Blender menus:
> Name: 'Blender Interactive Console'
> Blender: 234
> Group: 'Wizards'
> Tip: 'Blenders python '
> """
>
> global VARDICT
> VARDICT = {}
>
> import Blender
> from Blender import *
> import sys
>
> filename = 'cmd_blender'
>
> # Touch a file for storing anything printed.
>
> file = open(filename, 'w')
> file.close()
>
> # Include external file with internal namespace
> def include(filename):
> 	file = open(filename, 'r')
> 	filedata = file.read()
> 	file.close()
> 	return compile(filedata, filename, 'exec')
>
> # Autoexec,bat??
> #try:
> #	exec(include(Get('scriptsdir')+ '/console_autoexec.py'))	
> 	
>
> class cmdLine:
> 	# cmd: is the command string, or any other message
> 	# type: 0:user input  1:program feedback  2:error message.
> 	# exe; 0- not yet executed   1:executed
> 	def __init__(self, cmd, type, exe):
> 		self.cmd = cmd
> 		self.type = type
> 		self.exe = exe
>
> def writeCmdData(cmdLineList, type):
> 	if type == 3:
> 		typeList = [0,1,2, None] # all
> 	else:
> 		typeList = [type] # so we can use athe lists 'in' methiod
> 	
> 	newText = Text.New('command.py', 1)
> 	for myCmd in cmdLineList:
> 		if myCmd.type in typeList: # user input
> 			newText.write('%s\n' % myCmd.cmd)
> 	Draw.PupMenu('%s written' % newText.name)
>
>
> def run(py):
> 	global VARDICT
> 	# OPEN A FILE TO PUT THE STDOUT IN
> 	sys.stdout.flush() # Get rid of whatever came before
> 	file = open(filename, 'w')
> 	std=sys.stdout
> 	sys.stdout=file
> 	
> 	try:
> 		# Load all variabls from global dict to local space.
> 		for TMPVARNAME in VARDICT.keys():
> 			exec('%s%s%s%s' % (TMPVARNAME,'=VARDICT["', TMPVARNAME, '"]'))
> 		
> 		#exec(py)
> 		exec(compile(py, 'blender_cmd.py', 'exec')) # EXECUTE THE CODE
> 		
> 		# WRITE VARS to global VARLIST
> 		for TMPVARNAME in dir():
> 			if TMPVARNAME not in ['file', 'std', 'py']:
> 				exec('%s%s' % ('VARDICT[TMPVARNAME]=', TMPVARNAME))
> 		
> 	except: # Prints the REAL exception.
> 		error = str(sys.exc_value)
> 		for errorLine in error.split('\n'):
> 			cmdBuffer.append(cmdLine(errorLine, 2, None)) # new line to type  
> into
> 			
> 	sys.stdout=std # Close file
> 	file.close()
>
> 	# Open the file to read the lines to the buffer.
> 	file = open(filename, 'r')
> 	for line in file.readlines():
> 		cmdBuffer.append(cmdLine(line, 1, None))
> 	cmdBuffer.append(cmdLine(' ', 0, 0)) # new line to type into
> 	sys.stdout=std
> 	file.close()
> 	
>
>
> cmdBuffer = [cmdLine("Welcome Ideasman's Blender Console", 1, None),\
> 	cmdLine(' * Right Click to save output', 1, None),\
> 	cmdLine(' * Arrow keys for command history and cursor', 1, None),\
> 	cmdLine(' * Ctrl + Enter for multiline functions', 1, None),\
> 	cmdLine(' ', 0, 0)] # A history of commands
> shift = 0 # Bool used to work out if were using caps.
> enter = 0
> cursor = -1 # How far back from the first letter are we? - in cmd tha  
> tis.
> prompt = '>> '
> def main():
> 	global cmd
> 	global shift
> 	global cursor
> 	global histIndex
> 	histIndex = -1
> 	 
> #---------------------------------------------------------------------- 
> --------#
> 	#                             event handling code                      
>          #
> 	 
> #---------------------------------------------------------------------- 
> --------#
> 	def handle_event(evt, val):
> 		def insCh(ch): # Instert a char
> 			global cmdBuffer
> 			global cursor
> 			# Later account for a cursor variable
> 			cmdBuffer[-1].cmd = ('%s%s%s' % ( cmdBuffer[-1].cmd[:cursor], ch,  
> cmdBuffer[-1].cmd[cursor:]))
>
> 		if (evt == Draw.ESCKEY and not val):
> 			Draw.Exit()
> 		elif evt == Draw.MOUSEX: # AVOID TOO MANY REDRAWS.
> 			return
> 		elif evt == Draw.MOUSEY:
> 			return
> 		
> 		
> 		global cmdBuffer
> 		global shift
> 		global enter
> 		global cursor
> 		global histIndex
> 		
> 		if (evt == Draw.AKEY and val and shift): insCh('A')
> 		elif (evt == Draw.AKEY and val and not shift): insCh('a')
> 		elif (evt == Draw.BKEY and val and shift): insCh('B')
> 		elif (evt == Draw.BKEY and val and not shift): insCh('b')
> 		elif (evt == Draw.CKEY and val and shift): insCh('C')
> 		elif (evt == Draw.CKEY and val and not shift): insCh('c')
> 		elif (evt == Draw.DKEY and val and shift): insCh('D')
> 		elif (evt == Draw.DKEY and val and not shift): insCh('d')
> 		elif (evt == Draw.EKEY and val and shift): insCh('E')
> 		elif (evt == Draw.EKEY and val and not shift): insCh('e')
> 		elif (evt == Draw.FKEY and val and shift): insCh('F')
> 		elif (evt == Draw.FKEY and val and not shift): insCh('f')
> 		elif (evt == Draw.GKEY and val and shift): insCh('G')
> 		elif (evt == Draw.GKEY and val and not shift): insCh('g')
> 		elif (evt == Draw.HKEY and val and shift): insCh('H')
> 		elif (evt == Draw.HKEY and val and not shift): insCh('h')
> 		elif (evt == Draw.IKEY and val and shift): insCh('I')
> 		elif (evt == Draw.IKEY and val and not shift): insCh('i')
> 		elif (evt == Draw.JKEY and val and shift): insCh('J')
> 		elif (evt == Draw.JKEY and val and not shift): insCh('j')
> 		elif (evt == Draw.KKEY and val and shift): insCh('K')
> 		elif (evt == Draw.KKEY and val and not shift): insCh('j')
> 		elif (evt == Draw.LKEY and val and shift): insCh('L')
> 		elif (evt == Draw.LKEY and val and not shift): insCh('l')
> 		elif (evt == Draw.MKEY and val and shift): insCh('M')
> 		elif (evt == Draw.MKEY and val and not shift): insCh('m')
> 		elif (evt == Draw.NKEY and val and shift): insCh('N')
> 		elif (evt == Draw.NKEY and val and not shift): insCh('n')
> 		elif (evt == Draw.OKEY and val and shift): insCh('O')
> 		elif (evt == Draw.OKEY and val and not shift): insCh('o')
> 		elif (evt == Draw.PKEY and val and shift): insCh('P')
> 		elif (evt == Draw.PKEY and val and not shift): insCh('p')
> 		elif (evt == Draw.QKEY and val and shift): insCh('Q')
> 		elif (evt == Draw.QKEY and val and not shift): insCh('q')
> 		elif (evt == Draw.RKEY and val and shift): insCh('R')
> 		elif (evt == Draw.RKEY and val and not shift): insCh('r')
> 		elif (evt == Draw.SKEY and val and shift): insCh('S')
> 		elif (evt == Draw.SKEY and val and not shift): insCh('s')
> 		elif (evt == Draw.TKEY and val and shift): insCh('T')
> 		elif (evt == Draw.TKEY and val and not shift): insCh('t')
> 		elif (evt == Draw.UKEY and val and shift): insCh('U')
> 		elif (evt == Draw.UKEY and val and not shift): insCh('u')
> 		elif (evt == Draw.VKEY and val and shift): insCh('V')
> 		elif (evt == Draw.VKEY and val and not shift): insCh('v')
> 		elif (evt == Draw.WKEY and val and shift): insCh('W')
> 		elif (evt == Draw.WKEY and val and not shift): insCh('w')
> 		elif (evt == Draw.XKEY and val and shift): insCh('X')
> 		elif (evt == Draw.XKEY and val and not shift): insCh('x')
> 		elif (evt == Draw.YKEY and val and shift): insCh('Y')
> 		elif (evt == Draw.YKEY and val and not shift): insCh('y')
> 		elif (evt == Draw.ZKEY and val and shift): insCh('Z')
> 		elif (evt == Draw.ZKEY and val and not shift): insCh('z')
> 		
>
> 		elif (evt == Draw.ONEKEY and val and shift): insCh('!')
> 		elif (evt == Draw.ONEKEY and val and not shift): insCh('1')
> 		elif (evt == Draw.TWOKEY and val and shift): insCh('@')
> 		elif (evt == Draw.TWOKEY and val and not shift): insCh('2')
> 		elif (evt == Draw.THREEKEY and val and shift): insCh('#')
> 		elif (evt == Draw.THREEKEY and val and not shift): insCh('3')
> 		elif (evt == Draw.FOURKEY and val and shift): insCh('$')
> 		elif (evt == Draw.FOURKEY and val and not shift): insCh('4')
> 		elif (evt == Draw.FIVEKEY and val and shift): insCh('%')
> 		elif (evt == Draw.FIVEKEY and val and not shift): insCh('5')
> 		elif (evt == Draw.SIXKEY and val and shift): insCh('^')
> 		elif (evt == Draw.SIXKEY and val and not shift): insCh('6')
> 		elif (evt == Draw.SEVENKEY and val and shift): insCh('&')
> 		elif (evt == Draw.SEVENKEY and val and not shift): insCh('7')
> 		elif (evt == Draw.EIGHTKEY and val and shift): insCh('*')
> 		elif (evt == Draw.EIGHTKEY and val and not shift): insCh('8')
> 		elif (evt == Draw.NINEKEY and val and shift): insCh('(')
> 		elif (evt == Draw.NINEKEY and val and not shift): insCh('9')
> 		elif (evt == Draw.ZEROKEY and val and shift): insCh(')')
> 		elif (evt == Draw.ZEROKEY and val and not shift): insCh('0')
> 			
> 		elif (evt == Draw.COMMAKEY and val and shift): insCh('<')
> 		elif (evt == Draw.COMMAKEY and val and not shift): insCh(",")
> 		
> 		elif (evt == Draw.PERIODKEY and val and shift): insCh('>')
> 		elif (evt == Draw.PERIODKEY and val and not shift): insCh(".")
> 		
> 		elif (evt == Draw.QUOTEKEY and val and shift): insCh('"')
> 		elif (evt == Draw.QUOTEKEY and val and not shift): insCh("'")
> 		
> 		elif (evt == Draw.LEFTBRACKETKEY and val and not shift): insCh('[')
> 		elif (evt == Draw.LEFTBRACKETKEY and val and shift): insCh('{')
> 		elif (evt == Draw.RIGHTBRACKETKEY and val and not shift): insCh(']')
> 		elif (evt == Draw.RIGHTBRACKETKEY and val and shift): insCh('}')
> 		elif (evt == Draw.SEMICOLONKEY and val and shift): insCh(':')
> 		elif (evt == Draw.SEMICOLONKEY and val and not shift): insCh(';')
> 		elif (evt == Draw.BACKSLASHKEY and val and shift): insCh('|')
> 		elif (evt == Draw.BACKSLASHKEY and val and not shift): insCh('\\')
> 		elif (evt == Draw.SLASHKEY and val and shift): insCh('?')
> 		elif (evt == Draw.SLASHKEY and val and not shift): insCh('/')
>
>
> 		# UP DOWN ARROW KEYS, TO TRAVERSE HISTORY
> 		elif (evt == Draw.UPARROWKEY and val):
> 			if abs(histIndex)+1 >= len(cmdBuffer):
> 				histIndex = -1
> 			histIndex -= 1
> 			while cmdBuffer[histIndex].type != 0 and abs(histIndex) <  
> len(cmdBuffer):
> 				histIndex -= 1
> 			if cmdBuffer[histIndex].type == 0: # we found one
> 				cmdBuffer[-1].cmd = cmdBuffer[histIndex].cmd
> 		
> 		# UP DOWN ARROW KEYS, TO TRAVERSE HISTORY
> 		elif (evt == Draw.DOWNARROWKEY and val):
> 			if histIndex >= -2:
> 				histIndex = -len(cmdBuffer)
> 			histIndex += 1
> 			while cmdBuffer[histIndex].type != 0 and histIndex != -2:
> 				histIndex += 1
> 			if cmdBuffer[histIndex].type == 0: # we found one
> 				cmdBuffer[-1].cmd = cmdBuffer[histIndex].cmd
>
>
> 		elif (evt == Draw.MINUSKEY and val and shift): insCh("_")
> 		elif (evt == Draw.MINUSKEY and val and not shift): insCh("-")
>
> 		elif (evt == Draw.EQUALKEY and val and shift): insCh("+")
> 		elif (evt == Draw.EQUALKEY and val and not shift): insCh("=")
> 		
> 		# SPACE
> 		elif (evt == Draw.SPACEKEY and val): insCh(' ')
> 		elif (evt == Draw.TABKEY and val): insCh('\t')
> 		
> 		elif (evt == Draw.RIGHTARROWKEY and val):
> 			cursor +=1
> 			if cursor > -1:
> 				cursor = -1
> 		elif (evt == Draw.LEFTARROWKEY and val):
> 			cursor -=1
> 		
>
> 			
> 		
> 		elif (evt == Draw.BACKSPACEKEY and val): cmdBuffer[-1].cmd = ('%s%s'  
> % (cmdBuffer[-1].cmd[:cursor-1] , cmdBuffer[-1].cmd[cursor:]))
> 		# FIXDEL
> 		elif (evt == Draw.DELKEY and val) and cursor < -1:
> 			cmdBuffer[-1].cmd = cmdBuffer[-1].cmd[:cursor] +  
> cmdBuffer[-1].cmd[cursor+1:]
> 			print cursor
> 			cursor +=1
> 		
> 		# HANDLE CAPITALS/ SHIFT KEY
> 		elif (evt == Draw.LEFTSHIFTKEY and not val): shift = 0
> 		elif (evt == Draw.RIGHTSHIFTKEY and not val): shift = 0
>
> 		elif (evt == Draw.LEFTSHIFTKEY and val): shift = 1
> 		elif (evt == Draw.RIGHTSHIFTKEY and val): shift = 1
> 		
> 		elif (evt == Draw.RETKEY and not val): enter = 0
> 		elif (evt == Draw.RETKEY and val): enter = 1
> 		
> 		elif (evt == Draw.RIGHTMOUSE and not val):
> 			choice = Draw.PupMenu('Console Data to Blender Text%t|Input Data  
> (white)|Output Data (blue)?|Error Data (red)|All Text')
> 			if choice == 1:
> 				writeCmdData(cmdBuffer, 0) # type 0 user
> 			elif choice == 2:
> 				writeCmdData(cmdBuffer, 1) # type 1 user output
> 			elif choice == 3:
> 				writeCmdData(cmdBuffer, 2) # type 2 errors
> 			elif choice == 4:
> 				writeCmdData(cmdBuffer, 3) # All
>
> 		Draw.Redraw()
> 		
> 		print 'redraw', evt
>
>
> 	# This recieves the event index, call a function from here depending  
> on the event.
> 	def handle_button_event(evt):
> 		pass
>
>
> 	def draw_gui():
> 		global cmdBuffer
> 		global enter
> 		global shift
> 		global cursor
> 		global histIndex
> 		lineHeight = 16
> 		# find the width of the widest button
> 		fontsize = "normal"
> 		
> 		# Check for the neter kay hit
> 		if enter:
> 			if Window.GetKeyQualifiers() & Window.Qual.CTRL: # HOLDING DOWN  
> SHIFT, GO TO NEXT LINE.
> 				cmdBuffer.append(cmdLine(' ', 0, 0))
> 			else:
> 				# Multiline code will still run with 1 line,
> 				if cmdBuffer[-1].cmd != ' ':
> 					multiLineCode = [cmdBuffer[-1].cmd]
> 				else:
> 					multiLineCode = []
> 				cmdBuffer[-1].exe = 1
> 				i = 2
> 				while cmdBuffer[-i].exe == 0:
> 					if cmdBuffer[-i].cmd != ' ':
> 						multiLineCode.append(cmdBuffer[-i].cmd)
> 					# Mark as executed
> 					cmdBuffer[-i].exe = 1
> 					i+=1
> 				multiLineCode.reverse()
> 				run('\n'.join(multiLineCode))
> 			
> 			cursor = -1 # Reset cursor
> 			histIndex = -1
> 		
> 		# Clear the screen
> 		BGL.glClearColor(0.0, 0.0, 0.0, 1.0)
> 		BGL.glClear(BGL.GL_COLOR_BUFFER_BIT)         # use it to clear the  
> color buffer
> 		
> 		# Draw cursor location colour
> 		cmd2curWidth = Draw.GetStringWidth(cmdBuffer[-1].cmd[:cursor],  
> fontsize)
> 		BGL.glColor3f(0.8, 0.2, 0.2)
> 		BGL.glRecti(cmd2curWidth-1,12,cmd2curWidth+1, 28)
> 		
> 		BGL.glColor3f(1,1,1)
> 		# Draw the set of cammands to the buffer
> 		Ln = len(cmdBuffer)
> 		while Ln:
>
> 			if cmdBuffer[-Ln].type == 0:
> 				BGL.glColor3f(1, 1, 1)
> 			elif cmdBuffer[-Ln].type == 1:
> 				BGL.glColor3f(.3, .3, 1)
> 			elif cmdBuffer[-Ln].type == 2:
> 				BGL.glColor3f(1.0, 0, 0)
> 			else:
> 				BGL.glColor3f(1, 1, 0)
> 			
> 			BGL.glRasterPos2i(0, lineHeight*Ln)
> 			
> 			Draw.Text('%s' % cmdBuffer[-Ln].cmd  )
> 			Ln -= 1
> 		
> 	 
> #---------------------------------------------------------------------- 
> --------#
> 	#                    register the event handling code, GUI             
>          #
> 	 
> #---------------------------------------------------------------------- 
> --------#
> 	Draw.Register(draw_gui, handle_event, handle_button_event)
>
> main()
> _______________________________________________
> Bf-committers mailing list
> Bf-committers at projects.blender.org
> http://projects.blender.org/mailman/listinfo/bf-committers
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: text/enriched
Size: 15004 bytes
Desc: not available
Url : http://projects.blender.org/pipermail/bf-committers/attachments/20050324/86f6ae2a/attachment-0001.bin


More information about the Bf-committers mailing list