From bee5e2fd263d81b7dc8180e831cbc96500cece1f Mon Sep 17 00:00:00 2001 From: Thomas White Date: Sun, 28 Sep 2014 13:43:34 +0200 Subject: SCEditor, part II --- src/colloquium.c | 134 +++++++++++++++++++++++++++++++++++++++++++++---- src/narrative_window.c | 114 +++++++++++++++++++++++++++++++++++++++++ src/notes.c | 1 + src/presentation.c | 1 + src/sc_editor.c | 48 ++++++++++-------- src/slide_window.c | 2 + 6 files changed, 269 insertions(+), 31 deletions(-) diff --git a/src/colloquium.c b/src/colloquium.c index ce23be5..51b60c9 100644 --- a/src/colloquium.c +++ b/src/colloquium.c @@ -32,12 +32,79 @@ #include "narrative_window.h" +typedef struct +{ + GtkApplication parent_instance; +} Colloquium; + + +typedef GtkApplicationClass ColloquiumClass; + + +G_DEFINE_TYPE(Colloquium, colloquium, GTK_TYPE_APPLICATION) + + static void colloquium_activate(GApplication *app) { printf("activate!\n"); } +static void new_sig(GSimpleAction *action, GVariant *parameter, gpointer vp) +{ + GApplication *app = vp; + g_application_activate(app); +} + + +static void about_sig(GSimpleAction *action, GVariant *parameter, gpointer vp) +{ + GtkWidget *window; + + const gchar *authors[] = { + "Thomas White ", + NULL + }; + + window = gtk_about_dialog_new(); + + gtk_about_dialog_set_program_name(GTK_ABOUT_DIALOG(window), + "Colloquium"); + gtk_about_dialog_set_version(GTK_ABOUT_DIALOG(window), + PACKAGE_VERSION); + gtk_about_dialog_set_copyright(GTK_ABOUT_DIALOG(window), + "© 2013 Thomas White "); + gtk_about_dialog_set_comments(GTK_ABOUT_DIALOG(window), + "A tiny presentation program"); + gtk_about_dialog_set_license(GTK_ABOUT_DIALOG(window), + "© 2013 Thomas White \n"); + gtk_about_dialog_set_website(GTK_ABOUT_DIALOG(window), + "http://www.bitwiz.org.uk/"); + gtk_about_dialog_set_authors(GTK_ABOUT_DIALOG(window), authors); + + g_signal_connect(window, "response", G_CALLBACK(gtk_widget_destroy), + NULL); + + gtk_widget_show_all(window); +} + + +static void quit_sig(GSimpleAction *action, GVariant *parameter, gpointer vp) +{ + GApplication *app = vp; + g_application_quit(app); +} + + +GActionEntry app_entries[] = { + + { "new", new_sig, NULL, NULL, NULL }, + { "about", about_sig, NULL, NULL, NULL }, + { "quit", quit_sig, NULL, NULL, NULL }, + +}; + + static void colloquium_open(GApplication *app, GFile **files, gint n_files, const gchar *hint) { @@ -46,7 +113,6 @@ static void colloquium_open(GApplication *app, GFile **files, gint n_files, for ( i = 0; istartup(app); + + g_action_map_add_action_entries(G_ACTION_MAP(app), app_entries, + G_N_ELEMENTS(app_entries), app); + + builder = gtk_builder_new(); + gtk_builder_add_from_string(builder, + "" + + " " + "
" + " " + " _New" + " app.new" + " <Primary>n" + " " + "
" + "
" + " " + " _About" + " app.about" + " " + "
" + "
" + " " + " _Quit" + " app.quit" + " <Primary>q" + " " + "
" + "
" + + " " + " " + " File" + "
" + " " + " _Save" + " file.save" + " <Primary>s" + " " + " " + " Export PDF" + " file.exportpdf" + " " + "
" + "
" + "
" + + "
", -1, NULL); + + gtk_application_set_app_menu(GTK_APPLICATION(app), + G_MENU_MODEL(gtk_builder_get_object(builder, "app-menu"))); + gtk_application_set_menubar(GTK_APPLICATION(app), + G_MENU_MODEL(gtk_builder_get_object(builder, "menubar"))); + + g_object_unref(builder); } diff --git a/src/narrative_window.c b/src/narrative_window.c index 7fd51a3..f529f29 100644 --- a/src/narrative_window.c +++ b/src/narrative_window.c @@ -36,12 +36,98 @@ struct _narrative_window { GtkWidget *window; + GtkWidget *drawingarea; /* FIXME: Should be an SCEditor */ + GApplication *app; + struct presentation *p; }; +static void save_sig(GSimpleAction *action, GVariant *parameter, gpointer vp) +{ +} + + +static void exportpdf_sig(GSimpleAction *action, GVariant *parameter, + gpointer vp) +{ +} + + +GActionEntry nw_entries[] = { + + { "save", save_sig, NULL, NULL, NULL, }, + { "exportpdf", exportpdf_sig, NULL, NULL, NULL }, + +#if 0 + { "EditAction", NULL, "_Edit", NULL, NULL, NULL }, + { "SorterAction", NULL, "_Open Slide Sorter...", + NULL, NULL, G_CALLBACK(open_slidesorter_sig) }, + { "UndoAction", GTK_STOCK_UNDO, "_Undo", + NULL, NULL, NULL }, + { "RedoAction", GTK_STOCK_REDO, "_Redo", + NULL, NULL, NULL }, + { "CutAction", GTK_STOCK_CUT, "Cut", + NULL, NULL, NULL }, + { "CopyAction", GTK_STOCK_COPY, "Copy", + NULL, NULL, NULL }, + { "PasteAction", GTK_STOCK_PASTE, "Paste", + NULL, NULL, NULL }, + { "DeleteFrameAction", GTK_STOCK_DELETE, "Delete Frame", + NULL, NULL, G_CALLBACK(delete_frame_sig) }, +// { "EditStyleAction", NULL, "Stylesheet...", +// NULL, NULL, G_CALLBACK(open_stylesheet_sig) }, + + { "InsertAction", NULL, "_Insert", NULL, NULL, NULL }, + { "NewSlideAction", GTK_STOCK_ADD, "_New Slide", + NULL, NULL, G_CALLBACK(add_slide_sig) }, + + { "ToolsAction", NULL, "_Tools", NULL, NULL, NULL }, + { "TSlideshowAction", GTK_STOCK_FULLSCREEN, "_Start Slideshow", + "F5", NULL, G_CALLBACK(start_slideshow_sig) }, + { "NotesAction", NULL, "_Open slide notes", + "F8", NULL, G_CALLBACK(open_notes_sig) }, + { "ClockAction", NULL, "_Open presentation clock", + "F9", NULL, G_CALLBACK(open_clock_sig) }, + { "PrefsAction", GTK_STOCK_PREFERENCES, "_Preferences", + NULL, NULL, NULL }, + + { "HelpAction", NULL, "_Help", NULL, NULL, NULL }, + { "AboutAction", GTK_STOCK_ABOUT, "_About...", + NULL, NULL, G_CALLBACK(about_sig) }, + + { "SlideshowAction", GTK_STOCK_FULLSCREEN, "Start Presentation", + NULL, NULL, G_CALLBACK(start_slideshow_sig) }, + { "AddSlideAction", GTK_STOCK_ADD, "Add Slide", + NULL, NULL, G_CALLBACK(add_slide_sig) }, + { "ButtonFirstSlideAction", GTK_STOCK_GOTO_FIRST, "First Slide", + NULL, NULL, G_CALLBACK(first_slide_sig) }, + { "ButtonPrevSlideAction", GTK_STOCK_GO_BACK, "Previous Slide", + NULL, NULL, G_CALLBACK(prev_slide_sig) }, + { "ButtonNextSlideAction", GTK_STOCK_GO_FORWARD, "Next Slide", + NULL, NULL, G_CALLBACK(next_slide_sig) }, + { "ButtonLastSlideAction", GTK_STOCK_GOTO_LAST, "Last Slide", + NULL, NULL, G_CALLBACK(last_slide_sig) }, +#endif + +}; + + +static gboolean button_press_sig(GtkWidget *da, GdkEventButton *event, + NarrativeWindow *nw) +{ + if ( event->type == GDK_2BUTTON_PRESS ) { + nw->p->slidewindow = slide_window_open(nw->p, nw->app); + } + + return 0; +} + + NarrativeWindow *narrative_window_new(struct presentation *p, GApplication *app) { NarrativeWindow *nw; + GtkWidget *vbox; + GtkWidget *scroll; if ( p->narrative_window != NULL ) { fprintf(stderr, "Narrative window is already open!\n"); @@ -51,11 +137,39 @@ NarrativeWindow *narrative_window_new(struct presentation *p, GApplication *app) nw = calloc(1, sizeof(NarrativeWindow)); if ( nw == NULL ) return NULL; + nw->app = app; + nw->p = p; + nw->window = gtk_application_window_new(GTK_APPLICATION(app)); p->narrative_window = nw; + g_action_map_add_action_entries(G_ACTION_MAP(nw->window), nw_entries, + G_N_ELEMENTS(nw_entries), nw->window); + // update_titlebar(nw); + vbox = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0); + gtk_container_add(GTK_CONTAINER(nw->window), vbox); + + nw->drawingarea = gtk_drawing_area_new(); + scroll = gtk_scrolled_window_new(NULL, NULL); + gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scroll), + GTK_POLICY_AUTOMATIC, + GTK_POLICY_AUTOMATIC); + gtk_scrolled_window_add_with_viewport(GTK_SCROLLED_WINDOW(scroll), + GTK_WIDGET(nw->drawingarea)); + + g_signal_connect(G_OBJECT(nw->drawingarea), "button-press-event", + G_CALLBACK(button_press_sig), nw); + gtk_widget_set_can_focus(GTK_WIDGET(nw->drawingarea), TRUE); + gtk_widget_add_events(GTK_WIDGET(nw->drawingarea), + GDK_POINTER_MOTION_HINT_MASK + | GDK_BUTTON1_MOTION_MASK + | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK + | GDK_KEY_PRESS_MASK | GDK_KEY_RELEASE_MASK); + + gtk_box_pack_start(GTK_BOX(vbox), scroll, TRUE, TRUE, 0); + gtk_widget_show_all(nw->window); return nw; diff --git a/src/notes.c b/src/notes.c index 2210f55..5c884df 100644 --- a/src/notes.c +++ b/src/notes.c @@ -94,6 +94,7 @@ void grab_current_notes(struct presentation *p) void notify_notes_slide_changed(struct presentation *p, struct slide *np) { + if ( p->notes == NULL ) return; grab_current_notes(p); p->notes->slide = np; update_notes(p); diff --git a/src/presentation.c b/src/presentation.c index 8cd39ce..e565edf 100644 --- a/src/presentation.c +++ b/src/presentation.c @@ -234,6 +234,7 @@ struct presentation *new_presentation() new->num_slides = 0; new->slides = NULL; + add_slide(new, 0); new->completely_empty = 1; new->stylesheet = NULL; diff --git a/src/sc_editor.c b/src/sc_editor.c index 3a398c5..780c58d 100644 --- a/src/sc_editor.c +++ b/src/sc_editor.c @@ -398,24 +398,26 @@ static void draw_overlay(cairo_t *cr, SCEditor *e) { double x, y, w, h; - draw_editing_box(cr, e->selection); - x = e->selection->x; - y = e->selection->y; - w = e->selection->w; - h = e->selection->h; + if ( e->selection != NULL ) { - /* Draw resize handles */ - /* FIXME: Not if this frame can't be resized */ - draw_resize_handle(cr, x, y+h-20.0); - draw_resize_handle(cr, x+w-20.0, y); - draw_resize_handle(cr, x, y); - draw_resize_handle(cr, x+w-20.0, y+h-20.0); + draw_editing_box(cr, e->selection); + + x = e->selection->x; + y = e->selection->y; + w = e->selection->w; + h = e->selection->h; + + /* Draw resize handles */ + /* FIXME: Not if this frame can't be resized */ + draw_resize_handle(cr, x, y+h-20.0); + draw_resize_handle(cr, x+w-20.0, y); + draw_resize_handle(cr, x, y); + draw_resize_handle(cr, x+w-20.0, y+h-20.0); - /* If only one frame is selected, draw the caret */ - if ( e->selection != NULL ) { draw_caret(cr, e->cursor_frame, e->cursor_line, e->cursor_box, e->cursor_pos); + } if ( (e->drag_status == DRAG_STATUS_DRAGGING) @@ -473,9 +475,8 @@ static gboolean draw_sig(GtkWidget *da, cairo_t *cr, e->border_offs_x = xoff; e->border_offs_y = yoff; /* Draw the slide from the cache */ - if ( e->cur_slide->rendered_edit != NULL ) { - cairo_set_source_surface(cr, e->cur_slide->rendered_edit, - xoff, yoff); + if ( e->surface != NULL ) { + cairo_set_source_surface(cr, e->surface, xoff, yoff); cairo_paint(cr); } else { fprintf(stderr, "Current slide not rendered yet!\n"); @@ -1402,7 +1403,10 @@ SCEditor *sc_editor_new(struct presentation *p) sceditor = calloc(1, sizeof(SCEditor)); if ( sceditor == NULL ) return NULL; + sceditor->p = p; sceditor->drawingarea = gtk_drawing_area_new(); + sceditor->cur_slide = p->slides[0]; /* FIXME */ + sceditor->surface = NULL; gtk_widget_set_size_request(GTK_WIDGET(sceditor->drawingarea), p->slide_width + 20, @@ -1426,13 +1430,13 @@ SCEditor *sc_editor_new(struct presentation *p) gtk_drag_dest_set(sceditor->drawingarea, 0, targets, 1, GDK_ACTION_PRIVATE); g_signal_connect(sceditor->drawingarea, "drag-data-received", - G_CALLBACK(dnd_receive), p); + G_CALLBACK(dnd_receive), sceditor); g_signal_connect(sceditor->drawingarea, "drag-motion", - G_CALLBACK(dnd_motion), p); + G_CALLBACK(dnd_motion), sceditor); g_signal_connect(sceditor->drawingarea, "drag-drop", - G_CALLBACK(dnd_drop), p); + G_CALLBACK(dnd_drop), sceditor); g_signal_connect(sceditor->drawingarea, "drag-leave", - G_CALLBACK(dnd_leave), p); + G_CALLBACK(dnd_leave), sceditor); gtk_widget_set_can_focus(GTK_WIDGET(sceditor->drawingarea), TRUE); gtk_widget_add_events(GTK_WIDGET(sceditor->drawingarea), @@ -1442,11 +1446,11 @@ SCEditor *sc_editor_new(struct presentation *p) | GDK_KEY_PRESS_MASK | GDK_KEY_RELEASE_MASK); g_signal_connect(G_OBJECT(sceditor->drawingarea), "draw", - G_CALLBACK(draw_sig), p); + G_CALLBACK(draw_sig), sceditor); gtk_widget_grab_focus(GTK_WIDGET(sceditor->drawingarea)); gtk_widget_show(sceditor->drawingarea); - return 0; + return sceditor; } diff --git a/src/slide_window.c b/src/slide_window.c index bd64538..9163c69 100644 --- a/src/slide_window.c +++ b/src/slide_window.c @@ -591,6 +591,8 @@ SlideWindow *slide_window_open(struct presentation *p, GApplication *app) window = gtk_application_window_new(GTK_APPLICATION(app)); sw->window = window; + sw->p = p; + sw->cur_slide = p->slides[0]; update_titlebar(p); -- cgit v1.2.3