0

I have a python program, and inside it are a lot of images linked specifically through a file path. I used pyinstaller to export the program and it worked on my computer, however when sending it to another computer - an error occurred. It said the resource could not be found. Is there any way to bundle the images into a single executable file?

Edit:

I did try this however it didn't work:

def resource_path(relative_path):
""" Get absolute path to resource, works for dev and for PyInstaller """
try:
    # PyInstaller creates a temp folder and stores path in _MEIPASS
    base_path = sys._MEIPASS
except Exception:
    base_path = os.path.abspath(".")

return os.path.join(base_path, relative_path)

Edit:

I'm creating the application in tkinter.

Thanks.

  • this solution might help you. https://stackoverflow.com/questions/31836104/pyinstaller-and-onefile-how-to-include-an-image-in-the-exe-file – MEdwin Jul 19 '22 at 10:12
  • @MEdwin I tried that and it didn't work, for some reason. – Joshilovessnow Jul 19 '22 at 10:12
  • Does this answer your question? [pyinstaller seems not to find a data file](https://stackoverflow.com/questions/7838606/pyinstaller-seems-not-to-find-a-data-file) – l -_- l Jul 19 '22 at 10:16
  • @l-_-l I tried that however it didn't work – Joshilovessnow Jul 19 '22 at 10:17
  • You need to make sure that each of the files are listed in your MANIFEST file, and then they should each be paired with its corresponding output path in your spec file – Alexander Jul 19 '22 at 11:31
  • @alexpdev Not to be stupid or anything, but what is the MANIFEST file and how do I edit it? – Joshilovessnow Jul 19 '22 at 11:38
  • @Joshilovessnow Read this https://packaging.python.org/en/latest/guides/using-manifest-in/ – Alexander Jul 19 '22 at 11:49
  • @Joshilovessnow is this project you are trying to compile saved in its own github repo? – Alexander Jul 19 '22 at 11:52
  • Cool I'll read that, thanks :) – Joshilovessnow Jul 19 '22 at 11:52
  • @alexpdev No I'm not, Im trying to compile it into a setup file (using inno setup) so I can send it to other people. – Joshilovessnow Jul 20 '22 at 06:37
  • I understand that, however if you had it setup in a github repo I could clone it and try to compile it to help figure out what is going wrong. Can you create an example repo project that has the same issue and put it on github?? – Alexander Jul 20 '22 at 06:52
  • https://github.com/joshilovessnow/BundledImageError/blob/main/BundledImageError – Joshilovessnow Jul 20 '22 at 23:24
  • That's the basis on what I'm trying to do...My actual application has a couple more buttons, where I need to set their image backgrounds. Also the icon of the window is a problem. Thanks for helping so far :) – Joshilovessnow Jul 20 '22 at 23:27
  • @alexpdev sorry I forgot to ping you :) – Joshilovessnow Jul 21 '22 at 23:10
  • @Joshilovessnow you only provided the program code though.... I need the full project. So all of the external icons and what not you can just use blank images if you want but it needs to be structured in the same way as your project directory names and all for it to be of any use – Alexander Jul 22 '22 at 03:17
  • @alexpdev Thanks for helping so far! The code in the repository is not nearly as long as my actual program. However, the concept is the same. I added the icon for the window, and the button background into the repo and the directories are identical to the ones in my proper application. If you manage to compile it, would it be possible for you to let me know how? Thanks a lot. https://github.com/joshilovessnow/BundledImageError – Joshilovessnow Jul 24 '22 at 00:14

1 Answers1

0

I lost days on this, so I'm adding this answer as much for myself as anyone else. It combines many other SO answers into one 'simpler' example. This builds an 'All in One' windows .exe file.

First, create a build.py file for PyInstaller in the applications root directory. (Note : PyInstaller overwrites .spec files so avoid editing them). You will have to run the command multiple times after code edits, so it makes sense to create a reusable script. Here is an example which you need to customise:

import PyInstaller.__main__

PyInstaller.__main__.run([
    'gui\main.py',
    '--name=myappname', # Name for .exe
    '--distpath=dist',  
    '--add-data=images/main.ico;./images', # Icon to replace tkinter feather
    '--add-data=images/logo.png;./images', # An image used in the app
    '--clean',
    '--onefile',
    '--windowed',
    '--noconsole',
], )

Above I use ; because I'm creating an .exe for windows, use : for Linux and Mac.

Second : As mentioned above you need to include the resource_path function in your app:

import os
import sys

def resource_path(relative_path):
    try:
        base_path = sys._MEIPASS
    except Exception:
        base_path = os.path.abspath(".")

    return os.path.join(base_path, relative_path)

Third : Use this function with your images :

self.iconbitmap(resource_path("images/main.ico"))

Wrap other images used in your app such as a company logo used within the app :

path_to_image = os.path.join("images", "logo.png")
self.myImage = PhotoImage(file=(resource_path(path_to_image)))

This should now build a onefile .exe with the images bundled nicely inside, and work on other computers (at least with the same version of Windows you built the app on).

Inyoka
  • 1,287
  • 16
  • 24