home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / wxos2233.zip / wxOS2-2_3_3.zip / wxWindows-2.3.3 / src / common / imagxpm.cpp < prev    next >
C/C++ Source or Header  |  2002-02-16  |  9KB  |  237 lines

  1. /////////////////////////////////////////////////////////////////////////////
  2. // Name:        imagxpm.cpp
  3. // Purpose:     wxXPMHandler
  4. // Author:      Vaclav Slavik, Robert Roebling
  5. // RCS-ID:      $Id: imagxpm.cpp,v 1.12 2002/02/16 01:45:30 VS Exp $
  6. // Copyright:   (c) 2001 Vaclav Slavik
  7. // Licence:     wxWindows licence
  8. /////////////////////////////////////////////////////////////////////////////
  9.  
  10. /*
  11.  
  12. This file is partially based on source code of ImageMagick by John Cristy. Its
  13. license is as follows:
  14.  
  15. %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
  16. %                                                                             %
  17. %                                                                             %
  18. %                                                                             %
  19. %                            X   X  PPPP   M   M                              %
  20. %                             X X   P   P  MM MM                              %
  21. %                              X    PPPP   M M M                              %
  22. %                             X X   P      M   M                              %
  23. %                            X   X  P      M   M                              %
  24. %                                                                             %
  25. %                                                                             %
  26. %                    Read/Write ImageMagick Image Format.                     %
  27. %                                                                             %
  28. %                                                                             %
  29. %                              Software Design                                %
  30. %                                John Cristy                                  %
  31. %                                 July 1992                                   %
  32. %                                                                             %
  33. %                                                                             %
  34. %  Copyright (C) 2001 ImageMagick Studio, a non-profit organization dedicated %
  35. %  to making software imaging solutions freely available.                     %
  36. %                                                                             %
  37. %  Permission is hereby granted, free of charge, to any person obtaining a    %
  38. %  copy of this software and associated documentation files ("ImageMagick"),  %
  39. %  to deal in ImageMagick without restriction, including without limitation   %
  40. %  the rights to use, copy, modify, merge, publish, distribute, sublicense,   %
  41. %  and/or sell copies of ImageMagick, and to permit persons to whom the       %
  42. %  ImageMagick is furnished to do so, subject to the following conditions:    %
  43. %                                                                             %
  44. %  The above copyright notice and this permission notice shall be included in %
  45. %  all copies or substantial portions of ImageMagick.                         %
  46. %                                                                             %
  47. %  The software is provided "as is", without warranty of any kind, express or %
  48. %  implied, including but not limited to the warranties of merchantability,   %
  49. %  fitness for a particular purpose and noninfringement.  In no event shall   %
  50. %  ImageMagick Studio be liable for any claim, damages or other liability,    %
  51. %  whether in an action of contract, tort or otherwise, arising from, out of  %
  52. %  or in connection with ImageMagick or the use or other dealings in          %
  53. %  ImageMagick.                                                               %
  54. %                                                                             %
  55. %  Except as contained in this notice, the name of the ImageMagick Studio     %
  56. %  shall not be used in advertising or otherwise to promote the sale, use or  %
  57. %  other dealings in ImageMagick without prior written authorization from the %
  58. %  ImageMagick Studio.                                                        %
  59. %                                                                             %
  60. %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
  61. %
  62. %
  63. */
  64.  
  65. #ifdef __GNUG__
  66. #pragma implementation "imagxpm.h"
  67. #endif
  68.  
  69. // For compilers that support precompilation, includes "wx.h".
  70. #include "wx/wxprec.h"
  71.  
  72. #ifdef __BORLANDC__
  73. #  pragma hdrstop
  74. #endif
  75.  
  76. #ifndef WX_PRECOMP
  77. #  include "wx/defs.h"
  78. #endif
  79.  
  80. #if wxUSE_XPM
  81.  
  82. #include "wx/imagxpm.h"
  83. #include "wx/wfstream.h"
  84. #include "wx/log.h"
  85. #include "wx/intl.h"
  86. #include "wx/utils.h"
  87. #include "wx/xpmdecod.h"
  88.  
  89. IMPLEMENT_DYNAMIC_CLASS(wxXPMHandler,wxImageHandler)
  90.  
  91. //-----------------------------------------------------------------------------
  92. // wxXPMHandler
  93. //-----------------------------------------------------------------------------
  94.  
  95. #if wxUSE_STREAMS
  96.  
  97. bool wxXPMHandler::LoadFile(wxImage *image,
  98.                             wxInputStream& stream,
  99.                             bool WXUNUSED(verbose), int WXUNUSED(index))
  100. {
  101.     wxXPMDecoder decoder;
  102.  
  103.     wxImage img = decoder.ReadFile(stream);
  104.     if ( !img.Ok() )
  105.         return FALSE;
  106.     *image = img;
  107.     return TRUE;
  108. }
  109.  
  110. bool wxXPMHandler::SaveFile(wxImage * image,
  111.                             wxOutputStream& stream, bool WXUNUSED(verbose))
  112. {
  113.     wxString tmp;
  114.     char tmp_c;
  115.  
  116.     // 1. count colours:
  117.     #define MaxCixels  92
  118.     static const char Cixel[MaxCixels+1] =
  119.                          " .XoO+@#$%&*=-;:>,<1234567890qwertyuipasdfghjk"
  120.                          "lzxcvbnmMNBVCZASDFGHJKLPIUYTREWQ!~^/()_`'][{}|";
  121.     int chars_per_pixel;
  122.     int cols;
  123.     int i, j, k;
  124.  
  125.     cols = image->CountColours();
  126.     chars_per_pixel = 1;
  127.     for ( k = MaxCixels; cols > k; k *= MaxCixels)
  128.         chars_per_pixel++;
  129.  
  130.     // 2. write the header:    
  131.     wxString sName;
  132.     if ( image->HasOption(wxIMAGE_OPTION_FILENAME) )
  133.     {
  134.         wxSplitPath(image->GetOption(wxIMAGE_OPTION_FILENAME),
  135.                     NULL, &sName, NULL);
  136.         sName << wxT("_xpm");
  137.     }
  138.     
  139.     if ( !sName.IsEmpty() )
  140.         sName = wxString(wxT("/* XPM */\nstatic char *")) + sName;
  141.     else 
  142.         sName = wxT("/* XPM */\nstatic char *xpm_data");
  143.     stream.Write(sName.c_str(), sName.Len());
  144.  
  145.     char tmpbuf[200];
  146.     // VS: 200b is safe upper bound for anything produced by sprintf below
  147.     //     (<101 bytes the string, neither %i can expand into more than 10 chars)
  148.     sprintf(tmpbuf, 
  149.                "[] = {\n"
  150.                "/* columns rows colors chars-per-pixel */\n"
  151.                "\"%i %i %i %i\",\n",
  152.                image->GetWidth(), image->GetHeight(), cols, chars_per_pixel);
  153.     stream.Write(tmpbuf, strlen(tmpbuf));
  154.  
  155.     // 3. create color symbols table:
  156.     wxImageHistogram histogram;
  157.     image->ComputeHistogram(histogram);
  158.  
  159.     char *symbols_data = new char[cols * (chars_per_pixel+1)];
  160.     char **symbols = new char*[cols];
  161.  
  162.     // 2a. find mask colour:
  163.     unsigned long mask_key = 0x1000000 /*invalid RGB value*/;
  164.     if (image->HasMask())
  165.         mask_key = (image->GetMaskRed() << 16) |
  166.                    (image->GetMaskGreen() << 8) | image->GetMaskBlue();
  167.  
  168.     // 2b. generate colour table:
  169.     for (wxImageHistogram::iterator entry = histogram.begin();
  170.          entry != histogram.end(); entry++ )
  171.     {
  172.         unsigned long index = entry->second.index;
  173.         symbols[index] = symbols_data + index * (chars_per_pixel+1);
  174.         char *sym = symbols[index];
  175.  
  176.         k = index % MaxCixels;
  177.         sym[0] = Cixel[k];
  178.         for (j = 1; j < chars_per_pixel; j++)
  179.         {
  180.             k = ((index - k) / MaxCixels) % MaxCixels;
  181.             sym[j] = Cixel[k];
  182.         }
  183.         sym[j] = '\0';
  184.  
  185.         unsigned long key = entry->first;
  186.  
  187.         if (key == 0)
  188.             tmp.Printf(wxT("\"%s c Black\",\n"), sym);
  189.         else if (key == mask_key)
  190.             tmp.Printf(wxT("\"%s c None\",\n"), sym);
  191.         else
  192.             tmp.Printf(wxT("\"%s c #%s%s%s\",\n"), sym,
  193.                        wxDecToHex((unsigned char)(key >> 16)).c_str(),
  194.                        wxDecToHex((unsigned char)(key >> 8)).c_str(),
  195.                        wxDecToHex((unsigned char)(key)).c_str());
  196.         stream.Write(tmp.mb_str(), tmp.Length());
  197.     }
  198.  
  199.     tmp = wxT("/* pixels */\n");
  200.     stream.Write(tmp.mb_str(), tmp.Length());
  201.  
  202.     unsigned char *data = image->GetData();
  203.     for (j = 0; j < image->GetHeight(); j++)
  204.     {
  205.         tmp_c = '\"'; stream.Write(&tmp_c, 1);
  206.         for (i = 0; i < image->GetWidth(); i++, data += 3)
  207.         {
  208.             unsigned long key = (data[0] << 16) | (data[1] << 8) | (data[2]);
  209.             stream.Write(symbols[histogram[key].index], chars_per_pixel);
  210.         }
  211.         tmp_c = '\"'; stream.Write(&tmp_c, 1);
  212.         if ( j + 1 < image->GetHeight() )
  213.         {
  214.             tmp_c = ','; stream.Write(&tmp_c, 1);
  215.         }
  216.         tmp_c = '\n'; stream.Write(&tmp_c, 1);
  217.     }
  218.     tmp = wxT("};\n");
  219.     stream.Write(tmp.mb_str(), 3);
  220.  
  221.     // Clean up:
  222.     delete[] symbols;
  223.     delete[] symbols_data;
  224.  
  225.     return TRUE;
  226. }
  227.  
  228. bool wxXPMHandler::DoCanRead(wxInputStream& stream)
  229. {
  230.     wxXPMDecoder decoder;
  231.     return decoder.CanRead(stream);
  232. }
  233.  
  234. #endif  // wxUSE_STREAMS
  235.  
  236. #endif // wxUSE_XPM
  237.