class TestSet(param.Parameterized): numpy_params = ['r'] pandas_params = ['s','t','u'] conditionally_unsafe = ['f', 'o'] a = param.Integer(default=5, doc='Example doc', bounds=(2,30), inclusive_bounds=(True, False)) b = param.Number(default=4.3, allow_None=True) c = param.String(default='foo') d = param.Boolean(default=False) e = param.List([1,2,3], class_=int) f = param.List([1,2,3]) g = param.Date(default=datetime.datetime.now()) h = param.Tuple(default=(1,2,3), length=3) i = param.NumericTuple(default=(1,2,3,4)) j = param.XYCoordinates(default=(32.1, 51.5)) k = param.Integer(default=1) l = param.Range(default=(1.1,2.3), bounds=(1,3)) m = param.String(default='baz', allow_None=True) n = param.ObjectSelector(default=3, objects=[3,'foo'], allow_None=False) o = param.ObjectSelector(default=simple_list, objects=[simple_list], allow_None=False) p = param.ListSelector(default=[1,4,5], objects=[1,2,3,4,5,6]) q = param.CalendarDate(default=datetime.date.today()) r = None if np is None else param.Array(default=ndarray) s = None if pd is None else param.DataFrame(default=df1, columns=2) t = None if pd is None else param.DataFrame(default=pd.DataFrame( {'A':[1,2,3], 'B':[1.1,2.2,3.3]}), columns=(1,4), rows=(2,5)) u = None if pd is None else param.DataFrame(default=df2, columns=['A', 'B']) v = param.Dict({'1':2})
class _BigDumbParams(param.Parameterized): action = param.Action(default_action, allow_None=True) array = param.Array(np.array([1.0, 2.0])) boolean = param.Boolean(True, allow_None=True) callable = param.Callable(default_action, allow_None=True) class_selector = param.ClassSelector(int, is_instance=False, allow_None=True) color = param.Color("#FFFFFF", allow_None=True) composite = param.Composite(["action", "array"], allow_None=True) try: data_frame = param.DataFrame( pd.DataFrame({"A": 1.0, "B": np.arange(5)}), allow_None=True ) except TypeError: data_frame = param.DataFrame(pd.DataFrame({"A": 1.0, "B": np.arange(5)})) date = param.Date(datetime.now(), allow_None=True) date_range = param.DateRange((datetime.min, datetime.max), allow_None=True) dict_ = param.Dict({"foo": "bar"}, allow_None=True, doc="dict means dictionary") dynamic = param.Dynamic(default=default_action, allow_None=True) file_selector = param.FileSelector( os.path.join(FILE_DIR_DIR, "LICENSE"), path=os.path.join(FILE_DIR_DIR, "*"), allow_None=True, ) filename = param.Filename( os.path.join(FILE_DIR_DIR, "LICENSE"), allow_None=True ) foldername = param.Foldername(os.path.join(FILE_DIR_DIR), allow_None=True) hook_list = param.HookList( [CallableObject(), CallableObject()], class_=CallableObject, allow_None=True ) integer = param.Integer(10, allow_None=True) list_ = param.List([1, 2, 3], allow_None=True, class_=int) list_selector = param.ListSelector([2, 2], objects=[1, 2, 3], allow_None=True) magnitude = param.Magnitude(0.5, allow_None=True) multi_file_selector = param.MultiFileSelector( [], path=os.path.join(FILE_DIR_DIR, "*"), allow_None=True, check_on_set=True, ) number = param.Number(-10.0, allow_None=True, doc="here is a number") numeric_tuple = param.NumericTuple((5.0, 10.0), allow_None=True) object_selector = param.ObjectSelector( False, objects={"False": False, "True": 1}, allow_None=True ) path = param.Path(os.path.join(FILE_DIR_DIR, "LICENSE"), allow_None=True) range_ = param.Range((-1.0, 2.0), allow_None=True) series = param.Series(pd.Series(range(5)), allow_None=True) string = param.String("foo", allow_None=True, doc="this is a string") tuple_ = param.Tuple((3, 4, "fi"), allow_None=True) x_y_coordinates = param.XYCoordinates((1.0, 2.0), allow_None=True)
class MyParameterized(param.Parameterized): enable = param.Boolean(True, doc="A sample Boolean parameter", allow_None=True) what_proportion = param.Magnitude(default=0.9) age = param.Number(49, bounds=(0, 100), doc="Any Number between 0 to 100") how_many = param.Integer() favorite_quote = param.String(default="Hello, world!") choose_file_or_folder = param.Path(search_paths='./') choose_folder = param.Foldername(search_paths="./") choose_file = param.Filename(search_paths="./") select_a_file = param.FileSelector(path='./*') select_multiple_files = param.MultiFileSelector(path='./*') favorite_color = param.ObjectSelector( default="green", objects=["red", "yellow", "green"]) favorite_fruit = param.Selector(default="Apple", objects=["Orange", "Apple", "Mango"]) select_multiple = param.ListSelector(default=[3, 5], objects=[1, 2, 3, 4, 5]) birthday = param.CalendarDate(dt.date(2017, 1, 1), bounds=(dt.date(2017, 1, 1), dt.date(2017, 2, 1))) appointment = param.Date(dt.datetime(2017, 1, 1), bounds=(dt.datetime(2017, 1, 1), dt.datetime(2017, 2, 1))) least_favorite_color = param.Color(default='#FF0000') dataset = param.DataFrame(pd.util.testing.makeDataFrame().iloc[:3]) this_strange_thing = param.Tuple(default=(False, ), allow_None=True) some_numbers = param.NumericTuple(default=(1, 2, 3.0, 4.0)) home_city = param.XYCoordinates(default=(-111.65, 40.23)) bounds = param.Range(default=(-10, 10))
class ObservationsExplorer(param.Parameterized): """Param interface for inspecting observations""" observation_df = param.DataFrame( doc='The DataFrame for the observations.', precedence=-1 # Don't show widget ) images_df = param.DataFrame( doc='The DataFrame for the images from the selected observations.', precedence=-1 # Don't show widget ) show_recent = param.Boolean(label='Show recent observations', doc='Show recent observations', default=True) search_name = param.String( label='Coordinates for object', doc='Field name for coordinate lookup', ) coords = param.XYCoordinates(label='RA/Dec Coords [deg]', doc='RA/Dec Coords [degrees]', default=(0, 0)) radius = param.Number(label='Search radius [deg]', doc='Search radius [degrees]', default=15., bounds=(0, 180), softbounds=(0, 25)) time = param.DateRange( label='Date Range', default=(pendulum.parse('2016-01-01').replace(tzinfo=None), now), bounds=(pendulum.parse('2016-01-01').replace(tzinfo=None), now)) min_num_images = param.Integer(doc='Minimum number of images.', default=1, bounds=(1, 50), softbounds=(1, 10)) unit_id = param.ListSelector( doc='Unit IDs', label='Unit IDs', ) def __init__(self, **kwargs): super().__init__(**kwargs) logger.debug(f'Getting recent stats from {BASE_URL}') self._observations_path = download_file(f'{BASE_URL}', cache='update', show_progress=False, pkgname='panoptes') self._observations_df = pd.read_csv( self._observations_path).convert_dtypes() # Setup up widgets # Set some default for the params now that we have data. units = sorted(self._observations_df.unit_id.unique()) units.insert(0, 'The Whole World! 🌎') self.param.unit_id.objects = units self.unit_id = [units[0]] # Create the source objects. self.update_dataset() @param.depends('coords', 'radius', 'time', 'min_num_images', 'unit_id', 'search_name') def update_dataset(self): if self.show_recent: # Get just the recent result on initial load df = search_observations(ra=180, dec=0, radius=180, start_date=now.subtract(months=1), end_date=now, min_num_images=1, source=self._observations_df).sort_values( by=['time', 'unit_id', 'camera_id'], ascending=False) else: # If using the default unit_ids option, then search for all. unit_ids = self.unit_id if unit_ids == self.param.unit_id.objects[0:1]: unit_ids = self.param.unit_id.objects[1:] if self.search_name != '': coords = SkyCoord.from_name(self.search_name) self.coords = (round(coords.ra.value, 3), round(coords.dec.value, 3)) # Search for the observations given the current params. df = search_observations(ra=self.coords[0], dec=self.coords[1], radius=self.radius, start_date=self.time[0], end_date=self.time[1], min_num_images=self.min_num_images, unit_id=unit_ids).sort_values( by=['time', 'unit_id', 'camera_id'], ascending=False) df.time = pd.to_datetime(df.time) cds = ColumnDataSource(data=df, name='observations_source') def obs_row_selected(attrname, old_row_index, new_row_index): # We only lookup one even if they select multiple rows. newest_index = new_row_index[-1] row = df.iloc[newest_index] print(f'Looking up sequence_id={row.sequence_id}') self.images_df = get_metadata(sequence_id=row.sequence_id) if self.images_df is not None: self.images_df = self.images_df.dropna() cds.selected.on_change('indices', obs_row_selected) return cds @param.depends("images_df") def selected_title(self): try: sequence_id = self.images_df.sequence_id.iloc[0] except AttributeError: sequence_id = '' return pn.panel(f'<h5>{sequence_id}</h5>') @param.depends('images_df') def image_table(self): columns = [('time', 'Time [UTC]')] try: images_table = self.images_df.hvplot.table(columns=columns).opts( width=250, height=100, title=f'Images ({len(self.images_df)})', ) except AttributeError: images_table = self.images_df return images_table @param.depends('images_df') def image_preview(self): try: image_url = self.images_df.public_url.dropna().iloc[0].replace( '.fits.fz', '.jpg') return pn.pane.HTML(f''' <div class="media" style="width: 300px; height: 200px"> <a href="{image_url}" target="_blank"> <img src="{image_url}" class="card-img-top" alt="Observation Image"> </a> </div> ''') except AttributeError: return '' @param.depends('observation_df') def fits_file_list_to_csv_cb(self): """ Generates a CSV file from current image list.""" df = self.images_df.public_url.dropna() sio = StringIO() df.to_csv(sio, index=False, header=False) sio.seek(0) return sio def table_download_button(self): """ A button for downloading the images CSV.""" try: sequence_id = self.images_df.sequence_id.iloc[0] return pn.widgets.FileDownload( callback=self.fits_file_list_to_csv_cb, filename=f'fits-list-{sequence_id}.txt', label='Download FITS List (.txt)', ) except AttributeError: return '' def sources_download_button(self): try: sequence_id = self.images_df.sequence_id.iloc[0] parquet_url = f'{OBSERVATIONS_BASE_URL}/{sequence_id}-sources.parquet' source_btn = pn.widgets.Button( name='Download sources list (.parquet)', ) source_btn.js_on_click(args=dict(url=parquet_url), code=''' window.open(url, '_blank') ''') return source_btn except AttributeError: return '' def table(self): columns = [ TableColumn( field="unit_id", title="Unit ID", width=60, ), TableColumn( field="camera_id", title="Camera ID", width=60, ), TableColumn( field="time", title="Time [UTC]", formatter=DateFormatter(format='%Y-%m-%d %H:%M'), width=130, ), TableColumn( field="field_name", title="Field Name", width=240, ), TableColumn( field="ra", title="RA [deg]", formatter=NumberFormatter(format="0.000"), width=70, ), TableColumn( field="dec", title="Dec [deg]", formatter=NumberFormatter(format="0.000"), width=70, ), TableColumn( field="num_images", title="Images", width=40, ), TableColumn( field="status", title="Status", width=75, ), TableColumn( field="exptime", title="Exptime [sec]", formatter=NumberFormatter(format="0.00"), width=60, ), TableColumn( field="total_minutes_exptime", title="Total Minutes", formatter=NumberFormatter(format="0.0"), width=60, ), ] cds = self.update_dataset() data_table = DataTable( source=cds, name='observations_table', columns=columns, index_position=None, min_width=1100, fit_columns=True, sizing_mode='stretch_both', ) return data_table
class MyParamXYCoordinates(param.Parameterized): xy_coordinates = param.XYCoordinates(default=(-111.65, 40.23))
class MyParamXYCoordinates(param.Parameterized): home_town = param.XYCoordinates(default=(-111.65, 40.23)) my_numeric_tuples = param.NumericTuple(default=(1, 2, 3))