diff --git a/gtk/Makefile.am b/gtk/Makefile.am
index e6f9557..347ceee 100644
--- a/gtk/Makefile.am
+++ b/gtk/Makefile.am
@@ -11,6 +11,7 @@ rtbuf_gtk_SOURCES = \
rtbuf_gtk_output.c \
rtbuf_gtk_resources.c \
rtbuf_gtk_rtbuf.c \
+ rtbuf_gtk_rtbuf_info.c \
rtbuf_input_widget.c \
rtbuf_output_widget.c \
rtbuf_widget.c \
@@ -22,6 +23,7 @@ rtbuf_include_HEADERS = \
queue.h \
rtbuf_gtk.h \
rtbuf_gtk_library.h \
+ rtbuf_gtk_rtbuf_info.h \
rtbuf_input_widget.h \
rtbuf_output_widget.h \
rtbuf_widget.h \
diff --git a/gtk/rtbuf_gtk.c b/gtk/rtbuf_gtk.c
index 3301e3b..89c7ead 100644
--- a/gtk/rtbuf_gtk.c
+++ b/gtk/rtbuf_gtk.c
@@ -65,8 +65,8 @@ void rtbuf_gtk_drag_connection_end (RtbufInputWidget *input_widget)
s_rtbuf *dest = rtbuf_input_widget_get_rtbuf(input_widget);
unsigned int in = rtbuf_input_widget_get_in(input_widget);
unsigned int src_i = src - g_rtbuf;
- rtbuf_bind(src_i, out, dest, in);
dc->input_widget = input_widget;
+ rtbuf_bind(src_i, out, dest, in);
}
else
rtbuf_gtk_connection_remove_one(&modular_connections, dc);
@@ -82,12 +82,12 @@ void rtbuf_gtk_drag_connection_end (RtbufInputWidget *input_widget)
}
}
-RtbufWidget * rtbuf_gtk_modular_layout_new (s_rtbuf *rtbuf,
- const gint x, const gint y)
+RtbufWidget * rtbuf_gtk_modular_layout_new (s_rtbuf *rtbuf)
{
RtbufWidget *widget;
GtkWidget *event_box;
char label[1024];
+ s_rtbuf_gtk_rtbuf_info *info;
assert(rtbuf);
assert(rtbuf >= g_rtbuf && (rtbuf - g_rtbuf) < RTBUF_MAX);
printf("rtbuf-gtk modular layout new\n");
@@ -98,7 +98,9 @@ RtbufWidget * rtbuf_gtk_modular_layout_new (s_rtbuf *rtbuf,
g_next_id++);
rtbuf_var_rtbuf_set(label, rtbuf - g_rtbuf);
widget = rtbuf_widget_new(rtbuf, label);
- gtk_layout_put(modular_layout, GTK_WIDGET(widget), x, y);
+ info = (s_rtbuf_gtk_rtbuf_info*) rtbuf->user_ptr;
+ info->widget = widget;
+ gtk_layout_put(modular_layout, GTK_WIDGET(widget), info->x, info->y);
event_box = rtbuf_widget_get_event_box(widget);
g_signal_connect_swapped(G_OBJECT(event_box), "button-press-event",
G_CALLBACK(rtbuf_gtk_rtbuf_button_press),
@@ -115,18 +117,18 @@ RtbufWidget * rtbuf_gtk_modular_layout_new (s_rtbuf *rtbuf,
return widget;
}
-RtbufWidget * rtbuf_gtk_new (gchar *library, const gint x, const gint y)
+void rtbuf_gtk_new (gchar *library, const gint x, const gint y)
{
int i;
s_rtbuf_lib *rl = 0;
- s_rtbuf *rtb = 0;
+ s_rtbuf_gtk_rtbuf_info *info;
printf("rtbuf-gtk new %s\n", library);
i = rtbuf_lib_find(library);
if (i < 0) {
printf("load %s\n", library);
if (!(rl = rtbuf_lib_load(library))) {
fprintf(stderr, "rtbuf-gtk: load failed: '%s'\n", library);
- return NULL;
+ return;
}
rtbuf_lib_print(rl);
}
@@ -135,13 +137,19 @@ RtbufWidget * rtbuf_gtk_new (gchar *library, const gint x, const gint y)
rl = &g_rtbuf_lib[i];
}
assert(g_rtbuf);
- i = rtbuf_new(rl->proc);
+ info = rtbuf_gtk_rtbuf_info_new();
+ if (!info) {
+ fprintf(stderr, "rtbuf-gtk: rtbuf_gtk_rtbuf_info_new failed.\n"
+ "Please increase RTBUF_MAX.\n");
+ return;
+ }
+ info->x = x;
+ info->y = y;
+ i = rtbuf_new_ptr(rl->proc, info);
if (i < 0) {
fprintf(stderr, "rtbuf-gtk new rtbuf_new failed: %s\n", library);
- return NULL;
+ return;
}
- rtb = &g_rtbuf[i];
- return rtbuf_gtk_modular_layout_new(rtb, x, y);
}
void rtbuf_gtk_library_menu_activate (GtkMenuItem *menuitem,
@@ -485,26 +493,125 @@ int rtbuf_gtk_builder ()
{
GError *error = NULL;
builder = gtk_builder_new ();
- if (gtk_builder_add_from_resource(builder, "/rtbuf/rtbuf_modular.ui", &error) == 0) {
- g_printerr("Error loading resource /rtbuf/rtbuf_modular.ui: %s\n", error->message);
+ if (gtk_builder_add_from_resource(builder, "/rtbuf/rtbuf_modular.ui",
+ &error) == 0) {
+ g_printerr("Error loading resource /rtbuf/rtbuf_modular.ui: %s\n",
+ error->message);
g_clear_error(&error);
return 1;
}
return 0;
}
+void rtbuf_gtk_new_cb (s_rtbuf *rtbuf)
+{
+ printf("rtbuf-gtk new\n");
+ if (!rtbuf->user_ptr) {
+ s_rtbuf_gtk_rtbuf_info *info = rtbuf_gtk_rtbuf_info_new();
+ assert(info);
+ info->x = 0;
+ info->y = 0;
+ rtbuf->user_ptr = info;
+ }
+ rtbuf_gtk_modular_layout_new(rtbuf);
+}
+
+void rtbuf_gtk_delete_cb (s_rtbuf *rtbuf)
+{
+ printf("rtbuf-gtk delete\n");
+ if (rtbuf->user_ptr) {
+ s_rtbuf_gtk_rtbuf_info *info =
+ (s_rtbuf_gtk_rtbuf_info*) rtbuf->user_ptr;
+ gtk_widget_destroy(GTK_WIDGET(info->widget));
+ }
+}
+
+void rtbuf_gtk_bind_cb (s_rtbuf *src, unsigned int out,
+ s_rtbuf *dest, unsigned int in)
+{
+ s_rtbuf_gtk_rtbuf_info *src_info;
+ s_rtbuf_gtk_rtbuf_info *dest_info;
+ RtbufOutputWidget *output_widget;
+ RtbufInputWidget *input_widget;
+ s_rtbuf_gtk_connection *connection;
+ printf("rtbuf-gtk bind\n");
+ assert(src);
+ assert(src->proc);
+ assert(out < src->proc->out_n);
+ assert(dest);
+ assert(dest->proc);
+ assert(in < dest->proc->in_n);
+ src_info = (s_rtbuf_gtk_rtbuf_info*) src->user_ptr;
+ assert(src_info);
+ output_widget = src_info->out[out];
+ assert(output_widget);
+ dest_info = (s_rtbuf_gtk_rtbuf_info*) dest->user_ptr;
+ assert(dest_info);
+ input_widget = dest_info->in[in];
+ assert(input_widget);
+ if (rtbuf_gtk_connection_find(modular_connections,
+ output_widget, input_widget))
+ return;
+ connection = rtbuf_gtk_connection_new();
+ if (!connection) {
+ rtbuf_err("failed to allocate rtbuf_gtk_connection");
+ return;
+ }
+ connection->output_widget = output_widget;
+ connection->input_widget = input_widget;
+ rtbuf_gtk_connection_push(&modular_connections, connection);
+ gtk_widget_queue_draw(GTK_WIDGET(modular_layout));
+}
+
+void rtbuf_gtk_unbind_cb (s_rtbuf *src, unsigned int out,
+ s_rtbuf *dest, unsigned int in)
+{
+ s_rtbuf_gtk_rtbuf_info *src_info;
+ s_rtbuf_gtk_rtbuf_info *dest_info;
+ RtbufOutputWidget *output_widget;
+ RtbufInputWidget *input_widget;
+ s_rtbuf_gtk_connection *connection;
+ printf("rtbuf-gtk unbind\n");
+ assert(src);
+ assert(src->proc);
+ assert(out < src->proc->out_n);
+ assert(dest);
+ assert(dest->proc);
+ assert(in < dest->proc->in_n);
+ src_info = (s_rtbuf_gtk_rtbuf_info*) src->user_ptr;
+ assert(src_info);
+ output_widget = src_info->out[out];
+ assert(output_widget);
+ dest_info = (s_rtbuf_gtk_rtbuf_info*) dest->user_ptr;
+ assert(dest_info);
+ input_widget = dest_info->in[in];
+ assert(input_widget);
+ connection = rtbuf_gtk_connection_find(modular_connections,
+ output_widget, input_widget);
+ printf("connection %p\n", connection);
+ if (connection)
+ rtbuf_gtk_connection_remove_one(&modular_connections,
+ connection);
+ gtk_widget_queue_draw(GTK_WIDGET(modular_layout));
+}
+
int main (int argc, char *argv[])
{
symbols_init();
+ g_rtbuf_new_cb = rtbuf_gtk_new_cb;
+ g_rtbuf_delete_cb = rtbuf_gtk_delete_cb;
+ g_rtbuf_bind_cb = rtbuf_gtk_bind_cb;
+ g_rtbuf_unbind_cb = rtbuf_gtk_unbind_cb;
librtbuf_init();
assert(g_rtbuf);
gtk_init(&argc, &argv);
rtbuf_gtk_connection_init();
+ rtbuf_gtk_rtbuf_info_init();
rtbuf_gtk_library_load();
if (rtbuf_gtk_builder())
return 1;
rtbuf_gtk_modular();
- gtk_main ();
+ gtk_main();
return 0;
}
diff --git a/gtk/rtbuf_gtk.h b/gtk/rtbuf_gtk.h
index d869bc1..bf6a162 100644
--- a/gtk/rtbuf_gtk.h
+++ b/gtk/rtbuf_gtk.h
@@ -18,6 +18,7 @@
#include <gtk/gtk.h>
#include "rtbuf_gtk_connection.h"
+#include "rtbuf_gtk_rtbuf_info.h"
#include "rtbuf_input_widget.h"
#include "rtbuf_output_widget.h"
#include "rtbuf_widget.h"
diff --git a/gtk/rtbuf_gtk_input.c b/gtk/rtbuf_gtk_input.c
index 53621ab..42577d3 100644
--- a/gtk/rtbuf_gtk_input.c
+++ b/gtk/rtbuf_gtk_input.c
@@ -25,21 +25,10 @@ void rtbuf_gtk_input_disconnect (RtbufInputWidget *widget)
{
s_rtbuf *rtbuf;
unsigned int in;
- s_rtbuf_gtk_connection **conn = &modular_connections;
printf("rtbuf-gtk input disconnect\n");
rtbuf = rtbuf_input_widget_get_rtbuf(widget);
in = rtbuf_input_widget_get_in(widget);
rtbuf_in_unbind(rtbuf, in);
- while (*conn) {
- if ((*conn)->input_widget == widget) {
- s_rtbuf_gtk_connection *tmp = *conn;
- *conn = tmp->next;
- rtbuf_gtk_connection_delete(tmp);
- }
- else
- conn = &(*conn)->next;
- }
- gtk_widget_queue_draw(GTK_WIDGET(modular_layout));
}
void rtbuf_gtk_input_menu (RtbufInputWidget *widget, GdkEvent *event)
diff --git a/gtk/rtbuf_gtk_output.c b/gtk/rtbuf_gtk_output.c
index d7c379e..36e8991 100644
--- a/gtk/rtbuf_gtk_output.c
+++ b/gtk/rtbuf_gtk_output.c
@@ -25,21 +25,10 @@ void rtbuf_gtk_output_disconnect (RtbufOutputWidget *widget)
{
s_rtbuf *rtbuf;
unsigned int out;
- s_rtbuf_gtk_connection **conn = &modular_connections;
printf("rtbuf-gtk output disconnect\n");
rtbuf = rtbuf_output_widget_get_rtbuf(widget);
out = rtbuf_output_widget_get_out(widget);
rtbuf_out_unbind(rtbuf, out);
- while (*conn) {
- if ((*conn)->output_widget == widget) {
- s_rtbuf_gtk_connection *tmp = *conn;
- *conn = tmp->next;
- rtbuf_gtk_connection_delete(tmp);
- }
- else
- conn = &(*conn)->next;
- }
- gtk_widget_queue_draw(GTK_WIDGET(modular_layout));
}
void rtbuf_gtk_output_menu (RtbufOutputWidget *widget, GdkEvent *event)
diff --git a/gtk/rtbuf_gtk_rtbuf.c b/gtk/rtbuf_gtk_rtbuf.c
index 36d804a..b998678 100644
--- a/gtk/rtbuf_gtk_rtbuf.c
+++ b/gtk/rtbuf_gtk_rtbuf.c
@@ -30,11 +30,7 @@ void rtbuf_gtk_rtbuf_rename (RtbufWidget *widget)
void rtbuf_gtk_rtbuf_delete (RtbufWidget *widget)
{
s_rtbuf *rtbuf = rtbuf_widget_get_rtbuf(widget);
- printf("rtbuf-gtk rtbuf delete\n");
- rtbuf_gtk_connection_remove_rtbuf(&modular_connections, rtbuf);
- gtk_container_remove(GTK_CONTAINER(modular_layout),
- GTK_WIDGET(widget));
- gtk_widget_queue_draw(GTK_WIDGET(modular_layout));
+ printf("rtbuf> delete %ld\n", rtbuf - g_rtbuf);
rtbuf_delete(rtbuf);
}
diff --git a/gtk/rtbuf_gtk_rtbuf_info.c b/gtk/rtbuf_gtk_rtbuf_info.c
new file mode 100644
index 0000000..f3c9a01
--- /dev/null
+++ b/gtk/rtbuf_gtk_rtbuf_info.c
@@ -0,0 +1,46 @@
+/*
+ * Copyright 2020 Thomas de Grivel <thoxdg@gmail.com>
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <assert.h>
+#include <gtk/gtk.h>
+#include "rtbuf_gtk_rtbuf_info.h"
+
+s_data_type g_rtbuf_gtk_rtbuf_info_type = {
+ sizeof(s_rtbuf_gtk_rtbuf_info) * 8,
+ DATA_TYPE_BITS
+};
+
+s_data_alloc g_rtbuf_gtk_rtbuf_info_alloc;
+
+void rtbuf_gtk_rtbuf_info_init ()
+{
+ data_alloc_init(&g_rtbuf_gtk_rtbuf_info_alloc,
+ &g_rtbuf_gtk_rtbuf_info_type,
+ RTBUF_MAX, 0, 0);
+}
+
+s_rtbuf_gtk_rtbuf_info *rtbuf_gtk_rtbuf_info_new ()
+{
+ s_rtbuf_gtk_rtbuf_info *info =
+ data_new(&g_rtbuf_gtk_rtbuf_info_alloc);
+ return info;
+}
+
+void rtbuf_gtk_rtbuf_info_delete (s_rtbuf_gtk_rtbuf_info *info)
+{
+ assert(info);
+ data_delete(&g_rtbuf_gtk_rtbuf_info_alloc, info);
+}
diff --git a/gtk/rtbuf_gtk_rtbuf_info.h b/gtk/rtbuf_gtk_rtbuf_info.h
new file mode 100644
index 0000000..a27e49b
--- /dev/null
+++ b/gtk/rtbuf_gtk_rtbuf_info.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright 2020 Thomas de Grivel <thoxdg@gmail.com>
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+#ifndef RTBUF_GTK_RTBUF_INFO_H
+#define RTBUF_GTK_RTBUF_INFO_H
+
+#include "rtbuf_widget.h"
+#include "rtbuf_input_widget.h"
+#include "rtbuf_output_widget.h"
+
+typedef struct rtbuf_gtk_rtbuf_info {
+ RtbufWidget *widget;
+ short x;
+ short y;
+ RtbufInputWidget *in[RTBUF_PROC_IN_MAX];
+ RtbufOutputWidget *out[RTBUF_PROC_OUT_MAX];
+} s_rtbuf_gtk_rtbuf_info;
+
+void rtbuf_gtk_rtbuf_info_init ();
+s_rtbuf_gtk_rtbuf_info *rtbuf_gtk_rtbuf_info_new ();
+void rtbuf_gtk_rtbuf_info_delete (s_rtbuf_gtk_rtbuf_info *info);
+
+#endif /* RTBUF_GTK_RTBUF_INFO_H */
diff --git a/gtk/rtbuf_widget.c b/gtk/rtbuf_widget.c
index c950f96..a52aef5 100644
--- a/gtk/rtbuf_widget.c
+++ b/gtk/rtbuf_widget.c
@@ -189,9 +189,11 @@ void rtbuf_widget_set_rtbuf (RtbufWidget *widget, s_rtbuf *rtbuf)
GtkContainer *outputs;
s_rtbuf_proc *proc;
unsigned int i;
+ s_rtbuf_gtk_rtbuf_info *info;
printf("rtbuf_widget set rtbuf\n");
priv->rtbuf = rtbuf;
proc = rtbuf->proc;
+ info = (s_rtbuf_gtk_rtbuf_info*) rtbuf->user_ptr;
inputs = GTK_CONTAINER(priv->inputs);
outputs = GTK_CONTAINER(priv->outputs);
gtk_container_clear(inputs);
@@ -199,12 +201,14 @@ void rtbuf_widget_set_rtbuf (RtbufWidget *widget, s_rtbuf *rtbuf)
RtbufInputWidget *input_widget =
rtbuf_input_widget_new(priv->rtbuf, i);
gtk_container_add(inputs, GTK_WIDGET(input_widget));
+ info->in[i] = input_widget;
}
gtk_container_clear(outputs);
for (i = 0; i < proc->out_n; i++) {
RtbufOutputWidget *output_widget =
rtbuf_output_widget_new(priv->rtbuf, i);
gtk_container_add(outputs, GTK_WIDGET(output_widget));
+ info->out[i] = output_widget;
}
}