0 Daumen
291 Aufrufe

Frage:

Ich habe x und y Daten einer Autofahrt. Also Auto startet bei (0|0) nach 1 Sekunde befindet es sich auf stelle (2|-1) usw... Ich habe mir nun aus den Daten den zurĂŒckgelegten Weg als .svg Datei ausgeben lassen. Dort sehe ich nun den zurĂŒckgelegten Weg als eine Linie.

Ich möchte nun gerne meinen Code so erweitern dass in der .svg die Autofahrt simuliert wird. Also wenn ich die .svg öffne sollte die Linie jede Sekunde um den Wert x, y weiterfahren. Ist das ĂŒberhaupt möglich? Falls ja wie mache ich dies?

Code:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>


int main() {
  FILE *input_file, *svg_file;

  input_file = fopen("result.csv", "r");
  if (!input_file) {
      printf("fail to open result.csv\n");
      exit(1);
  }

  svg_file = fopen("path.svg", "w");
  if (!svg_file) {
      printf("fail to open path.svg\n");
      exit(1);
  }

  // write svg head
  const char *svg_head = "<svg xmlns='http://www.w3.org/2000/svg'><defs><rect width="10" height="10">;
  <animate attributeName="rx" values="0;5;0" dur="10s" repeatCount="indefinite" />
</rect>
</svg>\n";
  fputs(svg_head, svg_file);

  double min_x = 0.0, min_y = 0.0;

  char line[1024];
  while (fgets(line, sizeof(line), input_file)) {
      char *save = line;
      char *_x = strtok_r(line, ",", &save);
      double x = atof(_x);
      char *_y = strtok_r(NULL, ",", &save);
      double y = -atof(_y);
      if (x < min_x) min_x = x;
      if (y < min_y) min_y = y;
      fprintf(svg_file, "%f,%f\n", x, y);
  }

  // write svg tail
  const char *svg_tail = "'/></defs><use href='#line' x='%f' y='%f' fill='none' stroke='black' /></svg>";
  fprintf(svg_file, svg_tail, -min_x, -min_y);

  fclose(input_file);
  fclose(svg_file);
}

Avatar von

1 Antwort

0 Daumen

Antwort mit KI erzeugt

Autofahrt in C aus Daten visualisieren

Um die Autofahrt mit einer Linie in einer SVG-Datei zu simulieren, die jede Sekunde um den Wert \(x, y\) weiterfĂ€hrt, mĂŒssen Sie den SVG-Code anpassen, um Animationen zu unterstĂŒtzen. SVG bietet das <animate>-Element, mit dem Objekte ĂŒber die Zeit verĂ€ndert werden können. Leider unterstĂŒtzt SVG nicht direkt die Animation entlang einer arbitrĂ€ren Pfadkurve (wie Ihre Autofahrt) mit sich ĂŒber die Zeit Ă€ndernden Geschwindigkeiten in so einer direkten Weise, ohne zusĂ€tzliches JavaScript oder komplexe Manipulationen.

Jedoch können wir eine AnnĂ€herung erreichen, indem wir eine Linie zeichnen, die den gesamten Pfad darstellt, und dann einen kleinen Kreis (oder ein anderes Symbol, das das Auto reprĂ€sentiert) entlang dieses Pfades animieren. Das bedeutet, dass der Pfad zunĂ€chst vollstĂ€ndig gezeichnet wird und anschließend das "Auto" darauf animiert wird.

Hier ist ein Überblick, wie Sie Ihren Code modifizieren können, um eine derartige Animation zu erzeugen:

- Pfad erstellen aus den x, y Datenpunkten, die den gesamten zurĂŒckgelegten Weg darstellen.
- Auto hinzufĂŒgen, das den Pfad entlang fĂ€hrt. Dies kann durch ein Kreiselement (<circle>) symbolisiert werden, das entlang des Pfades animiert wird.

Update des Codes

Das grundlegende Vorgehen umfasst folgende Schritte:

1. Erstellung des SVG-Pfads aus Ihren x, y-Daten.
2. HinzufĂŒgen eines <circle>-Elements und dessen Animation entlang des Pfades.

Hier ein Beispiel, wie der Code aussehen könnte:

c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main() {
    FILE *input_file, *svg_file;

    input_file = fopen("result.csv", "r");
    if (!input_file) {
        printf("fail to open result.csv\n");
        exit(1);
    }

    svg_file = fopen("path.svg", "w");
    if (!svg_file) {
        printf("fail to open path.svg\n");
        exit(1);
    }

    // Schreiben des SVG-Headers
    fputs("<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 500 500' style='background-color:#FFF'>\n", svg_file);

    char line[1024];
    char path_data[10000] = "M ";
    
    while (fgets(line, sizeof(line), input_file)) {
        strcat(path_data, line);
        strcat(path_data, " ");
    }

    // Schreiben des Pfades
    fprintf(svg_file, "<path d='%s' fill='none' stroke='black'/>\n", path_data);

    // Kreis (Auto) hinzufĂŒgen
    fprintf(svg_file, "<circle r='5' fill='red'>\n");
    // Animation des Kreises entlang des Pfades
    fprintf(svg_file, "<animateMotion dur='10s' repeatCount='indefinite'>\n");
    fprintf(svg_file, "<mpath href='#path'/>\n");
    fprintf(svg_file, "</animateMotion>\n");
    fprintf(svg_file, "</circle>\n");

    // SVG abschließen
    fputs("</svg>\n", svg_file);

    fclose(input_file);
    fclose(svg_file);

    return 0;
}

Wichtige Anmerkungen zu diesem Beispiel:

- Dieser Code fĂŒgt alle x, y-Punkte aus Ihrer result.csv-Datei in einer einzigen M x1,y1 x2,y2 ... xn,yn-Anweisung zusammen. SVG nutzt diese Anweisung, um einen zusammenhĂ€ngenden Pfad zu zeichnen.
- Der Kreis wird durch <circle> definiert und mittels <animateMotion> entlang dieses Pfades animiert. Derzeit wird dabei angenommen, dass #path die ID des Pfades ist, welches in diesem Code-Beispiel fehlt. Sie mĂŒssen also id='path' zu Ihrem <path>-Element hinzufĂŒgen oder die Animation entsprechend Ihrer Implementierung anpassen.

Bitte beachten Sie, dass dieser Code nur als Ausgangspunkt dient und angepasst werden muss, um korrekt mit Ihren spezifischen Daten und Anforderungen zu arbeiten. Insbesondere sollen Sie den Umgang mit negativen \(y\)-Werten, die Skalierung der SVG-viewBox entsprechend der tatsÀchlichen Daten und die korrekte Zuweisung des Pfades an das <mpath>-Element beachten.
Avatar von 4,6 k

Ein anderes Problem?

Stell deine Frage

Willkommen bei der Stacklounge! Stell deine Frage einfach und kostenlos

x
Made by a lovely community