Elektronik-Labor Projekte Mikrocontroller Raspberry
_______________________scriptmicroscope.py_______________________
#! /usr/bin/env python
# -*- coding: utf-8
try:
import tkinter as tk
except ImportError:
import Tkinter as tk
import time
import datetime
import cv2
from PIL import Image, ImageTk
from functools import partial
WIDTH = 640
HEIGHT = 480
VIDEO_CODEC = "XVID"
# -1 --> erste vorhandene kamera
# erste = 0 / zweite = 1 usw. --> aendern, wenn mehr vorhanden sind
DEFAULT_CAM_ID = -1
class Microscope(object):
PROPID_WIDTH = 3
PROPID_HEIGHT = 4
def __init__(self, cam_id = id):
self.cam = cv2.VideoCapture(cam_id)
self.recording = False
if not self.cam.isOpened():
raise RuntimeError("can not open camera {0!r}".format(
cam_id))
self.cam_width = self.zoom_width = self.cam.get(self.PROPID_WIDTH)
self.cam_height = self.zoom_height = self.cam.get(self.PROPID_HEIGHT)
self.aspect_ratio = self.zoom_width / self.zoom_height
def __enter__(self):
return self
def __exit__(self, *args):
self.release()
@property
def size(self):
return (int(self.cam_width), int(self.cam_height))
@property
def zoom_size(self):
return (int(self.zoom_width), int(self.zoom_height))
def get_image(self):
state, frame = self.cam.read()
if state:
image = Image.frombytes("RGB", self.size ,frame,
"raw", "BGR").resize(self.zoom_size)
if self.recording:
self.video_writer.write(frame)
return image
else:
return state
def recording_start_stop(self, state, path = ""):
self.recording = state
if self.recording:
self.video_writer = cv2.VideoWriter(path, cv2.cv.CV_FOURCC(
* VIDEO_CODEC), 24, (self.size))
def take_picture(self, path):
self.get_image().save(path)
def zoom_image(self, step):
width = int(self.zoom_width + step * self.aspect_ratio)
height = int(self.zoom_height + step)
if width > 0 and height > 0:
self.zoom_width = width
self.zoom_height = height
def reset_zoom(self):
self.zoom_width, self.zoom_height = self.size
def release(self):
self.cam.release()
class MicroscopeUI(tk.Frame):
UPDATE_INTERVAL = 200
def __init__(self, parent, microscope, width, height,
zoom_step = 10, picture_path = "", video_path = ""):
tk.Frame.__init__(self, parent)
self.parent = parent
self.width = width
self.height = height
self.picture_path = picture_path
self.video_path = video_path
self.tk_image = None
self.buttons = list()
self.microscope = microscope
self.canvas = tk.Canvas(self, width=width, height=height)
self.canvas.grid(column=0, row=0)
vscrollbar = tk.Scrollbar(self)
vscrollbar.grid(column=1, row=0, sticky=tk.N+tk.S)
self.canvas.config(yscrollcommand=vscrollbar.set)
vscrollbar.config(command=self.canvas.yview)
hscrollbar = tk.Scrollbar(self, orient=tk.HORIZONTAL)
hscrollbar.grid(column=0, row=1, columnspan=5, sticky=tk.E+tk.W)
self.canvas.config(xscrollcommand=hscrollbar.set)
hscrollbar.config(command=self.canvas.xview)
button_frame = tk.Frame(self)
button_frame.grid(column=0, row=3, columnspan=2)
for column, (text, command, var)in enumerate(
(("||", self.start_stop, None),
("+", self.microscope.zoom_image, zoom_step),
("-", self.microscope.zoom_image, -zoom_step),
("+/-", self.reset_zoom, None),
("[ ]", self.take_picture, None),
("REC", self.recording_film, None))):
button = tk.Button(button_frame, text=text, width=4,
relief="raised", font="Arial 10 bold")
button.grid(column=column, row=0)
self.buttons.append(button)
if var:
button.config(command=partial(command, var))
else:
button.config(command=command)
self.buttons[-1].config(bg = "lightgreen")
def start_stop(self):
if self.after_id is None:
self.buttons[0].config(text = "||")
self.run()
else:
self.buttons[0].config(text = ">")
self.after_cancel(self.after_id)
self.after_id = None
def run(self):
self.tk_image = self.microscope.get_image()
if self.tk_image:
self.canvas.delete("img")
self.tk_image = ImageTk.PhotoImage(self.tk_image)
self.canvas.create_image((0,0), anchor=tk.NW,
image=self.tk_image, tag="img")
width, height = self.microscope.zoom_size
self.canvas.config(scrollregion = (0, 0, width, height))
self.after_id = self.after(self.UPDATE_INTERVAL, self.run)
else:
self.raise_cam_id_error()
def raise_cam_id_error(self):
self.canvas.create_text((self.width / 2, self.height / 2),
text='NO CAM', font='Arial 40')
for button in self.buttons:
button.config(state="disabled")
def reset_zoom(self):
self.microscope.reset_zoom()
def recording_film(self):
if self.buttons[-1].config("bg")[-1] == "lightgreen":
self.buttons[-1].config(bg = "red")
self.microscope.recording_start_stop(True,
"{0}{1:%d%b%Y_%H_%M_%S.%f}.avi".format(self.video_path,
datetime.datetime.utcnow()))
else:
self.buttons[-1].config(bg = "lightgreen")
self.microscope.recording_start_stop(False)
def take_picture(self):
self.microscope.take_picture("{0}{1:%d%b%Y_%H_%M_%S.%f}.tiff"
.format(self.picture_path, datetime.datetime.utcnow()))
def release(self):
self.parent.destroy()
def main():
root = tk.Tk()
root.title('MICROSCOPE')
try:
with Microscope(DEFAULT_CAM_ID) as microscope:
microscope_ui = MicroscopeUI(
root, microscope, WIDTH, HEIGHT)
microscope_ui.pack(expand=tk.YES)
microscope_ui.run()
root.protocol("WM_DELETE_WINDOW", microscope_ui.release)
root.mainloop()
except RuntimeError:
tk.Label(root, text = 'can not open camera {0!r}'.format(
DEFAULT_CAM_ID), font = "Arial 20", height = 10).pack()
root.mainloop()
if __name__ == '__main__':
main()
... und in der „kleinen“ Version:
__________________________________________________________________
__________________scriptmicroscope_raspberry.py__________________
#! /usr/bin/env python
# -*- coding: utf-8
try:
import tkinter as tk
except ImportError:
import Tkinter as tk
import time
import datetime
import cv2
from PIL import Image, ImageTk
from functools import partial
WIDTH = 320
HEIGHT = 240
VIDEO_CODEC = "XVID"
# -1 --> erste vorhandene kamera
# erste = 0 / zweite = 1 usw. --> aendern, wenn mehr vorhanden sind
DEFAULT_CAM_ID = -1
class Microscope(object):
PROPID_WIDTH = 3
PROPID_HEIGHT = 4
def __init__(self, cam_id = id):
self.cam = cv2.VideoCapture(cam_id)
self.recording = False
if not self.cam.isOpened():
raise RuntimeError("can not open camera {0!r}".format(
cam_id))
self.cam_width = self.cam.get(self.PROPID_WIDTH)
self.cam_height = self.cam.get(self.PROPID_HEIGHT)
def __enter__(self):
return self
def __exit__(self, *args):
self.release()
@property
def size(self):
return (int(self.cam_width), int(self.cam_height))
def get_image(self):
state, frame = self.cam.read()
if state:
image = Image.frombytes("RGB", self.size ,frame,
"raw", "BGR")
if self.recording:
self.video_writer.write(frame)
return image
else:
return state
def recording_start_stop(self, state, path = ""):
self.recording = state
if self.recording:
self.video_writer = cv2.VideoWriter(path, cv2.cv.CV_FOURCC(
* VIDEO_CODEC), 24, (self.size))
def take_picture(self, path):
self.get_image().save(path)
def release(self):
self.cam.release()
class MicroscopeUI(tk.Frame):
UPDATE_INTERVAL = 100
def __init__(self, parent, microscope, width, height,
zoom_step = 10, picture_path = "", video_path = ""):
tk.Frame.__init__(self, parent)
self.parent = parent
self.width = width
self.height = height
self.picture_path = picture_path
self.video_path = video_path
self.tk_image = None
self.buttons = list()
self.microscope = microscope
self.canvas = tk.Canvas(self, width=width, height=height)
self.canvas.grid(column=0, row=0)
button_frame = tk.Frame(self)
button_frame.grid(column=0, row=3, columnspan=2)
for column, (text, command, var)in enumerate(
(("||", self.start_stop, None),
("[]", self.take_picture, None),
("REC", self.recording_film, None))):
button = tk.Button(button_frame, text=text, width=4,
relief="raised", font="Arial 10 bold")
button.grid(column=column, row=0)
self.buttons.append(button)
if var:
button.config(command=partial(command, var))
else:
button.config(command=command)
self.buttons[-1].config(bg = "lightgreen")
def start_stop(self):
if self.after_id is None:
self.buttons[0].config(text = "||")
self.run()
else:
self.buttons[0].config(text = ">")
self.after_cancel(self.after_id)
self.after_id = None
def run(self):
self.tk_image = self.microscope.get_image().resize(
(self.width, self.height))
if self.tk_image:
self.canvas.delete("img")
self.tk_image = ImageTk.PhotoImage(self.tk_image)
self.canvas.create_image((0,0), anchor=tk.NW,
image=self.tk_image, tag="img")
self.after_id = self.after(self.UPDATE_INTERVAL, self.run)
else:
self.canvas.create_text((self.width / 2, self.height / 2),
text='NO CAM', font='Arial 40')
for button in self.buttons:
button.config(state="disabled")
def recording_film(self):
if self.buttons[-1].config("bg")[-1] == "lightgreen":
self.buttons[-1].config(bg = "red")
self.microscope.recording_start_stop(True,
"{0}{1:%d%b%Y_%H_%M_%S.%f}.avi".format(self.video_path,
datetime.datetime.utcnow()))
else:
self.buttons[-1].config(bg = "lightgreen")
self.microscope.recording_start_stop(False)
def take_picture(self):
self.microscope.take_picture("{0}{1:%d%b%Y_%H_%M_%S.%f}.tiff"
.format(self.picture_path, datetime.datetime.utcnow()))
def release(self):
self.parent.destroy()
def main():
root = tk.Tk()
root.title('MICROSCOPE')
try:
with Microscope(DEFAULT_CAM_ID) as microscope:
microscope_ui = MicroscopeUI(
root, microscope, WIDTH, HEIGHT)
microscope_ui.pack(expand=tk.YES)
microscope_ui.run()
root.protocol("WM_DELETE_WINDOW", microscope_ui.release)
root.mainloop()
except RuntimeError:
tk.Label(root, text = 'can not open camera {0!r}'.format(
DEFAULT_CAM_ID), font = "Arial 20", height = 10).pack()
root.mainloop()
if __name__ == '__main__':
main()
__________________________________________________________________