Klavye Tuşuyla Çağırdığım Fonksiyonu Arayüzde Pushbuttonile Çağırmak

Merhaba,

Video ile OCR uygulaması yapan bir kod kullandım ve bunu arayüzde 2 adet butona atayarak kullanmayı denemek istiyorum. Program webcam açılıyor ve klavyeden s ve q tuşlarına basarak ocr işlemini gerçekleştiriyorum. Bu s’e basma işlemini de butona atamak istiyorum.

from PyQt5 import QtCore, QtGui, QtWidgets
import algorithm


class Ui_MainWindow ( object ) :
    def setupUi (self, MainWindow) :
        MainWindow.setObjectName ( "MainWindow" )
        MainWindow.resize ( 519, 354 )
        self.centralwidget = QtWidgets.QWidget ( MainWindow )
        self.centralwidget.setObjectName ( "centralwidget" )
        self.pushButton = QtWidgets.QPushButton ( self.centralwidget )
        self.pushButton.setGeometry ( QtCore.QRect ( 210, 140, 75, 23 ) )
        self.pushButton.setObjectName ( "pushButton" )
        self.pushButton_2 = QtWidgets.QPushButton ( self.centralwidget )
        self.pushButton_2.setObjectName ( "pushButton_2" )
        MainWindow.setCentralWidget ( self.centralwidget )
        self.retranslateUi ( MainWindow )
        QtCore.QMetaObject.connectSlotsByName ( MainWindow )

    def retranslateUi (self, MainWindow) :
        _translate = QtCore.QCoreApplication.translate
        MainWindow.setWindowTitle ( _translate ( "MainWindow", "MainWindow" ) )
        self.pushButton.setText ( _translate ( "MainWindow", "Open" ) )
        self.pushButton_2.setText ( _translate ( "MainWindow", "Get" ) )
        self.pushButton.clicked.connect ( self.OpenClick )
        self.pushButton_2.clicked.connect ( self.OpenClick_2 )

    def OpenClick (self) :
        algorithm.FunctionAlgo ()

    def OpenClick_2 (self) :

        cf = 1
        algorithm.tessfunc ()


if __name__ == "__main__" :
    import sys

    app = QtWidgets.QApplication ( sys.argv )
    MainWindow = QtWidgets.QMainWindow ()
    ui = Ui_MainWindow ()
    ui.setupUi ( MainWindow )
    MainWindow.show ()
    sys.exit ( app.exec_ () )

buradaki main.py’den arayüzü çağırıyorum. Ocr işlemini:

    def FunctionAlgo():
        import cv2
        from PIL import Image
        import numpy as np
        import sys
        import glob
        import os
        from subprocess import call
        from urllib.request import urlopen
        from collections import Counter
        import json
        from pathlib import Path
        import re
        import webbrowser

        cf = 0
        ResultStr = [ '' ]

        def LogicOpStrings ( ) :
            l = len ( ResultStr )
            newArr = [ ]
            for i in range ( 0, l ) :
                if not ResultStr[ i ] == "" :
                    newArr.append ( ResultStr[ i ].replace ( "\n", "" ).strip () )

            newArrSet = set ( newArr )

            url = ("https://raw.githubusercontent.com/dwyl/english-words/master/words_dictionary.json")
            print ( "Loading english dictionary from internet..." )
            wordDic = get_jsonparsed_data ( url )
            print ( "English word vocabulary has been successfully loaded!" )

            validWordCountMap = [ ]

            l = len ( newArr )
            for i in range ( 0, l ) :
                count = 0
                wordChunks = newArr[ i ].split ( ' ' )
                for j in range ( 0, len ( wordChunks ) ) :
                    if wordChunks[ j ].lower () in wordDic :
                        count = count + 1
                    else :
                        print ( wordChunks[ j ], " is not a valid word!" )
                validWordCountMap.append ( count )

                print ( "-----Overall result:-----" )
                print ( newArr[ validWordCountMap.index ( most_Common ( validWordCountMap ) ) ] )
                print ( "-------------------------" )

        def get_jsonparsed_data (url) :
            response = urlopen ( url )
            data = response.read ().decode ( "utf-8" )
            return json.loads ( data )

        def most_Common (lst) :
            data = Counter ( lst )
            return data.most_common ( 1 )[ 0 ][ 0 ]

        def tessfunc ( ) :
            os.system ( "tesseract file.png data" )
            clearTesseractExecNote ()
            with open ( 'data.txt', 'r' ) as mf :
                try :
                    content = mf.read ()
                    if (not content.isspace ()) :
                        ResultStr.append ( content )
                        print ( "\nResult:\n********************************************\n",
                                re.sub ( '[^0-9\r\n]+', ' ', content ), "\n********************************************" )
                except UnicodeDecodeError :
                    print ( "Unicode character found which cant be decoded" )

        def removechunk ( ) :
            for i in glob.glob ( 'file*.png' ) :
                print ( "Unlinked %s" % i )
                os.unlink ( i )

        def clearTesseractExecNote ( ) :
            print ( "\033[A                                                          \033[A" )
            print ( "\033[A                                                          \033[A" )

        print ( "Accessing device's camera..." )
        cap = cv2.VideoCapture ( 0 )
        print ( "\033[A                                           \033[A" )
        print ( "Camera ready!" )
        print ( "Activated command mode!\nPress 's' to start text recognition" )
        count = 0
        while (True) :
            ret, frame = cap.read ()
            gray = cv2.cvtColor ( frame, cv2.COLOR_BGR2GRAY )
            cv2.imshow ( 'Frame', gray )
            ret, thresh = cv2.threshold ( gray, 0, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU )
            cv2.imwrite ( 'file.png', thresh )
            if cf == 1 :
                tessfunc ()
            if cv2.waitKey ( 1 ) & 0xFF == ord ( 'q' ) :
                cf = 0
            if cv2.waitKey ( 1 ) & 0xFF == ord ( 's' ) :
                cf = 1
                text = f = open ( "data.txt", "r" )
                url = "url"
                url2 = "url2"
                url3 = url + "J" + "text" + url2

                print ( url3 )
                webbrowser.open ( url3, new=0, autoraise=True )

            if cv2.waitKey ( 1 ) & 0xFF == ord ( 'e' ) :
                print ( "Terminating the program" )
                break

        cap.release ()
        exit ()

ile yapıyorum. Burada en yukarıda tanımlanmış olan cf değeri tessfunc olarak tanımlı. Bunu da push buttonlara openclick1 ve openclick2 tuşları ile tanımladım. Ancak pushbutton_2 yi def olarak tessfunc() çağıramıyorum. Tuşa basılı değilse cf=0 ve s tuşu cf değerini 1 yapıyor ve ocr işlemi gerçekleşiyor.

Bunu yapabilmek mümkünse nasıl yapabilirim?

Asagidaki kod basli basina calisan bir program. Bir GUI ile etkilesmesini istiyorsan yapisini ve akisini degistirmen lazim. En basidinden: Ana while loop’u GUI thread’inde calisamaz. exit hic bir thread’den cagrilamaz.

PyQt5 veya genel GUI kutuphanesi akisi ogrenirken (veya hic bulasmadan) hacky cozumlere gitmek de mumkun, kodu cok degistirmeden. Fakat bu konuda yardim edebilmek icin su dediklerini anlamamiz gerekiyor olabilir:

Benim gordugum, 0 olarak tanimlanmis:

openclick2 tusu yok da OpenClick_2 fonksiyonu var. Yerel bir cf degiskeni yaratiyor. algorithm modulunun FunctionAlgo fonksiyonunun icindeki cf degiskenini degistirmek istiyorsun gibi gozukuyor. Bu zor; cf’yi modul seviyesine global degisken olarak cikartman lazim. Veya FunctionAlgo’yu bir sinifa donusturmen.

OpenClick_2 fonksiyonunun icinden algorithm modulundeki FunctionAlgo fonksiyonundaki tessfunc fonksiyonunu cagiramadigini soyluyorsun sanirim. Aradaki kismi atlamissin.

1 Beğeni

Evet hepsini doğru anlamışsın :slight_smile: cf = 0 yani bunu global değişken haline getir diyorsun bu tamam fakat Bu durumda FunctionAlgoyu sınıfa dönüştürdüğümde kod çalışmıyor. Format sorunu çıkarıyor.

FunctionAlgo ilk önce class olarak tanımlıydı fakat executable hatasından dolayı definition’a çevirdim ve kod çalıştığı için kurcalamadım.

OpenClick_2 fonksiyonunun icinden algorithm modulundeki FunctionAlgo fonksiyonundaki tessfunc fonksiyonunu cagiramadigini soyluyorsun sanirim. Aradaki kismi atlamissin.

doğrudur tam olarak çözemediğim kısım budur.

Bunun sebebi tess func fonksiyonunun yaptığı belirtilen şeyleri diğer kod blokları yaptığı için olabilir mi?

FunctionAlgo‘Yu class olarak oluşturup tessfunc()’ı

from program import App

Olarak çağırmam mümkün müdür?

Bunlar nedir bilemedim. Istersen sinifa dondur, bakalim.

algorithm.FunctionAlgo.tessfunc


Yalniz cf’yi global yapmak bunlarin hepsinden bagimsiz bir cozum sanki.


Hayir, bu kod program modulundeki App ismini iceri alir, baska bir sey yapmaz. tessfunc program modulunde bile degil, algorithm’de FunctionAlgo altinda degil miydi?

Her halukarda tessfunc’u modul seviyesine cikartarak baslayabilirsin (tessfunc’u FunctionAlgo metodu yapmaya alternatif)

      from PIL import Image
      import numpy as np
      import sys
      import glob
      import os
      from subprocess import call
      from urllib.request import urlopen
      from collections import Counter
      import json
      from pathlib import Path
      import re
      import webbrowser
      
      from program import get_jsonparsed_data
  
      class FunctionAlgo(object):
          def __init__ (self) :
              self.cf = 0
              self.ResultStr = [ '' ]
     
      
      
          def LogicOpStrings (self ) :
              l = len ( self.ResultStr )
              self.newArr = [ ]
              for i in range ( 0, l ) :
                  if not self.ResultStr[ i ] == "" :
                     self.newArr.append ( self.ResultStr[ i ].replace ( "\n", "" ).strip () )
      
              newArrSet = set ( self.newArr )
      
              url = ("https://raw.githubusercontent.com/dwyl/english-words/master/words_dictionary.json")
              print ( "Loading english dictionary from internet..." )
              wordDic = get_jsonparsed_data ( url )
              print ( "English word vocabulary has been successfully loaded!" )
      
              validWordCountMap = [ ]
      
              l = len ( self.newArr )
              for i in range ( 0, l ) :
                  count = 0
                  wordChunks = self.newArr[ i ].split ( ' ' )
                  for j in range ( 0, len ( wordChunks ) ) :
                      if wordChunks[ j ].lower () in wordDic :
                          count = count + 1
                      else :
                         print ( wordChunks[ j ], " is not a valid word!" )
                 validWordCountMap.append ( count )
     
                 print ( "-----Overall result:-----" )
                 print ( self.newArr[ validWordCountMap.index ( self.most_Common ( validWordCountMap ) ) ] )
                  print ( "-------------------------" )
     
          def get_jsonparsed_data (url) :
              response = urlopen ( url )
              data = response.read ().decode ( "utf-8" )
              return json.loads ( data )
      
          def most_Common (lst) :
              data = Counter ( lst )
              return data.most_common ( 1 )[ 0 ][ 0 ]
      
          def tessfunc (self ) :
              os.system ( "tesseract file.png data" )
              self.clearTesseractExecNote ()
              with open ( 'data.txt', 'r' ) as mf :
                  try :
                      content = mf.read ()
                     if (not content.isspace ()) :
                          self.ResultStr.append ( content )
                          print ( "\nResult:\n********************************************\n",
                                 re.sub ( '[^0-9\r\n]+', ' ', content ), "\n********************************************" )
                  except UnicodeDecodeError :
                      print ( "Unicode character found which cant be decoded" )
      
          def removechunk ( self) :
             for i in self.glob.glob ( 'file*.png' ) :
                 print ( "Unlinked %s" % i )
                  self.os.unlink ( i )
      
          def clearTesseractExecNote ( self) :
              print ( "\033[A                                                          \033[A" )
              print ( "\033[A                                                          \033[A" )
      
          print ( "Accessing device's camera..." )
          cap = cv2.VideoCapture ( 0 )
          print ( "\033[A                                           \033[A" )
          print ( "Camera ready!" )
          print ( "Activated command mode!\nPress 's' to start text recognition" )
          count = 0
          while (True) :
              ret, frame = cap.read ()
              gray = cv2.cvtColor ( frame, cv2.COLOR_BGR2GRAY )
              cv2.imshow ( 'Frame', gray )
              ret, thresh = cv2.threshold ( gray, 0, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU )
             cv2.imwrite ( 'file.png', thresh )
              if cf == 1 :
                  tessfunc ()
              if cv2.waitKey ( 1 ) & 0xFF == ord ( 'q' ) :
                  cf = 0
              if cv2.waitKey ( 1 ) & 0xFF == ord ( 's' ) :
                  cf = 1
                  text = f = open ( "data.txt", "r" )
                 url = "url"
                  url2 = "url2"
                  url3 = url + "J" + "text" + url2
      
                  print ( url3 )
                  webbrowser.open ( url3, new=0, autoraise=True )
      
              if cv2.waitKey ( 1 ) & 0xFF == ord ( 'e' ) :
                  print ( "Terminating the program" )
           break
     
          cap.release ()
         exit ()
main.py
```     from PyQt5 import QtCore, QtGui, QtWidgets
      import algorithm
      from program import tessfunc
       
       
       class Ui_MainWindow ( object ) :
           def setupUi (self, MainWindow) :
               MainWindow.setObjectName ( "MainWindow" )
               MainWindow.resize ( 519, 354 )
               self.centralwidget = QtWidgets.QWidget ( MainWindow )
              self.centralwidget.setObjectName ( "centralwidget" )
               self.pushButton = QtWidgets.QPushButton ( self.centralwidget )
               self.pushButton.setGeometry ( QtCore.QRect ( 210, 140, 75, 23 ) )
               self.pushButton.setObjectName ( "pushButton" )
               self.pushButton_2 = QtWidgets.QPushButton ( self.centralwidget )
               self.pushButton_2.setObjectName ( "pushButton_2" )
               MainWindow.setCentralWidget ( self.centralwidget )
               self.retranslateUi ( MainWindow )
               QtCore.QMetaObject.connectSlotsByName ( MainWindow )
      
           def retranslateUi (self, MainWindow) :
               _translate = QtCore.QCoreApplication.translate
               MainWindow.setWindowTitle ( _translate ( "MainWindow", "MainWindow" ) )
               self.pushButton.setText ( _translate ( "MainWindow", "Open" ) )
              self.pushButton_2.setText ( _translate ( "MainWindow", "Get" ) )
               self.pushButton.clicked.connect ( self.OpenClick )
               self.pushButton_2.clicked.connect ( self.OpenClick_2 )
      
      
      
           def OpenClick (self) :
               self.cf==0
               algorithm.FunctionAlgo().tessfunc ()
       
           def OpenClick_2 (self) :
               self.cf == 1
               algorithm.FunctionAlgo.tessfunc ()
      
       
       if __name__ == "__main__" :
           import sys
       
          app = QtWidgets.QApplication ( sys.argv )
           MainWindow = QtWidgets.QMainWindow ()
           ui = Ui_MainWindow ()
         ui.setupUi ( MainWindow )
         MainWindow.show ()
         sys.exit ( app.exec_ () )```

Kodu iki ``` satiri arasina alir misin

Pardon farketmemiştim şimdi düzelttim.

Malesef olmamis.

Kodu, dosyada bulundugu gibi alip koyman lazim.

Veya soyle soyleyeyim: benim yazdigini alip editore yapistirdigimda calistirabilmem lazim. (Belki 1-2 hata duzelterek.)


Okudugum kadariyla: Fonksiyon ici (yerel) degiskenleri class’a koymana gerek yok. newArr LogicOpStrings'e lokal gordugum kadariyla, self. ekstra kulfet olmus.

OpenClick'lerden adresledigin cf de Ui_MainWindow'un cf'si degil, FunctionAlgo'nun cf'si olmali.

FunctionAlgo'yu kullanabilmek icin ornekleyip ornegi bir yerde saklamali, tessfunc ve cf gibi uyelerini de ornek uzerinden kullanmalisin.

Main.py ve program.pyyi ayri tablara kopyalayip Main.py calistirinca acilmadi mi?

Bende o sekilde calisiyor. Olusturulan arayuzde open’a basınca tum kod calısıyor.

self.’ları Python önerdiği için koydum belirttiğim gibi öncelikli amacım arayuzun acılması ve open ile kodu calıstırmak. Bu şekilde calıştır dediğimde arayüz açılmıyor ve doğrudan open tuşuna basılmış gibi çalıştırıyor.

Burada tıkandım.

Otomatik formatlama olabilir. O zaman formatlama sonrasindaki kodu paylasmani rica edecegim.


Python degil, IDE onermistir.

Arayuzu bosverip main calistigi anda Algo’yu calistirmayi denedin mi? Once onu yapmak lazim. Sonra, cf’yi onden veya 3 saniye bekledikten sonra degistirmeyi deneyebilirsin. Onemli olan main’deki GUI degil cunku, Algo’nun disaridan kullanilabilecek sekilde tasarlanmasi.


Bi de genel olarak soyle bir tavsiye verecegim:

Bunlari aciklarken hangi arayuzun acilmasindan ve hangi kodu calistirmaktan bahsettigini netlestirirsen sadece karsindaki biriyle iletisimin kolaylasmaz, problemi kendin de daha iyi dusunmeye baslarsin.

Yapilmasi gerekeni de netlestireyim:

import algorithm
algo = algorithm.FunctionAlgo()
algo.run()

Bu kodun calisabilmesi, butona basinca olmasini istedigin seyi yapmasi lazim.

Veya, dedigim gibi, butun FunctionAlgo’nun PyQt5 ile calisabilecek sekilde yeniden yapilandirilmasi lazim.

Teşekkürler bu önerileri bir deneyeyim sonrasında hem güncel kodu hem de sonuçları yazacağım zira kurcalamaktan kod çalışmaz duruma geldi şu anda :slight_smile: