home *** CD-ROM | disk | FTP | other *** search
/ PC Pro 2002 April / pcpro0402.iso / essentials / graphics / Gimp / gimp-src-20001226.exe / src / gimp / app / info_window.c < prev    next >
Encoding:
C/C++ Source or Header  |  2000-12-17  |  15.5 KB  |  557 lines

  1. /* The GIMP -- an image manipulation program
  2.  * Copyright (C) 1995 Spencer Kimball and Peter Mattis
  3.  *
  4.  * This program is free software; you can redistribute it and/or modify
  5.  * it under the terms of the GNU General Public License as published by
  6.  * the Free Software Foundation; either version 2 of the License, or
  7.  * (at your option) any later version.
  8.  *
  9.  * This program is distributed in the hope that it will be useful,
  10.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  12.  * GNU General Public License for more details.
  13.  *
  14.  * You should have received a copy of the GNU General Public License
  15.  * along with this program; if not, write to the Free Software
  16.  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
  17.  */
  18.  
  19. #include "config.h"
  20.  
  21. #include <glib.h>
  22.  
  23. #include "apptypes.h"
  24.  
  25. #include "appenv.h"
  26. #include "apptypes.h"
  27. #include "colormaps.h"
  28. #include "gdisplay.h"
  29. #include "gimpcontext.h"
  30. #include "gimpset.h"
  31. #include "gimpui.h"
  32. #include "gximage.h"
  33. #include "info_dialog.h"
  34. #include "info_window.h"
  35. #include "scroll.h"
  36. #include "tools.h"
  37.  
  38. #include "libgimp/gimpunit.h"
  39.  
  40. #include "libgimp/gimpintl.h"
  41.  
  42. #define MAX_BUF 256
  43.  
  44. typedef struct _InfoWinData InfoWinData;
  45.  
  46. struct _InfoWinData
  47. {
  48.   gchar      dimensions_str[MAX_BUF];
  49.   gchar      real_dimensions_str[MAX_BUF];
  50.   gchar      scale_str[MAX_BUF];
  51.   gchar      color_type_str[MAX_BUF];
  52.   gchar      visual_class_str[MAX_BUF];
  53.   gchar      visual_depth_str[MAX_BUF];
  54.   gchar      resolution_str[MAX_BUF];
  55.   gchar      unit_str[MAX_BUF];
  56.  
  57.   GDisplay  *gdisp;
  58.  
  59.   GtkWidget *labelBvalue;
  60.   GtkWidget *labelGvalue;
  61.   GtkWidget *labelRvalue;
  62.   GtkWidget *labelAvalue;
  63.  
  64.   gboolean   showingPreview;
  65. };
  66.  
  67. /*  The different classes of visuals  */
  68. static gchar *visual_classes[] =
  69. {
  70.   N_("Static Gray"),
  71.   N_("Grayscale"),
  72.   N_("Static Color"),
  73.   N_("Pseudo Color"),
  74.   N_("True Color"),
  75.   N_("Direct Color"),
  76. };
  77.  
  78. static gchar * info_window_title (GDisplay *gdisp);
  79.  
  80.  
  81. static void
  82. info_window_image_rename_callback (GimpImage *gimage,
  83.                    gpointer   data)
  84. {
  85.   InfoDialog *id;
  86.   gchar *title;
  87.   GDisplay * gdisp;
  88.   InfoWinData *iwd;
  89.  
  90.   id = (InfoDialog *) data;
  91.  
  92.   iwd = (InfoWinData *) id->user_data;
  93.  
  94.   gdisp = (GDisplay *) iwd->gdisp;
  95.  
  96.   title = info_window_title(gdisp);
  97.   gtk_window_set_title (GTK_WINDOW (id->shell), title);
  98.   g_free (title);
  99. }
  100.  
  101. static void
  102. info_window_close_callback (GtkWidget *widget,
  103.                 gpointer   data)
  104. {
  105.   info_dialog_popdown ((InfoDialog *) data);
  106. }
  107.  
  108. static void
  109. info_window_page_switch (GtkWidget       *widget, 
  110.              GtkNotebookPage *page, 
  111.              gint             page_num)
  112. {
  113.   InfoDialog *info_win;
  114.   InfoWinData *iwd;
  115.   
  116.   info_win = (InfoDialog *) gtk_object_get_user_data (GTK_OBJECT (widget));
  117.   iwd = (InfoWinData *) info_win->user_data;
  118.  
  119.   /* Only deal with the second page */
  120.   if (page_num != 1)
  121.     {
  122.       iwd->showingPreview = FALSE;
  123.       return;
  124.     }
  125.  
  126.   iwd->showingPreview = TRUE;
  127. }
  128.  
  129. static void
  130. info_window_create_extended (InfoDialog *info_win)
  131. {
  132.   GtkWidget *hbox;
  133.   GtkWidget *frame;
  134.   GtkWidget *alignment;
  135.   GtkWidget *table;
  136.   GtkWidget *label;
  137.   GtkWidget *pixmap;
  138.  
  139.   InfoWinData *iwd;
  140.  
  141.   iwd = (InfoWinData *) info_win->user_data;
  142.  
  143.   hbox = gtk_hbox_new (FALSE, 0);
  144.  
  145.   alignment = gtk_alignment_new (0.5, 0.5, 0.0, 0.0);
  146.   gtk_box_pack_start (GTK_BOX (hbox), alignment, TRUE, TRUE, 0);
  147.   gtk_widget_show (alignment);
  148.  
  149.   frame = gtk_frame_new (NULL);
  150.   gtk_container_set_border_width (GTK_CONTAINER (frame), 4);
  151.   gtk_container_add (GTK_CONTAINER (alignment), frame); 
  152.   gtk_widget_show (frame);
  153.  
  154.   table = gtk_table_new (5, 2, FALSE);
  155.   gtk_table_set_col_spacing (GTK_TABLE (table), 0, 4);
  156.   gtk_table_set_row_spacings (GTK_TABLE (table), 4);
  157.   gtk_container_set_border_width (GTK_CONTAINER (table), 4);
  158.   gtk_container_add (GTK_CONTAINER (frame), table);
  159.   gtk_widget_show (table);
  160.  
  161.   pixmap = gtk_pixmap_new (tool_get_pixmap (COLOR_PICKER),
  162.                tool_get_mask (COLOR_PICKER));
  163.   gtk_table_attach (GTK_TABLE (table), pixmap, 0, 2, 0, 1,
  164.                     GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 2, 2);
  165.   gtk_widget_show (pixmap);
  166.  
  167.   label = gtk_label_new (_("R:"));
  168.   gtk_misc_set_alignment (GTK_MISC (label), 1.0, 0.5);
  169.   gtk_table_attach (GTK_TABLE (table), label, 0, 1, 1, 2,
  170.                     GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
  171.   gtk_widget_show (label);
  172.  
  173.   label = gtk_label_new (_("G:"));
  174.   gtk_misc_set_alignment (GTK_MISC (label), 1.0, 0.5);
  175.   gtk_table_attach (GTK_TABLE (table), label, 0, 1, 2, 3,
  176.                     GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
  177.   gtk_widget_show (label);
  178.  
  179.   label = gtk_label_new (_("B:"));
  180.   gtk_misc_set_alignment (GTK_MISC (label), 1.0, 0.5);
  181.   gtk_table_attach (GTK_TABLE (table), label, 0, 1, 3, 4,
  182.                     GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
  183.   gtk_widget_show (label);
  184.  
  185.   label = gtk_label_new (_("A:"));
  186.   gtk_misc_set_alignment (GTK_MISC (label), 1.0, 0.5);
  187.   gtk_table_attach (GTK_TABLE (table), label, 0, 1, 4, 5,
  188.             GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
  189.   gtk_widget_show (label);
  190.  
  191.   iwd->labelRvalue = label = gtk_label_new (_("N/A"));
  192.   gtk_misc_set_alignment (GTK_MISC (label), 1.0, 0.5);
  193.   gtk_table_attach (GTK_TABLE (table), label, 1, 2, 1, 2,
  194.             GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
  195.   gtk_widget_show (label);
  196.  
  197.   iwd->labelGvalue = label = gtk_label_new (_("N/A"));
  198.   gtk_misc_set_alignment (GTK_MISC (label), 1.0, 0.5);
  199.   gtk_table_attach (GTK_TABLE (table), label, 1, 2, 2, 3,
  200.                     GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
  201.   gtk_widget_show (label);
  202.  
  203.   iwd->labelBvalue = label = gtk_label_new (_("N/A"));
  204.   gtk_misc_set_alignment (GTK_MISC (label), 1.0, 0.5);
  205.   gtk_table_attach (GTK_TABLE (table), label, 1, 2, 3, 4,
  206.                     GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
  207.   gtk_widget_show (label);
  208.  
  209.   iwd->labelAvalue = label = gtk_label_new (_("N/A"));
  210.   gtk_misc_set_alignment (GTK_MISC (label), 1.0, 0.5);
  211.   gtk_table_attach (GTK_TABLE (table), label, 1, 2, 4, 5,
  212.                     GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
  213.   gtk_widget_show (label);
  214.  
  215.  
  216.   gtk_notebook_append_page (GTK_NOTEBOOK(info_win->info_notebook),
  217.                 hbox, gtk_label_new (_("Extended")));
  218.   gtk_widget_show (hbox);
  219.  
  220.   /* Set back to first page */
  221.   gtk_notebook_set_page (GTK_NOTEBOOK(info_win->info_notebook), 0);
  222.  
  223.   gtk_object_set_user_data (GTK_OBJECT (info_win->info_notebook),
  224.                 (gpointer)info_win);
  225.  
  226.   gtk_signal_connect (GTK_OBJECT (info_win->info_notebook), "switch_page",
  227.               GTK_SIGNAL_FUNC (info_window_page_switch), NULL);
  228. }
  229.  
  230. /*  displays information:
  231.  *    image name
  232.  *    image width, height
  233.  *    zoom ratio
  234.  *    image color type
  235.  *    Display info:
  236.  *      visual class
  237.  *      visual depth
  238.  */
  239.  
  240. InfoDialog *
  241. info_window_create (GDisplay *gdisp)
  242. {
  243.   InfoDialog *info_win;
  244.   InfoWinData *iwd;
  245.   gchar *title, *title_buf;
  246.   gint type;
  247.  
  248.   title = g_basename (gimage_filename (gdisp->gimage));
  249.   type = gimage_base_type (gdisp->gimage);
  250.  
  251.   /*  create the info dialog  */
  252.   title_buf = info_window_title (gdisp);
  253.   info_win = info_dialog_notebook_new (title_buf,
  254.                        gimp_standard_help_func,
  255.                        "dialogs/info_window.html");
  256.   g_free (title_buf);
  257.  
  258.   /*  create the action area  */
  259.   gimp_dialog_create_action_area (GTK_DIALOG (info_win->shell),
  260.  
  261.                   _("Close"), info_window_close_callback,
  262.                   info_win, NULL, NULL, TRUE, FALSE,
  263.  
  264.                   NULL);
  265.  
  266.   iwd = g_new (InfoWinData, 1);
  267.   info_win->user_data = iwd;
  268.  
  269.   iwd->dimensions_str[0]       = '\0';
  270.   iwd->real_dimensions_str[0]  = '\0';
  271.   iwd->resolution_str[0]       = '\0';
  272.   iwd->scale_str[0]            = '\0';
  273.   iwd->color_type_str[0]       = '\0';
  274.   iwd->visual_class_str[0]     = '\0';
  275.   iwd->visual_depth_str[0]     = '\0';
  276.   iwd->gdisp                   = gdisp;
  277.   iwd->showingPreview          = FALSE;
  278.  
  279.   /*  add the information fields  */
  280.   info_dialog_add_label (info_win, _("Dimensions (w x h):"),
  281.              iwd->dimensions_str);
  282.   info_dialog_add_label (info_win, '\0',
  283.              iwd->real_dimensions_str);
  284.   info_dialog_add_label (info_win, _("Resolution:"),
  285.             iwd->resolution_str);
  286.   info_dialog_add_label (info_win, _("Scale Ratio:"),
  287.              iwd->scale_str);
  288.   info_dialog_add_label (info_win, _("Display Type:"),
  289.              iwd->color_type_str);
  290.   info_dialog_add_label (info_win, _("Visual Class:"),
  291.              iwd->visual_class_str);
  292.   info_dialog_add_label (info_win, _("Visual Depth:"),
  293.              iwd->visual_depth_str);
  294.   /*  update the fields  */
  295.   /*gdisp->window_info_dialog = info_win;*/
  296.   info_window_update (gdisp);
  297.  
  298.   /*  Add extra tabs  */
  299.   info_window_create_extended (info_win);
  300.  
  301.   /*  keep track of image name changes  */
  302.   gtk_signal_connect (GTK_OBJECT (gdisp->gimage), "rename",
  303.               GTK_SIGNAL_FUNC (info_window_image_rename_callback),
  304.               info_win);
  305.  
  306.   return info_win;
  307. }
  308.  
  309. static InfoDialog *info_window_auto = NULL;
  310.  
  311. static gchar *
  312. info_window_title (GDisplay *gdisp)
  313. {
  314.   gchar *title;
  315.   gchar *title_buf;
  316.   
  317.   title = g_basename (gimage_filename (gdisp->gimage));
  318.   
  319.   /*  create the info dialog  */
  320.   title_buf = g_strdup_printf (_("Info: %s-%d.%d"), 
  321.                    title,
  322.                    pdb_image_to_id (gdisp->gimage),
  323.                    gdisp->instance);
  324.  
  325.   return title_buf;
  326. }
  327.  
  328. static void
  329. info_window_change_display (GimpContext *context, /* NOT USED */
  330.                 GDisplay    *newdisp,
  331.                 gpointer     data /* Not used */)
  332. {
  333.   GDisplay * gdisp = newdisp;
  334.   GDisplay * old_gdisp;
  335.   GimpImage * gimage;
  336.   InfoWinData *iwd;
  337.  
  338.   iwd = (InfoWinData *) info_window_auto->user_data;
  339.  
  340.   old_gdisp = (GDisplay *) iwd->gdisp;
  341.  
  342.   if (!info_window_auto || gdisp == old_gdisp || !gdisp)
  343.     {
  344.       return;
  345.     }
  346.  
  347.   gimage = gdisp->gimage;
  348.  
  349.   if (gimage && gimp_set_have (image_context, gimage))
  350.     {
  351.       iwd->gdisp = gdisp;
  352.       info_window_update(gdisp);
  353.     }
  354. }
  355.  
  356. void
  357. info_window_follow_auto (void)
  358. {
  359.   GDisplay * gdisp;
  360.  
  361.   gdisp = gdisplay_active (); 
  362.   
  363.   if (!gdisp) 
  364.     return;
  365.  
  366.   if(!info_window_auto)
  367.     {
  368.       info_window_auto = info_window_create ((void *) gdisp);
  369.       gtk_signal_connect (GTK_OBJECT (gimp_context_get_user ()), "display_changed",
  370.               GTK_SIGNAL_FUNC (info_window_change_display), NULL);
  371.       info_window_update(gdisp); /* Update to include the info */
  372.     }
  373.  
  374.   info_dialog_popup (info_window_auto);
  375.   /*
  376.   iwd = (NavWinData *)nav_window_auto->user_data;
  377.   gtk_widget_set_sensitive(nav_window_auto->vbox,TRUE);
  378.   iwd->frozen = FALSE;
  379.   */
  380. }
  381.  
  382. void  
  383. info_window_update_RGB (GDisplay *gdisp,
  384.             gdouble   tx,
  385.             gdouble   ty)
  386. {
  387.   InfoWinData *iwd;
  388.   gchar buff[4];
  389.   guchar *color;
  390.   GimpImageType sample_type;
  391.   InfoDialog *info_win = gdisp->window_info_dialog;
  392.   gboolean force_update = FALSE;
  393.  
  394.   if (!info_win && info_window_auto != NULL)
  395.     {
  396.       info_win = info_window_auto;
  397.     }
  398.  
  399.   if (!info_win)
  400.     return;
  401.  
  402.   iwd = (InfoWinData *) info_win->user_data;
  403.  
  404.   if(iwd->gdisp != gdisp)
  405.     force_update = TRUE;
  406.  
  407.   iwd->gdisp = gdisp;
  408.  
  409.   if(force_update == TRUE)
  410.     {
  411.       gchar       *title_buf;
  412.       info_window_update(gdisp);
  413.       title_buf = info_window_title(gdisp);
  414.       
  415.       gtk_window_set_title (GTK_WINDOW (info_window_auto->shell), title_buf);
  416.       
  417.       g_free (title_buf);
  418.     }
  419.  
  420.  
  421.   if (!iwd || iwd->showingPreview == FALSE)
  422.     return;
  423.  
  424.   /* gimage_active_drawable (gdisp->gimage) */
  425.   if (!(color = gimp_image_get_color_at (gdisp->gimage, tx, ty))
  426.       || (tx <  0.0 && ty < 0.0))
  427.     {
  428.       gtk_label_set_text (GTK_LABEL (iwd->labelRvalue), _("N/A"));
  429.       gtk_label_set_text (GTK_LABEL (iwd->labelGvalue), _("N/A"));
  430.       gtk_label_set_text (GTK_LABEL (iwd->labelBvalue), _("N/A"));
  431.       gtk_label_set_text (GTK_LABEL (iwd->labelAvalue), _("N/A"));
  432.  
  433.       return;
  434.     }
  435.  
  436.   g_snprintf (buff, sizeof (buff), "%d", (gint) color[RED_PIX]);
  437.   gtk_label_set_text (GTK_LABEL (iwd->labelRvalue), buff);
  438.  
  439.   g_snprintf (buff, sizeof (buff), "%d", (gint) color[GREEN_PIX]);
  440.   gtk_label_set_text (GTK_LABEL (iwd->labelGvalue), buff);
  441.  
  442.   g_snprintf (buff, sizeof (buff), "%d", (gint) color[BLUE_PIX]);
  443.   gtk_label_set_text (GTK_LABEL (iwd->labelBvalue), buff);
  444.  
  445.   sample_type = gimp_image_composite_type (gdisp->gimage);
  446.  
  447.   if (GIMP_IMAGE_TYPE_HAS_ALPHA (sample_type))
  448.     {
  449.       g_snprintf (buff, sizeof (buff), "%d", (gint) color[ALPHA_PIX]);
  450.       gtk_label_set_text (GTK_LABEL (iwd->labelAvalue), buff);
  451.     }
  452.   else
  453.     gtk_label_set_text (GTK_LABEL (iwd->labelAvalue), _("N/A"));
  454.  
  455.   g_free(color);
  456. }
  457.  
  458. void
  459. info_window_free (InfoDialog *info_win)
  460. {
  461.   InfoWinData *iwd;
  462.   extern gint gimage_image_count (void);
  463.  
  464.   if (!info_win && info_window_auto)
  465.     {
  466.       gtk_widget_set_sensitive (info_window_auto->vbox, FALSE);
  467.       return;
  468.     }
  469.  
  470.   if (!info_win)
  471.     return;
  472.  
  473.   iwd = (InfoWinData *) info_win->user_data;
  474.  
  475.   gtk_signal_disconnect_by_data (GTK_OBJECT (iwd->gdisp->gimage), info_win);
  476.  
  477.   g_free (iwd);
  478.   info_dialog_free (info_win);
  479. }
  480.  
  481. void
  482. info_window_update (GDisplay *gdisp)
  483. {
  484.   InfoWinData *iwd;
  485.   gint         type;
  486.   gdouble      unit_factor;
  487.   gint         unit_digits;
  488.   gchar        format_buf[32];
  489.   InfoDialog *info_win = gdisp->window_info_dialog;
  490.  
  491.   if (!info_win && info_window_auto != NULL)
  492.     info_win = info_window_auto;
  493.  
  494.   if (!info_win)
  495.     return;
  496.  
  497.   iwd = (InfoWinData *) info_win->user_data;
  498.  
  499.   /* Make it sensitive... */
  500.   if (info_window_auto)
  501.     gtk_widget_set_sensitive (info_window_auto->vbox, TRUE);
  502.  
  503.   /* If doing info_window_auto then return if this display
  504.    * is not the one we are showing.
  505.    */
  506.  
  507.   if (info_window_auto && iwd->gdisp != gdisp)
  508.     return;
  509.  
  510.   /*  width and height  */
  511.   unit_factor = gimp_unit_get_factor (gdisp->gimage->unit);
  512.   unit_digits = gimp_unit_get_digits (gdisp->gimage->unit);
  513.   g_snprintf (iwd->dimensions_str, MAX_BUF,
  514.           _("%d x %d pixels"),
  515.           (int) gdisp->gimage->width,
  516.           (int) gdisp->gimage->height);
  517.   g_snprintf (format_buf, sizeof (format_buf),
  518.           "%%.%df x %%.%df %s",
  519.           unit_digits + 1, unit_digits + 1,
  520.           gimp_unit_get_plural (gdisp->gimage->unit));
  521.   g_snprintf (iwd->real_dimensions_str, MAX_BUF, format_buf,
  522.           gdisp->gimage->width * unit_factor / gdisp->gimage->xresolution,
  523.           gdisp->gimage->height * unit_factor / gdisp->gimage->yresolution);
  524.  
  525.   /*  image resolution  */
  526.   g_snprintf (iwd->resolution_str, MAX_BUF, _("%g x %g dpi"),
  527.           gdisp->gimage->xresolution,
  528.           gdisp->gimage->yresolution);
  529.  
  530.   /*  user zoom ratio  */
  531.   g_snprintf (iwd->scale_str, MAX_BUF, "%d:%d",
  532.        SCALEDEST (gdisp), SCALESRC (gdisp));
  533.  
  534.   type = gimage_base_type (gdisp->gimage);
  535.  
  536.   /*  color type  */
  537.   if (type == RGB)
  538.     g_snprintf (iwd->color_type_str, MAX_BUF, "%s", _("RGB Color"));
  539.   else if (type == GRAY)
  540.     g_snprintf (iwd->color_type_str, MAX_BUF, "%s", _("Grayscale"));
  541.   else if (type == INDEXED)
  542.     g_snprintf (iwd->color_type_str, MAX_BUF, "%s (%d %s)", 
  543.         _("Indexed Color"), gdisp->gimage->num_cols, _("colors"));
  544.  
  545.   /*  visual class  */
  546.   if (type == RGB ||
  547.       type == INDEXED)
  548.     g_snprintf (iwd->visual_class_str, MAX_BUF, "%s", gettext (visual_classes[g_visual->type]));
  549.   else if (type == GRAY)
  550.     g_snprintf (iwd->visual_class_str, MAX_BUF, "%s", gettext (visual_classes[g_visual->type]));
  551.  
  552.   /*  visual depth  */
  553.   g_snprintf (iwd->visual_depth_str, MAX_BUF, "%d", gdisp->depth);
  554.  
  555.   info_dialog_update (info_win);
  556. }
  557.