GUI 采用 wxPython, 图像处理采用 opencv, 制作了一款简单的图片处理工具. 其效果如下
output.gif
主要的功能及实现
选中文件资源管理器中的图片
这个采用 tkinter 库的 filedialog 模块很容易实现
image_path = filedialog.askopenfilename(initialdir=r"..\\", title="select an image whose filename endwiths .jpg/PNG",filetypes=[ ("JPG", ".jpg"),("PNG", ".PNG")])
参数一: initialdir 是打开文件资源管理器的初始路径, 可以不设置
参数二: title 是打开的文件资源管理器的最左上方的标题
参数三: filetypes, 比如我上面的设置过滤掉了其他非. jpg,.PNG 文件
askopenfilename 的返回值就是你选择的文件路径
图像处理
我主要加了图片涂鸦, 图片黑白化, 图片裁剪这几个功能, 具体效果参考最上面的效果图, 实现的话算法 + 业务逻辑很容易
算法算是比较简单的算法, 但是业务逻辑和其中不少的坑是只有动手后才能深有体会的, 这里贴出这部分的主要代码:
- def OnImageGrayClicked(self,event):
- if self.isLoaded == True:
- dlg = wx.MessageDialog(self, u"this Operation cannot be undo", u"Warning", wx.YES_NO)
- value = dlg.ShowModal()
- if value == wx.ID_YES:
- self.setImage(cv2.cvtColor(self.image, cv2.COLOR_BGR2GRAY))
- self.editMenu.Check(ID_IMAGE_GRAY, True)
- self.image_gray.Enable(False)
- else:
- self.editMenu.Check(ID_IMAGE_GRAY, False)
- dlg.Destroy()
- else:
- wx.MessageDialog(self, u"please make sure you have loaded the image successfully", u"Warning", wx.OK).ShowModal()
- self.editMenu.Check(ID_IMAGE_GRAY, False)
- def OnImageDrawClicked(self,event):
- if self.isLoaded == True:
- self.canDraw = not self.canDraw
- if self.canDraw == True:
- self.image_draw.SetItemLabel("disabel drawing on the image")
- self.image_cut.Enable(False)
- else:
- self.image_draw.SetItemLabel("enabel drawing on the image")
- self.image_cut.Enable(True)
- pass
- else:
- wx.MessageDialog(self, u"please make sure you have loaded the image successfully", u"Warning", wx.OK).ShowModal()
- def OnImageCutClicked(self,event):
- if self.isLoaded == True:
- self.canCut = not self.canCut
- if self.canCut == True:
- self.image_copy = self.image.copy()
- self.image_cut.SetItemLabel("disabel cutting on the image")
- self.image_draw.Enable(False)
- else:
- self.image_cut.SetItemLabel("enabel cutting on the image")
- self.image_draw.Enable(True)
- return
- else:
- wx.MessageDialog(self, u"please make sure you have loaded the image successfully", u"Warning", wx.OK).ShowModal()
- def OnSettingsLineWeightClicked(self,event):
- self.lineWeight = wx.GetNumberFromUser(message="input the line_weight(from 1 to 10)",
- prompt="lineWeight", caption="drawer settings",
- value=self.lineWeight,
- parent=self.bmp, max=10, min=1)
- print("SLW")
- pass
去掉 opencv 自带的窗口, 把图片绑定到 wxPython 框架上来
我感觉这部分是最复杂的, 需要两个实例, image = cv2.imread() 和 bitmap = wx.bitmap(), 从而搭起一个从 opencv 到 wxPython 的桥梁
这里最核心的代码是
- def setImage(self,img):
- self.image = img
- img_height, img_width = img.shape[:2]
- try:
- image1 = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)
- except:
- image1 = cv2.cvtColor(img,cv2.COLOR_GRAY2RGB)
- finally:
- pic = wx.Bitmap.FromBuffer(img_width, img_height, image1)
- # 显示图片在 panel 上
- self.bmp.SetBitmap(pic)
关于代码
代码设计的初衷是做一款功能比较全面的图片编辑软件, 但是一个人的力量有限, 我写了一个晚上, 只写好了框架和图片裁剪, 图片黑白化, 图片涂鸦这几个功能, 希望以后有小伙伴一起参与进来
暂时不考虑开源, 不过可以下载 exe 程序体验
链接: https://pan.baidu.com/s/1heSY9U-DJnRinoqihD-eJA
提取码: 5k63
(小声 bb, 过了期末考试周就发代码, 代码协作也是)
来源: http://www.jianshu.com/p/23cdc21717c9