diff --git a/c/gtk3/gravity-control/gravitycontrol.c b/c/gtk3/gravity-control/gravitycontrol.c
new file mode 100644
index 0000000..fd3e783
--- /dev/null
+++ b/c/gtk3/gravity-control/gravitycontrol.c
@@ -0,0 +1,99 @@
+#include <math.h>
+#include <stdlib.h>
+#include <time.h>
+#include <gtk/gtk.h>
+
+
+const double pi = 3.141592653589793;
+
+const guint interval_ms = 5;
+const guint interval2_ms = 50;
+const double G = 1000000;
+const double radius = 30;
+
+int width = 700;
+int height = 500;
+
+double mx = 0;
+double my = 0;
+double x = 200;
+double y = 200;
+double vx = 0;
+double vy = 0;
+
+GtkWidget *window;
+
+
+gboolean motion(GtkWidget *widget, GdkEventMotion *event, gpointer data) {
+  mx = event->x;
+  my = event->y;
+  return TRUE;
+}
+
+gboolean timeout(gpointer data) {
+  double t = interval_ms/1000.0;
+
+  double dx = mx - x;
+  double dy = my - y;
+  double d = sqrt(dx*dx + dy*dy);
+
+  double ax = G*dx/(d*d*d);
+  double ay = G*dy/(d*d*d);
+  if (d < 10.0) ax = ay = 0.0;
+
+  vx += ax*t;
+  vy += ay*t;
+
+  x += vx*t;
+  y += vy*t;
+  
+  if (x < radius)
+    { x = radius; vx = fabs(vx); }
+  if (x > width - radius)
+    { x = width - radius; vx = -fabs(vx); }
+  if (y < radius)
+    { y = radius; vy = fabs(vy); }
+  if (y > height - radius)
+    { y = height - radius; vy = -fabs(vy); }
+  
+  return TRUE;
+}
+
+gboolean timeout2(gpointer data) {
+  gtk_widget_queue_draw(window);
+  return TRUE;
+}
+
+gboolean draw(GtkWidget *widget, cairo_t *cr, gpointer data) {
+  cairo_set_source_rgba(cr, 0.9, 0.9, 0.9, 1);
+  cairo_paint(cr);
+
+  cairo_set_source_rgba(cr, 0, 0, 0, 1);
+  cairo_set_line_width(cr, 1.0);
+  cairo_arc(cr, x, y, radius, 0, 2*pi);
+  cairo_stroke(cr);
+
+  return TRUE;
+}
+
+void activate(GtkApplication* app, gpointer data) {
+  window = gtk_application_window_new (app);
+  g_signal_connect(window, "draw", G_CALLBACK(draw), NULL);
+  g_signal_connect(window, "motion-notify-event", G_CALLBACK(motion), NULL);
+  gtk_widget_add_events(window, GDK_POINTER_MOTION_MASK);
+  gtk_window_set_default_size(GTK_WINDOW(window), width, height);
+  gtk_widget_show_all(window);
+
+  g_timeout_add(interval_ms, timeout, NULL);
+  g_timeout_add(interval2_ms, timeout2, NULL);
+}
+
+int main(int argc, char **argv) {
+  GtkApplication *application = gtk_application_new(NULL, 0);
+  g_signal_connect(application, "activate", G_CALLBACK(activate), NULL);
+  int status = g_application_run(G_APPLICATION(application), argc, argv);
+  g_object_unref(application);
+  return status;
+}
+
+