Введение
Я учусь в университете по программированию.Мои курсы сосредоточены на Java, C # и C ++, поэтому у меня есть некоторый опыт работы с ООП.В настоящее время я занят своим кооперативом, и мне нужно создать графический интерфейс с использованием Python и tkinter (которые я изучаю по ходу работы).
Моя проблема связана именно с Python OOP инаследование нескольких файлов в нескольких каталогах, и я просто не могу понять это (прошло 3 дня)
Если вы не хотите просматривать несколько строк сокращенных файлов и примеров кода, вы можете найтиФактический код здесь:
https://github.com/bkleynhans/Landsat-Buoy-Calibration.git
Затем перейдите в конец страницы, чтобы перейти к списку вопросов.
Вы не сможете запуститьСистема калибровки, если у вас не установлен ModTran, который является дорогим лицензионным программным обеспечением.Тем не менее, графический интерфейс должен быть полностью работоспособным, единственное нестандартное требование - tkcalendar.
Что я сделал
Я работал с ссылками ниже, а также со ссылками, включенными воба других члена.
ImportError: невозможно импортировать имя
ImportError: Невозможно импортировать имя X
, а также
https://www.digitalocean.com/community/tutorials/understanding-class-inheritance-in-python-3
https://www.python -course.eu / python3_inheritance.php
https://chrisyeh96.github.io/2017/08/08/definitive-guide-python-imports.html
К сожалению, я не могуКажется, они не связаны с моей проблемой, будь то из-за того, что я недостаточно осведомлен или просто медлительный.
Структура папок
Моя структура папок выглядит следующим образом:
Z:.
│
│ tarca_gui
│
└───gui
│
│ __init__.py
│ tarca_gui.py
│
│
└───forms
│
│ input_notebook.py
│ status_frame.py
│ settings_frame.py
│ example_date_picker_supplied.py
│ settings_notebook.py
│ input_frame.py
│ help_menu.py
│ header_frame.py
│ progress_bar.py
│ __init__.py
│ menu_bar.py
│ example_date_picker.py
│ output_frame.py
│
└─
Сводка файлов
tarca_gui в корне - это просто bash-скрипт, который переходит в рабочий каталог и выполняет графический интерфейс пользователя
cd ~/Landsat-Buoy-Calibration/gui
python3 tarca_gui.py
Размещение файлов и их кода здесьбудет большой беспорядок, однако я буду вставлять заголовки и структуры.Ссылка GitHub на проект находится в разделе введения выше.
Обязательные нестандартные библиотеки: tkcalendar - https://pypi.org/project/tkcalendar/
tarca_gui.py - запускает программу из терминала linux и создаетинтерфейс с использованием tkinter.Все остальные файлы получены на основе следующей структуры
Базовый класс
tarca_gui.py
from tkinter import *
from tkinter import messagebox
import inspect
import sys
import os
import pdb
class Tarca_Gui:
def __init__(self, master):
# Import gui paths
from forms import progress_bar
from forms import menu_bar
from forms import header_frame
from forms import input_frame
from forms import output_frame
from forms import status_frame
# Create the root Tkinter object
master.title('CIS Top Of Atmosphere Radiance Calibration System')
master.geometry('800x600')
master.resizable(False, False)
#master.configure(background = '#FFFFFF')
master.option_add('*tearOff', False)
# Create the Progressbar window - accessed via master.progressbar_window.progress_bar
progress_bar.Progress_Bar(master)
# Create the Menubar - accessed via master.menu_bar
menu_bar.Menu_Bar(master)
# Create the Header - accessed via master.header_frame
header_frame.Header_Frame(master)
# Create the Input Frame - accessed via master.
input_frame.Input_Frame(master)
# Create the Input Frame - accessed via master.
output_frame.Output_Frame(master)
# Create the Input Frame - accessed via master.
status_frame.Status_Frame(master)
# Calculate fully qualified path to location of program execution
def get_module_path():
filename = inspect.getfile(inspect.currentframe())
path = os.path.dirname(os.path.abspath(inspect.getfile(inspect.currentframe())))
return path, filename
# Set environment variables to locate current execution path
def set_path_variables():
path, filename = get_module_path()
# find the Calibration program path
path_index = path.rfind('/')
# append gui paths
sys.path.append(path[:path_index])
sys.path.append(path)
sys.path.append(path + "/forms")
def on_closing(root):
if messagebox.askyesno("Quit", "Do you really wish to quit?"):
root.destroy()
def main():
set_path_variables()
root = Tk()
root.protocol("WM_DELETE_WINDOW", lambda: on_closing(root))
tarca_gui = Tarca_Gui(root)
root.mainloop()
if __name__ == "__main__": main()
progress_bar, menu_bar, header_frame, input_frame, output_frame и рамка состоянияполучены из (extends) targa_gui
Резюме производных классов
progress_bar.py extends tarca_gui.py
from tkinter import *
from tkinter import ttk
import tarca_gui
class Progress_Bar(tarca_gui.Tarca_Gui):
def __init__(self, master):
menu_bar.py extends tarca_gui.py
from tkinter import *
from tkinter import ttk
import tarca_gui
import help_menu
from gui.forms import settings_frame
class Menu_Bar(tarca_gui.Tarca_Gui):
def __init__(self, master):
header_frame.py extends tarca_gui.py
from tkinter import *
from tkinter import ttk
from forms import input_frame
class Header_Frame(input_frame.Input_Frame):
def __init__(self, master):
input_frame.py extends tarca_gui.py
from tkinter import *
from tkinter import ttk
import tarca_gui
from gui.forms import input_notebook
class Input_Frame(tarca_gui.Tarca_Gui):
def __init__(self, master):
output_frame.py extends tarca_gui.py
from tkinter import *
from tkinter import ttk
import tarca_gui
class Output_Frame(tarca_gui.Tarca_Gui):
def __init__(self, master):
status_frame.py extends tarca_gui.py
from tkinter import *
from tkinter import ttk
import tarca_gui
class Status_Frame(tarca_gui.Tarca_Gui):
def __init__(self, master):
Остальные классы: help_menu, settings_frame, settings_notebook, header_frame и input_notebook получены из (расширений) других классов
header_frame.py extendsinput_frame.py
from tkinter import *
from tkinter import ttk
from forms import input_frame.py
import pdb
class Header_Frame(input_frame.Input_Frame):
def __init__(self, master):
input_notebook.py extends input_frame.py
from tkinter import *
from tkinter import ttk
from tkinter import filedialog
from gui.forms import input_frame
from tkcalendar import Calendar, DateEntry
from datetime import date
class Input_Notebook(input_frame.Input_Frame):
def __init__(self, master):
help_menu.py extends menu_bar.py
from tkinter import *
from tkinter import ttk
import time
import threading
import menu_bar
class Help_Menu(menu_bar.Menu_Bar):
def __init__(self, master):
settings_frame.py extends settings_notebook.py
from tkinter import *
from tkinter import ttk
from tkinter import messagebox
from gui.forms import menu_bar
from gui.forms import settings_notebook
class Settings_Frame(menu_bar.Menu_Bar):
def __init__(self, master):
settings_notebook.py extends settings_frame.py
from tkinter import *
from tkinter import ttk
from tkinter import filedialog
from gui.forms import settings_frame
class Settings_Notebook(settings_frame.Settings_Frame):
def __init__(self, master):
Проблема и вопрос
Во-первых, PYTHONPATH обновляется при запуске графического интерфейса через функцииВы можете просмотреть в базовом классе.
Во-вторых, я понимаю, что в настоящее время все классы импортируются не одинаково, они были и были изменены в моих попытках найти проблему и будут стандартизированы в ближайшее время.как проблема была решена.
Проблема
Весь графический интерфейс работает нормально, пока я не попытаюсь импортировать Settings_Frame в settings_notebook.py
Получена ошибка
% ./tarca_gui
Traceback (most recent call last):
File "tarca_gui.py", line 104, in <module>
if __name__ == "__main__": main()
File "tarca_gui.py", line 100, in main
tarca_gui = Tarca_Gui(root)
File "tarca_gui.py", line 31, in __init__
from forms import menu_bar
File "/cis/otherstu/bxk8027/Landsat-Buoy-Calibration/gui/forms/menu_bar.py", line 20, in <module>
import help_menu
File "/cis/otherstu/bxk8027/Landsat-Buoy-Calibration/gui/forms/help_menu.py", line 21, in <module>
import menu_bar
File "/cis/otherstu/bxk8027/Landsat-Buoy-Calibration/gui/forms/menu_bar.py", line 21, in <module>
from gui.forms import settings_frame
File "/cis/otherstu/bxk8027/Landsat-Buoy-Calibration/gui/forms/settings_frame.py", line 21, in <module>
from gui.forms import settings_notebook
File "/cis/otherstu/bxk8027/Landsat-Buoy-Calibration/gui/forms/settings_notebook.py", line 25, in <module>
class Settings_Notebook(settings_frame.Settings_Frame):
AttributeError: module 'gui.forms.settings_frame' has no attribute 'Settings_Frame'
Выводы
Я полагаю, что это связано с циклическим импортом, поскольку settings_frame импортирует settings_notebook и наоборот.
Путаница
Я понимаю, что по возможности следует избегать циклических ссылок, однако, как я сейчас понимаю Python OOP, мне нужно импортировать settings_notebook в settings_frame, чтобы построить его, но в то же время мне нужно импортировать settings_frame в settings_notebook для того, чтобырасширить его (settings_notebook должен быть потомком settings_frame)
Вопрос
Я не знаю, что я делаю неправильно.
- Это импортили я так структурировал свои классы?
- Если я неправильно понимаю структуру классов (с импортом), пожалуйста, объясните, что я сделал неправильно, чтобы я мог учиться и больше не повторять ту же ошибку.
- Буду очень признателен за любые другие предложения, касающиеся контейнера.
В заключение
Если вы сделали это далеко, во-первых, большое спасибо.
Как уже упоминалось, я учусь в университете и изучаю C ++, C #, Java, Python, HTML, CSS, JavaScript, PHP, SQL, Unity иd Нереальный движок в то же время (иногда я путаюсь с понятиями между ними), поэтому любые предложения, касающиеся какой-либо части моего кода, будут с благодарностью.