1"""Rendering engine parameter handling."""
2
3import typing
4
5from . import base
6
7__all__ = ['ENGINES', 'verify_engine', 'Engine']
8
9ENGINES = {'dot', # https://www.graphviz.org/pdf/dot.1.pdf
10 'neato',
11 'twopi',
12 'circo',
13 'fdp',
14 'sfdp',
15 'patchwork',
16 'osage'}
17
18DEFAULT_ENGINE = 'dot'
19
20REQUIRED = True
21
22
23def verify_engine(engine: str, *, required: bool = REQUIRED) -> None:
24 if engine is None:
25 if required:
26 raise ValueError('missing engine')
27 elif engine.lower() not in ENGINES:
28 raise ValueError(f'unknown engine: {engine!r}'
29 f' (must be one of {sorted(ENGINES)})')
30
31
32class Engine(base.ParameterBase):
33 """Rendering engine parameter with ``'dot''`` default."""
34
35 _engine = DEFAULT_ENGINE
36
37 _verify_engine = staticmethod(verify_engine)
38
39 def __init__(self, *, engine: typing.Optional[str] = None, **kwargs) -> None:
40 super().__init__(**kwargs)
41
42 if engine is not None:
43 self.engine = engine
44
45 def _copy_kwargs(self, **kwargs):
46 """Return the kwargs to create a copy of the instance."""
47 engine = self._getattr_from_dict('_engine')
48 if engine is not None:
49 kwargs['engine'] = engine
50 return super()._copy_kwargs(**kwargs)
51
52 @property
53 def engine(self) -> str:
54 """The layout engine used for rendering
55 (``'dot'``, ``'neato'``, ...)."""
56 return self._engine
57
58 @engine.setter
59 def engine(self, engine: str) -> None:
60 engine = engine.lower()
61 self._verify_engine(engine)
62 self._engine = engine