コード例 #1
0
ファイル: file-save.c プロジェクト: AnonPower/picman
GimpPDBStatusType
file_save (Gimp                *gimp,
           GimpImage           *image,
           GimpProgress        *progress,
           const gchar         *uri,
           GimpPlugInProcedure *file_proc,
           GimpRunMode          run_mode,
           gboolean             change_saved_state,
           gboolean             export_backward,
           gboolean             export_forward,
           GError             **error)
{
  GimpDrawable      *drawable;
  GimpValueArray    *return_vals;
  GimpPDBStatusType  status;
  gchar             *filename;
  gint32             image_ID;
  gint32             drawable_ID;

  g_return_val_if_fail (GIMP_IS_GIMP (gimp), GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (GIMP_IS_IMAGE (image), GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (progress == NULL || GIMP_IS_PROGRESS (progress),
                        GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (uri != NULL, GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (GIMP_IS_PLUG_IN_PROCEDURE (file_proc),
                        GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail ((export_backward && export_forward) == FALSE,
                        GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (error == NULL || *error == NULL,
                        GIMP_PDB_CALLING_ERROR);

  drawable = gimp_image_get_active_drawable (image);

  if (! drawable)
    return GIMP_PDB_EXECUTION_ERROR;

  filename = file_utils_filename_from_uri (uri);

  if (filename)
    {
      /* check if we are saving to a file */
      if (g_file_test (filename, G_FILE_TEST_EXISTS))
        {
          if (! g_file_test (filename, G_FILE_TEST_IS_REGULAR))
            {
              g_set_error_literal (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,
				   _("Not a regular file"));
              status = GIMP_PDB_EXECUTION_ERROR;
              goto out;
            }

          if (g_access (filename, W_OK) != 0)
            {
              g_set_error_literal (error, G_FILE_ERROR, G_FILE_ERROR_ACCES,
                                   g_strerror (errno));
              status = GIMP_PDB_EXECUTION_ERROR;
              goto out;
            }
        }

      if (file_proc->handles_uri)
        {
          g_free (filename);
          filename = g_strdup (uri);
        }
    }
  else
    {
      filename = g_strdup (uri);
    }

  /* ref the image, so it can't get deleted during save */
  g_object_ref (image);

  image_ID    = gimp_image_get_ID (image);
  drawable_ID = gimp_item_get_ID (GIMP_ITEM (drawable));

  return_vals =
    gimp_pdb_execute_procedure_by_name (image->gimp->pdb,
                                        gimp_get_user_context (gimp),
                                        progress, error,
                                        gimp_object_get_name (file_proc),
                                        GIMP_TYPE_INT32,       run_mode,
                                        GIMP_TYPE_IMAGE_ID,    image_ID,
                                        GIMP_TYPE_DRAWABLE_ID, drawable_ID,
                                        G_TYPE_STRING,         filename,
                                        G_TYPE_STRING,         uri,
                                        G_TYPE_NONE);

  status = g_value_get_enum (gimp_value_array_index (return_vals, 0));

  gimp_value_array_unref (return_vals);

  if (status == GIMP_PDB_SUCCESS)
    {
      GimpDocumentList *documents;
      GimpImagefile    *imagefile;

      if (change_saved_state)
        {
          gimp_image_set_uri (image, uri);
          gimp_image_set_save_proc (image, file_proc);

          /* Forget the import source when we save. We interpret a
           * save as that the user is not interested in being able
           * to quickly export back to the original any longer
           */
          gimp_image_set_imported_uri (image, NULL);

          gimp_image_clean_all (image);
        }
      else if (export_backward)
        {
          /* We exported the image back to its imported source,
           * change nothing about export/import flags, only set
           * the export state to clean
           */
          gimp_image_export_clean_all (image);

          gimp_object_name_changed (GIMP_OBJECT (image));
        }
      else if (export_forward)
        {
          /* Remember the last entered Export URI for the image. We
           * only need to do this explicitly when exporting. It
           * happens implicitly when saving since the GimpObject name
           * of a GimpImage is the last-save URI
           */
          gimp_image_set_exported_uri (image, uri);

          /* An image can not be considered both exported and imported
           * at the same time, so stop consider it as imported now
           * that we consider it exported.
           */
          gimp_image_set_imported_uri (image, NULL);

          gimp_image_export_clean_all (image);
        }

      if (export_backward || export_forward)
        gimp_image_exported (image, uri);
      else
        gimp_image_saved (image, uri);

      documents = GIMP_DOCUMENT_LIST (image->gimp->documents);
      imagefile = gimp_document_list_add_uri (documents,
                                              uri,
                                              file_proc->mime_type);

      /* only save a thumbnail if we are saving as XCF, see bug #25272 */
      if (GIMP_PROCEDURE (file_proc)->proc_type == GIMP_INTERNAL)
        gimp_imagefile_save_thumbnail (imagefile, file_proc->mime_type, image);
    }
  else if (status != GIMP_PDB_CANCEL)
    {
      if (error && *error == NULL)
        {
          g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,
                       _("%s plug-in could not save image"),
                       gimp_plug_in_procedure_get_label (file_proc));
        }
    }

  gimp_image_flush (image);

  g_object_unref (image);

 out:
  g_free (filename);

  return status;
}
コード例 #2
0
GimpImage *
file_open_with_proc_and_display (Gimp                *gimp,
                                 GimpContext         *context,
                                 GimpProgress        *progress,
                                 const gchar         *uri,
                                 const gchar         *entered_filename,
                                 gboolean             as_new,
                                 GimpPlugInProcedure *file_proc,
                                 GimpPDBStatusType   *status,
                                 GError             **error)
{
    GimpImage   *image;
    const gchar *mime_type = NULL;

    g_return_val_if_fail (GIMP_IS_GIMP (gimp), NULL);
    g_return_val_if_fail (GIMP_IS_CONTEXT (context), NULL);
    g_return_val_if_fail (progress == NULL || GIMP_IS_PROGRESS (progress), NULL);
    g_return_val_if_fail (status != NULL, NULL);

    image = file_open_image (gimp, context, progress,
                             uri,
                             entered_filename,
                             as_new,
                             file_proc,
                             GIMP_RUN_INTERACTIVE,
                             status,
                             &mime_type,
                             error);

    if (image)
    {
        /* If the file was imported we want to set the layer name to the
         * file name. For now, assume that multi-layered imported images
         * have named the layers already, so only rename the layer of
         * single-layered imported files. Note that this will also
         * rename already named layers from e.g. single-layered PSD
         * files. To solve this properly, we would need new file plug-in
         * API.
         */
        if (file_open_file_proc_is_import (file_proc) &&
                gimp_image_get_n_layers (image) == 1)
        {
            GimpObject *layer    = gimp_image_get_layer_iter (image)->data;
            gchar      *basename = file_utils_uri_display_basename (uri);

            gimp_item_rename (GIMP_ITEM (layer), basename, NULL);
            gimp_image_undo_free (image);
            gimp_image_clean_all (image);

            g_free (basename);
        }

        gimp_create_display (image->gimp, image, GIMP_UNIT_PIXEL, 1.0);

        if (! as_new)
        {
            GimpDocumentList *documents = GIMP_DOCUMENT_LIST (gimp->documents);
            GimpImagefile    *imagefile;

            imagefile = gimp_document_list_add_uri (documents, uri, mime_type);

            /*  can only create a thumbnail if the passed uri and the
             *  resulting image's uri match.
             */
            if (strcmp (uri, gimp_image_get_uri_or_untitled (image)) == 0)
            {
                /*  no need to save a thumbnail if there's a good one already  */
                if (! gimp_imagefile_check_thumbnail (imagefile))
                {
                    gimp_imagefile_save_thumbnail (imagefile, mime_type, image);
                }
            }
        }

        /*  the display owns the image now  */
        g_object_unref (image);

        /*  announce that we opened this image  */
        gimp_image_opened (image->gimp, uri);
    }

    return image;
}
コード例 #3
0
GList *
file_open_layers (Gimp                *gimp,
                  GimpContext         *context,
                  GimpProgress        *progress,
                  GimpImage           *dest_image,
                  gboolean             merge_visible,
                  const gchar         *uri,
                  GimpRunMode          run_mode,
                  GimpPlugInProcedure *file_proc,
                  GimpPDBStatusType   *status,
                  GError             **error)
{
    GimpImage   *new_image;
    GList       *layers    = NULL;
    const gchar *mime_type = NULL;

    g_return_val_if_fail (GIMP_IS_GIMP (gimp), NULL);
    g_return_val_if_fail (GIMP_IS_CONTEXT (context), NULL);
    g_return_val_if_fail (progress == NULL || GIMP_IS_PROGRESS (progress), NULL);
    g_return_val_if_fail (GIMP_IS_IMAGE (dest_image), NULL);
    g_return_val_if_fail (uri != NULL, NULL);
    g_return_val_if_fail (status != NULL, NULL);
    g_return_val_if_fail (error == NULL || *error == NULL, NULL);

    new_image = file_open_image (gimp, context, progress,
                                 uri, uri, FALSE,
                                 file_proc,
                                 run_mode,
                                 status, &mime_type, error);

    if (new_image)
    {
        gint n_visible = 0;

        gimp_image_undo_disable (new_image);

        layers = file_open_get_layers (new_image, merge_visible, &n_visible);

        if (merge_visible && n_visible > 1)
        {
            GimpLayer *layer;

            g_list_free (layers);

            layer = gimp_image_merge_visible_layers (new_image, context,
                    GIMP_CLIP_TO_IMAGE,
                    FALSE, FALSE);

            layers = g_list_prepend (NULL, layer);
        }

        if (layers)
        {
            gchar *basename = file_utils_uri_display_basename (uri);

            file_open_convert_items (dest_image, basename, layers);
            g_free (basename);

            gimp_document_list_add_uri (GIMP_DOCUMENT_LIST (gimp->documents),
                                        uri, mime_type);
        }
        else
        {
            g_set_error_literal (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,
                                 _("Image doesn't contain any layers"));
            *status = GIMP_PDB_EXECUTION_ERROR;
        }

        g_object_unref (new_image);
    }

    return g_list_reverse (layers);
}
コード例 #4
0
ファイル: file-save.c プロジェクト: jdburton/gimp-osx
GimpPDBStatusType
file_save (GimpImage           *image,
           GimpContext         *context,
           GimpProgress        *progress,
           const gchar         *uri,
           GimpPlugInProcedure *file_proc,
           GimpRunMode          run_mode,
           gboolean             save_a_copy,
           GError             **error)
{
  GimpDrawable      *drawable;
  GValueArray       *return_vals;
  GimpPDBStatusType  status;
  gchar             *filename;
  gint32             image_ID;
  gint32             drawable_ID;

  g_return_val_if_fail (GIMP_IS_IMAGE (image), GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (GIMP_IS_CONTEXT (context), GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (progress == NULL || GIMP_IS_PROGRESS (progress),
                        GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (uri != NULL, GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (GIMP_IS_PLUG_IN_PROCEDURE (file_proc),
                        GIMP_PDB_CALLING_ERROR);
  g_return_val_if_fail (error == NULL || *error == NULL,
                        GIMP_PDB_CALLING_ERROR);

  drawable = gimp_image_get_active_drawable (image);

  if (! drawable)
    return GIMP_PDB_EXECUTION_ERROR;

  filename = file_utils_filename_from_uri (uri);

  if (filename)
    {
      /* check if we are saving to a file */
      if (g_file_test (filename, G_FILE_TEST_EXISTS))
        {
          if (! g_file_test (filename, G_FILE_TEST_IS_REGULAR))
            {
              g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,
                           "%s", _("Not a regular file"));
              status = GIMP_PDB_EXECUTION_ERROR;
              goto out;
            }

          if (g_access (filename, W_OK) != 0)
            {
              g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_ACCES,
                           "%s", g_strerror (errno));
              status = GIMP_PDB_EXECUTION_ERROR;
              goto out;
            }
        }
    }
  else
    {
      filename = g_strdup (uri);
    }

  /* ref the image, so it can't get deleted during save */
  g_object_ref (image);

  image_ID    = gimp_image_get_ID (image);
  drawable_ID = gimp_item_get_ID (GIMP_ITEM (drawable));

  return_vals =
    gimp_pdb_execute_procedure_by_name (image->gimp->pdb,
                                        context, progress, error,
                                        GIMP_OBJECT (file_proc)->name,
                                        GIMP_TYPE_INT32,       run_mode,
                                        GIMP_TYPE_IMAGE_ID,    image_ID,
                                        GIMP_TYPE_DRAWABLE_ID, drawable_ID,
                                        G_TYPE_STRING,         filename,
                                        G_TYPE_STRING,         uri,
                                        G_TYPE_NONE);

  status = g_value_get_enum (&return_vals->values[0]);

  g_value_array_free (return_vals);

  if (status == GIMP_PDB_SUCCESS)
    {
      GimpDocumentList *documents;
      GimpImagefile    *imagefile;

      if (save_a_copy)
        {
          /*  remember the "save-a-copy" filename for the next invocation  */
          g_object_set_data_full (G_OBJECT (image), "gimp-image-save-a-copy",
                                  g_strdup (uri),
                                  (GDestroyNotify) g_free);
        }
      else
        {
          /*  reset the "save-a-copy" filename when the image URI changes  */
          if (strcmp (uri, gimp_image_get_uri (image)))
            g_object_set_data (G_OBJECT (image),
                               "gimp-image-save-a-copy", NULL);

          gimp_image_set_uri (image, uri);
          gimp_image_set_save_proc (image, file_proc);

          gimp_image_clean_all (image);
        }

      gimp_image_saved (image, uri);

      documents = GIMP_DOCUMENT_LIST (image->gimp->documents);
      imagefile = gimp_document_list_add_uri (documents,
                                              uri,
                                              file_proc->mime_type);

      /* only save a thumbnail if we are saving as XCF, see bug #25272 */
      if (GIMP_PROCEDURE (file_proc)->proc_type == GIMP_INTERNAL)
        gimp_imagefile_save_thumbnail (imagefile, file_proc->mime_type, image);
    }
  else if (status != GIMP_PDB_CANCEL)
    {
      if (error && *error == NULL)
        {
          g_set_error (error, G_FILE_ERROR, G_FILE_ERROR_FAILED,
                       _("%s plug-in could not save image"),
                       gimp_plug_in_procedure_get_label (file_proc));
        }
    }

  gimp_image_flush (image);

  g_object_unref (image);

 out:
  g_free (filename);

  return status;
}