• Skip to content
  • Skip to link menu
KDE 4.3 API Reference
  • KDE API Reference
  • kdelibs
  • Sitemap
  • Contact Us
 

KImgIO

xview.cpp

Go to the documentation of this file.
00001 
00009 #include "xview.h"
00010 
00011 #include <stdio.h>
00012 #include <string.h>
00013 #include <stdlib.h>
00014 #include <QtGui/QImage>
00015 
00016 #define BUFSIZE 1024
00017 
00018 static const int b_255_3[]= {0,85,170,255},  // index*255/3
00019            rg_255_7[]={0,36,72,109,145,182,218,255}; // index *255/7
00020 
00021 
00022 XVHandler::XVHandler()
00023 {
00024 }
00025 
00026 bool XVHandler::canRead() const
00027 {
00028     if (canRead(device())) {
00029         setFormat("xv");
00030         return true;
00031     }
00032     return false;
00033 }
00034 
00035 bool XVHandler::read(QImage *retImage)
00036 {
00037     int x=-1;
00038     int y=-1;
00039     int maxval=-1;
00040     QIODevice *iodev = device();
00041 
00042     char str[ BUFSIZE ];
00043 
00044     // magic number must be "P7 332"
00045     iodev->readLine( str, BUFSIZE );
00046     if (strncmp(str,"P7 332",6))
00047         return false;
00048 
00049     // next line #XVVERSION
00050     iodev->readLine( str, BUFSIZE );
00051     if (strncmp(str, "#XVVERSION", 10))
00052         return false;
00053 
00054     // now it gets interesting, #BUILTIN means we are out.
00055     // if IMGINFO comes, we are happy!
00056     iodev->readLine( str, BUFSIZE );
00057     if (strncmp(str, "#IMGINFO:", 9))
00058         return false;
00059 
00060     // after this an #END_OF_COMMENTS signals everything to be ok!
00061     iodev->readLine( str, BUFSIZE );
00062     if (strncmp(str, "#END_OF", 7))
00063         return false;
00064 
00065     // now a last line with width, height, maxval which is
00066     // supposed to be 255
00067     iodev->readLine( str, BUFSIZE );
00068     sscanf(str, "%d %d %d", &x, &y, &maxval);
00069 
00070     if (maxval != 255)
00071         return false;
00072     int blocksize = x*y;
00073     if(x < 0 || y < 0 || blocksize < x || blocksize < y)
00074         return false;
00075 
00076     // now follows a binary block of x*y bytes.
00077     char *block = (char*) malloc(blocksize);
00078     if(!block)
00079         return false;
00080 
00081     if (iodev->read(block, blocksize) != blocksize )
00082     {
00083     free(block);
00084         return false;
00085     }
00086 
00087     // Create the image
00088     QImage image( x, y, QImage::Format_Indexed8 );
00089     int numColors;
00090     numColors = qMin( maxval + 1, 0 );
00091     numColors = qMax( 0, maxval + 1 );
00092     image.setNumColors( numColors );
00093 
00094     // how do the color handling? they are absolute 24bpp
00095     // or at least can be calculated as such.
00096     int r,g,b;
00097 
00098     for ( int j = 0; j < 256; j++ )
00099     {
00100         r =  rg_255_7[((j >> 5) & 0x07)];
00101         g =  rg_255_7[((j >> 2) & 0x07)];
00102         b =  b_255_3[((j >> 0) & 0x03)];
00103         image.setColor( j, qRgb( r, g, b ) );
00104     }
00105 
00106     for ( int py = 0; py < y; py++ )
00107     {
00108         uchar *data = image.scanLine( py );
00109         memcpy( data, block + py * x, x );
00110     }
00111 
00112     *retImage = image;
00113 
00114     free(block);
00115     return true;
00116 }
00117 
00118 bool XVHandler::write(const QImage &image)
00119 {
00120     QIODevice& f = *( device() );
00121 
00122     // Removed "f.open(...)" and "f.close()" (tanghus)
00123 
00124     int w = image.width(), h = image.height();
00125 
00126     char str[ 1024 ];
00127 
00128     // magic number must be "P7 332"
00129     f.write( "P7 332\n", 7 );
00130 
00131     // next line #XVVERSION
00132     f.write( "#XVVERSION:\n", 12 );
00133 
00134     // now it gets interesting, #BUILTIN means we are out.
00135     // if IMGINFO comes, we are happy!
00136     f.write( "#IMGINFO:\n", 10 );
00137 
00138     // after this an #END_OF_COMMENTS signals everything to be ok!
00139     f.write( "#END_OF_COMMENTS:\n", 18 );
00140 
00141     // now a last line with width, height, maxval which is supposed to be 255
00142     sprintf( str, "%i %i 255\n", w, h );
00143     f.write( str, strlen( str ) );
00144 
00145 
00146     QImage tmpImage( image );
00147     if ( image.depth() == 1 )
00148         tmpImage = image.convertToFormat( QImage::Format_Indexed8, Qt::AutoColor );
00149 
00150     uchar* buffer = new uchar[ w ];
00151 
00152     for ( int py = 0; py < h; py++ )
00153     {
00154         const uchar *data = tmpImage.scanLine( py );
00155         for ( int px = 0; px < w; px++ )
00156         {
00157             int r, g, b;
00158             if ( tmpImage.depth() == 32 )
00159             {
00160                 const QRgb *data32 = (QRgb*) data;
00161                 r = qRed( *data32 ) >> 5;
00162                 g = qGreen( *data32 ) >> 5;
00163                 b = qBlue( *data32 ) >> 6;
00164                 data += sizeof( QRgb );
00165             }
00166             else
00167             {
00168                 QRgb color = tmpImage.color( *data );
00169                 r = qRed( color ) >> 5;
00170                 g = qGreen( color ) >> 5;
00171                 b = qBlue( color ) >> 6;
00172                 data++;
00173             }
00174             buffer[ px ] = ( r << 5 ) | ( g << 2 ) | b;
00175         }
00176         f.write( (const char*)buffer, w );
00177     }
00178     delete[] buffer;
00179 
00180     return true;
00181 }
00182 
00183 QByteArray XVHandler::name() const
00184 {
00185     return "xv";
00186 }
00187 
00188 bool XVHandler::canRead(QIODevice *device)
00189 {
00190      if (!device) {
00191         qWarning("XVHandler::canRead() called with no device");
00192         return false;
00193     }
00194 
00195     qint64 oldPos = device->pos();
00196 
00197     char head[6];
00198     qint64 readBytes = device->read(head, sizeof(head));
00199     if (readBytes != sizeof(head)) {
00200         if (device->isSequential()) {
00201             while (readBytes > 0)
00202                 device->ungetChar(head[readBytes-- - 1]);
00203         } else {
00204             device->seek(oldPos);
00205         }
00206         return false;
00207     }
00208 
00209     if (device->isSequential()) {
00210         while (readBytes > 0)
00211             device->ungetChar(head[readBytes-- - 1]);
00212     } else {
00213         device->seek(oldPos);
00214     }
00215 
00216     return qstrncmp(head, "P7 332", 6) == 0;
00217 }
00218 
00219 
00220 class XVPlugin : public QImageIOPlugin
00221 {
00222 public:
00223     QStringList keys() const;
00224     Capabilities capabilities(QIODevice *device, const QByteArray &format) const;
00225     QImageIOHandler *create(QIODevice *device, const QByteArray &format = QByteArray()) const;
00226 };
00227 
00228 QStringList XVPlugin::keys() const
00229 {
00230     return QStringList() << "xv";
00231 }
00232 
00233 QImageIOPlugin::Capabilities XVPlugin::capabilities(QIODevice *device, const QByteArray &format) const
00234 {
00235     if (format == "xv")
00236         return Capabilities(CanRead | CanWrite);
00237     if (!format.isEmpty())
00238         return 0;
00239     if (!device->isOpen())
00240         return 0;
00241 
00242     Capabilities cap;
00243     if (device->isReadable() && XVHandler::canRead(device))
00244         cap |= CanRead;
00245     if (device->isWritable())
00246         cap |= CanWrite;
00247     return cap;
00248 }
00249 
00250 QImageIOHandler *XVPlugin::create(QIODevice *device, const QByteArray &format) const
00251 {
00252     QImageIOHandler *handler = new XVHandler;
00253     handler->setDevice(device);
00254     handler->setFormat(format);
00255     return handler;
00256 }
00257 
00258 Q_EXPORT_STATIC_PLUGIN(XVPlugin)
00259 Q_EXPORT_PLUGIN2(xv, XVPlugin)

KImgIO

Skip menu "KImgIO"
  • Main Page
  • Class Hierarchy
  • Alphabetical List
  • Class List
  • File List
  • Class Members
  • Related Pages

kdelibs

Skip menu "kdelibs"
  • DNSSD
  • Interfaces
  •   KHexEdit
  •   KMediaPlayer
  •   KSpeech
  •   KTextEditor
  • Kate
  • kconf_update
  • KDE3Support
  •   KUnitTest
  • KDECore
  • KDED
  • KDEsu
  • KDEUI
  • KDocTools
  • KFile
  • KHTML
  • KImgIO
  • KInit
  • kio
  • KIOSlave
  • KJS
  •   KJS-API
  •   WTF
  • kjsembed
  • KNewStuff
  • KParts
  • KPty
  • Kross
  • KUtils
  • Nepomuk
  • Plasma
  • Solid
  • Sonnet
  • ThreadWeaver
Generated for kdelibs by doxygen 1.6.1
This website is maintained by Adriaan de Groot and Allen Winter.
KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal