0

I am trying to display 3 sets of X/Y coordinates on an animated plotly scatter graph in which the animation key is time. Currently my workaround was to add all the coordinate sets into the same dataframe however I believe this will cause me problems as I need to change marker properties to easily distinguish between each point.

This is what my workaround looks like:workaround

This is how I am generating the graph:

x1_trim += x2_trim
x1_trim += x3_trim
y1_trim += y2_trim
y1_trim += y3_trim

d = {
    "x1": x1_trim,
    "y1": y1_trim,
    "time": time_trim
}
df = pd.DataFrame(d)

#Default x and y axis
x_range = [-1,1]
y_range = [-1,1]

fig = px.scatter(df, x="x1", y="y1", animation_frame="time", range_x=x_range, range_y=y_range)
fig.add_shape(type="rect",x0=-0.5, y0=-0.5, x1=0.5, y1=0.5, line=dict(color="Green",width=2))

As you can see I'm adding my x2/y2 and x3/y3 data onto the end of my x1/y1 list, how would I keep these separate whilst still having all the information on my animated plot? I was trying to display multiple scatter graphs on the same plot however never managed to get it working.

My solution attempt:

#Building the dataframe and drawing graph
d1 = {
    "x": x1_trim,
    "y": y1_trim,
    "time": time_trim
}

d2 = {
    "x": x2_trim,
    "y": y2_trim,
    "time":time_trim
}

d3 = {
    "x": x3_trim,
    "y": y3_trim,
    "time": time_trim
}

dfs = {"d1": d1, "d2": d2, "d3": d3}

fig = go.Figure()

for i in dfs:
   fig = fig.add_trace(go.Scatter(x = dfs[i]["x"], y = dfs[i]["y"], name = i, animation_frame=dfs[0]["time"] ))
Eog
  • 102
  • 11

1 Answers1

1
import numpy as np
import itertools
import pandas as pd
import plotly.express as px
import plotly.graph_objects as go

# construct a dataframe that has four columns, x, y, trace: 0,1,2 as string for trace, time for animation frame
df = pd.DataFrame(np.random.uniform(1, 5, [288, 2]), columns=["x", "y"]).join(
    pd.DataFrame(
        itertools.product(
            pd.Series(
                pd.date_range("1-jan-2021", freq="1H", periods=24 * 4)
            ).dt.time.astype(str),
            range(3),
        ),
        columns=["time", "trace"],
    ).astype(str)
)

fig = px.scatter(
    df.assign(size=8),
    x="x",
    y="y",
    color="trace",
    animation_frame="time",
    symbol="trace",
    size="size",
    size_max=10,
)
fig

data frame structure

x        float64
y        float64
time      object
trace     object
dtype: object

enter image description here

raw data

  • per comments - construction of data frame has a number of techniques that are not core to solution
  • this shows just two times sample data and being loaded into a data frame
import io
df = pd.read_csv(io.StringIO("""x,y,time,trace
4.47189433943762,2.2663279945423125,00:00:00,0
3.263751615344729,2.7707896475420433,00:00:00,1
3.5073083888118197,3.937926244743114,00:00:00,2
3.254552306893224,1.7740014652497695,01:00:00,0
1.6111813732639115,1.5324478432794377,01:00:00,1
3.411314175447148,4.495634466903654,01:00:00,2
1.7036170024927264,4.284719804413246,00:00:00,0
1.9797441059531726,3.9012400136550798,00:00:00,1
1.5178030860172549,3.7904674709011084,00:00:00,2
2.03612601506845,2.5378053661978592,01:00:00,0
2.230688800088902,2.946463794148376,01:00:00,1
1.3626620551885207,2.442489690168825,01:00:00,2
4.733618949813925,3.9103378744051014,00:00:00,0
4.4816142771548435,1.1245335267028125,00:00:00,1
4.9550805577829315,3.2454665809417227,00:00:00,2
2.9007566994079816,1.1620429771047482,01:00:00,0
2.11807366926913,3.9811777626521083,01:00:00,1
2.0753910017252144,4.416934286540347,01:00:00,2
2.3867481776916804,1.6378885254464284,00:00:00,0
1.4021710772900526,2.1565431787254536,00:00:00,1
3.5150580308648562,2.2722969079838387,00:00:00,2
4.987010605760303,1.943335174662026,01:00:00,0
3.0504403251471484,4.398673922531113,01:00:00,1
4.021398175417694,4.422199058284852,01:00:00,2"""))

df["trace"] = df["trace"].astype(str)
px.scatter(df, x="x", y="y", color="trace", animation_frame="time")
Rob Raymond
  • 29,118
  • 3
  • 14
  • 30
  • Thank you so much for answering my question, I'm getting quite confused about how you're creating the dataframe as I had never used pandas before. Would you be able to show me how the dataframe could be created with hard coded data as a more simple example? Apologies. – Eog Oct 19 '21 at 15:29
  • I know I've used a lot of coding sugar to generate the DF... hence reason I included 20 sample rows in answer. that's really the hard coded data – Rob Raymond Oct 19 '21 at 15:47
  • have updated answer with sample data as CSV to construct data frame. no need to comprehend techniques I have used for generating test data – Rob Raymond Oct 19 '21 at 16:23
  • Ah ok thank you, when using this technique how would I then apply different marker appearances to each set of x/y coordinates? – Eog Oct 20 '21 at 07:21
  • 1
    further updated - found simpler approach to symbols – Rob Raymond Oct 20 '21 at 08:35