0

I'm trying to build a one-file EXE with pyinstaller that uses pytesseract OCR. The .exe file is going to be used in several PC's. Let's suppose this is my .py code that I want to turn to .exe

import cv2
import os
import ast
import sys

def OCR():
    # direct path to pytesseract used previously
    # pytesseract.pytesseract.tesseract_cmd = r'C:\Users\user\AppData\Local\Programs\Tesseract-OCR\tesseract.exe'

    pytesseract.pytesseract.tesseract_cmd = resource_path('tesseract.exe')

    #Replace with random jpeg or png file
    image = cv2.imread(r'C:\Users\user\Downloads\IMG_1.JPG')

    Read = pytesseract.image_to_string(image, config='--psm 11')
    print(Read)


def resource_path(relative_path):
    if hasattr(sys, "_MEIPASS"):
        return os.path.join(sys._MEIPASS, 'Tesseract-OCR', relative_path)
    return os.path.join(relative_path)


OCR()

And the .spec file

# -*- mode: python ; coding: utf-8 -*-


block_cipher = None


a = Analysis(
    ['C:\\Users\\user\\AppData\\Local\\Microsoft\\WindowsApps\\pythonProject3\\SimpleOCR.py'],
    pathex=[],
    binaries=[(r'C:\\Users\\user\\AppData\\Local\\Programs\\Tesseract-OCR', 'Tesseract-OCR') ],
    datas=[],
    hiddenimports=[],
    hookspath=[],
    hooksconfig={},
    runtime_hooks=[],
    excludes=[],
    win_no_prefer_redirects=False,
    win_private_assemblies=False,
    cipher=block_cipher,
    noarchive=False,
)
pyz = PYZ(a.pure, a.zipped_data, cipher=block_cipher)

exe = EXE(
    pyz,
    a.scripts,
    a.binaries,
    a.zipfiles,
    a.datas,
    [],
    name='SimpleOCR',
    debug=False,
    bootloader_ignore_signals=False,
    strip=False,
    upx=True,
    upx_exclude=[],
    runtime_tmpdir=None,
    console=True,
    disable_windowed_traceback=False,
    argv_emulation=False,
    target_arch=None,
    codesign_identity=None,
    entitlements_file=None,
)

After creating the .exe file and When executing the .exe file in another computer. It gives me a TypeError: Unsupported image object, although I'm using the same image (not hard coded) making it unavailable to use the OCR.

Any ideas?

Added my full code below

from PySide2.QtWidgets import QLabel, QVBoxLayout, QMessageBox, QGridLayout
from PySide2.QtWidgets import QScrollArea, QMainWindow
from PySide2.QtWidgets import QHBoxLayout,QLineEdit, QApplication, QWidget, QPushButton, QStackedLayout, QFileDialog
from PySide2.QtCore import Qt
from PySide2.QtGui import QPixmap,QTransform
import pyautogui
import sys
from os.path import expanduser
import pytesseract
import cv2
import os
import pandas as pd
import ast
pd.set_option('display.max_columns', None)
pd.set_option('display.max_rows', None)
pd.set_option('display.max_colwidth', None)
#pytesseract.pytesseract.tesseract_cmd = r'C:\Users\francisco.carmo\AppData\Local\Programs\Tesseract-OCR\tesseract.exe'

## ---- Main Programs ----

def ocr():

    pytesseract.pytesseract.tesseract_cmd = resource_path('tesseract.exe')
    print(pytesseract.pytesseract.tesseract_cmd)
    pyautogui.FAILSAFE = True
    pyautogui.PAUSE = 2
    # ---- Absolute Path Imagens ----

    # ---- Código ocr ----

    Data = {'Fotos': folder_pick.imgList,
            'PN': [0] * len(folder_pick.imgList),
            'Fotosaux': folder_pick.imgListaux}

    Data2 = {'Fotos': folder_pick.tagList}

    # Create DataFrame
    folder_pick.df = pd.DataFrame(Data)
    folder_pick.df['PN'] = folder_pick.df['PN'].astype(str)
    folder_pick.df2 = pd.DataFrame(Data2)
    folder_pick.df3 = folder_pick.df.loc[folder_pick.df['Fotosaux'].isin(folder_pick.df2['Fotos'])]
    folder_pick.df3index = folder_pick.df3.index.tolist()
    vari = 0

    for i in folder_pick.df3.index.tolist():

        try:

            image = cv2.imread(folder_pick.df['Fotos'][i])

            Read = pytesseract.image_to_string(image, config='--psm 11')

            for l in range(len(Read)):

                if Read[l] == '2' and Read[l + 1] == '3' and Read[l + 2] == '0':
                    if Read[l:l + 8].isnumeric() == True:
                        folder_pick.df.loc[i,'PN'] = Read[l:l + 8]

                        print(str(vari)+', ' + Read[l:l + 8])
                        break
                    else:
                        break

            if folder_pick.df['PN'][i] == '0':

                gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
                thresh = cv2.threshold(gray, 0, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU)[1]
                data = pytesseract.image_to_string(thresh, config='--psm 6')
                for k in range(len(data)):

                    if data[k] == '2' and data[k + 1] == '3' and data[k + 2] == '0':
                        if data[k:k + 8].isnumeric() == True:

                            folder_pick.df.loc[i, 'PN'] = data[k:k + 8]
                            print(str(vari)+', ' + data[k:k + 8] + ', 2')
                            break
                        else:
                            break
                if folder_pick.df['PN'][i] == '0':
                    print(str(vari)+', ' + folder_pick.df['Fotos'][i])
            vari +=1

        except Exception as error:
            print("An exception occurred:", type(error).__name__, "–", error)
            pass


    for i in folder_pick.df[~folder_pick.df.index.isin(folder_pick.df3index)].index.tolist():

        if i > 0:
            k = i-1
        else:
            k = 0
        while folder_pick.df['PN'][i] == '0':

            if k in folder_pick.df3index:
                folder_pick.df.loc[i, 'PN'] = folder_pick.df['PN'][k]
                break
            elif k == 0:
                break
            else:
                k -= 1
                continue

    preview_screen.preview_table()

        #######################################


def change_PN():

    #folderPath
    for i in folder_pick.df['PN'].unique():
        var = 1
        #o k tem valor 0,1,2 ou o index real da coluna?
        for k in folder_pick.df.index[folder_pick.df['PN'] == i].tolist():
            folder_pick.df.at[k, 'PN'] = str(folder_pick.df['PN'][k]) + '__' + str(var)
            var += 1

    for i in range(len(folder_pick.df['Fotos'])):
        if folder_pick.df['PN'][i] == '0':
            continue
        else:
            os.rename(str(folder_pick.df['Fotos'][i]), (str(folder_pick.folderPath) + "\\" + folder_pick.df['PN'][i] + '.jpg'))





    ## ---- GUI ---- ##
class user_interface(QMainWindow):
    def __init__(self, parent=None):
        super(user_interface, self).__init__(parent)
        self.setWindowTitle('Atribuição de PN avaliação')

        # ---- Different Windows ----
        user_interface.normalInstructions = instructions(self)
        user_interface.folderPick = folder_pick(self)
        user_interface.previewScreen = preview_screen(self)
        user_interface.runningScreen = running_screen(self)
        user_interface.filesdone = files_done(self)

        # ---- Layout Central Widget ----
        centralWidget = QWidget()
        centralLayout = QGridLayout()
        centralLayout.addWidget(self.normalInstructions, 0, 0)

        centralLayout.addWidget(self.folderPick, 0, 0)
        centralLayout.addWidget(self.previewScreen, 0, 0)
        centralLayout.addWidget(self.runningScreen, 0, 0)
        centralLayout.addWidget(self.filesdone, 0, 0)
        centralWidget.setLayout(centralLayout)

        self.setCentralWidget(centralWidget)

        ## --- Set Up ----
        user_interface.normalInstructions.show()
        self.show()


## ---- Instructions Window ---- ##
class instructions(QWidget):
    def __init__(self, parent=None):
        super(instructions, self).__init__(parent)
        # --- Widget Layout ---
        self.windowLayout = QVBoxLayout()
        self.textLayout = QStackedLayout()
        self.tickLayout = QVBoxLayout()
        self.buttonLayout = QGridLayout()

        # ---- Instruction Text ---
        msg_1 = "Instruções:"
        msg_1 += "\n \n 1. Tirar fotos na ordem etiqueta -> restantes fotos."
        msg_1 += "\n 2. Colocar fotos numa pasta no computador. NÃO numa drive."
        msg_1 += "\n 3. Orientar as fotos horizontalmente antes de iniciar o programa."
        msg_1 += "\n 4. Correr programa."
        msg_1 += "\n Nota: Não colocar primeiro na drive e depois na pasta final - ao passarem pela drive, as fotos perdem resolução. \n"


        text_1 = QLabel(msg_1, self)
        text_1.setWordWrap(True)
        text_1.adjustSize()
        self.textLayout.addWidget(text_1)




        # ---- OK button -----
        self.instructionsButton = QPushButton("Next")
        self.instructionsButton.pressed.connect(self.instructions_OK)
        self.buttonLayout.addWidget(QLabel(), 0, 0)
        self.buttonLayout.addWidget(QLabel(), 0, 1)
        self.buttonLayout.addWidget(self.instructionsButton, 0, 2, Qt.AlignRight)

        self.windowLayout.addLayout(self.textLayout)
        self.windowLayout.addLayout(self.tickLayout)
        self.windowLayout.addLayout(self.buttonLayout)

        self.setLayout(self.windowLayout)
        self.hide()



    def instructions_OK(self):
        user_interface.normalInstructions.hide()



        user_interface.folderPick.show()

        adjust_size()


class folder_pick(QWidget):
    def __init__(self, parent=None):
        super(folder_pick, self).__init__(parent)

        # --- Widget Layout ---
        self.windowLayout = QVBoxLayout()
        self.textLayout = QVBoxLayout()
        self.folderselectLayout = QGridLayout()
        self.tagselectLayout = QGridLayout()
        self.tickLayout = QVBoxLayout()
        self.tick2Layout = QVBoxLayout()
        self.buttonLayout = QGridLayout()

        # ---- Text ----
        msg = "Seleccione a pasta que contém as imagens a alterar o PN."
        text = QLabel(msg, self)
        text.setWordWrap(True)
        text.adjustSize()
        self.textLayout.addWidget(text)

        # ---- Image Selection ----
        folder_pick.folder_input = QLineEdit()
        folder_pick.folder_input.setFixedWidth(350)
        folder_pick.folder_input.textChanged.connect(self.foldertext_changed)

        # ---- Tag Selection ----
        folder_pick.tag_input = QLineEdit()
        folder_pick.tag_input.setFixedWidth(350)
        folder_pick.tag_input.textChanged.connect(self.foldertext_changed2)

        self.folderButton = QPushButton("Procurar")
        self.folderButton.pressed.connect(self.folder_dialogue)

        self.folderselectLayout.addWidget(folder_pick.folder_input, 0, 0, Qt.AlignCenter)
        self.folderselectLayout.addWidget(self.folderButton, 0, 1, Qt.AlignCenter)

        self.folderButton2 = QPushButton("Procurar")
        self.folderButton2.setEnabled(False)
        self.folderButton2.pressed.connect(self.folder_dialogue2)

        self.tagselectLayout.addWidget(folder_pick.tag_input, 0, 0, Qt.AlignCenter)
        self.tagselectLayout.addWidget(self.folderButton2, 0, 1, Qt.AlignCenter)



        # ---- Buttons ----
        self.backFolder = QPushButton("Back")
        self.backFolder.pressed.connect(self.backbtn_folder)
        self.nextFolder = QPushButton("Next")
        self.nextFolder.pressed.connect(self.nextbtn_folder)
        self.nextFolder.setEnabled(False)
        self.buttonLayout.addWidget(self.backFolder, 0, 0, Qt.AlignLeft)
        self.buttonLayout.addWidget(QLabel(), 0, 1)
        self.buttonLayout.addWidget(self.nextFolder, 0, 2, Qt.AlignRight)

        # ---- Set Up ----
        self.windowLayout.addLayout(self.textLayout)
        self.windowLayout.addLayout(self.folderselectLayout)
        self.windowLayout.addLayout(self.tickLayout)
        self.windowLayout.addLayout(self.tagselectLayout)
        self.windowLayout.addLayout(self.tick2Layout)
        self.windowLayout.addLayout(self.buttonLayout)

        self.setLayout(self.windowLayout)

        self.hide()



    # ---- Folder Select ----
    def folder_dialogue(self):
        folder_pick.df = None
        folder_pick.folderPath = QFileDialog.getExistingDirectory(self, 'Pasta c/ fotografias',
                                                      expanduser("~") + '\Documents', QFileDialog.ShowDirsOnly)

        #print(os.listdir(folderPath))
        folder_pick.folder_input.setText(folder_pick.folderPath)

    def folder_dialogue2(self):
        folder_pick.df2 = None
        folder_pick.folderPath2, _ = QFileDialog.getOpenFileNames(self, 'Selecionar imagens de etiquetas apenas', folder_pick.folderPath,'Image Files (*.png *.jpg *.jpeg)')
        folder_pick.tag_input.setText(str(folder_pick.folderPath2))




    # ---- Path Validator ----
    # If the file is an image that exists in the system
    # The Next button is enabled
    # Otherwise the text shows up in red and the Next button is disabled
    def foldertext_changed(self):
        if os.path.exists(folder_pick.folder_input.text()):
            folder_pick.folder_input.setStyleSheet("color:black;")
            self.folderButton2.setEnabled(True)
        else:
            folder_pick.folder_input.setStyleSheet("color:red;")
            self.nextFolder.setEnabled(False)

    def foldertext_changed2(self):
        self.nextFolder.setEnabled(True)


    # --- Window Change Buttons ----
    def backbtn_folder(self):
        user_interface.folderPick.hide()
        if instructions.qecTick.isChecked():
            user_interface.normalInstructions.show()
        else:
            user_interface.normalInstructions.show()
        adjust_size()

    def nextbtn_folder(self):
        folder_pick.imgListaux = []
        imgList = get_pics()
        tagList = get_pics2()
        if len(imgList) == 0:
            QMessageBox.critical(self, 'Erro!', "Pasta sem imagens!", QMessageBox.Ok)
        elif len(imgList) == 0:
            QMessageBox.critical(self, 'Erro!', "Nenhuma etiqueta selecionada!", QMessageBox.Ok)
        else:
            folder_pick.imgList = imgList
            folder_pick.tagList = tagList
            user_interface.folderPick.hide()
            user_interface.runningScreen.show()
            adjust_size()
            QMessageBox.information(self, '!', "Programa a correr!", QMessageBox.Ok)

            ocr()
            user_interface.runningScreen.hide()
            adjust_size()
            width = 1600
            height = 1000
            window.setFixedSize(width, height)
            user_interface.previewScreen.show()



## ---- Screen with the images ----
class preview_screen(QWidget):
    def __init__(self, parent=None):
        super(preview_screen, self).__init__(parent)

        # --- Widget Layout ---
        self.windowLayout = QVBoxLayout()
        preview_screen.previewLayout = QGridLayout()
        self.scroll_layout = QVBoxLayout()
        self.buttonLayout = QGridLayout()

        # --- Image List ---
        self.scroll = QScrollArea()
        self.img_list = QWidget()
        self.img_list.setLayout(preview_screen.previewLayout)
        self.scroll.setWidgetResizable(True)
        self.scroll.setWidget(self.img_list)
        self.scroll_layout.addWidget(self.scroll)

        # ---- Buttons ----
        self.backPreview = QPushButton("Back")
        self.backPreview.pressed.connect(self.backbtn_preview)
        self.goButton = QPushButton("Go")
        self.goButton.pressed.connect(self.go_button)
        self.buttonLayout.addWidget(self.backPreview, 0, 0, Qt.AlignLeft)
        self.buttonLayout.addWidget(QLabel(), 0, 1)
        self.buttonLayout.addWidget(self.goButton, 0, 2, Qt.AlignRight)

        # ---- Set Up ----
        self.windowLayout.addLayout(self.scroll_layout)
        self.windowLayout.addLayout(self.buttonLayout)

        self.setLayout(self.windowLayout)

        self.hide()

    def preview_table():

        preview_screen.previewLayout.addWidget(QLabel('Fase'), 0, 0, Qt.AlignCenter)
        preview_screen.previewLayout.addWidget(QLabel('Fotografia'), 0, 1, Qt.AlignCenter)
        #sliderlist = list(range(len(folder_pick.df['Fotos'])))
        buttonlist = list(range(len(folder_pick.df['Fotos'])))
        #print(folder_pick.df)
        aux = [0] * len(folder_pick.df['Fotos'])
        no = 0
        preview_screen.img = list(range(len(folder_pick.df['Fotos'])))
        preview_screen.img_map = list(range(len(folder_pick.df['Fotos'])))
        preview_screen.rotate_angle = [0] *(len(folder_pick.df['Fotos']))
        for i in range(len(folder_pick.df['Fotos'])):

            # ---- Image Rotation button----
            buttonlist[i] = QPushButton("Rotate")

            #print(sliderlist[i])
            no += 1
            preview_screen.img_map[i] = QPixmap(folder_pick.df['Fotos'][i])
            preview_screen.img_map[i] = preview_screen.img_map[i].scaledToWidth(1200)
            preview_screen.img[i] = QLabel()
            preview_screen.img[i].setPixmap(preview_screen.img_map[i])

            faseNo = str(i + 1) + str(0)

            preview_screen.previewLayout.addWidget(QLabel(""), no, 0, Qt.AlignCenter)
            no += 1
            preview_screen.previewLayout.addWidget(QLabel(""), no, 0, Qt.AlignCenter)
            no += 1
            preview_screen.previewLayout.addWidget(QLabel("PN Lido:"), no, 0, Qt.AlignCenter)

            # Create a container widget to hold both the button and line edit
            container = QWidget()
            container_layout = QHBoxLayout()



            if folder_pick.df['PN'][i] == '0':
                aux[i] = QLineEdit()
                #aux[i].setInputMask('00000000')
                container_layout.addWidget(aux[i])
            else:
                aux[i] = QLineEdit()
                aux[i].setText(folder_pick.df['PN'][i])
                #aux[i].setInputMask('00000000')
                container_layout.addWidget(aux[i])

            aux[i].textEdited.connect(lambda s, index=i: preview_screen.text_edited(s, index))
            #preview_screen.previewLayout.addWidget(buttonlist[i], no, 1)
            container_layout.addWidget(buttonlist[i])
            container.setLayout(container_layout)
            preview_screen.previewLayout.addWidget(container, no, 1, Qt.AlignLeft)
            #folder_pick.folder_input.textChanged.connect(preview_screen.text_changed)
            no += 1
            #preview_screen.previewLayout.addWidget(QCheckBox("Done"), no, 0, Qt.AlignTop)


            # Create a closure to capture the current values of img_map[i] and img[i]
            def create_button_handler(image, label, i):
                return lambda angle = 90, img=image, lbl=label: preview_screen.rotate_image(angle, img, lbl, i)

            # Connect the button to the closure
            buttonlist[i].clicked.connect(create_button_handler(preview_screen.img_map[i], preview_screen.img[i], i))


            #adicionar imagem e número
            preview_screen.previewLayout.addWidget(QLabel(faseNo), no, 0, Qt.AlignCenter)
            preview_screen.previewLayout.addWidget(preview_screen.img[i], no, 1, Qt.AlignCenter)


    def rotate_image(angle, image, img, i):
        preview_screen.rotate_angle[i] = (preview_screen.rotate_angle[i] + 90) % 360
        transform = QTransform().rotate(preview_screen.rotate_angle[i])
        rotated_image = image.transformed(transform, Qt.SmoothTransformation)
        img.setPixmap(rotated_image)

        # Update img_map with the rotated image
        preview_screen.img_map[i] = rotated_image
        preview_screen.img[i].setPixmap(rotated_image)

    def text_edited(s, i):
        folder_pick.df.loc[i, 'PN'] = s
        print(folder_pick.df)

    def backbtn_preview(self):
        user_interface.previewScreen.hide()
        user_interface.folderPick.show()
        adjust_size()

    def go_button(self):
        user_interface.previewScreen.hide()
        user_interface.runningScreen.show()
        adjust_size()
        window.showMinimized()
        change_PN()
        user_interface.runningScreen.hide()
        user_interface.filesdone.show()
        window.showMaximized()

class running_screen(QWidget):
    def __init__(self, parent=None):
        super(running_screen, self).__init__(parent)
        # --- Widget Layout ---
        self.windowLayout = QVBoxLayout()
        self.textLayout = QVBoxLayout()
        self.buttonLayout = QVBoxLayout()

        # ---- Text ----
        msg = "Programa a correr."
        text = QLabel(msg, self)
        text.setWordWrap(True)
        text.adjustSize()
        self.textLayout.addWidget(text)

        # ---- Buttons ----
        self.button = QPushButton("Terminar")
        self.button.pressed.connect(self.close_button)
        self.buttonLayout.addWidget(self.button, Qt.AlignHCenter)
        # ---- Set Up ----
        self.windowLayout.addLayout(self.textLayout)
        self.windowLayout.addLayout(self.buttonLayout)

        self.setLayout(self.windowLayout)

        self.hide()

    def close_button(self):
        sys.exit()

class files_done(QWidget):
    def __init__(self, parent=None):
        super(files_done, self).__init__(parent)
        # --- Widget Layout ---
        self.windowLayout = QVBoxLayout()
        self.textLayout = QVBoxLayout()
        self.buttonLayout = QVBoxLayout()

        # ---- Text ----
        msg = "Concluído com sucesso!"
        text = QLabel(msg, self)
        text.setWordWrap(True)
        text.adjustSize()
        self.textLayout.addWidget(text)

        # ---- Buttons ----
        self.button = QPushButton("Ok")
        self.button.pressed.connect(self.close_button)
        self.buttonLayout.addWidget(self.button, Qt.AlignHCenter)
        # ---- Set Up ----
        self.windowLayout.addLayout(self.textLayout)
        self.windowLayout.addLayout(self.buttonLayout)

        self.setLayout(self.windowLayout)

        self.hide()

    def close_button(self):
        QApplication.exit()

## ---- FILE PROCESSING ---- ##

# ---- Relative Path ----

def resource_path(relative_path):
    if hasattr(sys, "_MEIPASS"):
        return os.path.join(sys._MEIPASS, 'Tesseract-OCR', relative_path)
    return os.path.join(relative_path)


# ---- Get array with pictures ----
def get_pics():
    folder_pick.folderPath = folder_pick.folder_input.text().replace('/', '\\')
    #print(os.listdir(folderPath))
    imgList = []

    for img in os.listdir(folder_pick.folderPath):
        imgPath = folder_pick.folderPath + '\\' + img
        if imgpath_good(imgPath):
            imgList.append(imgPath)

    #imgList = sorted(imgList)
    imgList = sorted(imgList, key=os.path.getctime)
    for i in range(len(imgList)):
        folder_pick.imgListaux.append(imgList[i].replace(' ', ''))

    return imgList

def get_pics2():
    list=[]
    folder_pick.folderPath2 = sorted(folder_pick.folderPath2, key=os.path.getctime)
    folder_pick.folderPath2 = folder_pick.tag_input.text().replace('/', '\\')
    #print(os.listdir(folderPath))
    folder_pick.folderPath2 = folder_pick.folderPath2.replace("[", "").replace("]", "").replace(" ", "").replace("'", "")
    elements = folder_pick.folderPath2.split(",")
    for element in elements:
        list.append(element)
    list.append(folder_pick.folderPath2)
    folder_pick.folderPath2 = list


    return folder_pick.folderPath2



## ---- AUXILIARY FUNCTIONS ---- ##

# ---- Auto-adjust size and Make user unable to resize window ----
def adjust_size():
    window.setMinimumSize(0,0)
    window.setMaximumSize(1600,1200)
    window.adjustSize()
    width = window.frameGeometry().width()
    height= window.frameGeometry().height()
    #width = 1200
    #height = 900
    window.setFixedSize(width,height)

# ---- Check if the image has an acceptable path ----
def imgpath_good(testPath: str, pathGood = False):
    imgType = ('.jpg','.jpeg','.png','.gif','.bmp','.JPG')
    if testPath.endswith(imgType) and os.path.exists(testPath):
        pathGood = True
    return pathGood




app = QApplication([])

window = user_interface()
adjust_size()
app.exec_()

I get this message 4068 WARNING: lib not found: libgcc_s_dw2-1.dll dependency of C:\Users\francisco.carmo\AppData\Local\Programs\Tesseract-OCR\ambiguous_words.exe, 4175 INFO: Cannot get manifest resource from non-PE file C:\Users\francisco.carmo\AppData\Local\Programs\Tesseract-OCR\combine_lang_model.1.html and 5942 WARNING: Cannot get binary dependencies for file: C:\Users\francisco.carmo\AppData\Local\Programs\Tesseract-OCR\lstmeval.1.html for several files when creating the .exe file, am putting tesseract the right way in the .spec file?

  • Can you please format your question and use code markup so its easier to read? See also https://meta.stackoverflow.com/questions/251361/how-do-i-format-my-code-blocks – stranger0612 Jul 25 '23 at 12:32
  • put tesseract on your PATH and then you can just use shutil.which() – Alexander Jul 26 '23 at 03:31
  • I honestly don't know the executable you use, but maybe the executable is missing some dependencies? Have you tried to append the whole contet of 'C:\Users\user\AppData\Local\Programs\Tesseract-OCR' to the executable? – stranger0612 Jul 26 '23 at 05:34
  • I've updated the problem – Francisco Carmo Jul 26 '23 at 10:58

2 Answers2

1

I used the auto-py-to-ex to create the .exe giving tesseract folder as an additional file also did it on my personal computer. Althought I need to install tesseract on every PC I want to use the exe file. Check this if you have the same problem How to compile Python code with PyTesseract to EXE?

0

As mentioned in my comment, i don't know, if the executable has some dependencies that must be relative to it. That's why I would try to bundle the whole content of the folder instead of only the exe. To achieve this, update the two following lines.

return os.path.join(sys._MEIPASS, 'Tesseract-OCR', relative_path)

binaries=[(r'C:\\Users\\user\\AppData\\Local\\Programs\\Tesseract-OCR', 'Tesseract-OCR')],

EDIT:

In your current implementation you set you image hardcoded to

image = cv2.imread(r'C:\Users\user\Downloads\IMG_1.JPG')

Thats why the executable only works on your PC. If you keep the line as shown above, the file must be always at that location. I would recommend to do something like this.

import os
import sys

execution_path = os.path.dirname(sys.argv[0])
image = os.path.join(execuation_path, 'IMG_1.JPG')

With that approach, just keep an image named 'IMG_1.JPG' relative to the executable and it should work.

EDIT 2:

Check if the image path you create is valid and absolute by printing the image paths in your try/except case of function ocr to the console. Make sure to compile it with console True, so you get the output. Not a nice way of debugging but it should do the job.

stranger0612
  • 301
  • 1
  • 2
  • 12
  • That did work, but only on my computer. When executing the .exe file in another computer. It gives me a TypeError: Unsupported image object, although I'm using the same image. – Francisco Carmo Jul 26 '23 at 16:10
  • See my edit above – stranger0612 Jul 27 '23 at 04:42
  • That's not the problem, in my real code the images are being given as an input by the app user. In my code above IMG_1.JPG is just an example – Francisco Carmo Jul 27 '23 at 08:44
  • How do you provide the path of the image? Mind to update the question, so we see how the "real" code works? Also check this entry here. https://stackoverflow.com/questions/51364353/unsupported-image-object-using-tesseract – stranger0612 Jul 27 '23 at 09:35
  • I'm using a pyside QLineEdit() and let the user select the images. I have updated my full code. I have already looked at that, but didn't find anything useful to solve the problem. – Francisco Carmo Jul 27 '23 at 10:06
  • Sorry to hear that you still got no success :( At least we could fix your initial pyinstaller problem I guess? The problem is, I also have not used Qt, yet. But I got one last idea you could try. I add it to my answer – stranger0612 Jul 27 '23 at 11:22
  • Yes, it's printing the right path of the image. It's strange that I can run the .exe on a pen throw my computer and works fine, but not on another computer. I even installed the tesseract in the other PCs and the code doesn't work. Thank you for your help. – Francisco Carmo Jul 27 '23 at 14:10
  • I have updated the question. It's giving me some warnings when creating the .exe file – Francisco Carmo Jul 27 '23 at 14:53