Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
jnumainville committed Apr 5, 2024
1 parent e1a135d commit c295cbc
Show file tree
Hide file tree
Showing 3 changed files with 221 additions and 1 deletion.
2 changes: 1 addition & 1 deletion plugins/ui/DESIGN.md
Original file line number Diff line number Diff line change
Expand Up @@ -1385,7 +1385,7 @@ ui.date_picker(
granularity: Granularity | None = None,
on_change: Callable[[Date], None] | None = None,
**props: Any
) -> ListViewElement
) -> DatePickerElement
```

###### Parameters
Expand Down
192 changes: 192 additions & 0 deletions plugins/ui/src/deephaven/ui/components/date_picker.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,192 @@
from __future__ import annotations

from typing import Any, Sequence, Callable

from deephaven.dtypes import Instant, ZonedDateTime, LocalDate
from deephaven.time import to_j_instant, to_j_zdt, to_j_local_date

from ..elements import Element
from .._internal.utils import create_props, wrap_callable
from ..types import Date, Granularity

DatePickerElement = Element


def convert_to_java_date(
date: Date,
) -> Instant | ZonedDateTime | LocalDate: # type: ignore
"""
Convert a Date to a Java date type.
In order of preference, tries to convert to Instant, ZonedDateTime, and LocalDate.
If none of these work, raises a TypeError.
Args:
date: The date to convert to a Java date type.
Returns:
The Java date type.
"""
try:
return to_j_instant(date)
except TypeError:
# ignore, try next
pass

try:
return to_j_zdt(date)
except TypeError:
# ignore, try next
pass

try:
return to_j_local_date(date)
except TypeError:
raise TypeError(
f"Could not convert {date} to one of Instant, ZonedDateTime, or LocalDate."
)


def date_converter(
props: dict[str, Any],
) -> Callable[[Date], Instant | ZonedDateTime | LocalDate]: # type: ignore
"""
Go through "value", "default_value", and "placeholder_value" in props to
determine the type of date converter to use.
If none of these are present, defaults to Instant.
This is used to convert callback arguments to Java date types.
Args:
props: The props to check for date types.
Returns:
The date converter.
"""
converters = {
Instant: to_j_instant,
ZonedDateTime: to_j_zdt,
LocalDate: to_j_local_date,
}

if "value" in props:
return converters[type(props["value"])]
elif "default_value" in props:
return converters[type(props["default_value"])]
elif "placeholder_value" in props:
return converters[type(props["placeholder_value"])]

return to_j_instant


def wrap_date_callable(
date_callable: Callable[[Date], None],
converter: Callable[[Date], Any],
) -> Callable[[Date], None]:
"""
Wrap a callable to convert the Date argument to a Java date type.
This maintains the original callable signature so that the Date argument can be dropped.
Args:
date_callable: The callable to wrap.
converter: The date converter to use.
Returns:
The wrapped callable.
"""
return lambda date: wrap_callable(date_callable)(converter(date))


def convert_date_props(
props: dict[str, Any],
simple_date_props: set[str],
list_date_props: set[str],
callable_date_props: set[str],
converter: Callable[[Date], Any],
) -> None:
"""
Convert date props to Java date types in place.
Args:
props: The props passed to the component.
simple_date_props: A set of simple date keys to convert. The prop value should be a single Date.
list_date_props: A set of list date keys to convert. The prop value should be a list of Dates.
callable_date_props: A set of callable date keys to convert.
The prop value should be a callable that takes a Date.
converter: The date converter to use.
Returns:
The converted props.
"""
for key in simple_date_props:
if key in props:
props[key] = convert_to_java_date(props[key])

for key in list_date_props:
if key in props:
if not isinstance(props[key], list):
raise TypeError(f"{key} must be a list of Dates")
props[key] = [convert_to_java_date(date) for date in props[key]]

for key in callable_date_props:
if key in props:
if not callable(props[key]):
raise TypeError(f"{key} must be a callable")
props[key] = wrap_date_callable(props[key], converter)


def convert_date_picker_props(
props: dict[str, Any],
) -> dict[str, Any]:
"""
Convert date picker props to Java date types.
Args:
props: The props passed to the date picker.
Returns:
The converted props.
"""
simple_date_props = {
"placeholder_value",
"value",
"default_value",
"min_value",
"max_value",
}
list_date_props = {"unavailable_values"}
callable_date_props = {"on_change"}

converter = date_converter(props)

convert_date_props(
props, simple_date_props, list_date_props, callable_date_props, converter
)

return props


def date_picker(
placeholder_value: Date | None = None,
value: Date | None = None,
default_value: Date | None = None,
min_value: Date | None = None,
max_value: Date | None = None,
unavailable_values: Sequence[Date] | None = None,
granularity: Granularity | None = None,
on_change: Callable[[Date], None] | None = None,
**props: Any,
) -> DatePickerElement | None:
"""
Args:
Returns:
"""
_, props = create_props(locals())

convert_date_picker_props(props)

print(props)

return None # BaseElement("deephaven.ui.components.DatePicker", **props)
28 changes: 28 additions & 0 deletions plugins/ui/src/deephaven/ui/types/types.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
import datetime
import pandas
import numpy
from typing import Any, Dict, Literal, Union, List, Tuple, Callable, TypedDict, Sequence
from deephaven import SortDirection
from deephaven.dtypes import LocalDate, Instant, ZonedDateTime


class CellData(TypedDict):
Expand Down Expand Up @@ -106,6 +110,30 @@ class RowDataValue(CellData):
Stringable = Union[str, int, float, bool]
Key = Stringable
ActionKey = Key
LocalDateConvertible = Union[
None,
LocalDate, # type: ignore
str,
datetime.date,
datetime.datetime,
numpy.datetime64,
pandas.Timestamp,
]
InstantConvertible = Union[
None, Instant, int, str, datetime.datetime, numpy.datetime64, pandas.Timestamp # type: ignore
]
ZonedDateTimeConvertible = Union[
None, ZonedDateTime, str, datetime.datetime, numpy.datetime64, pandas.Timestamp # type: ignore
]
Date = Union[
Instant, # type: ignore
LocalDate, # type: ignore
ZonedDateTime, # type: ignore
LocalDateConvertible,
InstantConvertible,
ZonedDateTimeConvertible,
]
Granularity = Literal["DAY", "HOUR", "MINUTE", "SECOND"]

Dependencies = Union[Tuple[Any], List[Any]]
Selection = Sequence[Key]

0 comments on commit c295cbc

Please sign in to comment.