Skip to content

Commit

Permalink
Added track label display
Browse files Browse the repository at this point in the history
  • Loading branch information
kb- committed Mar 27, 2024
1 parent fe154dc commit 5edc871
Show file tree
Hide file tree
Showing 13 changed files with 54 additions and 15 deletions.
6 changes: 3 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -74,11 +74,11 @@ ts1 = pd.Series(np.random.randn(len(date_rng)), index=date_rng)
ts2 = pd.Series(np.random.randn(len(date_rng)), index=date_rng)
df = pd.DataFrame({'Time Series 1': ts1, 'Time Series 2': ts2})

template = "x: %{x}<br>y: %{y:.2f}<br>ID: %{pointNumber}<br>name: %{customdata[0]}<br>unit: %{customdata[1]}"
template = "%{label}<br>x: %{x}<br>y: %{y:.2f}<br>ID: %{pointNumber}<br>name: %{customdata[0]}<br>unit: %{customdata[1]}"
fig10 = px.line(df, x=df.index, y=df.columns, title="Time Series Plot")

for i, trace in enumerate(fig10.data):
trace.customdata = np.column_stack((np.repeat(df.columns[i], len(df)), np.repeat('#{}'.format(i+1), len(df))))
trace.customdata = [[f"Series {i+1}", f'Point {j+1}'] for j in range(len(df))]
trace.hovertemplate = template

app10 = Dash(__name__)
Expand All @@ -104,7 +104,7 @@ tooltip(app10, graph_ids=["graph-id"], template=template, debug=True)

Tooltips can be formatted using templates similar to Plotly's hovertemplates. The tooltip template allows custom formatting and the inclusion of text and values.

For example, you can use a template like `"x: %{x:.2f}<br>y: %{y:.2f}"` to display the x and y values with two decimal places.
For example, you can use a template like `"{label}<br>x: %{x:.2f}<br>y: %{y:.2f}"` to display the track label, plus x and y values with two decimal places.

Refer to [Plotly’s documentation on hover text and formatting](https://plotly.com/python/hover-text-and-formatting/) for more details on how to construct and customize your tooltip templates.

Expand Down
14 changes: 11 additions & 3 deletions dash_qt_demo.py
Original file line number Diff line number Diff line change
@@ -1,15 +1,15 @@
import http.client
import threading
import os
import sys
import threading
import time

import dash
import numpy as np
from dash import dcc, html
from PyQt6.QtCore import QUrl
from PyQt6.QtWebEngineWidgets import QWebEngineView
from PyQt6.QtWidgets import QApplication, QFileDialog, QMainWindow, QVBoxLayout
from PyQt6.QtWidgets import QApplication, QFileDialog, QMainWindow

from dash_tooltip import tooltip

Expand Down Expand Up @@ -74,6 +74,7 @@ def create_dash_app():

x = np.linspace(0, 10, 100)
y = np.sin(x)
y1 = np.cos(x)

app.layout = html.Div(
[
Expand All @@ -88,6 +89,13 @@ def create_dash_app():
"mode": "lines",
"name": "sin(x)",
},
{
"x": x,
"y": y1,
"type": "scatter",
"mode": "lines",
"name": "cos(x)",
},
],
"layout": {
"title": "Dash by Plotly in PyQt",
Expand All @@ -110,7 +118,7 @@ def create_dash_app():
"overflow": "hidden",
}, # Full viewport width and height
)
template = "x: %{x:.2f},<br>y: %{y:.3f}"
template = "%{label},<br>x: %{x:.2f},<br>y: %{y:.3f}"
tooltip(app, template=template)
return app

Expand Down
3 changes: 3 additions & 0 deletions dash_tooltip/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -203,6 +203,9 @@ def _display_click_data(
else:
yaxis = "y"

# Extract label from the curve data
point["label"] = figure["data"][point["curveNumber"]]["name"]

# If the x-axis is logarithmic, adjust `x_val`
# This is a fix for longstanding Plotly bug
# https://github.com/plotly/plotly.py/issues/2580
Expand Down
25 changes: 21 additions & 4 deletions dash_tooltip_demo.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
# extension: .py
# format_name: percent
# format_version: '1.3'
# jupytext_version: 1.15.2
# jupytext_version: 1.16.1
# kernelspec:
# display_name: Python 3 (ipykernel)
# language: python
Expand Down Expand Up @@ -236,7 +236,7 @@
if __name__ == "__main__":
app3.run(debug=True, port=8083)

# %% jupyter={"source_hidden": true}
# %%
# ---- Test 4: Multiple Traces with Tooltips ----
app4 = Dash(__name__)

Expand Down Expand Up @@ -310,7 +310,7 @@
"arrowsize": 2.5,
# ... any other customization
}
template = "x: %{x},<br>y: %{y},<br>%{customdata[0]}"
template = "%{label},<br>x: %{x},<br>y: %{y},<br>%{customdata[0]}"
tooltip(app4, style=custom_style, template=template)

if __name__ == "__main__":
Expand Down Expand Up @@ -679,6 +679,17 @@ def toggle_tooltip(change):
"ignore", category=FutureWarning, message=".*is_datetime64tz_dtype is deprecated.*"
)

# Suppress the specific warning about H
# in plotly_resampler
warnings.filterwarnings(
"ignore", category=FutureWarning, message=".*'H' is deprecated.*"
)

# Suppress the specific warning about m
# in plotly_resampler
warnings.filterwarnings(
"ignore", category=FutureWarning, message=".*'m' is deprecated.*"
)

# Generate random time series data
date_rng = pd.date_range(start="2020-01-01", end="2020-12-31", freq="h")
Expand Down Expand Up @@ -944,7 +955,13 @@ def interactive_plot(fig, graphid, template):
id="example-graph",
figure={
"data": [
{"x": x1, "y": y1, "type": "line", "name": "sin(x)"}
{
"x": x1,
"y": y1,
"type": "line",
"mode": "lines",
"name": "sin(x)",
}
],
"layout": {
"title": "Direct Data Injection into "
Expand Down
2 changes: 1 addition & 1 deletion requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -25,5 +25,5 @@ nox
wheel
PyQt6; python_version >= "3.8"
PyQt6-WebEngine; python_version >= "3.8"
tsdownsample; python_version >= "3.12"
git+https://github.com/predict-idlab/tsdownsample.git#egg=tsdownsample; python_version >= "3.12"

2 changes: 1 addition & 1 deletion tests/test_11_direct_figure_in_dcc_graph.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@

np.random.seed(20)
y1 = np.random.normal(0, 10, 50)
x1 = np.arange(0, 50)
x1 = np.arange(0, 30)

app13.layout = dbc.Container(
[
Expand Down
1 change: 1 addition & 0 deletions tests/test_1_tooltip_function.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
This tests the basic functionality and setup of tooltips.
Run multiple times because of variability in click results
"""

import time
from typing import Any, Dict

Expand Down
1 change: 1 addition & 0 deletions tests/test_2_tooltip_configuration.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
reflect the desired properties (e.g., arrow color, font size).
This ensures that the function respects custom configurations.
"""

from typing import Any, Dict, Union

import dash
Expand Down
11 changes: 8 additions & 3 deletions tests/test_3_template_formating.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
according to the template.
This ensures that the function respects custom formatting.
"""

import time
from typing import Any, Dict

Expand Down Expand Up @@ -39,6 +40,7 @@ def display_click_data(clickData: Dict[str, Any]) -> str:
x2 = np.arange(0, 50)
custom_labels = [f"Label {i}" for i in range(50)]
fig2 = px.scatter(x=x2, y=y2, custom_data=[custom_labels, y2 * 2])
fig2.update_traces(name="LABEL")
fig2.update_layout(title_text="Editable Title", title_x=0.5)

app.layout = dbc.Container(
Expand Down Expand Up @@ -78,9 +80,7 @@ def display_click_data(clickData: Dict[str, Any]) -> str:
)

# Tooltip template from dash_tooltip_demo.py
tooltip_template = (
"x: %{x},<br>y: %{y:.2f},<br>%{customdata[0]},<br>2y=%{customdata[1]:.3f}"
)
tooltip_template = "%{label},<br>x: %{x},<br>y: %{y:.2f},<br>%{customdata[0]},<br>2y=%{customdata[1]:.3f}"
tooltip(app, template=tooltip_template, debug=True)


Expand All @@ -97,9 +97,11 @@ def test_customdata_tooltip(dash_duo: Any) -> None:
x_value = x2[idx]
y_value = y2[idx]
expected_custom_label2 = y_value * 2
expected_label = "LABEL"

expected_annotation_text = (
tooltip_template.replace("<br>", "")
.replace("%{label}", expected_label)
.replace("%{x}", str(x_value))
.replace("%{y:.2f}", f"{y_value:.2f}")
.replace("%{customdata[0]}", expected_custom_label)
Expand Down Expand Up @@ -143,3 +145,6 @@ def test_customdata_tooltip(dash_duo: Any) -> None:
# Check if the actual annotation text matches the expected text based on the
# customdata
assert actual_annotation_text == expected_annotation_text

# Check if the actual annotation text contains the expected label
assert expected_label in actual_annotation_text
1 change: 1 addition & 0 deletions tests/test_4a_multiple_graph.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
and verify that tooltips are functional for all graphs.
This ensures that the function can handle multiple graphs on subplots correctly.
"""

import time
from typing import Any

Expand Down
1 change: 1 addition & 0 deletions tests/test_4b_multiple_graph.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
functional for all graphs.
This ensures that the function can handle multiple graphs correctly.
"""

import time
from typing import Any

Expand Down
1 change: 1 addition & 0 deletions tests/test_7_tooltip_removal.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
4. Delete a specific tooltip.
5. Count the number of tooltips again and validate that it has decreased by one.
"""

import time
from typing import Any, Dict

Expand Down
1 change: 1 addition & 0 deletions tests/test_8__display_click_data.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
scenarios, we maintain the tooltip feature's integrity, ensuring that users get
consistent and accurate tooltip displays during interactions.
"""

from typing import Dict, List, Union

import dash
Expand Down

0 comments on commit 5edc871

Please sign in to comment.