gtk-stream 0.11.6__py3-none-any.whl → 0.12__py3-none-any.whl

Sign up to get free protection for your applications and to get access to all the features.
gtk_stream/_version.py CHANGED
@@ -12,5 +12,5 @@ __version__: str
12
12
  __version_tuple__: VERSION_TUPLE
13
13
  version_tuple: VERSION_TUPLE
14
14
 
15
- __version__ = version = '0.11.6'
16
- __version_tuple__ = version_tuple = (0, 11, 6)
15
+ __version__ = version = '0.12'
16
+ __version_tuple__ = version_tuple = (0, 12)
gtk_stream/application.py CHANGED
@@ -15,6 +15,9 @@
15
15
  # along with this program. If not, see <https://www.gnu.org/licenses/>.
16
16
 
17
17
  import sys
18
+ import threading
19
+ import signal
20
+
18
21
  from . import Gtk, GLib, Gdk
19
22
  from .common import printEvent
20
23
  from .properties import parse_property, get_prop_type, set_parse_prop
@@ -68,14 +71,31 @@ class GtkStreamApp(Gtk.Application):
68
71
  for cb in callback_queue:
69
72
  GLib.idle_add(cb)
70
73
  self.run_when_idle = GLib.idle_add
74
+
75
+ def on_sigint(a,b):
76
+ self.logger.info("SIGINT received, quitting application")
77
+ self.quit()
78
+ signal.signal(signal.SIGINT, on_sigint)
71
79
  self.connect('startup', on_startup)
80
+
81
+ def on_activate(a):
82
+ a.hold()
83
+ self.connect('activate', on_activate)
84
+
85
+ self.attrs_set = threading.Semaphore()
86
+ self.attrs_set.acquire()
72
87
 
73
- def nameWidget(self, id, w):
88
+ def name_widget(self, id, w):
74
89
  if id is not None:
75
90
  self.namedWidgets[id] = w
76
91
 
92
+ def set_attrs(self, attrs):
93
+ for name, val in attrs.items():
94
+ set_parse_prop(self, self, name, val)
95
+ self.attrs_set.release()
96
+
77
97
  @app_message('file-dialog')
78
- def openFileDialog(self, id, parent):
98
+ def open_file_dialog(self, id, parent):
79
99
  dialog = Gtk.FileDialog()
80
100
  dialog.props.modal = True
81
101
  def on_choose(_, b):
@@ -90,7 +110,7 @@ class GtkStreamApp(Gtk.Application):
90
110
  dialog.open(parent = self.namedWindows[parent], callback = on_choose)
91
111
 
92
112
  @app_message('window', single_store)
93
- def newWindow(self, document, id, **attrs):
113
+ def new_window(self, document, id, **attrs):
94
114
  win = Gtk.Window(application=self)
95
115
  for (attr_name, attr_val) in attrs.items():
96
116
  self.logger.debug("Setting attr '%s' on window", attr_name)
@@ -101,31 +121,31 @@ class GtkStreamApp(Gtk.Application):
101
121
  win.present()
102
122
 
103
123
  @app_message('style', style_store)
104
- def addStyle(self, style):
124
+ def add_style(self, style):
105
125
  provider = Gtk.CssProvider()
106
126
  provider.load_from_data(style)
107
127
  Gtk.StyleContext.add_provider_for_display(Gdk.Display.get_default(), provider, Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION)
108
128
 
109
129
  @app_message('add-icon-path')
110
- def addIconPath(self, path):
130
+ def add_icon_path(self, path):
111
131
  theme = Gtk.IconTheme.get_for_display(Gdk.Display.get_default())
112
132
  theme.add_search_path(path)
113
133
 
114
134
  @app_message('close-window')
115
- def closeWindow(self, id):
135
+ def close_window(self, id):
116
136
  self.namedWindows[id].close()
117
137
 
118
138
  @app_message('remove')
119
- def removeWidget(self, id):
139
+ def remove_widget(self, id):
120
140
  w = self.namedWidgets[id]
121
141
  w.get_parent().remove(w)
122
142
 
123
143
  @app_message('insert', multiple_store)
124
- def insertWidgets(self, documents, into):
144
+ def insert_widgets(self, documents, into):
125
145
  for doc in documents:
126
- self.insertWidget(doc, into)
146
+ self.insert_widget(doc, into)
127
147
 
128
- def insertWidget(self, document, into):
148
+ def insert_widget(self, document, into):
129
149
  if into in self.namedWidgets:
130
150
  w = self.namedWidgets[into]
131
151
  w.insert_child(document)
@@ -133,7 +153,7 @@ class GtkStreamApp(Gtk.Application):
133
153
  raise Exception(f"Error: unknown widget id '{into}'")
134
154
 
135
155
  @app_message('set-prop')
136
- def setProp(self, id, name, value):
156
+ def set_prop(self, id, name, value):
137
157
  w = self.namedWidgets[id]
138
158
  w.set_property(name, parse_property(get_prop_type(w.__class__, name), value)(self))
139
159
 
@@ -59,7 +59,9 @@ function GTK.receive() {
59
59
  import io
60
60
  import sys
61
61
  import os
62
+ import threading
62
63
  import xml.sax as sax
64
+
63
65
  from .parser import GtkStreamXMLHandler
64
66
  from .application import GtkStreamApp
65
67
  from .common import Logger, LogLevel
@@ -75,13 +77,24 @@ function GTK.receive() {
75
77
  logger = Logger(logLevel)
76
78
 
77
79
  app = GtkStreamApp(logger)
78
- handler = GtkStreamXMLHandler(logger,app)
79
- errHandler = GtkStreamErrorHandler()
80
- parser = sax.make_parser()
81
- parser.setContentHandler(handler)
82
- parser.setErrorHandler(errHandler)
83
- try:
84
- parser.parse(io.FileIO(0, 'r', closefd=False))
85
- except Exception as e:
86
- logger.error("Done with exception : %s", e)
87
- handler.quit_application()
80
+
81
+ def parser_main():
82
+ handler = GtkStreamXMLHandler(app)
83
+ errHandler = GtkStreamErrorHandler()
84
+ parser = sax.make_parser()
85
+ parser.setContentHandler(handler)
86
+ parser.setErrorHandler(errHandler)
87
+ try:
88
+ parser.parse(io.FileIO(0, 'r', closefd=False))
89
+ except Exception as e:
90
+ logger.error("Done with exception : %s", e)
91
+ handler.quit_application()
92
+
93
+ parser_thread = threading.Thread(target = parser_main, daemon = True)
94
+ parser_thread.start()
95
+
96
+ # When the parser parses the 'application' tag, it sets the
97
+ # application attributes, and releases the semaphore so the
98
+ # application can start
99
+ app.attrs_set.acquire()
100
+ app.run()
@@ -37,7 +37,7 @@ class Document:
37
37
  """Method to render the document to a widet"""
38
38
  raise Exception("Method 'render' not implemented")
39
39
  def set_properties(self, w):
40
- self.app.nameWidget(self.id, w)
40
+ self.app.name_widget(self.id, w)
41
41
  for (p,v) in self.props.items():
42
42
  val = v(self.app)
43
43
  self.app.logger.debug("Setting property '%s' to '%s' in widget %s", p, val, self.__class__)
gtk_stream/parser.py CHANGED
@@ -52,28 +52,29 @@ WIDGET_DOCUMENTS = {
52
52
  }
53
53
 
54
54
  class GtkStreamXMLHandler(sax.ContentHandler):
55
- def __init__(self, logger, app):
56
- self.logger = logger
55
+ def __init__(self, app):
57
56
  self.app = app
57
+ self.logger = app.logger
58
+
58
59
  self.transition_enter = self.transE_conn
59
60
  self.transition_leave = self.transL_final
60
61
  self.transition_chars = self.ignore_chars
61
- self.namedWidgets = { }
62
- self.windows = { }
62
+
63
+ # Get all messages directly from the application
64
+ # class. This allows defining new messages without
65
+ # touching the parser
66
+ self.messages = {
67
+ f.__tag_name__: self.startMessage(functools.partial(f,self.app), f.__store__)
68
+ for f in self.app.__class__.__dict__.values()
69
+ if hasattr(f, '__tag_name__')
70
+ }
63
71
 
64
72
  def quit_application(self):
65
73
  def cb():
66
74
  self.logger.info("Quitting app")
67
75
  self.app.quit()
68
76
  GLib.idle_add(cb)
69
- self.logger.info("Waiting for app to terminate")
70
- self.app_thread.join()
71
- self.logger.info("App terminated")
72
- sys.exit(0)
73
77
 
74
- def setNamed(self, attrs, ):
75
- if 'id' in attrs:
76
- self.namedWidgets[attrs['id']] = widget
77
78
  def ignore_chars(self, s):
78
79
  pass
79
80
 
@@ -95,32 +96,7 @@ class GtkStreamXMLHandler(sax.ContentHandler):
95
96
  def transE_conn(self, name, attrs):
96
97
  match name:
97
98
  case 'application':
98
- for name, val in attrs.items():
99
- set_parse_prop(self.app, self.app, name, val)
100
-
101
- def on_activate(a):
102
- a.hold()
103
- self.app.connect('activate', on_activate)
104
- def appMain():
105
- self.app.run([])
106
- self.app_thread = threading.Thread(target = appMain)
107
- self.app_thread.start()
108
-
109
- def on_sigint(a,b):
110
- self.logger.info("SIGINT received")
111
- self.quit_application()
112
- signal.signal(signal.SIGINT, on_sigint)
113
-
114
- # Get all messages directly from the application
115
- # class. This allows defining new messages without
116
- # touching the parser
117
- self.messages = {
118
- f.__tag_name__: self.startMessage(functools.partial(f,self.app), f.__store__)
119
- for f in self.app.__class__.__dict__.values()
120
- if hasattr(f, '__tag_name__')
121
- }
122
- self.logger.debug("Messages: %s", self.messages)
123
-
99
+ self.app.set_attrs(attrs)
124
100
  self.transition_enter = self.transE_message
125
101
  self.transition_leave = self.transL_tag('application', self.transE_final, self.transL_final)
126
102
  case _:
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: gtk-stream
3
- Version: 0.11.6
3
+ Version: 0.12
4
4
  Summary: A simple stream-oriented GUI protocol
5
5
  Author-email: Marc Coiffier <marc.coiffier@univ-grenoble-alpes.fr>
6
6
  Project-URL: Homepage, https://coiffier.net/projects/gtk-stream/
@@ -1,14 +1,14 @@
1
1
  gtk_stream/__init__.py,sha256=y6JLknVFexWrSo_Zl7-TXrPR6EQ5XVMeFO1bUzLN9Lg,98
2
- gtk_stream/_version.py,sha256=RuR7_99HIJZnbMWO9BLw2NHLj3e0QsUnhmSY4oBBd3U,413
3
- gtk_stream/application.py,sha256=Au4MngStEIKQdGnl-H6eGWDt923onqRDjW1mPFB9M8I,4911
4
- gtk_stream/command_line.py,sha256=Gq90sMePDmQfz6EByMEzmyGzxTLsmLv930s10WGAHaQ,2854
2
+ gtk_stream/_version.py,sha256=eOKjFr4-OgtTmAgooUIWvbplNekszFVZVHe7TLPOdeU,408
3
+ gtk_stream/application.py,sha256=SrWn_lHJNCyswOB9rPV3Mn5TcnDlAZXHZ5x6A6E5SdQ,5488
4
+ gtk_stream/command_line.py,sha256=g7Sed0ydnDGKyWHT09murwR-3vZyIKXRWgM4Oi0qDE4,3278
5
5
  gtk_stream/common.py,sha256=xdscxYgBg_Ux6iyk26gB-AMSgoUIqlZUPgso5YS_gKE,2106
6
- gtk_stream/parser.py,sha256=juAXyp-YP2Ju7zhhjY6filTAE84v2Ry3gBKOztCeHlw,6664
6
+ gtk_stream/parser.py,sha256=75SYm-5O5Q4TLxq3BfWhuMrxC3-gNLHR4J2gOh0YJg8,5628
7
7
  gtk_stream/properties.py,sha256=RjdRgKUSldIK4Nsij8leBANJicf6oP-Nr53tYI4uEE8,3551
8
8
  gtk_stream/documents/__init__.py,sha256=T9mIonSi9DWrpXQzbjq0s0TPU0hB7HylfhMA20OfWIg,831
9
9
  gtk_stream/documents/classes/Box.py,sha256=d01o2-JQ3-k0VjvvY8E7mly-u_f1v1NqYz1IDjHZLUo,1381
10
10
  gtk_stream/documents/classes/Button.py,sha256=21bVI7DUWmiusboxdsimTgcqKtLqzQydhS9ifIt4R64,1512
11
- gtk_stream/documents/classes/Document.py,sha256=eZ-nT62UfO_ZUsxOR89hFLiBzpxMuNlbcjdZ4yJIzZo,2356
11
+ gtk_stream/documents/classes/Document.py,sha256=_SHqP0ebCDTag0dmi-LdlhopCImtgy0utVp5G3IqgHM,2357
12
12
  gtk_stream/documents/classes/Dropdown.py,sha256=8fIUX1HCWIjUfKLPy9NYsW6OskhkontoNDTsCZ7qKxw,2446
13
13
  gtk_stream/documents/classes/Entry.py,sha256=KcBwjSu4tI30bQxPlSFSLPxFEUbTaqAdoAzd0XSQciY,1112
14
14
  gtk_stream/documents/classes/FlowBox.py,sha256=UoVYS2j_osOV-IgbVoaqluTBCiaXus5dq2e9qhAu2Xo,1225
@@ -24,8 +24,8 @@ gtk_stream/documents/classes/Separator.py,sha256=uw_EgAKs_6pNA8nrOLzruIlJfk4uaog
24
24
  gtk_stream/documents/classes/Stack.py,sha256=YA6NDzZL2u4Ko8GXtx8Or-jEWGMCEw2cC1HNkAMRw-8,1030
25
25
  gtk_stream/documents/classes/Switch.py,sha256=jQVuxqS9Pmpp1ymB_dbJPxasJNpm4e35ry0JYPHdAsk,1275
26
26
  gtk_stream/documents/classes/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
27
- gtk_stream-0.11.6.dist-info/METADATA,sha256=iRmfaDjvwaay_mEkJ2Qxg7u0EdLVzM8hHL4ldOKRPDI,807
28
- gtk_stream-0.11.6.dist-info/WHEEL,sha256=A3WOREP4zgxI0fKrHUG8DC8013e3dK3n7a6HDbcEIwE,91
29
- gtk_stream-0.11.6.dist-info/entry_points.txt,sha256=PmhKTb4MMQM6dN2HJcoDSMI8L0lZIFIlFn-BgdfPDpo,60
30
- gtk_stream-0.11.6.dist-info/top_level.txt,sha256=vE9zfHGe9Ke7FSe0wBK2WYJI-BpcQNu6xDC3Cu5O8rQ,11
31
- gtk_stream-0.11.6.dist-info/RECORD,,
27
+ gtk_stream-0.12.dist-info/METADATA,sha256=eUB3jj7wt3haezpyhFmYOTqL9YnzG9389R5Vn5dwmIM,805
28
+ gtk_stream-0.12.dist-info/WHEEL,sha256=A3WOREP4zgxI0fKrHUG8DC8013e3dK3n7a6HDbcEIwE,91
29
+ gtk_stream-0.12.dist-info/entry_points.txt,sha256=PmhKTb4MMQM6dN2HJcoDSMI8L0lZIFIlFn-BgdfPDpo,60
30
+ gtk_stream-0.12.dist-info/top_level.txt,sha256=vE9zfHGe9Ke7FSe0wBK2WYJI-BpcQNu6xDC3Cu5O8rQ,11
31
+ gtk_stream-0.12.dist-info/RECORD,,