+void history_rememberSweep(history_t* past, U16 frame, float x, float y, float r, int clockwise, int short_arc, interpolation_t* inter)
+{
+ float lastX, lastY, dX, dY;
+ U16 lastFrame;
+
+ past->lastFrame = frame;
+ state_t* change = dictionary_lookup(past->states, "x");
+ if (change) //should always be true
+ {
+ while (change->next)
+ change = change->next;
+ lastFrame = change->frame;
+ lastX = change->value;
+ change = dictionary_lookup(past->states, "y");
+ if (change) //should always be true
+ {
+ while (change->next)
+ change = change->next;
+ lastY = change->value;
+ dX = x - lastX;
+ dY = y - lastY;
+ if (dX == 0 && dY == 0)
+ syntaxerror("sweep not possible: startpoint and endpoint must not be equal");
+ if ((dX) * (dX) + (dY) * (dY) > 4 * r * r)
+ syntaxerror("sweep not possible: radius is to small");
+ if (change->frame > lastFrame)
+ {
+ lastFrame = change->frame;
+ history_remember(past, "x", lastFrame, CF_JUMP, lastX, 0);
+ }
+ else
+ if (change->frame < lastFrame)
+ history_remember(past, "y", lastFrame, CF_JUMP, lastY, 0);
+ float c1X, c1Y, c2X, c2Y;
+ if (dX == 0) //vertical
+ {
+ c1Y = c2Y = (lastY + y) / 2;
+ c1X = x + sqrt(r * r - (c1Y - y) * (c1Y - y));
+ c2X = 2 * x -c1X;
+ }
+ else
+ if (dY == 0) //horizontal
+ {
+ c1X = c2X = (lastX + x) / 2;
+ c1Y = y +sqrt(r * r - (c1X - x) * (c1X - x));
+ c2Y = 2 * y -c1Y;
+ }
+ else
+ {
+ c1X = sqrt((r * r - (dX * dX + dY * dY) / 4) / (1 + dX * dX / dY / dY));
+ c2X = -c1X;
+ c1Y = -dX / dY * c1X;
+ c2Y = -c1Y;
+ c1X += (x + lastX) / 2;
+ c2X += (x + lastX) / 2;
+ c1Y += (y + lastY) / 2;
+ c2Y += (y + lastY) / 2;
+ }
+ float angle1, angle2, delta_angle, centerX, centerY;
+ angle1 = getAngle(lastX - c1X, lastY - c1Y);
+ angle2 = getAngle(x - c1X, y - c1Y);
+ delta_angle = getDeltaAngle(angle1, angle2, clockwise);
+ if ((short_arc && fabs(delta_angle) <= M_PI) || (! short_arc && fabs(delta_angle) >= M_PI))
+ {
+ centerX = c1X;
+ centerY = c1Y;
+ }
+ else
+ {
+ angle1 = getAngle(lastX - c2X, lastY - c2Y);
+ angle2 = getAngle(x - c2X, y - c2Y);
+ delta_angle = getDeltaAngle(angle1, angle2, clockwise);
+ centerX = c2X;
+ centerY = c2Y;
+ }
+ change = dictionary_lookup(past->states, "x");
+ state_t* nextX = state_new(frame, CF_SWEEP, x, inter);
+ nextX->arc.r = r;
+ nextX->arc.angle = angle1;
+ nextX->arc.delta_angle = delta_angle;
+ nextX->arc.cX = centerX;
+ nextX->arc.cY = centerY;
+ nextX->arc.X = 1;
+ state_append(change, nextX);
+ change = dictionary_lookup(past->states, "y");
+ state_t* nextY = state_new(frame, CF_SWEEP, y, inter);
+ nextY->arc.r = r;
+ nextY->arc.angle = angle1;
+ nextY->arc.delta_angle = delta_angle;
+ nextY->arc.cX = centerX;
+ nextY->arc.cY = centerY;
+ nextY->arc.X = 0;
+ state_append(change, nextY);
+ }
+ else
+ syntaxerror("Internal error: changing parameter y in sweep, which is unknown for the instance.");
+ }
+ else
+ syntaxerror("Internal error: changing parameter x in sweep, which is unknown for the instance.");
+}
+