1
0
Fork 0
mirror of synced 2024-06-23 08:40:45 +12:00
Rare/rare/components/dialogs/install_dialog.py

188 lines
7.3 KiB
Python
Raw Normal View History

2021-02-10 23:48:25 +13:00
import os
from PyQt5.QtCore import Qt, QObject, QRunnable, QThreadPool, pyqtSignal, pyqtSlot
2021-05-22 02:48:15 +12:00
from PyQt5.QtWidgets import QDialog, QFileDialog, QCheckBox
2021-02-10 23:48:25 +13:00
from custom_legendary.core import LegendaryCore
2021-05-22 02:48:15 +12:00
from custom_legendary.utils.selective_dl import games
from rare.ui.components.dialogs.install_dialog import Ui_InstallDialog
2021-04-23 00:34:06 +12:00
from rare.utils.extra_widgets import PathEdit
from rare.utils.models import InstallOptionsModel
2021-05-21 09:00:38 +12:00
from rare.utils.utils import get_size
2021-02-10 23:48:25 +13:00
class InstallDialog(QDialog, Ui_InstallDialog):
2021-05-22 02:48:15 +12:00
options = False
2021-02-18 05:46:03 +13:00
2021-05-22 02:48:15 +12:00
def __init__(self, app_name, core: LegendaryCore, update=False, parent=None):
super(InstallDialog, self).__init__(parent)
self.setAttribute(Qt.WA_DeleteOnClose, True)
self.setupUi(self)
self.core = core
self.app_name = app_name
self.game = self.core.get_game(app_name)
self.update_game = update
self.threadpool = QThreadPool.globalInstance()
2021-05-22 02:48:15 +12:00
header = self.tr("Update") if update else self.tr("Install")
self.install_dialog_label.setText(f"<h3>{header} \"{self.game.app_title}\"</h3>")
self.setWindowTitle(f"{self.windowTitle()} - {header} \"{self.game.app_title}\"")
if self.core.lgd.config.has_option("Legendary", "install_dir"):
default_path = self.core.lgd.config.get("Legendary", "install_dir")
else:
default_path = os.path.expanduser("~/legendary")
if not default_path:
default_path = os.path.expanduser("~/legendary")
2021-05-22 02:48:15 +12:00
self.install_dir_edit = PathEdit(text=default_path,
file_type=QFileDialog.DirectoryOnly,
edit_func=self.on_install_dir_text_changed)
2021-05-22 02:48:15 +12:00
self.install_dir_layout.addWidget(self.install_dir_edit)
if update:
self.install_dir_label.setVisible(False)
2021-05-22 02:48:15 +12:00
self.install_dir_edit.setVisible(False)
2021-02-10 23:48:25 +13:00
if self.core.lgd.config.has_option("Legendary", "max_workers"):
max_workers = self.core.lgd.config.get("Legendary", "max_workers")
else:
max_workers = 0
self.max_workers_spin.setValue(int(max_workers))
2021-05-22 02:48:15 +12:00
self.sdl_list_checks = list()
self.tags = ['']
2021-05-22 02:48:15 +12:00
try:
for key, info in games[app_name].items():
cb = QDataCheckBox(info['name'], info['tags'])
if key == '__required':
self.tags.extend(info['tags'])
cb.setChecked(True)
cb.setDisabled(True)
self.sdl_list_layout.addWidget(cb)
self.sdl_list_checks.append(cb)
self.sdl_list_frame.resize(self.sdl_list_frame.minimumSize())
for cb in self.sdl_list_checks:
cb.stateChanged.connect(self.on_sdl_checkbox_changed)
2021-05-22 02:48:15 +12:00
except KeyError:
self.sdl_list_frame.setVisible(False)
self.sdl_list_label.setVisible(False)
self.get_install_info(app_name, default_path, self.tags)
2021-02-10 23:48:25 +13:00
self.install_button.clicked.connect(self.on_install_button_clicked)
self.cancel_button.clicked.connect(self.on_cancel_button_clicked)
2021-02-10 23:48:25 +13:00
2021-05-22 02:48:15 +12:00
self.resize(self.minimumSize())
self.setFixedSize(self.size())
2021-02-10 23:48:25 +13:00
2021-05-22 02:48:15 +12:00
def get_install_options(self, path=None):
2021-04-17 09:41:59 +12:00
if path:
2021-05-22 02:48:15 +12:00
self.install_dir_edit.setText(path)
2021-02-10 23:48:25 +13:00
self.exec_()
2021-05-22 02:48:15 +12:00
return self.options
2021-02-18 05:46:03 +13:00
2021-05-22 02:48:15 +12:00
def get_install_info(self, app_name, path, tags):
message = self.tr("Updating...")
self.download_size_info_label.setText(message)
self.download_size_info_label.setStyleSheet("font-style: italic; font-weight: normal")
2021-05-22 02:48:15 +12:00
self.install_size_info_label.setText(message)
self.install_size_info_label.setStyleSheet("font-style: italic; font-weight: normal")
self.install_button.setEnabled(False)
2021-05-22 02:48:15 +12:00
self.sdl_list_frame.setEnabled(False)
info_worker = InstallInfoWorker(app_name, path, tags, self.core)
info_worker.setAutoDelete(True)
info_worker.signals.finished.connect(self.on_worker_finished)
self.threadpool.start(info_worker)
2021-05-22 02:48:15 +12:00
def on_sdl_checkbox_changed(self):
self.tags = ['']
2021-05-22 02:48:15 +12:00
for cb in self.sdl_list_checks:
if data := cb.isChecked():
self.tags.extend(data)
self.get_install_info(self.app_name, self.install_dir_edit.text(), self.tags)
def on_install_dir_text_changed(self, path: str):
2021-05-22 02:48:15 +12:00
self.get_install_info(self.app_name, path, self.tags)
def on_install_button_clicked(self):
self.options = InstallOptionsModel(
2021-05-22 02:48:15 +12:00
app_name=self.app_name,
path=self.install_dir_edit.text() if not self.update_game else None,
max_workers=self.max_workers_spin.value(),
force=self.force_download_check.isChecked(),
ignore_free_space=self.ignore_space_check.isChecked(),
dl_only=self.download_only_check.isChecked(),
2021-05-22 02:48:15 +12:00
sdl_list=self.tags
)
self.threadpool.clear()
2021-02-18 05:46:03 +13:00
self.close()
def on_cancel_button_clicked(self):
self.threadpool.clear()
self.close()
2021-02-18 05:46:03 +13:00
def on_worker_finished(self, info: tuple):
download_size, install_size = info
# TODO: Check available size and act accordingly
# TODO: (show message in label | color it | disable install unless ignore)
# TODO: Find a way to get the installation size delta and show it
if download_size is not None and install_size is not None:
if download_size:
self.download_size_info_label.setText("{}".format(get_size(download_size)))
self.download_size_info_label.setStyleSheet("font-style: normal; font-weight: bold")
self.install_button.setEnabled(True)
else:
self.install_size_info_label.setText(self.tr("Game already installed"))
self.install_size_info_label.setStyleSheet("font-style: italics; font-weight: normal")
self.install_size_info_label.setText("{}".format(get_size(install_size)))
self.install_size_info_label.setStyleSheet("font-style: normal; font-weight: bold")
else:
self.download_size_info_label.setText("Error")
self.install_size_info_label.setText("Error")
2021-05-22 02:48:15 +12:00
self.sdl_list_frame.setEnabled(True)
2021-02-18 05:46:03 +13:00
class InstallInfoWorkerSignals(QObject):
finished = pyqtSignal(tuple)
2021-02-18 05:46:03 +13:00
class InstallInfoWorker(QRunnable):
2021-02-18 05:46:03 +13:00
2021-05-22 02:48:15 +12:00
def __init__(self, app_name, path, tags, core: LegendaryCore):
super(InstallInfoWorker, self).__init__()
self.signals = InstallInfoWorkerSignals()
self.core = core
self.app_name = app_name
self.path = path
2021-05-22 02:48:15 +12:00
self.tags = tags
@pyqtSlot()
def run(self):
try:
dlm, analysis, game, igame, repair, repair_file = self.core.prepare_download(
app_name=self.app_name,
base_path=self.path,
2021-05-22 02:48:15 +12:00
sdl_prompt=lambda app_name, title: self.tags
)
self.signals.finished.emit((analysis.dl_size, analysis.install_size))
except:
self.signals.finished.emit((None, None))
return
2021-05-22 02:48:15 +12:00
class QDataCheckBox(QCheckBox):
def __init__(self, text, data=None):
super(QDataCheckBox, self).__init__()
self.setText(text)
self.data = data
def isChecked(self):
if super(QDataCheckBox, self).isChecked():
return self.data
else:
return False