Commit 1a243849 authored by Simon Feltman's avatar Simon Feltman

docs: Standardize Python doc strings

Use consistent doc string quotations (three double quotes).
Update usage of GObject.GObject in docs to GObject.Object.
Use reStructuredText markup for parameter annotations, instance variables,
admonitions, and code examples.
This allows for better Sphinx documentation generation for the project.
Preliminary style guide:
https://wiki.gnome.org/Projects/PyGObject/StyleGuide
parent 2d268ef6
......@@ -68,17 +68,20 @@ class Option(optparse.Option):
filename The supplied arguments are read as filename, GOption
parses this type in with the GLib filename encoding.
Attributes:
optional_arg This does not need a arguement, but it can be supplied.
hidden The help list does not show this option
in_main This option apears in the main group, this should only
be used for backwards compatibility.
:ivar optional_arg:
This does not need a arguement, but it can be supplied.
:ivar hidden:
The help list does not show this option
:ivar in_main:
This option apears in the main group, this should only
be used for backwards compatibility.
Use Option.REMAINING as option name to get all positional arguments.
NOTE: Every argument to an option is passed as utf-8 coded string, the only
exception are options which use the 'filename' type, its arguments
are passed as strings in the GLib filename encoding.
.. NOTE::
Every argument to an option is passed as utf-8 coded string, the only
exception are options which use the 'filename' type, its arguments
are passed as strings in the GLib filename encoding.
For further help, see optparse.Option.
"""
......@@ -142,19 +145,24 @@ class Option(optparse.Option):
class OptionGroup(optparse.OptionGroup):
"""A group of command line options.
Arguements:
name: The groups name, used to create the
--help-{name} option
description: Shown as title of the groups help view
help_description: Shown as help to the --help-{name} option
option_list: The options used in this group, must be option.Option()
defaults: A dicitionary of default values
translation_domain: Sets the translation domain for gettext().
NOTE: This OptionGroup does not exactly map the optparse.OptionGroup
interface. There is no parser object to supply, but it is possible
to set default values and option_lists. Also the default values and
values are not shared with the OptionParser.
:param str name:
The groups name, used to create the --help-{name} option
:param str description:
Shown as title of the groups help view
:param str help_description:
Shown as help to the --help-{name} option
:param list option_list:
The options used in this group, must be option.Option()
:param dict defaults:
A dicitionary of default values
:param translation_domain:
Sets the translation domain for gettext().
.. NOTE::
This OptionGroup does not exactly map the optparse.OptionGroup
interface. There is no parser object to supply, but it is possible
to set default values and option_lists. Also the default values and
values are not shared with the OptionParser.
To pass a OptionGroup into a function which expects a GOptionGroup (e.g.
gnome_program_init() ). OptionGroup.get_option_group() can be used.
......@@ -234,15 +242,16 @@ class OptionGroup(optparse.OptionGroup):
class OptionParser(optparse.OptionParser):
"""Command line parser with GOption support.
NOTE: The OptionParser interface is not the exactly the same as the
optparse.OptionParser interface. Especially the usage parameter
is only used to show the metavar of the arguements.
:param bool help_enabled:
The --help, --help-all and --help-{group} options are enabled (default).
:param bool ignore_unknown_options:
Do not throw a exception when a option is not knwon, the option
will be in the result list.
Attribues:
help_enabled: The --help, --help-all and --help-{group}
options are enabled (default).
ignore_unknown_options: Do not throw a exception when a option is not
knwon, the option will be in the result list.
.. NOTE::
The OptionParser interface is not the exactly the same as the
optparse.OptionParser interface. Especially the usage parameter
is only used to show the metavar of the arguements.
OptionParser.add_option_group() does not only accept OptionGroup instances
but also glib.OptionGroup, which is returned by gtk_get_option_group().
......
......@@ -48,34 +48,59 @@ else:
class Property(object):
"""
Creates a new property which in conjunction with GObject subclass will
create a property proxy:
class MyObject(GObject.GObject):
... prop = GObject.Property(type=str)
"""Creates a new Property which when used in conjunction with
GObject subclass will create a Python property accessor for the
GObject ParamSpec.
:param callable getter:
getter to get the value of the property
:param callable setter:
setter to set the value of the property
:param type type:
type of property
:param default:
default value, must match the property type.
:param str nick:
short description
:param str blurb:
long description
:param GObject.ParamFlags flags:
parameter flags
:keyword minimum:
minimum allowed value (int, float, long only)
:keyword maximum:
maximum allowed value (int, float, long only)
.. code-block:: python
class MyObject(GObject.Object):
prop = GObject.Property(type=str)
obj = MyObject()
obj.prop = 'value'
obj.prop # now is 'value'
The API is similar to the builtin property:
The API is similar to the builtin :py:func:`property`:
.. code-block:: python
class AnotherObject(GObject.GObject):
@GObject.Property
def prop(self):
'''Read only property.'''
return ...
class AnotherObject(GObject.Object):
value = 0
@GObject.Property(type=int)
def propInt(self):
'''Read-write integer property.'''
return ...
@GObject.Property
def prop(self):
'Read only property.'
return 1
@propInt.setter
def propInt(self, value):
...
@GObject.Property(type=int)
def propInt(self):
'Read-write integer property.'
return self.value
@propInt.setter
def propInt(self, value):
self.value = value
"""
_type_from_pytype_lookup = {
# Put long_ first in case long_ and int are the same so int clobbers long_
......@@ -129,29 +154,6 @@ class Property(object):
def __init__(self, getter=None, setter=None, type=None, default=None,
nick='', blurb='', flags=_gobject.PARAM_READWRITE,
minimum=None, maximum=None):
"""
@param getter: getter to get the value of the property
@type getter: callable
@param setter: setter to set the value of the property
@type setter: callable
@param type: type of property
@type type: type
@param default: default value
@param nick: short description
@type nick: string
@param blurb: long description
@type blurb: string
@param flags: parameter flags, one of:
- gobject.PARAM_READABLE
- gobject.PARAM_READWRITE
- gobject.PARAM_WRITABLE
- gobject.PARAM_CONSTRUCT
- gobject.PARAM_CONSTRUCT_ONLY
- gobject.PARAM_LAX_VALIDATION
@keyword minimum: minimum allowed value (int, float, long only)
@keyword maximum: maximum allowed value (int, float, long only)
"""
self.name = None
if type is None:
......
......@@ -32,33 +32,54 @@ if (3, 0) <= sys.version_info < (3, 2):
class Signal(str):
"""
Object which gives a nice API for creating and binding signals.
Example:
class Spam(GObject.GObject):
velocity = 0
@GObject.Signal
def pushed(self):
self.velocity += 1
@GObject.Signal(flags=GObject.SignalFlags.RUN_LAST)
def pulled(self):
self.velocity -= 1
stomped = GObject.Signal('stomped', arg_types=(int,))
@GObject.Signal
def annotated_signal(self, a:int, b:str):
"Python3 annotation support for parameter types.
def on_pushed(obj):
print(obj)
spam = Spam()
spam.pushed.connect(on_pushed)
spam.pushed.emit()
"""Object which gives a nice API for creating and binding signals.
:param name:
Name of signal or callable closure when used as a decorator.
:type name: str or callable
:param callable func:
Callable closure method.
:param GObject.SignalFlags flags:
Flags specifying when to run closure.
:param type return_type:
Return type of the Signal.
:param list arg_types:
List of argument types specifying the signals function signature
:param str doc:
Documentation of signal object.
:param callable accumulator:
Accumulator method with the signature:
func(ihint, return_accu, handler_return, accu_data) -> boolean
:param object accu_data:
User data passed to the accumulator.
:Example:
.. code-block:: python
class Spam(GObject.Object):
velocity = 0
@GObject.Signal
def pushed(self):
self.velocity += 1
@GObject.Signal(flags=GObject.SignalFlags.RUN_LAST)
def pulled(self):
self.velocity -= 1
stomped = GObject.Signal('stomped', arg_types=(int,))
@GObject.Signal
def annotated_signal(self, a:int, b:str):
"Python3 annotation support for parameter types.
def on_pushed(obj):
print(obj)
spam = Spam()
spam.pushed.connect(on_pushed)
spam.pushed.emit()
"""
class BoundSignal(str):
"""
......@@ -81,12 +102,12 @@ class Signal(str):
return self.signal.func(self.gobj, *args, **kargs)
def connect(self, callback, *args, **kargs):
"""Same as GObject.GObject.connect except there is no need to specify
"""Same as GObject.Object.connect except there is no need to specify
the signal name."""
return self.gobj.connect(self, callback, *args, **kargs)
def connect_detailed(self, callback, detail, *args, **kargs):
"""Same as GObject.GObject.connect except there is no need to specify
"""Same as GObject.Object.connect except there is no need to specify
the signal name. In addition concats "::<detail>" to the signal name
when connecting; for use with notifications like "notify" when a property
changes.
......@@ -94,11 +115,11 @@ class Signal(str):
return self.gobj.connect(self + '::' + detail, callback, *args, **kargs)
def disconnect(self, handler_id):
"""Same as GObject.GObject.disconnect."""
"""Same as GObject.Object.disconnect."""
self.instance.disconnect(handler_id)
def emit(self, *args, **kargs):
"""Same as GObject.GObject.emit except there is no need to specify
"""Same as GObject.Object.emit except there is no need to specify
the signal name."""
return self.gobj.emit(str(self), *args, **kargs)
......@@ -109,25 +130,6 @@ class Signal(str):
def __init__(self, name='', func=None, flags=_gobject.SIGNAL_RUN_FIRST,
return_type=None, arg_types=None, doc='', accumulator=None, accu_data=None):
"""
@param name: name of signal or closure method when used as direct decorator.
@type name: string or callable
@param func: closure method.
@type func: callable
@param flags: flags specifying when to run closure
@type flags: GObject.SignalFlags
@param return_type: return type
@type return_type: type
@param arg_types: list of argument types specifying the signals function signature
@type arg_types: None
@param doc: documentation of signal object
@type doc: string
@param accumulator: accumulator method with the signature:
func(ihint, return_accu, handler_return, accu_data) -> boolean
@type accumulator: function
@param accu_data: user data passed to the accumulator
@type accu_data: object
"""
if func and not name:
name = func.__name__
elif callable(name):
......@@ -191,14 +193,17 @@ class Signal(str):
class SignalOverride(Signal):
"""Specialized sub-class of signal which can be used as a decorator for overriding
"""Specialized sub-class of Signal which can be used as a decorator for overriding
existing signals on GObjects.
Example:
class MyWidget(Gtk.Widget):
@GObject.SignalOverride
def configure_event(self):
pass
:Example:
.. code-block:: python
class MyWidget(Gtk.Widget):
@GObject.SignalOverride
def configure_event(self):
pass
"""
def get_signal_args(self):
"""Returns the string 'override'."""
......
......@@ -37,21 +37,26 @@ _generate_doc_string_func = None
def set_doc_string_generator(func):
"""Set doc string generator function
:Parameters:
func : callable
Function which takes a GIInfoStruct and returns
documentation for it.
:param callable func:
Callable which takes a GIInfoStruct and returns documentation for it.
"""
global _generate_doc_string_func
_generate_doc_string_func = func
def get_doc_string_generator():
"""Returns the currently registered doc string generator."""
return _generate_doc_string_func
def generate_doc_string(info):
"""Generator a doc string given a GIInfoStruct
"""Generate a doc string given a GIInfoStruct.
:param gi.types.BaseInfo info:
GI info instance to generate documentation for.
:returns:
Generated documentation as a string.
:rtype: str
This passes the info struct to the currently registered doc string
generator and returns the result.
......@@ -166,7 +171,7 @@ def _generate_callable_info_doc(info):
def _generate_class_info_doc(info):
doc = '\n:Constructors:\n' # start with \n to avoid auto indent of other lines
doc = '\n:Constructors:\n\n::\n\n' # start with \n to avoid auto indent of other lines
if isinstance(info, StructInfo):
# Don't show default constructor for disguised (0 length) structs
......
......@@ -42,8 +42,9 @@ static PyMethodDef _glib_functions[] = {
" flags=0, child_setup=None, user_data=None,\n"
" standard_input=None, standard_output=None,\n"
" standard_error=None) -> (pid, stdin, stdout, stderr)\n"
"\n"
"Execute a child program asynchronously within a glib.MainLoop()\n"
"See the reference manual for a complete reference." },
"See the reference manual for a complete reference.\n" },
{ NULL, NULL, 0 }
};
......
......@@ -76,7 +76,7 @@ class _VariantCreator(object):
}
def _create(self, format, args):
'''Create a GVariant object from given format and argument list.
"""Create a GVariant object from given format and argument list.
This method recursively calls itself for complex structures (arrays,
dictionaries, boxed).
......@@ -88,7 +88,7 @@ class _VariantCreator(object):
If args is None, then this won't actually consume any arguments, and
just parse the format string and generate empty GVariant structures.
This is required for creating empty dictionaries or arrays.
'''
"""
# leaves (simple types)
constructor = self._LEAF_CONSTRUCTORS.get(format[0])
if constructor:
......@@ -112,7 +112,7 @@ class _VariantCreator(object):
raise NotImplementedError('cannot handle GVariant type ' + format)
def _create_tuple(self, format, args):
'''Handle the case where the outermost type of format is a tuple.'''
"""Handle the case where the outermost type of format is a tuple."""
format = format[1:] # eat the '('
if args is None:
......@@ -146,7 +146,7 @@ class _VariantCreator(object):
return (builder.end(), rest_format, args)
def _create_dict(self, format, args):
'''Handle the case where the outermost type of format is a dict.'''
"""Handle the case where the outermost type of format is a dict."""
builder = None
if args is None or not args[0]:
......@@ -179,7 +179,7 @@ class _VariantCreator(object):
return (builder.end(), rest_format, args)
def _create_array(self, format, args):
'''Handle the case where the outermost type of format is an array.'''
"""Handle the case where the outermost type of format is an array."""
builder = None
if args is None or not args[0]:
......@@ -200,7 +200,7 @@ class _VariantCreator(object):
class Variant(GLib.Variant):
def __new__(cls, format_string, value):
'''Create a GVariant from a native Python object.
"""Create a GVariant from a native Python object.
format_string is a standard GVariant type signature, value is a Python
object whose structure has to match the signature.
......@@ -210,7 +210,7 @@ class Variant(GLib.Variant):
GLib.Variant('(is)', (1, 'hello'))
GLib.Variant('(asa{sv})', ([], {'foo': GLib.Variant('b', True),
'bar': GLib.Variant('i', 2)}))
'''
"""
creator = _VariantCreator()
(v, rest_format, _) = creator._create(format_string, [value])
if rest_format:
......@@ -250,7 +250,7 @@ class Variant(GLib.Variant):
return hash((self.get_type_string(), self.unpack()))
def unpack(self):
'''Decompose a GVariant into a native Python object.'''
"""Decompose a GVariant into a native Python object."""
LEAF_ACCESSORS = {
'b': self.get_boolean,
......@@ -305,14 +305,14 @@ class Variant(GLib.Variant):
@classmethod
def split_signature(klass, signature):
'''Return a list of the element signatures of the topmost signature tuple.
"""Return a list of the element signatures of the topmost signature tuple.
If the signature is not a tuple, it returns one element with the entire
signature. If the signature is an empty tuple, the result is [].
This is useful for e. g. iterating over method parameters which are
passed as a single Variant.
'''
"""
if signature == '()':
return []
......
......@@ -435,13 +435,21 @@ class _HandlerBlockManager(object):
def signal_handler_block(obj, handler_id):
"""Blocks the signal handler from being invoked until handler_unblock() is called.
"""Blocks the signal handler from being invoked until
handler_unblock() is called.
Returns a context manager which optionally can be used to
automatically unblock the handler:
:param GObject.Object obj:
Object instance to block handlers for.
:param int handler_id:
Id of signal to block.
:returns:
A context manager which optionally can be used to
automatically unblock the handler:
with GObject.signal_handler_block(obj, id):
pass
.. code-block:: python
with GObject.signal_handler_block(obj, id):
pass
"""
GObjectModule.signal_handler_block(obj, handler_id)
return _HandlerBlockManager(obj, handler_id)
......@@ -452,11 +460,13 @@ __all__.append('signal_handler_block')
def signal_parse_name(detailed_signal, itype, force_detail_quark):
"""Parse a detailed signal name into (signal_id, detail).
:Raises ValueError:
If the given signal is unknown.
:Returns:
:param str detailed_signal:
Signal name which can include detail.
For example: "notify:prop_name"
:returns:
Tuple of (signal_id, detail)
:raises ValueError:
If the given signal is unknown.
"""
res, signal_id, detail = GObjectModule.signal_parse_name(detailed_signal, itype,
force_detail_quark)
......@@ -584,14 +594,17 @@ class Object(GObjectModule.Object):
def freeze_notify(self):
"""Freezes the object's property-changed notification queue.
:returns:
A context manager which optionally can be used to
automatically thaw notifications.
This will freeze the object so that "notify" signals are blocked until
the thaw_notify() method is called.
Returns a context manager which optionally can be used to
automatically thaw notifications:
.. code-block:: python
with obj.freeze_notify():
pass
with obj.freeze_notify():
pass
"""
super(Object, self).freeze_notify()
return _FreezeNotifyManager(self)
......
......@@ -394,6 +394,9 @@ class Builder(Gtk.Builder):
the given mapping "obj_or_map". The handler/value aspect of the mapping
can also contain a tuple in the form of (handler [,arg1 [,argN]])
allowing for extra arguments to be passed to the handler. For example:
.. code-block:: python
builder.connect_signals({'on_clicked': (on_clicked, arg1, arg2)})
"""
def _full_callback(builder, gobj, signal_name, handler_name, connect_obj, flags, obj_or_map):
......@@ -510,7 +513,9 @@ class Dialog(Gtk.Dialog, Container):
pairs - button text (or stock ID) and a response ID integer are passed
individually. For example:
dialog.add_buttons(Gtk.STOCK_OPEN, 42, "Close", Gtk.ResponseType.CLOSE)
.. code-block:: python
dialog.add_buttons(Gtk.STOCK_OPEN, 42, "Close", Gtk.ResponseType.CLOSE)
will add "Open" and "Close" buttons to dialog.
"""
......@@ -635,24 +640,27 @@ class TextBuffer(Gtk.TextBuffer):
return table
def create_tag(self, tag_name=None, **properties):
"""
@tag_name: name of the new tag, or None
@properties: keyword list of properties and their values
"""Creates a tag and adds it to the tag table of the TextBuffer.
:param str tag_name:
Name of the new tag, or None
:param **properties:
Keyword list of properties and their values
Creates a tag and adds it to the tag table of the TextBuffer.
Equivalent to creating a Gtk.TextTag and then adding the
This is equivalent to creating a Gtk.TextTag and then adding the
tag to the buffer's tag table. The returned tag is owned by
the buffer's tag table.
If @tag_name is None, the tag is anonymous.
If ``tag_name`` is None, the tag is anonymous.
If @tag_name is not None, a tag called @tag_name must not already
If ``tag_name`` is not None, a tag called ``tag_name`` must not already
exist in the tag table for this buffer.
Properties are passed as a keyword list of names and values (e.g.
foreground = 'DodgerBlue', weight = Pango.Weight.BOLD)
foreground='DodgerBlue', weight=Pango.Weight.BOLD)
Return value: a new tag
:returns:
A new tag.
"""
tag = Gtk.TextTag(name=tag_name, **properties)
......
......@@ -24,14 +24,14 @@ def wraps(wrapped):
class _Registry(dict):
def __setitem__(self, key, value):
'''We do checks here to make sure only submodules of the override
"""We do checks here to make sure only submodules of the override
module are added. Key and value should be the same object and come
from the gi.override module.
We add the override to the dict as "override_module.name". For instance
if we were overriding Gtk.Button you would retrive it as such:
registry['Gtk.Button']
'''
"""
if not key == value:
raise KeyError('You have tried to modify the registry. This should only be done by the override decorator')
......@@ -59,7 +59,7 @@ class _Registry(dict):
class overridefunc(object):
'''decorator for overriding a function'''
"""decorator for overriding a function"""
def __init__(self, func):