質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

88.59%

PyQt5とOpenCVを用いたGUI作成時の__init__におけるエラー

解決済

回答 1

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 1,026

atusibba1014

score 17

 前提・実現したいこと

PyQt5とOpenCVを用いてボタンを押したらエッジ抽出してくれるGUIの作成
Executeボタンを押したら画面に表示された画像のエッジを抽出してくれるGUI
補足に記載されているURLを参考に進めてきました。正直Pythonを扱って一ヶ月ほどです。問題解決にあたり参考となるような資料も提示していただけると幸いです

追記
opencv_canny.py単体でしたら画像のエッジ抽出ができます。
『if name=='main':』以下のコードはそれを確認するためのコードになっています。
mainother.pyをコンパイルした際に上記のようなメッセージがでてきます。

 発生している問題・エラーメッセージ

File " ~~/mainother.py",line 42, in exe_canny
  cv_testOpencv_test(file)
NameError: name 'file' is not defined

 該当のソースコード

###mainnother.py
from __future__ import with_statement

import numpy as np
import os
from opencv_canny import *
import sys
from PyQt5 import *
from pyqt_Opencv import * ###このファイルはUIをQtdesignerで作成し.uiを.pyに変えたものです


class DesignerMainWindow(QtWidgets.QMainWindow,Ui_Qt_CV_MainWindow):
    def __init__(self,parent=None):
        super(DesignerMainWindow, self).__init__(parent)
        self.ui = Ui_Qt_CV_MainWindow()
        self.setupUi(self)

        #シグナルとスロットの設定場所
        self.file_button.clicked.connect(self.open_file)
        self.exec_button.clicked.connect(self.exe_canny)

    def open_file(self):

        file = QtWidgets.QFileDialog.getOpenFileName()#ここでファイルからデータを読み込み
        if file:#データが入ってたらif文にも入れる
            self.file_edit.setText(file[0])
            self.scene = QtWidgets.QGraphicsScene()
            pic_Item = QtWidgets.QGraphicsPixmapItem(QtGui.QPixmap(file[0]))
            __width = pic_Item.boundingRect().width()
            __height = pic_Item.boundingRect().height()
            __x = self.pic_View.x()
            __y = self.pic_View.y()
            self.pic_View.setGeometry(QtCore.QRect(__x, __y, __width, __height))
            __main_x = int(__x + __width + 20)
            __main_y = int(__y + __height + 50)
            self.resize(__main_x,__main_y)
            self.scene.addItem(pic_Item)
            self.pic_View.setScene(self.scene)
            return file

    def exe_canny(self):
        cv_test=Opencv_test(file)
        pic,pic2=cv_test.open_pic(self.file[0])
        self.cv_img=cv_test.canny(pic2)
        height,width,dim=self.cv_img.shape
        bytesPerLine=dim*width
        self.image=QtWidgets.QImage(self.cv_img.data,width,height,bytesPerLine,QtWidgets.QImage.Format_RGB888)
        pic_Item=QtWidgets.QGraphicsPixmapItem(QtWidgets.QPixmap.fromImage(self.image))
        self.scene.addItem(pic_Item)

if __name__ == '__main__':
        app = QtWidgets.QApplication(sys.argv)
        dmw = DesignerMainWindow()
        dmw.show()
        sys.exit(app.exec_())

######################opencv_canny.py#################################
import numpy as np 
import cv2

class Opencv_test:
    def __init__(self):
        self.file=file

    def open_pic(self,file):
        pic=cv2.imread(file)
        pic_color=cv2.cvtColor(pic,cv2.COLOR_BGR2RGB)
        return pic,pic_color

    def canny(self,pic):
        img=cv2.cvtColor(pic,cv2.COLOR_BGR2GRAY)
        edges=cv2.Canny(img,100,200)
        edges2=np.zeros_like(pic)
        for i in (0,1,2):
            edges2[:,:,i]=edges
        add=cv2.addWeighted(pic,1,edges2,0.4,0)
        return add
if __name__ == '__main__':
    #以下テスト用

    file="/media/atsushi/98501FCD501FB0CC/searchImge/depth.tif"
    a=Opencv_test()
    b,c=a.open_pic(file)
    d=a.canny(b)
    cv2.imshow("",d)
    cv2.waitKey(0)
    cv2.destroyAllWindows()

 試したこと

定義されていないといわれたからおとなしくinitでfileを定義してみたが

class Opencv_test:
    def __init__(self,file):
        self.file=file


TypeError:init()missing 1 required positional argument: 'file'

 補足情報(FW/ツールのバージョンなど)

http://tatabox.hatenablog.com/entry/2014/09/02/185727(参照ページ)
ubuntu18.04 OpenCV3.4.3 PyQt5 Python3.6.6

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 1

checkベストアンサー

+1

もう一歩です。

class Opencv_test:
    def __init__(self,file):
        self.file=file
(中略)

if __name__ == '__main__':
    #以下テスト用

    file="/media/atsushi/98501FCD501FB0CC/searchImge/depth.tif"
    a=Opencv_test(file)
    # ↑変数fileを渡してやる

    def exe_canny(self):
        cv_test=Opencv_test(file)
        # ↑上記のfileが未定義

ですので、

    def __init__(self,parent=None):
        self.file = ""
        # ↑個人的にコンストラクタできちんと初期化しておくのが好み

    def open_file(self):
        self.file = QtWidgets.QFileDialog.getOpenFileName()#ここでファイルからデータを読み込み
        # ↑fileをローカル変数ではなくクラスのメンバ変数とする

    def exe_canny(self):
        cv_test=Opencv_test(self.file)
        # ↑クラスのメンバ変数のself.fileを参照する


という経路で渡してやれば良いかと思います。

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/11/15 15:32

    説明不足で申し訳ありません。
    opencv_canny.py単体でしたら画像のエッジ抽出ができます。
    『if __name__=='__main__':』以下のコードはそれを確認するためのコードになっています。
    mainother.pyをコンパイルした際に上記のようなメッセージがでてきます。

    キャンセル

  • 2018/11/15 16:11

    なるほど。追記しました。

    キャンセル

  • 2018/11/19 12:23

    selfをつける意味としてはローカル変数からクラスのメンバ変数になれる、ということですね!
    勉強になりました。ありがとうございます。

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 88.59%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

関連した質問

同じタグがついた質問を見る