|
Packit |
0ec9dd |
/* viewer-main.c: Main routine for viewers
|
|
Packit |
0ec9dd |
*
|
|
Packit |
0ec9dd |
* Copyright (C) 1999,2004,2005 Red Hat, Inc.
|
|
Packit |
0ec9dd |
* Copyright (C) 2001 Sun Microsystems
|
|
Packit |
0ec9dd |
* Copyright (C) 2006 Behdad Esfahbod
|
|
Packit |
0ec9dd |
*
|
|
Packit |
0ec9dd |
* This library is free software; you can redistribute it and/or
|
|
Packit |
0ec9dd |
* modify it under the terms of the GNU Library General Public
|
|
Packit |
0ec9dd |
* License as published by the Free Software Foundation; either
|
|
Packit |
0ec9dd |
* version 2 of the License, or (at your option) any later version.
|
|
Packit |
0ec9dd |
*
|
|
Packit |
0ec9dd |
* This library is distributed in the hope that it will be useful,
|
|
Packit |
0ec9dd |
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
Packit |
0ec9dd |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
Packit |
0ec9dd |
* Library General Public License for more details.
|
|
Packit |
0ec9dd |
*
|
|
Packit |
0ec9dd |
* You should have received a copy of the GNU Library General Public
|
|
Packit |
0ec9dd |
* License along with this library; if not, write to the
|
|
Packit |
0ec9dd |
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
|
Packit |
0ec9dd |
* Boston, MA 02111-1307, USA.
|
|
Packit |
0ec9dd |
*/
|
|
Packit |
0ec9dd |
#include "config.h"
|
|
Packit |
0ec9dd |
#include <errno.h>
|
|
Packit |
0ec9dd |
#include <stdlib.h>
|
|
Packit |
0ec9dd |
#include <stdio.h>
|
|
Packit |
0ec9dd |
#include <string.h>
|
|
Packit |
0ec9dd |
#include <locale.h>
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
#include <glib.h>
|
|
Packit |
0ec9dd |
#include <glib/gstdio.h>
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
#ifdef G_OS_UNIX
|
|
Packit |
0ec9dd |
#include <sys/wait.h>
|
|
Packit |
0ec9dd |
#endif
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
#include "viewer.h"
|
|
Packit |
0ec9dd |
#include "viewer-render.h"
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
int
|
|
Packit |
0ec9dd |
main (int argc,
|
|
Packit |
0ec9dd |
char **argv)
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
const PangoViewer *view;
|
|
Packit |
0ec9dd |
gpointer instance;
|
|
Packit |
0ec9dd |
PangoContext *context;
|
|
Packit |
0ec9dd |
int run;
|
|
Packit |
0ec9dd |
int width, height;
|
|
Packit |
0ec9dd |
gpointer surface;
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
#if !GLIB_CHECK_VERSION (2, 35, 3)
|
|
Packit |
0ec9dd |
g_type_init();
|
|
Packit |
0ec9dd |
#endif
|
|
Packit |
0ec9dd |
g_set_prgname ("pango-view");
|
|
Packit |
0ec9dd |
setlocale (LC_ALL, "");
|
|
Packit |
0ec9dd |
parse_options (argc, argv);
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
view = opt_viewer;
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
g_assert (view->id);
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
instance = view->create (view);
|
|
Packit |
0ec9dd |
context = view->get_context (instance);
|
|
Packit |
0ec9dd |
width = height = 1;
|
|
Packit |
0ec9dd |
surface = view->create_surface (instance, width, height);
|
|
Packit |
0ec9dd |
view->render (instance, surface, context, &width, &height, NULL);
|
|
Packit |
0ec9dd |
view->destroy_surface (instance, surface);
|
|
Packit |
0ec9dd |
surface = view->create_surface (instance, width, height);
|
|
Packit |
0ec9dd |
for (run = 0; run < MAX(1,opt_runs); run++)
|
|
Packit |
0ec9dd |
view->render (instance, surface, context, &width, &height, NULL);
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
if (opt_output)
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
if (!view->write)
|
|
Packit |
0ec9dd |
fail ("%s viewer backend does not support writing", view->name);
|
|
Packit |
0ec9dd |
else
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
FILE *stream;
|
|
Packit |
0ec9dd |
GPid pid = 0;
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
if (view->write_suffix && g_str_has_suffix (opt_output, view->write_suffix))
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
stream = g_fopen (opt_output, "wb");
|
|
Packit |
0ec9dd |
if (!stream)
|
|
Packit |
0ec9dd |
fail ("Cannot open output file %s: %s\n",
|
|
Packit |
0ec9dd |
opt_output, g_strerror (errno));
|
|
Packit |
0ec9dd |
}
|
|
Packit |
0ec9dd |
else
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
int fd;
|
|
Packit |
0ec9dd |
const gchar *convert_argv[4] = {"convert", "-", "%s"};
|
|
Packit |
0ec9dd |
GError *error;
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
convert_argv[2] = opt_output;
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
if (!g_spawn_async_with_pipes (NULL, (gchar **)(void*)convert_argv, NULL,
|
|
Packit |
0ec9dd |
G_SPAWN_DO_NOT_REAP_CHILD |
|
|
Packit |
0ec9dd |
G_SPAWN_SEARCH_PATH |
|
|
Packit |
0ec9dd |
G_SPAWN_STDOUT_TO_DEV_NULL |
|
|
Packit |
0ec9dd |
G_SPAWN_STDERR_TO_DEV_NULL,
|
|
Packit |
0ec9dd |
NULL, NULL, &pid, &fd, NULL, NULL, &error))
|
|
Packit |
0ec9dd |
fail ("When running ImageMagick 'convert' command: %s\n", error->message);
|
|
Packit |
0ec9dd |
stream = fdopen (fd, "wb");
|
|
Packit |
0ec9dd |
}
|
|
Packit |
0ec9dd |
view->write (instance, surface, stream, width, height);
|
|
Packit |
0ec9dd |
fclose (stream);
|
|
Packit |
0ec9dd |
#ifdef G_OS_UNIX
|
|
Packit |
0ec9dd |
if (pid)
|
|
Packit |
0ec9dd |
waitpid (pid, NULL, 0);
|
|
Packit |
0ec9dd |
#endif
|
|
Packit |
0ec9dd |
}
|
|
Packit |
0ec9dd |
}
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
if (opt_display)
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
char *title;
|
|
Packit |
0ec9dd |
title = get_options_string ();
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
if (view->display)
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
gpointer window = NULL;
|
|
Packit |
0ec9dd |
gpointer state = NULL;
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
if (view->create_window)
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
window = view->create_window (instance, title, width, height);
|
|
Packit |
0ec9dd |
if (!window)
|
|
Packit |
0ec9dd |
goto no_display;
|
|
Packit |
0ec9dd |
}
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
opt_display = FALSE;
|
|
Packit |
0ec9dd |
while (1)
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
state = view->display (instance, surface, window, width, height, state);
|
|
Packit |
0ec9dd |
if (state == GINT_TO_POINTER (-1))
|
|
Packit |
0ec9dd |
break;
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
view->render (instance, surface, context, &width, &height, state);
|
|
Packit |
0ec9dd |
}
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
if (view->destroy_window)
|
|
Packit |
0ec9dd |
view->destroy_window (instance, window);
|
|
Packit |
0ec9dd |
}
|
|
Packit |
0ec9dd |
no_display:
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
/* If failed to display natively, call ImageMagick */
|
|
Packit |
0ec9dd |
if (opt_display)
|
|
Packit |
0ec9dd |
{
|
|
Packit |
0ec9dd |
int fd;
|
|
Packit |
0ec9dd |
FILE *stream;
|
|
Packit |
0ec9dd |
const gchar *display_argv[5] = {"display", "-title", "%s", "-"};
|
|
Packit |
0ec9dd |
GError *error = NULL;
|
|
Packit |
0ec9dd |
GPid pid;
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
if (!view->write)
|
|
Packit |
0ec9dd |
fail ("%s viewer backend does not support displaying or writing", view->name);
|
|
Packit |
0ec9dd |
display_argv[2] = title;
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
if (!g_spawn_async_with_pipes (NULL, (gchar **)(void*)display_argv, NULL,
|
|
Packit |
0ec9dd |
G_SPAWN_DO_NOT_REAP_CHILD |
|
|
Packit |
0ec9dd |
G_SPAWN_SEARCH_PATH |
|
|
Packit |
0ec9dd |
G_SPAWN_STDOUT_TO_DEV_NULL |
|
|
Packit |
0ec9dd |
G_SPAWN_STDERR_TO_DEV_NULL,
|
|
Packit |
0ec9dd |
NULL, NULL, &pid, &fd, NULL, NULL, &error))
|
|
Packit |
0ec9dd |
fail ("When running ImageMagick 'display' command: %s\n", error->message);
|
|
Packit |
0ec9dd |
stream = fdopen (fd, "wb");
|
|
Packit |
0ec9dd |
view->write (instance, surface, stream, width, height);
|
|
Packit |
0ec9dd |
fclose (stream);
|
|
Packit |
0ec9dd |
#ifdef G_OS_UNIX
|
|
Packit |
0ec9dd |
waitpid (pid, NULL, 0);
|
|
Packit |
0ec9dd |
#endif
|
|
Packit |
0ec9dd |
g_spawn_close_pid (pid);
|
|
Packit |
0ec9dd |
}
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
g_free (title);
|
|
Packit |
0ec9dd |
}
|
|
Packit |
0ec9dd |
|
|
Packit |
0ec9dd |
view->destroy_surface (instance, surface);
|
|
Packit |
0ec9dd |
g_object_unref (context);
|
|
Packit |
0ec9dd |
view->destroy (instance);
|
|
Packit |
0ec9dd |
finalize ();
|
|
Packit |
0ec9dd |
return 0;
|
|
Packit |
0ec9dd |
}
|