Jak dodać animację do fabuły postać w Pythonie

0

Pytanie

Obecnie mam ten kod:

fig= go.Figure()
for idx in range(len(reference)):
    df = reference.loc[idx]
    if df.ObjClass != 0:
        x,y = df.Polygon.exterior.xy
        fig.add_trace(go.Scatter(x=np.array(x), y=np.array(y)))
return fig

Harmonogram służy do rysowania prostokątów za pomocą wielokątów. Raczej nie jest najbardziej efektywny, ale i tam jest on otwarty dla ulepszeń.

Moje pytanie brzmi jak dodać animację do istniejącej fabuły figury? W moim df mam kolumnę czasu, który nadaje się do tego (df.Time). Gdy animacja zostanie dodana, chcę rysować wielokąty tylko dla tego znacznika czasu.

Aktualny fabuła bez animacji

EDYCJA: Dodawanie struktury danych

Tak że to nie działa podczas tworzenia grafiki, jak wyjaśniam w swoim komentarzu poniżej. Jednak, jeśli przejdę na sortowanie według ObjId zamiast Czasu, to zadziała, ale klatkę animacji nie będzie posortowana. Chcę, aby najniższy czas był pierwszy, a najwyższy-w końcu.

ObjClass    Time    ObjID   Corner  Lat Long
0   3.0 5.9 54.0    RR  21.549906   129.418088
563 3.0 5.9 54.0    LR  23.569243   129.523022
1126    3.0 5.9 54.0    LF  23.569243   136.523022
1689    3.0 5.9 54.0    RF  21.549906   136.418088
1   3.0 5.95    54.0    RR  17.946687   114.856340
564 3.0 5.95    54.0    LR  19.726662   114.919184
1127    3.0 5.95    54.0    LF  19.726662   121.919184
1690    3.0 5.95    54.0    RF  17.946687   121.856340
2   3.0 6.0 54.0    RR  17.685873   121.115523
565 3.0 6.0 54.0    LR  19.556310   121.182149
1128    3.0 6.0 54.0    LF  19.556310   128.182149
1691    3.0 6.0 54.0    RF  17.685873   128.115523
3   3.0 6.05    54.0    RR  17.685873   121.115523
566 3.0 6.05    54.0    LR  19.556310   121.182149
1129    3.0 6.05    54.0    LF  19.556310   128.182149
1692    3.0 6.05    54.0    RF  17.685873   128.115523
4   3.0 6.1 54.0    RR  17.375609   127.925362
567 3.0 6.1 54.0    LR  19.322351   127.848100
1130    3.0 6.1 54.0    LF  19.322351   134.848100
1693    3.0 6.1 54.0    RF  17.375609   134.925362
animation pandas plot plotly
2021-11-22 14:07:05
1

Najlepsza odpowiedź

1

Nie podałeś przykładowe dane. Pośrednio można zdefiniować ramki danych

Poligon Obiekt Klasa obiektów czas
WIELOKĄT ((58 91, 58 77, 0 73, -0 87, 58 91)) 0 1 00:00
WIELOKĄT ((51 102, 58 90, 7 62, 0 74, 51 102)) 0 1 01:00
WIELOKĄT ((40 110, 52 101, 18 54, 6 63, 40 110)) 0 1 02:00

To wymaga dodatkowej kolumny identyfikator obiektu, który jest jednym i tym samym poligon, którzy mają różne współrzędne dla każdego czasu

Najprostszym sposobem, aby stworzyć działka animowaną postać-używać Plotly Express. Dlatego реструктурируйте dane, aby były one sekwencji x i y w długim ujęciu danych

import io
import pandas as pd
import numpy as np
import plotly.graph_objects as go
import plotly.express as px
import shapely.wkt


df_p = pd.read_csv(io.StringIO("""Polygon,ObjectId,ObjClass,time
"POLYGON ((58 91, 58 77, 0 73, -0 87, 58 91))",0,1,00:00
"POLYGON ((51 102, 58 90, 7 62, 0 74, 51 102))",0,1,01:00
"POLYGON ((40 110, 52 101, 18 54, 6 63, 40 110))",0,1,02:00
"POLYGON ((28 112, 41 109, 30 52, 17 55, 28 112))",0,1,03:00
"POLYGON ((32 29, 20 33, 38 93, 50 89, 32 29))",1,1,00:00
"POLYGON ((45 31, 34 29, 25 91, 36 93, 45 31))",1,1,01:00
"POLYGON ((57 38, 47 32, 13 84, 23 90, 57 38))",1,1,02:00
"POLYGON ((65 50, 58 39, 5 72, 12 83, 65 50))",1,1,03:00
"POLYGON ((1 90, 7 90, 12 48, 6 48, 1 90))",2,1,00:00
"POLYGON ((-7 85, -2 89, 20 53, 15 49, -7 85))",2,1,01:00
"POLYGON ((-13 78, -10 83, 26 60, 23 55, -13 78))",2,1,02:00
"POLYGON ((-15 69, -14 75, 28 69, 27 63, -15 69))",2,1,03:00
"POLYGON ((59 12, 49 18, 84 92, 94 86, 59 12))",3,1,00:00
"POLYGON ((77 11, 65 11, 66 93, 78 93, 77 11))",3,1,01:00
"POLYGON ((94 17, 83 12, 49 87, 60 92, 94 17))",3,1,02:00
"POLYGON ((107 30, 99 21, 36 74, 44 83, 107 30))",3,1,03:00
"POLYGON ((9 29, 3 37, 13 43, 19 35, 9 29))",4,1,00:00
"POLYGON ((12 28, 4 34, 10 44, 18 38, 12 28))",4,1,01:00
"POLYGON ((15 29, 5 31, 7 43, 17 41, 15 29))",4,1,02:00
"POLYGON ((17 32, 8 29, 5 40, 14 43, 17 32))",4,1,03:00"""))

df_p["Polygon"] = df_p["Polygon"].apply(shapely.wkt.loads)

# explode out ploygons to x & y for plotly express
df_plot = (
    df_p["Polygon"]
    .apply(
        lambda p: [{"x": x, "y": y} for x, y in zip(p.exterior.xy[0], p.exterior.xy[1])]
    )
    .explode()
    .apply(pd.Series)
    .join(df_p)
)


px.line(df_plot, x="x", y="y", color="ObjectId", animation_frame="time")

enter image description here

korzystanie z przykładowych danych

import pandas as pd
import io
import plotly.express as px

df = pd.read_csv(
    io.StringIO(
        """ObjClass    Time    ObjID   Corner  Lat Long
0   3.0 5.9 54.0    RR  21.549906   129.418088
563 3.0 5.9 54.0    LR  23.569243   129.523022
1126    3.0 5.9 54.0    LF  23.569243   136.523022
1689    3.0 5.9 54.0    RF  21.549906   136.418088
1   3.0 5.95    54.0    RR  17.946687   114.856340
564 3.0 5.95    54.0    LR  19.726662   114.919184
1127    3.0 5.95    54.0    LF  19.726662   121.919184
1690    3.0 5.95    54.0    RF  17.946687   121.856340
2   3.0 6.0 54.0    RR  17.685873   121.115523
565 3.0 6.0 54.0    LR  19.556310   121.182149
1128    3.0 6.0 54.0    LF  19.556310   128.182149
1691    3.0 6.0 54.0    RF  17.685873   128.115523
3   3.0 6.05    54.0    RR  17.685873   121.115523
566 3.0 6.05    54.0    LR  19.556310   121.182149
1129    3.0 6.05    54.0    LF  19.556310   128.182149
1692    3.0 6.05    54.0    RF  17.685873   128.115523
4   3.0 6.1 54.0    RR  17.375609   127.925362
567 3.0 6.1 54.0    LR  19.322351   127.848100
1130    3.0 6.1 54.0    LF  19.322351   134.848100
1693    3.0 6.1 54.0    RF  17.375609   134.925362"""
    ),
    sep="\s+",
    engine="python",
)

# if polygon is a quadrangle, need five points to define it. 4 is just a linestring
# duplicate first corner
df = pd.concat([df, df.loc[df["Corner"].eq("RR")].assign(Corner="RR2")])

# need to sort by Corner, hence make it a categorical
df["Corner"] = pd.Categorical(
    df["Corner"], ["RR", "RF", "LF", "LR", "RR2"], ordered=True
)

px.line(
    df.sort_values(["ObjID", "Time", "Corner"]),
    x="Long",
    y="Lat",
    color="ObjID",
    animation_frame="Time",
).update_layout(
    xaxis={"range": [df["Long"].min(), df["Long"].max()]},
    yaxis={"range": [df["Lat"].min(), df["Lat"].max()]},
)
2021-12-03 15:41:12

Dziękuję bardzo za odpowiedź! Bardzo pomagaj miodu! Teraz jednak pojawiła się u mnie nowy problem. Używać twój przykład, ja przebudował swoją ramkę danych w długim formacie z "Szerokimi" i "Długie" kolumnami. To jednak wydaje się bardzo wybredny do tego, jak ja sprawdzam swoje dane. Jeśli отсортирую w "ObjId", to zadziała, ale oś czasu w pełni odwrócenie. Jeśli zamiast tego отсортирую dla "Czasu", oś czasu będzie w porządku, ale wtedy wyświetla się tylko jeden obiekt za wartość czasu, nawet jeśli jest ich kilka.
MartinCB

nie podzielili się swoją strukturą danych, więc musiałem stwierdzić. Chyba masz ramkę danych z wielokątów, gdzie każdy wielokąt ma ObjId, który jest stały w czasie / transformacje. dlatego tak właśnie структурировал przykładowe dane. zaktualizuj swoje pytanie za pomocą head(10) twój ramki danych, i mogę zaktualizować go. Dlatego wszystkie zalecenia SO do zadania pytań podkreślają konieczność wymiany przykładowych danych. Nie rób strasznej rzeczy-nie udostępniaj swoich danych w formie obrazu, zmuszając każdego pozwanego wykorzystać słabe rozpoznawanie ich wykorzystania
Rob Raymond

Dodano moja struktura danych powyżej. Wygląda trochę strasznie, ale mam nadzieję, że będziesz w stanie skopiować go bez większych kłopotów.
MartinCB

zaktualizowany odpowiedź - jesteś całkowicie porzucili mnie z próbką kodu, za pomocą zgrabna. Wygląda na to, że twój przykład kodu i przykłady danych nie są związane
Rob Raymond

Hehe, to dlatego, że zmieniłem swój smukły полигональный podejście, aby to on najbardziej odpowiadał państwa odpowiedzi. Dane źródłowe naprawdę zawierają wielokąta obiekty, ale odrzuciłem je, starając się dostosować swoją df do twojego przykładu.
MartinCB

dobrze - myślę, że lepiej zostawić jak wielokąty... to będzie wspierać innych wielokątów 3,4,5 itd klucz w tym, aby posortować go, zanim wysadzić
Rob Raymond

W innych językach

Ta strona jest w innych językach

Русский
..................................................................................................................
Italiano
..................................................................................................................
Română
..................................................................................................................
한국어
..................................................................................................................
हिन्दी
..................................................................................................................
Français
..................................................................................................................
Türk
..................................................................................................................
Česk
..................................................................................................................
Português
..................................................................................................................
ไทย
..................................................................................................................
中文
..................................................................................................................
Español
..................................................................................................................
Slovenský
..................................................................................................................