Skip to content

Commit 39afd6f

Browse files
committed
feat(gui): add dynamic welcome tab when no compiler engines are active
Signed-off-by: Samuel Amen Ague <ague.samuel27@gmail.com>
1 parent 37545bf commit 39afd6f

4 files changed

Lines changed: 264 additions & 7 deletions

File tree

Lines changed: 203 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,203 @@
1+
# SPDX-License-Identifier: Apache-2.0
2+
# Copyright 2026 Samuel Amen Ague
3+
#
4+
# Licensed under the Apache License, Version 2.0 (the "License");
5+
# you may not use this file except in compliance with the License.
6+
# You may obtain a copy of the License at
7+
#
8+
# http://www.apache.org/licenses/LICENSE-2.0
9+
#
10+
# Unless required by applicable law or agreed to in writing, software
11+
# distributed under the License is distributed on an "AS IS" BASIS,
12+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
# See the License for the specific language governing permissions and
14+
# limitations under the License.
15+
16+
from __future__ import annotations
17+
18+
from PySide6.QtCore import Qt
19+
from PySide6.QtWidgets import (
20+
QWidget,
21+
QVBoxLayout,
22+
QHBoxLayout,
23+
QLabel,
24+
QPushButton,
25+
QFrame,
26+
)
27+
28+
29+
class HelloTab(QWidget):
30+
def __init__(self, gui, parent=None):
31+
super().__init__(parent)
32+
self.gui = gui
33+
self.setObjectName("tab_hello")
34+
self.init_ui()
35+
if hasattr(self.gui, "register_language_refresh"):
36+
try:
37+
self.gui.register_language_refresh(self.retranslate_ui)
38+
except Exception:
39+
pass
40+
41+
def init_ui(self):
42+
# Main layout
43+
layout = QVBoxLayout(self)
44+
layout.setContentsMargins(30, 30, 30, 30)
45+
layout.setSpacing(12)
46+
layout.setAlignment(Qt.AlignmentFlag.AlignCenter)
47+
48+
# Title Label
49+
self.title_label = QLabel()
50+
self.title_label.setObjectName("welcome_title")
51+
self.title_label.setAlignment(Qt.AlignmentFlag.AlignCenter)
52+
self.title_label.setStyleSheet(
53+
"font-size: 16pt; font-weight: bold; color: #ffffff;"
54+
)
55+
56+
# Description Label
57+
self.desc_label = QLabel()
58+
self.desc_label.setObjectName("welcome_desc")
59+
self.desc_label.setAlignment(Qt.AlignmentFlag.AlignCenter)
60+
self.desc_label.setWordWrap(True)
61+
self.desc_label.setStyleSheet(
62+
"font-size: 9.5pt; color: #a0a0a0; max-width: 500px;"
63+
)
64+
65+
# Guide Box (Frame)
66+
self.guide_box = QFrame()
67+
self.guide_box.setStyleSheet(
68+
"QFrame {"
69+
" background-color: #2b2b2b;"
70+
" border: 1px solid #3d3d3d;"
71+
" border-radius: 6px;"
72+
" margin-top: 10px;"
73+
"}"
74+
)
75+
guide_layout = QVBoxLayout(self.guide_box)
76+
guide_layout.setContentsMargins(15, 15, 15, 15)
77+
guide_layout.setSpacing(6)
78+
79+
self.guide_title = QLabel()
80+
self.guide_title.setObjectName("welcome_guide_title")
81+
self.guide_title.setStyleSheet(
82+
"font-size: 10pt; font-weight: bold; color: #ffcc00; border: none;"
83+
)
84+
self.guide_title.setAlignment(Qt.AlignmentFlag.AlignCenter)
85+
86+
self.guide_desc = QLabel()
87+
self.guide_desc.setObjectName("welcome_guide")
88+
self.guide_desc.setStyleSheet("font-size: 9pt; color: #d4d4d4; border: none;")
89+
self.guide_desc.setWordWrap(True)
90+
self.guide_desc.setAlignment(Qt.AlignmentFlag.AlignCenter)
91+
92+
guide_layout.addWidget(self.guide_title)
93+
guide_layout.addWidget(self.guide_desc)
94+
95+
# Buttons layout
96+
btn_layout = QHBoxLayout()
97+
btn_layout.setSpacing(10)
98+
btn_layout.setAlignment(Qt.AlignmentFlag.AlignCenter)
99+
100+
# Settings/Config Button
101+
self.btn_config = QPushButton()
102+
self.btn_config.setObjectName("btn_welcome_config")
103+
self.btn_config.setMinimumSize(140, 30)
104+
self.btn_config.setStyleSheet(
105+
"QPushButton {"
106+
" background-color: #0e639c;"
107+
" color: #ffffff;"
108+
" font-weight: bold;"
109+
" font-size: 9pt;"
110+
" border: none;"
111+
" border-radius: 4px;"
112+
"}"
113+
"QPushButton:hover {"
114+
" background-color: #1177bb;"
115+
"}"
116+
)
117+
if hasattr(self.gui, "open_advanced_config_editor"):
118+
self.btn_config.clicked.connect(self.gui.open_advanced_config_editor)
119+
120+
# Help Button
121+
self.btn_help = QPushButton()
122+
self.btn_help.setObjectName("btn_welcome_help")
123+
self.btn_help.setMinimumSize(140, 30)
124+
self.btn_help.setStyleSheet(
125+
"QPushButton {"
126+
" background-color: #3c3c3c;"
127+
" color: #ffffff;"
128+
" font-size: 9pt;"
129+
" border: 1px solid #555555;"
130+
" border-radius: 4px;"
131+
"}"
132+
"QPushButton:hover {"
133+
" background-color: #454545;"
134+
"}"
135+
)
136+
if hasattr(self.gui, "show_help_dialog"):
137+
self.btn_help.clicked.connect(self.gui.show_help_dialog)
138+
139+
btn_layout.addWidget(self.btn_config)
140+
btn_layout.addWidget(self.btn_help)
141+
142+
# Spacer to push elements into center-top vertical layout
143+
layout.addSpacing(10)
144+
layout.addWidget(self.title_label)
145+
layout.addWidget(self.desc_label)
146+
layout.addWidget(self.guide_box)
147+
layout.addSpacing(10)
148+
layout.addLayout(btn_layout)
149+
layout.addStretch()
150+
151+
self.retranslate_ui()
152+
153+
def retranslate_ui(self):
154+
try:
155+
from pycompiler_ark.Ui.i18n import translate
156+
157+
ctx = self.gui.id if hasattr(self.gui, "id") else "ui"
158+
159+
t_title = translate(ctx, "welcome_title", "Bienvenue dans PyCompiler ARK")
160+
t_desc = translate(
161+
ctx,
162+
"welcome_desc",
163+
"Un outil de compilation et d'empaquetage universel pour vos applications Python.",
164+
)
165+
t_guide_title = translate(
166+
ctx, "welcome_guide_title", "Aucun moteur de compilation disponible"
167+
)
168+
t_guide_desc = translate(
169+
ctx,
170+
"welcome_guide",
171+
"Veuillez installer un moteur de compilation pour commencer.",
172+
)
173+
t_btn_config = translate(
174+
ctx, "btn_welcome_config", "Configurer les moteurs"
175+
)
176+
t_btn_help = translate(ctx, "btn_welcome_help", "Aide & Documentation")
177+
except Exception:
178+
t_title = "Bienvenue dans PyCompiler ARK"
179+
t_desc = "Un outil de compilation et d'empaquetage universel pour vos applications Python."
180+
t_guide_title = "Aucun moteur de compilation disponible"
181+
t_guide_desc = "Veuillez installer un moteur de compilation pour commencer."
182+
t_btn_config = "Configurer les moteurs"
183+
t_btn_help = "Aide & Documentation"
184+
185+
self.title_label.setText(t_title)
186+
self.desc_label.setText(t_desc)
187+
self.guide_title.setText(t_guide_title)
188+
self.guide_desc.setText(t_guide_desc)
189+
self.btn_config.setText(t_btn_config)
190+
self.btn_help.setText(t_btn_help)
191+
192+
def destroy(self, destroyWindow=True, destroySubWindows=True):
193+
if hasattr(self.gui, "unregister_language_refresh"):
194+
try:
195+
self.gui.unregister_language_refresh(self.retranslate_ui)
196+
except Exception:
197+
pass
198+
super().destroy(destroyWindow, destroySubWindows)
199+
200+
201+
def create_hello_tab(gui) -> HelloTab:
202+
"""Create a new HelloTab widget for the GUI."""
203+
return HelloTab(gui)

pycompiler_ark/Core/engine/registry.py

Lines changed: 45 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -537,8 +537,18 @@ def bind_tabs(gui) -> None:
537537
except Exception:
538538
pass
539539

540-
# Get the Hello tab if it exists
540+
# Get the Hello tab if it exists, or create it dynamically
541541
hello_tab = getattr(gui, "tab_hello", None)
542+
if hello_tab is None:
543+
try:
544+
from pycompiler_ark.Core.engine.hello_tab import create_hello_tab
545+
546+
hello_tab = create_hello_tab(gui)
547+
if hello_tab is not None:
548+
setattr(gui, "tab_hello", hello_tab)
549+
except Exception:
550+
pass
551+
542552
hello_tab_index = -1
543553
if hello_tab is not None:
544554
try:
@@ -648,10 +658,27 @@ def _wrap_tab_scroll(widget):
648658
)
649659
continue
650660

651-
# Hide the Hello tab if any engine has created a tab
652-
if any_engine_tab_created and hello_tab_index >= 0:
661+
# Show/add or hide/remove the Hello tab depending on whether engine tabs exist
662+
if hello_tab is not None:
653663
try:
654-
tabs.tabBar().hideTab(hello_tab_index)
664+
if any_engine_tab_created:
665+
if hello_tab_index >= 0:
666+
tabs.removeTab(hello_tab_index)
667+
else:
668+
if hello_tab_index < 0:
669+
title = "Bienvenue"
670+
try:
671+
from pycompiler_ark.Ui.i18n import translate
672+
673+
title = translate(
674+
gui.id if hasattr(gui, "id") else "ui",
675+
"tab_hello",
676+
"Bienvenue",
677+
)
678+
except Exception:
679+
pass
680+
tabs.insertTab(0, hello_tab, title)
681+
tabs.setCurrentWidget(hello_tab)
655682
except Exception:
656683
pass
657684
except Exception:
@@ -669,9 +696,20 @@ def show_hello_tab(gui) -> None:
669696
if hello_tab is not None:
670697
try:
671698
idx = tabs.indexOf(hello_tab)
672-
if idx >= 0:
673-
tabs.tabBar().showTab(idx)
674-
tabs.setCurrentIndex(idx)
699+
if idx < 0:
700+
title = "Bienvenue"
701+
try:
702+
from pycompiler_ark.Ui.i18n import translate
703+
704+
title = translate(
705+
gui.id if hasattr(gui, "id") else "ui",
706+
"tab_hello",
707+
"Bienvenue",
708+
)
709+
except Exception:
710+
pass
711+
tabs.insertTab(0, hello_tab, title)
712+
tabs.setCurrentWidget(hello_tab)
675713
except Exception:
676714
pass
677715
except Exception:

pycompiler_ark/languages/en.yml

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -112,3 +112,11 @@ init_project_install_reqs: Install dependencies
112112
init_project_note: 'Note: This will create an ark.yml file and configure the project
113113
structure.'
114114
init_project_success: Project initialized successfully!
115+
tab_hello: "Welcome"
116+
welcome_title: "Welcome to PyCompiler ARK"
117+
welcome_desc: "A universal Python compilation and packaging tool."
118+
welcome_guide_title: "No compiler engines available"
119+
welcome_guide: "Please install a compiler engine to get started."
120+
btn_welcome_config: "Configure Engines"
121+
btn_welcome_help: "Help & Docs"
122+

pycompiler_ark/languages/fr.yml

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -115,3 +115,11 @@ init_project_install_reqs: Installer les dépendances
115115
init_project_note: 'Note : Cela va créer un fichier ark.yml et configurer la structure
116116
du projet.'
117117
init_project_success: Projet initialisé avec succès !
118+
tab_hello: "Bienvenue"
119+
welcome_title: "Bienvenue dans PyCompiler ARK"
120+
welcome_desc: "Un outil de compilation et d'empaquetage universel pour vos applications Python."
121+
welcome_guide_title: "Aucun moteur de compilation disponible"
122+
welcome_guide: "Veuillez installer un moteur de compilation pour commencer."
123+
btn_welcome_config: "Configurer les moteurs"
124+
btn_welcome_help: "Aide & Documentation"
125+

0 commit comments

Comments
 (0)