Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
54 changes: 41 additions & 13 deletions examples/output_console.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

import logging
import sys
from argparse import ArgumentParser

import Qt
from Qt.QtCore import QDateTime
Expand All @@ -26,7 +27,7 @@


class ExampleApp(QMainWindow):
def __init__(self, parent=None):
def __init__(self, parent=None, init_preditor=True):
super().__init__(parent=parent)
# Use a .ui file to simplify the example code setup.
Qt.QtCompat.loadUi(__file__.replace(".py", ".ui"), self)
Expand All @@ -40,6 +41,8 @@ def __init__(self, parent=None):
self.uiAllLoggingChangeHandlersBTN.released.connect(
self.all_logging_change_handlers
)
self.uiUsePrEditorStyleCHK.toggled.connect(self.set_stdout_style)
self.uiRemovePrEditorStyleBTN.released.connect(self.clear_stdout_style)
self.uiLoggingCriticalBTN.released.connect(self.level_critical)
self.uiLoggingErrorBTN.released.connect(self.level_error)
self.uiLoggingWarningBTN.released.connect(self.level_warning)
Expand All @@ -51,12 +54,15 @@ def __init__(self, parent=None):
self.uiSendLoggingBTN.released.connect(self.send_logging)

# 1. Create the preditor instance and connect to the console's controllers
plog = preditor.instance(parent=self, create=True)
preditor.connect_preditor(self)
self.uiAllLog.controller = plog
self.uiSelectLog.controller = plog
self.uiStdout.controller = plog
self.uiStderr.controller = plog
if init_preditor:
plog = preditor.instance(parent=self, create=True)
preditor.connect_preditor(self)
self.uiAllLog.controller = plog
self.uiSelectLog.controller = plog
self.uiStdout.controller = plog
self.uiStderr.controller = plog
else:
self.setWindowTitle(f"{self.windowTitle()} - No PrEditor")

# 2. Configure the various OutputConsole widgets.
# Note: this can be done in the .ui file, but for this example we will
Expand Down Expand Up @@ -149,6 +155,11 @@ def clear_all(self):
self.uiStdout.clear()
self.uiStderr.clear()

def clear_stdout_style(self):
"""Reset uiStdout's style to not use PrEditor's style."""
self.uiUsePrEditorStyleCHK.setChecked(False)
self.uiStdout.setStyleSheet(None)

def level_critical(self):
logging.root.setLevel(logging.CRITICAL)

Expand Down Expand Up @@ -176,6 +187,14 @@ def print_time_stderr(self):
def raise_exception(self):
raise RuntimeError(self.message_time())

def set_stdout_style(self, state):
"""Enable/disable uiStdout using PrEditor's style.

Note: Disabling it doesn't clear the style, just prevent it from being
automatically updated when changed in PrEditor.
"""
self.uiStdout.use_console_stylesheet = state

def send_logging(self):
logger_a.critical("A critical msg for logger_a")
logger_a.error("A error msg for logger_a")
Expand All @@ -198,18 +217,27 @@ def send_logging(self):


if __name__ == '__main__':
parser = ArgumentParser("Example of using OutputConsole features.")
parser.add_argument(
"--no-preditor",
action="store_true",
help="Don't init and install the PrEditor console.",
)
args = parser.parse_args()

# Configure PrEditor for this application, start capturing all text output
# from stderr/stdout so once PrEditor is launched, it can show this text.
# This does not initialize any QtGui/QtWidgets.
preditor.configure(
# This is the name used to store PrEditor preferences and workboxes
# specific to this application.
'output_console',
)
if not args.no_preditor:
preditor.configure(
# This is the name used to store PrEditor preferences and workboxes
# specific to this application.
'output_console',
)

# Create a Gui Application allowing the user to show PrEditor
app = QApplication(sys.argv)
main_gui = ExampleApp()
main_gui = ExampleApp(init_preditor=not args.no_preditor)

main_gui.show()
app.exec_()
49 changes: 45 additions & 4 deletions examples/output_console.ui
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,11 @@
</property>
<layout class="QHBoxLayout" name="horizontalLayout_3">
<item>
<widget class="OutputConsole" name="uiAllLog"/>
<widget class="OutputConsole" name="uiAllLog">
<property name="use_console_stylesheet" stdset="0">
<bool>true</bool>
</property>
</widget>
</item>
<item>
<layout class="QGridLayout" name="gridLayout">
Expand Down Expand Up @@ -126,9 +130,46 @@
<property name="title">
<string>Stdout</string>
</property>
<layout class="QVBoxLayout" name="verticalLayout_2">
<item>
<widget class="OutputConsole" name="uiStdout"/>
<layout class="QGridLayout" name="gridLayout_2">
<item row="1" column="1">
<widget class="QPushButton" name="uiRemovePrEditorStyleBTN">
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Reset stylesheet to empty and disable Use PrEditor Style Sheet.&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>Remove Style Sheet</string>
</property>
</widget>
</item>
<item row="1" column="0">
<widget class="QCheckBox" name="uiUsePrEditorStyleCHK">
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Enable using the stylesheet from the PrEditor instances Options -&amp;gt; Style menu. This OutputConsole doesn't have it enabled by default so it doesn't have the stylesheet applied. Checking this will load the style sheet. If you then uncheck it, the style sheet won't be cleared but it will no longer respect the PrEditor Options -&amp;gt; Style changes.&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>Use PrEditor Style Sheet</string>
</property>
</widget>
</item>
<item row="1" column="2">
<spacer name="horizontalSpacer">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
<item row="0" column="0" colspan="3">
<widget class="OutputConsole" name="uiStdout">
<property name="use_console_stylesheet" stdset="0">
<bool>false</bool>
</property>
</widget>
</item>
</layout>
</widget>
Expand Down
42 changes: 42 additions & 0 deletions preditor/gui/console_base.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,10 @@ class ConsoleBase(QTextEdit):

def __init__(self, parent: QWidget, controller: Optional[LoggerWindow] = None):
super().__init__(parent)
self._controller = None
self._stylesheet_changed_meta = None
self.controller = controller

self._first_show = True
# The last time a repaint call was made when writing. Used to limit the
# number of refreshes to once per X.X seconds.
Expand Down Expand Up @@ -156,7 +159,14 @@ def controller(self) -> Optional[LoggerWindow]:

@controller.setter
def controller(self, value: LoggerWindow):
if self._stylesheet_changed_meta and self.controller:
# Remove the existing signals if connected
self.controller.styleSheetChanged.disconnect(self._stylesheet_changed_meta)
self._stylesheet_changed_meta = None

self._controller = value
# Ensure the stylesheet is up to date and stays up to date.
self.init_stylesheet()

def codeHighlighter(self):
"""Get the code highlighter for the console
Expand Down Expand Up @@ -343,6 +353,22 @@ def init_excepthook(self, attrName=None, value=None):
if self.write_error in PreditorExceptHook.callbacks:
PreditorExceptHook.callbacks.remove(self.write_error)

def init_stylesheet(self, attrName=None, value=None):
if not self.controller:
return

signal = self.controller.styleSheetChanged
if self.use_console_stylesheet:
# Apply the stylesheet and ensure that future updates are respected
self._stylesheet_changed_meta = signal.connect(self.update_stylesheet)
self.update_stylesheet()

elif self._stylesheet_changed_meta:
# if disabling use_console_stylesheet, then remove the existing
# connection if it was previously connected.
signal.disconnect(self._stylesheet_changed_meta)
self._stylesheet_changed_meta = None

def maybeRepaint(self, force=False):
"""Forces the console to repaint if enough time has elapsed from the
last repaint.
Expand Down Expand Up @@ -579,6 +605,12 @@ def update_streams(self, attrName=None, value=None):
else:
self.stream_manager.remove_callback(self.write)

def update_stylesheet(self):
sheet = None
if self.controller:
sheet = self.controller.styleSheet()
self.setStyleSheet(sheet)

def get_logging_info(self, name):
# Look for a specific rule to handle this logging message
parts = name.split(".")
Expand Down Expand Up @@ -864,6 +896,16 @@ def logging_formatter_str(self, value):
stream_echo_stderr is disabled or you likely will get duplicate output.
"""

use_console_stylesheet = QtPropertyInit(
"_use_console_stylesheet", False, callback=init_stylesheet
)
"""Set this widgets stylesheet to the PrEditor instance's style sheet.

This ensures that the style of random OutputConsoles match even when not
parented to PrEditor. Enabling this will update the widgets style sheet, but
disabling it will not update the style sheet.
"""


# Build and add the class properties for regex patterns so subclasses can use them.
ConsoleBase._ConsoleBase__defineRegexPatterns()
6 changes: 6 additions & 0 deletions preditor/gui/output_console.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,11 @@
from ..utils.cute import QtPropertyInit
from .console_base import ConsoleBase


class OutputConsole(ConsoleBase):
"""A text widget used to show stdout/stderr writes."""

# Enable these settings by default
use_console_stylesheet = QtPropertyInit(
"_use_console_stylesheet", True, callback=ConsoleBase.init_stylesheet
)