mirror of
				https://github.com/python/cpython.git
				synced 2025-10-31 05:31:20 +00:00 
			
		
		
		
	Created Vedit.py, the video editor. This uses the classes in Viewer.py.
Viewer.py in turn requires changes to VFile.py (unfortunately that file is now a complete mess...).
This commit is contained in:
		
							parent
							
								
									e1b4d7ce14
								
							
						
					
					
						commit
						9ee7e15966
					
				
					 6 changed files with 1080 additions and 217 deletions
				
			
		|  | @ -100,6 +100,10 @@ Vtime.py	(unrelated to vtime!!!) Copy a video file, | ||||||
| 		manipulating the time codes (e.g. faster/slower, or | 		manipulating the time codes (e.g. faster/slower, or | ||||||
| 		regenerate time codes, or drop frames too close apart) | 		regenerate time codes, or drop frames too close apart) | ||||||
| 
 | 
 | ||||||
|  | Vedit.py	interactive video editing program | ||||||
|  | 
 | ||||||
|  | Viewer.py	two viewer classes used by Vedit | ||||||
|  | 
 | ||||||
| 
 | 
 | ||||||
| The following are C programs, either for efficiency or because they | The following are C programs, either for efficiency or because they | ||||||
| need to link with a C library: | need to link with a C library: | ||||||
|  |  | ||||||
|  | @ -52,116 +52,12 @@ def conv_rgb8(rgb,d1,d2): | ||||||
| # xorigin, yorigin | # xorigin, yorigin | ||||||
| # fallback | # fallback | ||||||
| 
 | 
 | ||||||
| class VinFile: |  | ||||||
| 
 | 
 | ||||||
| 	# init() and initfp() raise Error if the header is bad. |  | ||||||
| 	# init() raises whatever open() raises if the file can't be opened. |  | ||||||
| 
 | 
 | ||||||
| 	def init(self, filename): | # XXX it's a total mess now -- VFile is a new base class | ||||||
| 		if filename == '-': | # XXX to support common functionality (e.g. showframe) | ||||||
| 			return self.initfp(sys.stdin, filename) |  | ||||||
| 		return self.initfp(open(filename, 'r'), filename) |  | ||||||
| 
 |  | ||||||
| 	def initfp(self, fp, filename): |  | ||||||
| 		self.colormapinited = 0 |  | ||||||
| 		self.magnify = 1.0 |  | ||||||
| 		self.xorigin = self.yorigin = 0 |  | ||||||
| 		self.fallback = 1 |  | ||||||
| 		self.skipchrom = 0 |  | ||||||
| 		self.fp = fp |  | ||||||
| 		self.filename = filename |  | ||||||
| 		self.quiet = 0 |  | ||||||
| 		# |  | ||||||
| 		line = self.fp.readline() |  | ||||||
| 		if line == 'CMIF video 1.0\n': |  | ||||||
| 			self.version = 1.0 |  | ||||||
| 		elif line == 'CMIF video 2.0\n': |  | ||||||
| 			self.version = 2.0 |  | ||||||
| 		elif line == 'CMIF video 3.0\n': |  | ||||||
| 			self.version = 3.0 |  | ||||||
| 		else: |  | ||||||
| 			raise Error, self.filename + ': bad video format' |  | ||||||
| 		# |  | ||||||
| 		if self.version < 2.0: |  | ||||||
| 			self.c0bits, self.c1bits, self.c2bits = 8, 0, 0 |  | ||||||
| 			self.chrompack = 0 |  | ||||||
| 			self.offset = 0 |  | ||||||
| 			self.format = 'grey' |  | ||||||
| 		elif self.version == 2.0: |  | ||||||
| 			line = self.fp.readline() |  | ||||||
| 			try: |  | ||||||
| 				self.c0bits, self.c1bits, self.c2bits, \ |  | ||||||
| 					self.chrompack = eval(line[:-1]) |  | ||||||
| 				if self.c1bits or self.c2bits: |  | ||||||
| 					self.format = 'yiq' |  | ||||||
| 				else: |  | ||||||
| 					self.format = 'grey' |  | ||||||
| 				self.offset = 0 |  | ||||||
| 			except: |  | ||||||
| 				raise Error, \ |  | ||||||
| 				  self.filename + ': bad 2.0 color info' |  | ||||||
| 		elif self.version == 3.0: |  | ||||||
| 			line = self.fp.readline() |  | ||||||
| 			try: |  | ||||||
| 				self.format, rest = eval(line[:-1]) |  | ||||||
| 				if self.format == 'rgb': |  | ||||||
| 					self.offset = 0 |  | ||||||
| 					self.c0bits = 0 |  | ||||||
| 					self.c1bits = 0 |  | ||||||
| 					self.c2bits = 0 |  | ||||||
| 					self.chrompack = 0 |  | ||||||
| 				elif self.format == 'grey': |  | ||||||
| 					self.offset = 0 |  | ||||||
| 					self.c0bits = rest |  | ||||||
| 					self.c1bits = self.c2bits = \ |  | ||||||
| 						self.chrompack = 0 |  | ||||||
| 				else: |  | ||||||
| 					self.c0bits,self.c1bits,self.c2bits,\ |  | ||||||
| 					  self.chrompack,self.offset = rest |  | ||||||
| 			except: |  | ||||||
| 				raise Error, \ |  | ||||||
| 					self.filename + ': bad 3.0 color info' |  | ||||||
| 
 |  | ||||||
| 		try: |  | ||||||
| 			self.convcolor = eval('conv_'+self.format) |  | ||||||
| 		except: |  | ||||||
| 			raise Error, \ |  | ||||||
| 			  self.filename + ': unknown colorsys ' + self.format |  | ||||||
| 		# |  | ||||||
| 		line = self.fp.readline() |  | ||||||
| 		try: |  | ||||||
| 			x = eval(line[:-1]) |  | ||||||
| 			if self.version > 1.0 or len(x) == 3: |  | ||||||
| 				self.width, self.height, self.packfactor = x |  | ||||||
| 				if self.packfactor == 0: |  | ||||||
| 					self.format = 'rgb' |  | ||||||
| 			else: |  | ||||||
| 				sef.width, self.height = x |  | ||||||
| 				self.packfactor = 2 |  | ||||||
| 		except: |  | ||||||
| 			raise Error, self.filename + ': bad (w,h,pf) info' |  | ||||||
| 		self.frameno = 0 |  | ||||||
| 		self.framecache = [] |  | ||||||
| 		self.hascache = 0 |  | ||||||
| 		# |  | ||||||
| 		return self |  | ||||||
| 
 |  | ||||||
| 	def warmcache(self): |  | ||||||
| 		if self.hascache: return |  | ||||||
| 		n = 0 |  | ||||||
| 		try: |  | ||||||
| 			while 1: |  | ||||||
| 				void = self.skipnextframe() |  | ||||||
| 				n = n + 1 |  | ||||||
| 		except EOFError: |  | ||||||
| 			pass |  | ||||||
| 		if not self.hascache: |  | ||||||
| 			raise Error, 'Cannot warm cache' |  | ||||||
| 
 |  | ||||||
| 	def close(self): |  | ||||||
| 		self.fp.close() |  | ||||||
| 		self.fp = None |  | ||||||
| 
 | 
 | ||||||
|  | class VFile: | ||||||
| 
 | 
 | ||||||
| 	# | 	# | ||||||
| 	# getinfo returns all info pertaining to a film. The returned tuple | 	# getinfo returns all info pertaining to a film. The returned tuple | ||||||
|  | @ -179,96 +75,12 @@ def reopen(self): | ||||||
| 		self.fp.seek(0) | 		self.fp.seek(0) | ||||||
| 		x = self.initfp(self.fp, self.filename) | 		x = self.initfp(self.fp, self.filename) | ||||||
| 
 | 
 | ||||||
| 	def rewind(self): | 	def setconvcolor(self): | ||||||
| 		if self.hascache: |  | ||||||
| 			self.frameno = 0 |  | ||||||
| 		else: |  | ||||||
| 			self.reopen() |  | ||||||
| 
 |  | ||||||
| 	def position(self): |  | ||||||
| 		if self.frameno >= len(self.framecache): |  | ||||||
| 			raise EOFError |  | ||||||
| 		self.fp.seek(self.framecache[self.frameno][0]) |  | ||||||
| 
 |  | ||||||
| 	# getnextframe() raises EOFError (built-in) if there is no next frame, |  | ||||||
| 	# or if the next frame is broken. |  | ||||||
| 	# So to getnextframeheader(), getnextframedata() and skipnextframe(). |  | ||||||
| 
 |  | ||||||
| 	def getnextframe(self): |  | ||||||
| 		time, size, chromsize = self.getnextframeheader() |  | ||||||
| 		data, chromdata = self.getnextframedata(size, chromsize) |  | ||||||
| 		return time, data, chromdata |  | ||||||
| 
 |  | ||||||
| 	def getnextframedata(self, size, chromsize): |  | ||||||
| 		if self.hascache: |  | ||||||
| 			self.position() |  | ||||||
| 		self.frameno = self.frameno + 1 |  | ||||||
| 		data = self.fp.read(size) |  | ||||||
| 		if len(data) <> size: raise EOFError |  | ||||||
| 		if chromsize: |  | ||||||
| 			chromdata = self.fp.read(chromsize) |  | ||||||
| 			if len(chromdata) <> chromsize: raise EOFError |  | ||||||
| 		else: |  | ||||||
| 			chromdata = None |  | ||||||
| 		# |  | ||||||
| 		return data, chromdata |  | ||||||
| 
 |  | ||||||
| 	def skipnextframe(self): |  | ||||||
| 		time, size, chromsize = self.getnextframeheader() |  | ||||||
| 		self.skipnextframedata(size, chromsize) |  | ||||||
| 		return time |  | ||||||
| 
 |  | ||||||
| 	def skipnextframedata(self, size, chromsize): |  | ||||||
| 		if self.hascache: |  | ||||||
| 			self.frameno = self.frameno + 1 |  | ||||||
| 			return |  | ||||||
| 		# Note that this won't raise EOFError for a partial frame. |  | ||||||
| 		try: | 		try: | ||||||
| 			self.fp.seek(size + chromsize, 1) # Relative seek | 			self.convcolor = eval('conv_'+self.format) | ||||||
| 		except: | 		except: | ||||||
| 			# Assume it's a pipe -- read the data to discard it | 			raise Error, \ | ||||||
| 			dummy = self.fp.read(size + chromsize) | 			  self.filename + ': unknown colorsys ' + self.format | ||||||
| 
 |  | ||||||
| 	def getnextframeheader(self): |  | ||||||
| 		if self.hascache: |  | ||||||
| 			if self.frameno >= len(self.framecache): |  | ||||||
| 				raise EOFError |  | ||||||
| 			return self.framecache[self.frameno][1] |  | ||||||
| 		line = self.fp.readline() |  | ||||||
| 		if not line: |  | ||||||
| 			self.hascache = 1 |  | ||||||
| 			raise EOFError |  | ||||||
| 		# |  | ||||||
| 		w, h, pf = self.width, self.height, self.packfactor |  | ||||||
| 		try: |  | ||||||
| 			x = eval(line[:-1]) |  | ||||||
| 			if type(x) in (type(0), type(0.0)): |  | ||||||
| 				time = x |  | ||||||
| 				if pf == 0: |  | ||||||
| 					size = w * h * 4 |  | ||||||
| 				else: |  | ||||||
| 					size = (w/pf) * (h/pf) |  | ||||||
| 			elif len(x) == 2: |  | ||||||
| 				time, size = x |  | ||||||
| 				cp = self.chrompack |  | ||||||
| 				if cp: |  | ||||||
| 					cw = (w + cp - 1) / cp |  | ||||||
| 					ch = (h + cp - 1) / cp |  | ||||||
| 					chromsize = 2 * cw * ch |  | ||||||
| 				else: |  | ||||||
| 					chromsize = 0 |  | ||||||
| 			else: |  | ||||||
| 				time, size, chromsize = x |  | ||||||
| 		except: |  | ||||||
| 			raise Error, self.filename + ': bad frame header' |  | ||||||
| 		cdata = (self.fp.tell(), (time, size, chromsize)) |  | ||||||
| 		self.framecache.append(cdata) |  | ||||||
| 		return time, size, chromsize |  | ||||||
| 
 |  | ||||||
| 	def shownextframe(self): |  | ||||||
| 		time, data, chromdata = self.getnextframe() |  | ||||||
| 		self.showframe(data, chromdata) |  | ||||||
| 		return time |  | ||||||
| 
 | 
 | ||||||
| 	def showframe(self, data, chromdata): | 	def showframe(self, data, chromdata): | ||||||
| 		w, h, pf = self.width, self.height, self.packfactor | 		w, h, pf = self.width, self.height, self.packfactor | ||||||
|  | @ -369,6 +181,205 @@ def initcmap(self): | ||||||
| 						gl.mapcolor(index, r, g, b) | 						gl.mapcolor(index, r, g, b) | ||||||
| 		void = gl.gflush() | 		void = gl.gflush() | ||||||
| 
 | 
 | ||||||
|  | 	 | ||||||
|  | 
 | ||||||
|  | class VinFile(VFile): | ||||||
|  | 
 | ||||||
|  | 	# init() and initfp() raise Error if the header is bad. | ||||||
|  | 	# init() raises whatever open() raises if the file can't be opened. | ||||||
|  | 
 | ||||||
|  | 	def init(self, filename): | ||||||
|  | 		if filename == '-': | ||||||
|  | 			return self.initfp(sys.stdin, filename) | ||||||
|  | 		return self.initfp(open(filename, 'r'), filename) | ||||||
|  | 
 | ||||||
|  | 	def initfp(self, fp, filename): | ||||||
|  | 		self.colormapinited = 0 | ||||||
|  | 		self.magnify = 1.0 | ||||||
|  | 		self.xorigin = self.yorigin = 0 | ||||||
|  | 		self.fallback = 1 | ||||||
|  | 		self.skipchrom = 0 | ||||||
|  | 		self.fp = fp | ||||||
|  | 		self.filename = filename | ||||||
|  | 		self.quiet = 0 | ||||||
|  | 		# | ||||||
|  | 		line = self.fp.readline() | ||||||
|  | 		if line == 'CMIF video 1.0\n': | ||||||
|  | 			self.version = 1.0 | ||||||
|  | 		elif line == 'CMIF video 2.0\n': | ||||||
|  | 			self.version = 2.0 | ||||||
|  | 		elif line == 'CMIF video 3.0\n': | ||||||
|  | 			self.version = 3.0 | ||||||
|  | 		else: | ||||||
|  | 			raise Error, self.filename + ': bad video format' | ||||||
|  | 		# | ||||||
|  | 		if self.version < 2.0: | ||||||
|  | 			self.c0bits, self.c1bits, self.c2bits = 8, 0, 0 | ||||||
|  | 			self.chrompack = 0 | ||||||
|  | 			self.offset = 0 | ||||||
|  | 			self.format = 'grey' | ||||||
|  | 		elif self.version == 2.0: | ||||||
|  | 			line = self.fp.readline() | ||||||
|  | 			try: | ||||||
|  | 				self.c0bits, self.c1bits, self.c2bits, \ | ||||||
|  | 					self.chrompack = eval(line[:-1]) | ||||||
|  | 				if self.c1bits or self.c2bits: | ||||||
|  | 					self.format = 'yiq' | ||||||
|  | 				else: | ||||||
|  | 					self.format = 'grey' | ||||||
|  | 				self.offset = 0 | ||||||
|  | 			except: | ||||||
|  | 				raise Error, \ | ||||||
|  | 				  self.filename + ': bad 2.0 color info' | ||||||
|  | 		elif self.version == 3.0: | ||||||
|  | 			line = self.fp.readline() | ||||||
|  | 			try: | ||||||
|  | 				self.format, rest = eval(line[:-1]) | ||||||
|  | 				if self.format == 'rgb': | ||||||
|  | 					self.offset = 0 | ||||||
|  | 					self.c0bits = 0 | ||||||
|  | 					self.c1bits = 0 | ||||||
|  | 					self.c2bits = 0 | ||||||
|  | 					self.chrompack = 0 | ||||||
|  | 				elif self.format == 'grey': | ||||||
|  | 					self.offset = 0 | ||||||
|  | 					self.c0bits = rest | ||||||
|  | 					self.c1bits = self.c2bits = \ | ||||||
|  | 						self.chrompack = 0 | ||||||
|  | 				else: | ||||||
|  | 					self.c0bits,self.c1bits,self.c2bits,\ | ||||||
|  | 					  self.chrompack,self.offset = rest | ||||||
|  | 			except: | ||||||
|  | 				raise Error, \ | ||||||
|  | 					self.filename + ': bad 3.0 color info' | ||||||
|  | 
 | ||||||
|  | 		self.setconvcolor() | ||||||
|  | 		# | ||||||
|  | 		line = self.fp.readline() | ||||||
|  | 		try: | ||||||
|  | 			x = eval(line[:-1]) | ||||||
|  | 			if self.version > 1.0 or len(x) == 3: | ||||||
|  | 				self.width, self.height, self.packfactor = x | ||||||
|  | 				if self.packfactor == 0: | ||||||
|  | 					self.format = 'rgb' | ||||||
|  | 			else: | ||||||
|  | 				sef.width, self.height = x | ||||||
|  | 				self.packfactor = 2 | ||||||
|  | 		except: | ||||||
|  | 			raise Error, self.filename + ': bad (w,h,pf) info' | ||||||
|  | 		self.frameno = 0 | ||||||
|  | 		self.framecache = [] | ||||||
|  | 		self.hascache = 0 | ||||||
|  | 		# | ||||||
|  | 		return self | ||||||
|  | 
 | ||||||
|  | 	def warmcache(self): | ||||||
|  | 		if self.hascache: return | ||||||
|  | 		n = 0 | ||||||
|  | 		try: | ||||||
|  | 			while 1: | ||||||
|  | 				void = self.skipnextframe() | ||||||
|  | 				n = n + 1 | ||||||
|  | 		except EOFError: | ||||||
|  | 			pass | ||||||
|  | 		if not self.hascache: | ||||||
|  | 			raise Error, 'Cannot warm cache' | ||||||
|  | 
 | ||||||
|  | 	def close(self): | ||||||
|  | 		self.fp.close() | ||||||
|  | 		self.fp = None | ||||||
|  | 
 | ||||||
|  | 	def rewind(self): | ||||||
|  | 		if self.hascache: | ||||||
|  | 			self.frameno = 0 | ||||||
|  | 		else: | ||||||
|  | 			self.reopen() | ||||||
|  | 
 | ||||||
|  | 	def position(self): | ||||||
|  | 		if self.frameno >= len(self.framecache): | ||||||
|  | 			raise EOFError | ||||||
|  | 		self.fp.seek(self.framecache[self.frameno][0]) | ||||||
|  | 
 | ||||||
|  | 	# getnextframe() raises EOFError (built-in) if there is no next frame, | ||||||
|  | 	# or if the next frame is broken. | ||||||
|  | 	# So to getnextframeheader(), getnextframedata() and skipnextframe(). | ||||||
|  | 
 | ||||||
|  | 	def getnextframe(self): | ||||||
|  | 		time, size, chromsize = self.getnextframeheader() | ||||||
|  | 		data, chromdata = self.getnextframedata(size, chromsize) | ||||||
|  | 		return time, data, chromdata | ||||||
|  | 
 | ||||||
|  | 	def getnextframedata(self, size, chromsize): | ||||||
|  | 		if self.hascache: | ||||||
|  | 			self.position() | ||||||
|  | 		self.frameno = self.frameno + 1 | ||||||
|  | 		data = self.fp.read(size) | ||||||
|  | 		if len(data) <> size: raise EOFError | ||||||
|  | 		if chromsize: | ||||||
|  | 			chromdata = self.fp.read(chromsize) | ||||||
|  | 			if len(chromdata) <> chromsize: raise EOFError | ||||||
|  | 		else: | ||||||
|  | 			chromdata = None | ||||||
|  | 		# | ||||||
|  | 		return data, chromdata | ||||||
|  | 
 | ||||||
|  | 	def skipnextframe(self): | ||||||
|  | 		time, size, chromsize = self.getnextframeheader() | ||||||
|  | 		self.skipnextframedata(size, chromsize) | ||||||
|  | 		return time | ||||||
|  | 
 | ||||||
|  | 	def skipnextframedata(self, size, chromsize): | ||||||
|  | 		if self.hascache: | ||||||
|  | 			self.frameno = self.frameno + 1 | ||||||
|  | 			return | ||||||
|  | 		# Note that this won't raise EOFError for a partial frame. | ||||||
|  | 		try: | ||||||
|  | 			self.fp.seek(size + chromsize, 1) # Relative seek | ||||||
|  | 		except: | ||||||
|  | 			# Assume it's a pipe -- read the data to discard it | ||||||
|  | 			dummy = self.fp.read(size + chromsize) | ||||||
|  | 
 | ||||||
|  | 	def getnextframeheader(self): | ||||||
|  | 		if self.hascache: | ||||||
|  | 			if self.frameno >= len(self.framecache): | ||||||
|  | 				raise EOFError | ||||||
|  | 			return self.framecache[self.frameno][1] | ||||||
|  | 		line = self.fp.readline() | ||||||
|  | 		if not line: | ||||||
|  | 			self.hascache = 1 | ||||||
|  | 			raise EOFError | ||||||
|  | 		# | ||||||
|  | 		w, h, pf = self.width, self.height, self.packfactor | ||||||
|  | 		try: | ||||||
|  | 			x = eval(line[:-1]) | ||||||
|  | 			if type(x) in (type(0), type(0.0)): | ||||||
|  | 				time = x | ||||||
|  | 				if pf == 0: | ||||||
|  | 					size = w * h * 4 | ||||||
|  | 				else: | ||||||
|  | 					size = (w/pf) * (h/pf) | ||||||
|  | 			elif len(x) == 2: | ||||||
|  | 				time, size = x | ||||||
|  | 				cp = self.chrompack | ||||||
|  | 				if cp: | ||||||
|  | 					cw = (w + cp - 1) / cp | ||||||
|  | 					ch = (h + cp - 1) / cp | ||||||
|  | 					chromsize = 2 * cw * ch | ||||||
|  | 				else: | ||||||
|  | 					chromsize = 0 | ||||||
|  | 			else: | ||||||
|  | 				time, size, chromsize = x | ||||||
|  | 		except: | ||||||
|  | 			raise Error, self.filename + ': bad frame header' | ||||||
|  | 		cdata = (self.fp.tell(), (time, size, chromsize)) | ||||||
|  | 		self.framecache.append(cdata) | ||||||
|  | 		return time, size, chromsize | ||||||
|  | 
 | ||||||
|  | 	def shownextframe(self): | ||||||
|  | 		time, data, chromdata = self.getnextframe() | ||||||
|  | 		self.showframe(data, chromdata) | ||||||
|  | 		return time | ||||||
|  | 
 | ||||||
| # | # | ||||||
| # A set of routines to grab images from windows | # A set of routines to grab images from windows | ||||||
| # | # | ||||||
|  | @ -417,7 +428,7 @@ def grab_hsv(w, h, pf): | ||||||
| # Notably it will accept almost any garbage and write it to the video | # Notably it will accept almost any garbage and write it to the video | ||||||
| # output file | # output file | ||||||
| # | # | ||||||
| class VoutFile: | class VoutFile(VFile): | ||||||
| 	def init(self, filename): | 	def init(self, filename): | ||||||
| 		if filename == '-': | 		if filename == '-': | ||||||
| 			return self.initfp(sys.stdout, filename) | 			return self.initfp(sys.stdout, filename) | ||||||
|  | @ -434,21 +445,21 @@ def initfp(self, fp, filename): | ||||||
| 		self.offset = 0 | 		self.offset = 0 | ||||||
| 		self.chrompack = 0 | 		self.chrompack = 0 | ||||||
| 		self.headerwritten = 0 | 		self.headerwritten = 0 | ||||||
|  | 		self.quiet = 0 | ||||||
|  | 		self.magnify = 1 | ||||||
|  | 		self.setconvcolor() | ||||||
|  | 		self.xorigin = self.yorigin = 0 | ||||||
| 		return self | 		return self | ||||||
| 
 | 
 | ||||||
| 	def close(self): | 	def close(self): | ||||||
| 		self.fp.close() | 		self.fp.close() | ||||||
| 		x = self.initfp(None, None) | 		x = self.initfp(None, None) | ||||||
| 
 | 
 | ||||||
| 	def getinfo(self): |  | ||||||
| 		return (self.format, self.width, self.height, self.packfactor,\ |  | ||||||
| 			  self.c0bits, self.c1bits, self.c2bits, self.offset, \ |  | ||||||
| 			  self.chrompack) |  | ||||||
| 
 |  | ||||||
| 	def setinfo(self, values): | 	def setinfo(self, values): | ||||||
| 		self.format, self.width, self.height, self.packfactor,\ | 		self.format, self.width, self.height, self.packfactor,\ | ||||||
| 			  self.c0bits, self.c1bits, self.c2bits, self.offset, \ | 			  self.c0bits, self.c1bits, self.c2bits, self.offset, \ | ||||||
| 			  self.chrompack = values | 			  self.chrompack = values | ||||||
|  | 		self.setconvcolor() | ||||||
| 
 | 
 | ||||||
| 	def writeheader(self): | 	def writeheader(self): | ||||||
| 		self.headerwritten = 1 | 		self.headerwritten = 1 | ||||||
|  |  | ||||||
							
								
								
									
										247
									
								
								Demo/sgi/video/Vedit.py
									
										
									
									
									
										Executable file
									
								
							
							
						
						
									
										247
									
								
								Demo/sgi/video/Vedit.py
									
										
									
									
									
										Executable file
									
								
							|  | @ -0,0 +1,247 @@ | ||||||
|  | #! /ufs/guido/bin/sgi/python | ||||||
|  | 
 | ||||||
|  | # Edit CMIF movies interactively -- copy one or more files to an output file | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | # Possibilities: | ||||||
|  | # | ||||||
|  | # - convert between formats (grey, rgb, rgb8, ...) | ||||||
|  | # - change size | ||||||
|  | # - cut out a given area of the image | ||||||
|  | # - change time base (a la Vtime) | ||||||
|  | # - skip stretches of frames | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | import sys | ||||||
|  | import os | ||||||
|  | import gl, GL, DEVICE | ||||||
|  | import fl, FL | ||||||
|  | import flp | ||||||
|  | import Viewer | ||||||
|  | import getopt | ||||||
|  | import string | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | def main(): | ||||||
|  | 	qsize = 20 | ||||||
|  | 	opts, args = getopt.getopt(sys.argv[1:], 'q:') | ||||||
|  | 	for o, a in opts: | ||||||
|  | 		if o == '-q': | ||||||
|  | 			qsize = string.atoi(a) | ||||||
|  | 	ed = Editor().init(qsize) | ||||||
|  | 	if args[0:]: | ||||||
|  | 		ed.open_input(args[0]) | ||||||
|  | 	if args[1:]: | ||||||
|  | 		ed.open_output(args[1]) | ||||||
|  | 	while 1: | ||||||
|  | 		dummy = fl.do_forms() | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | class Editor: | ||||||
|  | 
 | ||||||
|  | 	def init(self, qsize): | ||||||
|  | 		self.qsize = qsize | ||||||
|  | 		self.vin = None | ||||||
|  | 		self.vout = None | ||||||
|  | 		self.ifile = '' | ||||||
|  | 		self.ofile = '' | ||||||
|  | 		formdef = flp.parse_form('VeditForm', 'form') | ||||||
|  | 		flp.create_full_form(self, formdef) | ||||||
|  | 		self.form.show_form(FL.PLACE_SIZE, FL.TRUE, 'Vedit') | ||||||
|  | 		fl.set_event_call_back(self.do_event) | ||||||
|  | 		return self | ||||||
|  | 
 | ||||||
|  | 	def do_event(self, (dev, val)): | ||||||
|  | 		if dev == DEVICE.REDRAW: | ||||||
|  | 			if self.vin: | ||||||
|  | 				self.vin.redraw(val) | ||||||
|  | 			if self.vout: | ||||||
|  | 				self.vout.redraw(val) | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | 	def iocheck(self): | ||||||
|  | 		self.msg('') | ||||||
|  | 		if self.vin == None and self.vout == None: | ||||||
|  | 			self.err('Please open input and output files first') | ||||||
|  | 			return 0 | ||||||
|  | 		return self.icheck() and self.ocheck() | ||||||
|  | 
 | ||||||
|  | 	def icheck(self): | ||||||
|  | 		self.msg('') | ||||||
|  | 		if self.vin == None: | ||||||
|  | 			self.err('Please open an input file first') | ||||||
|  | 			return 0 | ||||||
|  | 		return 1 | ||||||
|  | 
 | ||||||
|  | 	def ocheck(self): | ||||||
|  | 		self.msg('') | ||||||
|  | 		if self.vout == None: | ||||||
|  | 			self.err('Please open an output file first') | ||||||
|  | 			return 0 | ||||||
|  | 		return 1 | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | 	def cb_in_new(self, args): | ||||||
|  | 		self.msg('') | ||||||
|  | 		hd, tl = os.path.split(self.ifile) | ||||||
|  | 		filename = fl.file_selector('Input video file', hd, '', tl) | ||||||
|  | 		if not filename: return | ||||||
|  | 		self.open_input(filename) | ||||||
|  | 
 | ||||||
|  | 	def cb_in_close(self, args): | ||||||
|  | 		self.msg('') | ||||||
|  | 		self.close_input() | ||||||
|  | 
 | ||||||
|  | 	def cb_in_skip(self, args): | ||||||
|  | 		if not self.icheck(): return | ||||||
|  | 		if not self.vin.get(): self.err('End of input file') | ||||||
|  | 		self.ishow() | ||||||
|  | 
 | ||||||
|  | 	def cb_in_back(self, args): | ||||||
|  | 		if not self.icheck(): return | ||||||
|  | 		if not self.vin.backup(): self.err('Input buffer exhausted') | ||||||
|  | 		self.ishow() | ||||||
|  | 
 | ||||||
|  | 	def cb_in_rewind(self, args): | ||||||
|  | 		if not self.icheck(): return | ||||||
|  | 		self.vin.rewind() | ||||||
|  | 		self.ishow() | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | 	def cb_copy(self, args): | ||||||
|  | 		if not self.iocheck(): return | ||||||
|  | 		data = self.vin.get() | ||||||
|  | 		if data: | ||||||
|  | 			if self.vout.getinfo() <> self.vin.getinfo(): | ||||||
|  | 				print 'Copying info...' | ||||||
|  | 				self.vout.setinfo(self.vin.getinfo()) | ||||||
|  | 			self.vout.put(data) | ||||||
|  | 			self.oshow() | ||||||
|  | 		self.ishow() | ||||||
|  | 
 | ||||||
|  | 	def cb_uncopy(self, args): | ||||||
|  | 		if not self.iocheck(): return | ||||||
|  | 		if not self.vout.backup(): | ||||||
|  | 			self.err('Output buffer exhausted') | ||||||
|  | 			return | ||||||
|  | 		self.oshow() | ||||||
|  | 		if not self.vin.backup(): | ||||||
|  | 			self.err('Input buffer exhausted') | ||||||
|  | 			return | ||||||
|  | 		self.ishow() | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | 	def cb_out_new(self, args): | ||||||
|  | 		self.msg('') | ||||||
|  | 		hd, tl = os.path.split(self.ofile) | ||||||
|  | 		filename = fl.file_selector('Output video file', hd, '', tl) | ||||||
|  | 		if not filename: return | ||||||
|  | 		self.open_output(filename) | ||||||
|  | 
 | ||||||
|  | 	def cb_out_close(self, args): | ||||||
|  | 		self.msg('') | ||||||
|  | 		self.close_output() | ||||||
|  | 
 | ||||||
|  | 	def cb_out_skip(self, arg): | ||||||
|  | 		if not self.ocheck(): return | ||||||
|  | 		if not self.vout.forward(): self.err('Output buffer exhausted') | ||||||
|  | 		self.oshow() | ||||||
|  | 		 | ||||||
|  | 	def cb_out_back(self, args): | ||||||
|  | 		if not self.ocheck(): return | ||||||
|  | 		if not self.vout.backup(): self.err('Output buffer exhausted') | ||||||
|  | 		self.oshow() | ||||||
|  | 
 | ||||||
|  | 	def cb_out_rewind(self, args): | ||||||
|  | 		if not self.ocheck(): return | ||||||
|  | 		self.vout.rewind() | ||||||
|  | 		self.oshow() | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | 	def cb_quit(self, args): | ||||||
|  | 		self.close_input() | ||||||
|  | 		self.close_output() | ||||||
|  | 		sys.exit(0) | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | 	def open_input(self, filename): | ||||||
|  | 		self.ifile = filename | ||||||
|  | 		basename = os.path.split(filename)[1] | ||||||
|  | 		title = 'in: ' + basename | ||||||
|  | 		try: | ||||||
|  | 			vin = Viewer.InputViewer().init(filename, \ | ||||||
|  | 				title, self.qsize) | ||||||
|  | 		except: | ||||||
|  | 			self.err('Can\'t open input file', filename) | ||||||
|  | 			return | ||||||
|  | 		self.close_input() | ||||||
|  | 		self.vin = vin | ||||||
|  | 		self.in_file.label = basename | ||||||
|  | 		self.ishow() | ||||||
|  | 
 | ||||||
|  | 	def close_input(self): | ||||||
|  | 		if self.vin: | ||||||
|  | 			self.msg('Closing input file...') | ||||||
|  | 			self.vin.close() | ||||||
|  | 		self.msg('') | ||||||
|  | 		self.vin = None | ||||||
|  | 		self.in_file.label = '(none)' | ||||||
|  | 		self.format('in') | ||||||
|  | 
 | ||||||
|  | 	def ishow(self): | ||||||
|  | 		self.vin.show() | ||||||
|  | 		self.format('in') | ||||||
|  | 
 | ||||||
|  | 	def open_output(self, filename): | ||||||
|  | 		self.ofile = filename | ||||||
|  | 		basename = os.path.split(filename)[1] | ||||||
|  | 		title = 'out: ' + basename | ||||||
|  | 		try: | ||||||
|  | 			vout = Viewer.OutputViewer().init(filename, \ | ||||||
|  | 				title, self.qsize) | ||||||
|  | 		except: | ||||||
|  | 			self.err('Can\'t open output file', filename) | ||||||
|  | 			return | ||||||
|  | 		self.close_output() | ||||||
|  | 		self.vout = vout | ||||||
|  | 		self.out_file.label = basename | ||||||
|  | 		if self.vin: | ||||||
|  | 			self.vout.setinfo(self.vin.getinfo()) | ||||||
|  | 			self.oshow() | ||||||
|  | 
 | ||||||
|  | 	def close_output(self): | ||||||
|  | 		if self.vout: | ||||||
|  | 			self.msg('Closing output file...') | ||||||
|  | 			self.vout.close() | ||||||
|  | 		self.msg('') | ||||||
|  | 		self.vout = None | ||||||
|  | 		self.out_file.label = '(none)' | ||||||
|  | 		self.format('out') | ||||||
|  | 
 | ||||||
|  | 	def oshow(self): | ||||||
|  | 		self.vout.show() | ||||||
|  | 		self.format('out') | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | 	def msg(self, *args): | ||||||
|  | 		str = string.strip(string.join(args)) | ||||||
|  | 		self.msg_area.label = str | ||||||
|  | 
 | ||||||
|  | 	def err(self, *args): | ||||||
|  | 		gl.ringbell() | ||||||
|  | 		apply(self.msg, args) | ||||||
|  | 
 | ||||||
|  | 	def format(self, io): | ||||||
|  | 		v = getattr(self, 'v' + io) | ||||||
|  | 		if v == None: | ||||||
|  | 			left = right = pos = 0 | ||||||
|  | 		else: | ||||||
|  | 			left, right = v.qsizes() | ||||||
|  | 			pos = v.tell() | ||||||
|  | 			left = pos - left | ||||||
|  | 			right = pos + right | ||||||
|  | 		getattr(self, io + '_info1').label = `left` | ||||||
|  | 		getattr(self, io + '_info2').label = `pos` | ||||||
|  | 		getattr(self, io + '_info3').label = `right` | ||||||
|  | 
 | ||||||
|  | main() | ||||||
							
								
								
									
										360
									
								
								Demo/sgi/video/VeditForm.fd
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										360
									
								
								Demo/sgi/video/VeditForm.fd
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,360 @@ | ||||||
|  | Magic: 12321 | ||||||
|  | 
 | ||||||
|  | Internal Form Definition File | ||||||
|  |     (do not change) | ||||||
|  | 
 | ||||||
|  | Number of forms: 1 | ||||||
|  | 
 | ||||||
|  | =============== FORM =============== | ||||||
|  | Name: form | ||||||
|  | Width: 480.000000 | ||||||
|  | Height: 350.000000 | ||||||
|  | Number of Objects: 23 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 1 | ||||||
|  | type: 1 | ||||||
|  | box: 0.000000 0.000000 480.000000 350.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label:  | ||||||
|  | name:  | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 4 | ||||||
|  | box: 170.000000 110.000000 140.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: -> Copy -> | ||||||
|  | name:  | ||||||
|  | callback: cb_copy | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 4 | ||||||
|  | box: 10.000000 110.000000 140.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Forward | ||||||
|  | name:  | ||||||
|  | callback: cb_in_skip | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 0 | ||||||
|  | box: 10.000000 10.000000 140.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Rewind input | ||||||
|  | name:  | ||||||
|  | callback: cb_in_rewind | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 0 | ||||||
|  | box: 330.000000 10.000000 140.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Reset output | ||||||
|  | name:  | ||||||
|  | callback: cb_out_rewind | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 0 | ||||||
|  | box: 10.000000 260.000000 80.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Input file... | ||||||
|  | name:  | ||||||
|  | callback: cb_in_new | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 0 | ||||||
|  | box: 330.000000 260.000000 80.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Output file... | ||||||
|  | name:  | ||||||
|  | callback: cb_out_new | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 2 | ||||||
|  | type: 0 | ||||||
|  | box: 10.000000 210.000000 140.000000 40.000000 | ||||||
|  | boxtype: 6 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 2 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: (none) | ||||||
|  | name: in_file | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 2 | ||||||
|  | type: 0 | ||||||
|  | box: 330.000000 210.000000 140.000000 40.000000 | ||||||
|  | boxtype: 6 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 2 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: (none) | ||||||
|  | name: out_file | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 2 | ||||||
|  | type: 0 | ||||||
|  | box: 10.000000 160.000000 30.000000 30.000000 | ||||||
|  | boxtype: 6 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 2 | ||||||
|  | style: 0 | ||||||
|  | size: 8.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label:  | ||||||
|  | name: in_info1 | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 0 | ||||||
|  | box: 170.000000 260.000000 140.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Quit | ||||||
|  | name:  | ||||||
|  | callback: cb_quit | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 4 | ||||||
|  | box: 330.000000 60.000000 140.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Back | ||||||
|  | name:  | ||||||
|  | callback: cb_out_back | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 4 | ||||||
|  | box: 10.000000 60.000000 140.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Back | ||||||
|  | name:  | ||||||
|  | callback: cb_in_back | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 4 | ||||||
|  | box: 330.000000 110.000000 140.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Forward | ||||||
|  | name:  | ||||||
|  | callback: cb_out_skip | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 4 | ||||||
|  | box: 170.000000 60.000000 140.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Uncopy | ||||||
|  | name:  | ||||||
|  | callback: cb_uncopy | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 0 | ||||||
|  | box: 100.000000 260.000000 50.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Close | ||||||
|  | name:  | ||||||
|  | callback: cb_in_close | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 11 | ||||||
|  | type: 0 | ||||||
|  | box: 420.000000 260.000000 50.000000 40.000000 | ||||||
|  | boxtype: 1 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 4 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: Close | ||||||
|  | name:  | ||||||
|  | callback: cb_out_close | ||||||
|  | argument: 0 | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 2 | ||||||
|  | type: 0 | ||||||
|  | box: 10.000000 310.000000 460.000000 30.000000 | ||||||
|  | boxtype: 6 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 2 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label: CMIF Video Editor, by Guido van Rossum | ||||||
|  | name: msg_area | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 2 | ||||||
|  | type: 0 | ||||||
|  | box: 50.000000 160.000000 60.000004 40.000000 | ||||||
|  | boxtype: 6 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 2 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label:  | ||||||
|  | name: in_info2 | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 2 | ||||||
|  | type: 0 | ||||||
|  | box: 120.000000 160.000000 30.000000 30.000000 | ||||||
|  | boxtype: 6 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 2 | ||||||
|  | style: 0 | ||||||
|  | size: 8.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label:  | ||||||
|  | name: in_info3 | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 2 | ||||||
|  | type: 0 | ||||||
|  | box: 330.000000 160.000000 30.000000 30.000000 | ||||||
|  | boxtype: 6 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 2 | ||||||
|  | style: 0 | ||||||
|  | size: 8.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label:  | ||||||
|  | name: out_info1 | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 2 | ||||||
|  | type: 0 | ||||||
|  | box: 370.000000 160.000000 60.000004 40.000000 | ||||||
|  | boxtype: 6 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 2 | ||||||
|  | style: 0 | ||||||
|  | size: 11.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label:  | ||||||
|  | name: out_info2 | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | -------------------- | ||||||
|  | class: 2 | ||||||
|  | type: 0 | ||||||
|  | box: 440.000000 160.000000 30.000000 30.000000 | ||||||
|  | boxtype: 6 | ||||||
|  | colors: 47 47 | ||||||
|  | alignment: 2 | ||||||
|  | style: 0 | ||||||
|  | size: 8.000000 | ||||||
|  | lcol: 0 | ||||||
|  | label:  | ||||||
|  | name: out_info3 | ||||||
|  | callback:  | ||||||
|  | argument:  | ||||||
|  | 
 | ||||||
|  | ============================== | ||||||
|  | create_the_forms | ||||||
							
								
								
									
										242
									
								
								Demo/sgi/video/Viewer.py
									
										
									
									
									
										Executable file
									
								
							
							
						
						
									
										242
									
								
								Demo/sgi/video/Viewer.py
									
										
									
									
									
										Executable file
									
								
							|  | @ -0,0 +1,242 @@ | ||||||
|  | import gl, GL | ||||||
|  | import VFile | ||||||
|  | import os | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | class InputViewer: | ||||||
|  | 
 | ||||||
|  | 	def init(self, filename, title, qsize): | ||||||
|  | 		try: | ||||||
|  | 			self.vin = VFile.VinFile().init(filename) | ||||||
|  | 		except (EOFError, VFile.Error): | ||||||
|  | 			raise IOError, 'bad video input file' | ||||||
|  | 		if not title: | ||||||
|  | 			title = os.path.split(filename)[1] | ||||||
|  | 		self.filename = filename | ||||||
|  | 		self.title = title | ||||||
|  | 		self.qsize = qsize | ||||||
|  | 		gl.foreground() | ||||||
|  | 		gl.prefsize(self.vin.width, self.vin.height) | ||||||
|  | 		self.wid = -1 | ||||||
|  | 		self.reset() | ||||||
|  | 		return self | ||||||
|  | 
 | ||||||
|  | 	def close(self): | ||||||
|  | 		self.vin.close() | ||||||
|  | 		if self.wid > 0: | ||||||
|  | 			gl.winclose(self.wid) | ||||||
|  | 
 | ||||||
|  | 	def rewind(self): | ||||||
|  | 		self.vin.rewind() | ||||||
|  | 		self.reset() | ||||||
|  | 
 | ||||||
|  | 	def getinfo(self): | ||||||
|  | 		return self.vin.getinfo() | ||||||
|  | 
 | ||||||
|  | 	# Internal | ||||||
|  | 	def reset(self): | ||||||
|  | 		if self.wid > 0: | ||||||
|  | 			gl.winset(self.wid) | ||||||
|  | 			gl.clear() | ||||||
|  | 			self.vin.initcolormap() | ||||||
|  | 		self.queue = [] | ||||||
|  | 		self.qindex = 0 | ||||||
|  | 		self.lost = 0 | ||||||
|  | 		self.lastt = 0 | ||||||
|  | 		self.eofread = 0 | ||||||
|  | 
 | ||||||
|  | 	# Internal | ||||||
|  | 	def fillq(self): | ||||||
|  | 		if self.qindex < len(self.queue) or self.eofread: return | ||||||
|  | 		try: | ||||||
|  | 			t, d, cd = self.vin.getnextframe() | ||||||
|  | 		except EOFError: | ||||||
|  | 			self.eofread = 1 | ||||||
|  | 			return | ||||||
|  | 		dt = t - self.lastt | ||||||
|  | 		self.lastt = t | ||||||
|  | 		self.queue.append(dt, d, cd) | ||||||
|  | 		while len(self.queue) > self.qsize: | ||||||
|  | 			del self.queue[0] | ||||||
|  | 			self.qindex = self.qindex - 1 | ||||||
|  | 			self.lost = self.lost + 1 | ||||||
|  | 
 | ||||||
|  | 	def show(self): | ||||||
|  | 		if self.wid < 0: | ||||||
|  | 			gl.foreground() | ||||||
|  | 			gl.prefsize(self.vin.width, self.vin.height) | ||||||
|  | 			self.wid = gl.winopen(self.title) | ||||||
|  | 			gl.clear() | ||||||
|  | 			self.vin.initcolormap() | ||||||
|  | 		self.fillq() | ||||||
|  | 		gl.winset(self.wid) | ||||||
|  | 		if self.qindex >= len(self.queue): | ||||||
|  | 			gl.clear() | ||||||
|  | 			return | ||||||
|  | 		dt, d, cd = self.queue[self.qindex] | ||||||
|  | 		self.vin.showframe(d, cd) | ||||||
|  | 
 | ||||||
|  | 	def redraw(self, wid): | ||||||
|  | 		if wid == self.wid >= 0: | ||||||
|  | 			gl.winset(self.wid) | ||||||
|  | 			gl.reshapeviewport() | ||||||
|  | 			self.show() | ||||||
|  | 
 | ||||||
|  | 	def get(self): | ||||||
|  | 		if self.qindex >= len(self.queue): | ||||||
|  | 			self.fillq() | ||||||
|  | 			if self.eofread: | ||||||
|  | 				return None | ||||||
|  | 		item = self.queue[self.qindex] | ||||||
|  | 		self.qindex = self.qindex + 1 | ||||||
|  | 		return item | ||||||
|  | 
 | ||||||
|  | 	def backup(self): | ||||||
|  | 		if self.qindex == 0: | ||||||
|  | 			return 0 | ||||||
|  | 		self.qindex = self.qindex - 1 | ||||||
|  | 		return 1 | ||||||
|  | 
 | ||||||
|  | 	def tell(self): | ||||||
|  | 		return self.lost + self.qindex | ||||||
|  | 
 | ||||||
|  | 	def qsizes(self): | ||||||
|  | 		return self.qindex, len(self.queue) - self.qindex | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | class OutputViewer: | ||||||
|  | 
 | ||||||
|  | 	def init(self, filename, title, qsize): | ||||||
|  | 		try: | ||||||
|  | 			self.vout = VFile.VoutFile().init(filename) | ||||||
|  | 		except (EOFError, VFile.Error): | ||||||
|  | 			raise IOError, 'bad video output file' | ||||||
|  | 		if not title: | ||||||
|  | 			title = os.path.split(filename)[1] | ||||||
|  | 		self.filename = filename | ||||||
|  | 		self.title = title | ||||||
|  | 		self.qsize = qsize | ||||||
|  | 		gl.foreground() | ||||||
|  | 		self.wid = -1 | ||||||
|  | 		self.reset() | ||||||
|  | 		return self | ||||||
|  | 
 | ||||||
|  | 	def close(self): | ||||||
|  | 		while self.queue: | ||||||
|  | 			self.flushq() | ||||||
|  | 		self.vout.close() | ||||||
|  | 		if self.wid > 0: | ||||||
|  | 			gl.winclose(self.wid) | ||||||
|  | 
 | ||||||
|  | 	def rewind(self): | ||||||
|  | 		info = self.vout.getinfo() | ||||||
|  | 		self.vout.close() | ||||||
|  | 		self.vout = VFile.VoutFile().init(self.filename) | ||||||
|  | 		self.vout.setinfo(info) | ||||||
|  | 		self.reset() | ||||||
|  | 
 | ||||||
|  | 	def getinfo(self): | ||||||
|  | 		return self.vout.getinfo() | ||||||
|  | 
 | ||||||
|  | 	def setinfo(self, info): | ||||||
|  | 		if info == self.getinfo(): return # No change | ||||||
|  | 		self.vout.setinfo(info) | ||||||
|  | 		if self.wid > 0: | ||||||
|  | 			gl.winclose(self.wid) | ||||||
|  | 			self.wid = -1 | ||||||
|  | 
 | ||||||
|  | 	# Internal | ||||||
|  | 	def reset(self): | ||||||
|  | 		if self.wid > 0: | ||||||
|  | 			gl.winset(self.wid) | ||||||
|  | 			gl.clear() | ||||||
|  | 			self.vout.initcolormap() | ||||||
|  | 		self.queue = [] | ||||||
|  | 		self.spares = [] | ||||||
|  | 		self.written = 0 | ||||||
|  | 		self.lastt = 0 | ||||||
|  | 
 | ||||||
|  | 	# Internal | ||||||
|  | 	def flushq(self): | ||||||
|  | 		if self.written == 0: | ||||||
|  | 			self.vout.writeheader() | ||||||
|  | 		dt, d, cd = self.queue[0] | ||||||
|  | 		self.lastt = self.lastt + dt | ||||||
|  | 		self.vout.writeframe(self.lastt, d, cd) | ||||||
|  | 		del self.queue[0] | ||||||
|  | 		self.written = self.written + 1 | ||||||
|  | 
 | ||||||
|  | 	def show(self): | ||||||
|  | 		if self.wid < 0: | ||||||
|  | 			gl.foreground() | ||||||
|  | 			gl.prefsize(self.vout.width, self.vout.height) | ||||||
|  | 			self.wid = gl.winopen(self.title) | ||||||
|  | 			gl.clear() | ||||||
|  | 			self.vout.initcolormap() | ||||||
|  | 		gl.winset(self.wid) | ||||||
|  | 		if not self.queue: | ||||||
|  | 			gl.clear() | ||||||
|  | 			return | ||||||
|  | 		dt, d, cd = self.queue[-1] | ||||||
|  | 		self.vout.showframe(d, cd) | ||||||
|  | 
 | ||||||
|  | 	def redraw(self, wid): | ||||||
|  | 		if wid == self.wid >= 0: | ||||||
|  | 			gl.winset(self.wid) | ||||||
|  | 			gl.reshapeviewport() | ||||||
|  | 			self.show() | ||||||
|  | 
 | ||||||
|  | 	def backup(self): | ||||||
|  | 		if len(self.queue) < 1: return 0 | ||||||
|  | 		self.spares.insert(0, self.queue[-1]) | ||||||
|  | 		del self.queue[-1] | ||||||
|  | 		return 1 | ||||||
|  | 
 | ||||||
|  | 	def forward(self): | ||||||
|  | 		if not self.spares: return 0 | ||||||
|  | 		self.queue.append(self.spares[0]) | ||||||
|  | 		del self.spares[0] | ||||||
|  | 		return 1 | ||||||
|  | 
 | ||||||
|  | 	def put(self, item): | ||||||
|  | 		self.queue.append(item) | ||||||
|  | 		self.spares = [] | ||||||
|  | 		while len(self.queue) > self.qsize: | ||||||
|  | 			self.flushq() | ||||||
|  | 
 | ||||||
|  | 	def tell(self): | ||||||
|  | 		return self.written + len(self.queue) | ||||||
|  | 
 | ||||||
|  | 	def qsizes(self): | ||||||
|  | 		return len(self.queue), len(self.spares) | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | def test(): | ||||||
|  | 	import sys | ||||||
|  | 	a = InputViewer().init(sys.argv[1], '') | ||||||
|  | 	b = OutputViewer().init(sys.argv[2], '') | ||||||
|  | 	b.setinfo(a.getinfo()) | ||||||
|  | 	 | ||||||
|  | 	while 1: | ||||||
|  | 		a.show() | ||||||
|  | 		data = a.get() | ||||||
|  | 		if data is None: | ||||||
|  | 			break | ||||||
|  | 		b.put(data) | ||||||
|  | 		b.show() | ||||||
|  | 
 | ||||||
|  | 	while a.backup(): | ||||||
|  | 		data = a.get() | ||||||
|  | 		b.put(data) | ||||||
|  | 		b.show() | ||||||
|  | 		if a.backup(): a.show() | ||||||
|  | 	 | ||||||
|  | 	while 1: | ||||||
|  | 		data = a.get() | ||||||
|  | 		if data is None: | ||||||
|  | 			break | ||||||
|  | 		b.put(data) | ||||||
|  | 		b.show() | ||||||
|  | 		a.show() | ||||||
|  | 
 | ||||||
|  | 	b.close() | ||||||
|  | @ -200,13 +200,15 @@ def playonce(vin): | ||||||
| 	vin.magnify = magnify | 	vin.magnify = magnify | ||||||
| 
 | 
 | ||||||
| 	if threading: | 	if threading: | ||||||
|  | 		MAXSIZE = 20 # Don't read ahead too much | ||||||
| 		import thread | 		import thread | ||||||
| 		queue = [] | 		import Queue | ||||||
|  | 		queue = Queue.Queue().init(MAXSIZE) | ||||||
| 		stop = [] | 		stop = [] | ||||||
| 		thread.start_new_thread(read_ahead, (vin, queue, stop)) | 		thread.start_new_thread(read_ahead, (vin, queue, stop)) | ||||||
| 		# Get the read-ahead thread going | 		# Get the read-ahead thread going | ||||||
| 		while len(queue) < 5 and None not in queue: | 		while queue.qsize() < MAXSIZE/2 and not stop: | ||||||
| 			time.millisleep(10) | 			time.millisleep(100) | ||||||
| 
 | 
 | ||||||
| 	tin = 0 | 	tin = 0 | ||||||
| 	told = 0 | 	told = 0 | ||||||
|  | @ -227,21 +229,18 @@ def playonce(vin): | ||||||
| 				if debug: sys.stderr.write('\n') | 				if debug: sys.stderr.write('\n') | ||||||
| 				if threading: | 				if threading: | ||||||
| 					stop.append(None) | 					stop.append(None) | ||||||
| 					while len(stop) < 2: | 					while 1: | ||||||
| 						time.millisleep(10) | 						item = queue.get() | ||||||
|  | 						if item == None: break | ||||||
| 				return (dev != LEFTMOUSE) | 				return (dev != LEFTMOUSE) | ||||||
| 			if dev == REDRAW: | 			if dev == REDRAW: | ||||||
| 				gl.reshapeviewport() | 				gl.reshapeviewport() | ||||||
| 				if data: vin.showframe(data, cdata) | 				if data: vin.showframe(data, cdata) | ||||||
| 		if threading: | 		if threading: | ||||||
| 			if not queue: | 			if debug and queue.empty(): sys.stderr.write('.') | ||||||
| 				if debug: sys.stderr.write('.') | 			item = queue.get() | ||||||
| 				time.millisleep(10) | 			if item == None: break | ||||||
| 				continue | 			tin, data, cdata = item | ||||||
| 			q0 = queue[0] |  | ||||||
| 			if q0 == None: break |  | ||||||
| 			del queue[0] |  | ||||||
| 			tin, data, cdata = q0 |  | ||||||
| 		else: | 		else: | ||||||
| 			try: | 			try: | ||||||
| 				tin, size, csize = vin.getnextframeheader() | 				tin, size, csize = vin.getnextframeheader() | ||||||
|  | @ -301,13 +300,13 @@ def playonce(vin): | ||||||
| 
 | 
 | ||||||
| def read_ahead(vin, queue, stop): | def read_ahead(vin, queue, stop): | ||||||
| 	try: | 	try: | ||||||
| 		while not stop: queue.append(vin.getnextframe()) | 		while not stop: queue.put(vin.getnextframe()) | ||||||
| 	except EOFError: | 	except EOFError: | ||||||
| 		queue.append(None) | 		pass | ||||||
|  | 	queue.put(None) | ||||||
| 	stop.append(None) | 	stop.append(None) | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| 
 |  | ||||||
| # Don't forget to call the main program | # Don't forget to call the main program | ||||||
| 
 | 
 | ||||||
| try: | try: | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Guido van Rossum
						Guido van Rossum