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
9 changes: 8 additions & 1 deletion highcharts_core/js_literal_functions.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,14 @@ def serialize_to_js_literal(item, encoding = 'utf-8') -> Optional[str]:
:rtype: :class:`str <python:str>` or :obj:`None <python:None>`
"""
if checkers.is_iterable(item, forbid_literals = (str, bytes, dict, UserDict)):
return [serialize_to_js_literal(x, encoding = encoding) for x in item]
requires_js_objects = all([getattr(x, 'requires_js_object', True)
for x in item])
if requires_js_objects:
return [serialize_to_js_literal(x, encoding = encoding)
for x in item]
else:
return [serialize_to_js_literal(x.to_array(), encoding = encoding)
for x in item]
elif hasattr(item, 'to_js_literal'):
return item.to_js_literal(encoding = encoding)
elif isinstance(item, constants.EnforcedNullType) or item == 'null':
Expand Down
15 changes: 13 additions & 2 deletions highcharts_core/options/series/data/arcdiagram.py
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
from typing import Optional
from typing import Optional, List, Dict
from decimal import Decimal
from collections import UserDict

from validator_collection import validators, checkers

from highcharts_core import utility_functions, constants
from highcharts_core import utility_functions, constants, errors
from highcharts_core.options.series.data.base import DataBase
from highcharts_core.utility_classes.gradients import Gradient
from highcharts_core.utility_classes.patterns import Pattern
Expand Down Expand Up @@ -126,6 +126,17 @@ def from_array(cls, value):

return collection

def _get_props_from_array(self) -> List[str]:
"""Returns a list of the property names that can be set using the
:meth:`.from_array() <highcharts_core.options.series.data.base.DataBase.from_array>`
method.

:rtype: :class:`list <python:list>` of :class:`str <python:str>`
"""
return ['from_',
'to',
'weight']

@classmethod
def _get_kwargs_from_dict(cls, as_dict):
"""Convenience method which returns the keyword arguments used to initialize the
Expand Down
59 changes: 58 additions & 1 deletion highcharts_core/options/series/data/bar.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from typing import Optional
from typing import Optional, List, Dict
from decimal import Decimal

import datetime
Expand Down Expand Up @@ -376,6 +376,63 @@ def from_array(cls, value):

return collection

def _get_props_from_array(self) -> List[str]:
"""Returns a list of the property names that can be set using the
:meth:`.from_array() <highcharts_core.options.series.data.base.DataBase.from_array>`
method.

:rtype: :class:`list <python:list>` of :class:`str <python:str>`
"""
return ['x', 'value', 'direction', 'y', 'name']

def to_array(self, force_object = False) -> List | Dict:
"""Generate the array representation of the data point (the inversion
of
:meth:`.from_array() <highcharts_core.options.series.data.base.DataBase.from_array>`).

.. warning::

If the data point *cannot* be serialized to a JavaScript array,
this method will instead return the untrimmed :class:`dict <python:dict>`
representation of the data point as a fallback.

:param force_object: if ``True``, forces the return of the instance's
untrimmed :class:`dict <python:dict>` representation. Defaults to ``False``.
:type force_object: :class:`bool <python:bool>`

:returns: The array representation of the data point.
:rtype: :class:`list <python:list>` of values or :class:`dict <python:dict>`
"""
if self.requires_js_object or force_object:
return self._to_untrimmed_dict()

if self.x is None and self.name is not None:
x = self.name
elif self.x is not None:
x = self.x
else:
x = constants.EnforcedNull

if self.y is not None:
y = self.y
else:
y = constants.EnforcedNull

if self.value is not None:
value = self.value
else:
value = constants.EnforcedNull

if self.direction is not None:
direction = self.direction
else:
direction = constants.EnforcedNull

if self.y is None:
return [x, value, direction]

return [x, value, direction, y]

@classmethod
def _get_kwargs_from_dict(cls, as_dict):
"""Convenience method which returns the keyword arguments used to initialize the
Expand Down
58 changes: 57 additions & 1 deletion highcharts_core/options/series/data/base.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from typing import Optional
from typing import Optional, List, Dict
from decimal import Decimal

from validator_collection import validators, checkers
Expand Down Expand Up @@ -304,6 +304,38 @@ def _to_untrimmed_dict(self, in_cls = None) -> dict:

return untrimmed

def _get_props_from_array(self) -> List[str]:
"""Returns a list of the property names that can be set using the
:meth:`.from_array() <highcharts_core.options.series.data.base.DataBase.from_array>`
method.

:rtype: :class:`list <python:list>` of :class:`str <python:str>`
"""
return []

@property
def requires_js_object(self) -> bool:
"""Indicates whether or not the data point *must* be serialized to a JS literal
object or whether it can be serialized to a primitive array.

:returns: ``True`` if the data point *must* be serialized to a JS literal object.
``False`` if it can be serialized to an array.
:rtype: :class:`bool <python:bool>`
"""
from_array_props = [utility_functions.to_camelCase(x)
for x in self._get_props_from_array()]

as_dict = self.to_dict()
trimmed_dict = self.trim_dict(as_dict)
for prop in from_array_props:
if prop in trimmed_dict:
del trimmed_dict[prop]

if trimmed_dict:
return True

return False

@classmethod
def from_array(cls, value):
"""Creates a collection of data point instances, parsing the contents of ``value``
Expand Down Expand Up @@ -416,3 +448,27 @@ def from_array(cls, value):
collection.append(as_obj)

return collection

def to_array(self, force_object = False) -> List | Dict:
"""Generate the array representation of the data point (the inversion
of
:meth:`.from_array() <highcharts_core.options.series.data.base.DataBase.from_array>`).

.. warning::

If the data point *cannot* be serialized to a JavaScript array,
this method will instead return the untrimmed :class:`dict <python:dict>`
representation of the data point as a fallback.

:param force_object: if ``True``, forces the return of the instance's
untrimmed :class:`dict <python:dict>` representation. Defaults to ``False``.
:type force_object: :class:`bool <python:bool>`

:returns: The array representation of the data point.
:rtype: :class:`list <python:list>` of values or :class:`dict <python:dict>`
"""
if self.requires_js_object or force_object:
return self._to_untrimmed_dict()

return [getattr(self, x, constants.EnforcedNull)
for x in self._get_props_from_array()]
69 changes: 68 additions & 1 deletion highcharts_core/options/series/data/boxplot.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from typing import Optional
from typing import Optional, List, Dict
from decimal import Decimal

from validator_collection import validators, checkers
Expand Down Expand Up @@ -290,6 +290,73 @@ def from_array(cls, value):

return collection

def _get_props_from_array(self) -> List[str]:
"""Returns a list of the property names that can be set using the
:meth:`.from_array() <highcharts_core.options.series.data.base.DataBase.from_array>`
method.

:rtype: :class:`list <python:list>` of :class:`str <python:str>`
"""
return ['x', 'low', 'q1', 'median', 'q3', 'high', 'name']

def to_array(self, force_object = False) -> List | Dict:
"""Generate the array representation of the data point (the inversion
of
:meth:`.from_array() <highcharts_core.options.series.data.base.DataBase.from_array>`).

.. warning::

If the data point *cannot* be serialized to a JavaScript array,
this method will instead return the untrimmed :class:`dict <python:dict>`
representation of the data point as a fallback.

:param force_object: if ``True``, forces the return of the instance's
untrimmed :class:`dict <python:dict>` representation. Defaults to ``False``.
:type force_object: :class:`bool <python:bool>`

:returns: The array representation of the data point.
:rtype: :class:`list <python:list>` of values or :class:`dict <python:dict>`
"""
if self.requires_js_object or force_object:
return self._to_untrimmed_dict()

if self.x is not None:
x = self.x
elif self.name is not None:
x = self.name
else:
x = constants.EnforcedNull

if self.low is not None:
low = self.low
else:
low = constants.EnforcedNull

if self.q1 is not None:
q1 = self.q1
else:
q1 = constants.EnforcedNull

if self.median is not None:
median = self.median
else:
median = constants.EnforcedNull

if self.q3 is not None:
q3 = self.q3
else:
q3 = constants.EnforcedNull

if self.high is not None:
high = self.high
else:
high = constants.EnforcedNull

if self.x is None and self.name is None:
return [low, q1, median, q3, high]

return [x, low, q1, median, q3, high]

@classmethod
def _get_kwargs_from_dict(cls, as_dict):
"""Convenience method which returns the keyword arguments used to initialize the
Expand Down
54 changes: 53 additions & 1 deletion highcharts_core/options/series/data/bullet.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from typing import Optional
from typing import Optional, List, Dict
from decimal import Decimal

from validator_collection import validators, checkers
Expand Down Expand Up @@ -99,6 +99,58 @@ def from_array(cls, value):

return collection

def _get_props_from_array(self) -> List[str]:
"""Returns a list of the property names that can be set using the
:meth:`.from_array() <highcharts_core.options.series.data.base.DataBase.from_array>`
method.

:rtype: :class:`list <python:list>` of :class:`str <python:str>`
"""
return ['x', 'y', 'target', 'name']

def to_array(self, force_object = False) -> List | Dict:
"""Generate the array representation of the data point (the inversion
of
:meth:`.from_array() <highcharts_core.options.series.data.base.DataBase.from_array>`).

.. warning::

If the data point *cannot* be serialized to a JavaScript array,
this method will instead return the untrimmed :class:`dict <python:dict>`
representation of the data point as a fallback.

:param force_object: if ``True``, forces the return of the instance's
untrimmed :class:`dict <python:dict>` representation. Defaults to ``False``.
:type force_object: :class:`bool <python:bool>`

:returns: The array representation of the data point.
:rtype: :class:`list <python:list>` of values or :class:`dict <python:dict>`
"""
if self.requires_js_object or force_object:
return self._to_untrimmed_dict()

if self.x is not None:
x = self.x
elif self.name is not None:
x = self.name
else:
x = constants.EnforcedNull

if self.y is not None:
y = self.y
else:
y = constants.EnforcedNull

if self.target is not None:
target = self.target
else:
target = constants.EnforcedNull

if self.x is None and self.name is None:
return [y, target]

return [x, y, target]

@classmethod
def _get_kwargs_from_dict(cls, as_dict):
"""Convenience method which returns the keyword arguments used to initialize the
Expand Down
Loading