krita

kis_adjustment_layer.cc

00001 /*
00002  *  Copyright (c) 2002 Patrick Julien <freak@codepimps.org>
00003  *  Copyright (c) 2005 Casper Boemann <cbr@boemann.dk>
00004  *
00005  *  this program is free software; you can redistribute it and/or modify
00006  *  it under the terms of the gnu general public license as published by
00007  *  the free software foundation; either version 2 of the license, or
00008  *  (at your option) any later version.
00009  *
00010  *  this program is distributed in the hope that it will be useful,
00011  *  but without any warranty; without even the implied warranty of
00012  *  merchantability or fitness for a particular purpose.  see the
00013  *  gnu general public license for more details.
00014  *
00015  *  you should have received a copy of the gnu general public license
00016  *  along with this program; if not, write to the free software
00017  *  foundation, inc., 675 mass ave, cambridge, ma 02139, usa.
00018  */
00019 
00020 #include <kdebug.h>
00021 #include <qimage.h>
00022 
00023 #include "kis_debug_areas.h"
00024 #include "kis_group_layer.h"
00025 #include "kis_image.h"
00026 #include "kis_layer.h"
00027 #include "kis_adjustment_layer.h"
00028 #include "kis_painter.h"
00029 #include "kis_undo_adapter.h"
00030 #include "kis_selection.h"
00031 #include "kis_fill_painter.h"
00032 
00033 KisAdjustmentLayer::KisAdjustmentLayer(KisImageSP img, const QString &name, KisFilterConfiguration * kfc, KisSelectionSP selection)
00034     : KisLayer (img, name, OPACITY_OPAQUE)
00035 {
00036     m_filterConfig = kfc;
00037     setSelection( selection );
00038     m_cachedPaintDev = new KisPaintDevice( img->colorSpace(), name.latin1());
00039     m_showSelection = true;
00040     Q_ASSERT(m_cachedPaintDev);
00041     connect(img, SIGNAL(sigSelectionChanged(KisImageSP)),
00042             this, SLOT(slotSelectionChanged(KisImageSP)));
00043 }
00044 
00045 KisAdjustmentLayer::KisAdjustmentLayer(const KisAdjustmentLayer& rhs)
00046     : KisLayer(rhs), KisLayerSupportsIndirectPainting(rhs)
00047 {
00048     m_filterConfig = new KisFilterConfiguration(*rhs.m_filterConfig);
00049     if (rhs.m_selection) {
00050         m_selection = new KisSelection( *rhs.m_selection.data() );
00051         m_selection->setParentLayer(this);
00052         m_selection->setInterestedInDirtyness(true);
00053         if (!m_selection->hasSelection())
00054             m_selection->setSelection(m_selection);
00055         connect(rhs.image(), SIGNAL(sigSelectionChanged(KisImageSP)),
00056                 this, SLOT(slotSelectionChanged(KisImageSP)));
00057     }
00058     m_cachedPaintDev = new KisPaintDevice( *rhs.m_cachedPaintDev.data() );
00059     m_showSelection = false;
00060 }
00061 
00062 
00063 KisAdjustmentLayer::~KisAdjustmentLayer()
00064 {
00065     delete m_filterConfig;
00066 }
00067 
00068 
00069 KisLayerSP KisAdjustmentLayer::clone() const
00070 {
00071     return new KisAdjustmentLayer(*this);
00072 }
00073 
00074 
00075 void KisAdjustmentLayer::resetCache()
00076 {
00077     m_cachedPaintDev = new KisPaintDevice(image()->colorSpace(), name().latin1());
00078 }
00079 
00080 KisFilterConfiguration * KisAdjustmentLayer::filter()
00081 {
00082     Q_ASSERT(m_filterConfig);
00083     return m_filterConfig;
00084 }
00085 
00086 
00087 void KisAdjustmentLayer::setFilter(KisFilterConfiguration * filterConfig)
00088 {
00089     Q_ASSERT(filterConfig);
00090     m_filterConfig = filterConfig;
00091 }
00092 
00093 
00094 KisSelectionSP KisAdjustmentLayer::selection()
00095 {
00096     return m_selection;
00097 }
00098 
00099 void KisAdjustmentLayer::setSelection(KisSelectionSP selection)
00100 {
00101     m_selection = new KisSelection();
00102     KisFillPainter gc(m_selection.data());
00103     KisColorSpace * cs = KisMetaRegistry::instance()->csRegistry()->getRGB8();
00104 
00105     if (selection) {
00106         gc.bitBlt(0, 0, COMPOSITE_COPY, selection.data(),
00107                   0, 0, image()->bounds().width(), image()->bounds().height());
00108     } else {
00109         gc.fillRect(image()->bounds(), KisColor(Qt::white, cs), MAX_SELECTED);
00110     }
00111 
00112     gc.end();
00113 
00114     m_selection->setParentLayer(this);
00115     m_selection->setInterestedInDirtyness(true);
00116 
00117     if (!m_selection->hasSelection())
00118         m_selection->setSelection(m_selection);
00119 }
00120 
00121 
00122 Q_INT32 KisAdjustmentLayer::x() const
00123 {
00124     if (m_selection)
00125         return m_selection->getX();
00126     else
00127         return 0;
00128 }
00129 
00130 void KisAdjustmentLayer::setX(Q_INT32 x)
00131 {
00132     if (m_selection) {
00133         m_selection->setX(x);
00134         resetCache();
00135     }
00136 
00137 }
00138 
00139 Q_INT32 KisAdjustmentLayer::y() const
00140 {
00141     if (m_selection)
00142         return m_selection->getY();
00143     else
00144         return 0;
00145 }
00146 
00147 void KisAdjustmentLayer::setY(Q_INT32 y)
00148 {
00149     if (m_selection) {
00150         m_selection->setY(y);
00151         resetCache();
00152     }
00153 }
00154 
00155 QRect KisAdjustmentLayer::extent() const
00156 {
00157     if (m_selection)
00158         return m_selection->selectedRect();
00159     else if (image())
00160         return image()->bounds();
00161     else
00162         return QRect();
00163 }
00164 
00165 QRect KisAdjustmentLayer::exactBounds() const
00166 {
00167     if (m_selection)
00168         return m_selection->selectedRect();
00169     else if (image())
00170         return image()->bounds();
00171     else
00172         return QRect();
00173 }
00174 
00175 bool KisAdjustmentLayer::accept(KisLayerVisitor & v)
00176 {
00177     return v.visit( this );
00178 }
00179 
00180 void KisAdjustmentLayer::paintSelection(QImage &img, Q_INT32 x, Q_INT32 y, Q_INT32 w, Q_INT32 h)
00181 {
00182     if (showSelection() && selection())
00183         selection()->paintSelection(img, x, y, w, h);
00184 }
00185 
00186 void KisAdjustmentLayer::paintSelection(QImage &img, const QRect& scaledImageRect, const QSize& scaledImageSize, const QSize& imageSize)
00187 {
00188     if (showSelection() && selection())
00189         selection()->paintSelection(img, scaledImageRect, scaledImageSize, imageSize);
00190 }
00191 
00192 QImage KisAdjustmentLayer::createThumbnail(Q_INT32 w, Q_INT32 h)
00193 {
00194     if (!selection())
00195         return QImage();
00196 
00197     int srcw, srch;
00198     if( image() )
00199     {
00200         srcw = image()->width();
00201         srch = image()->height();
00202     }
00203     else
00204     {
00205         const QRect e = extent();
00206         srcw = e.width();
00207         srch = e.height();
00208     }
00209 
00210     if (w > srcw)
00211     {
00212         w = srcw;
00213         h = Q_INT32(double(srcw) / w * h);
00214     }
00215     if (h > srch)
00216     {
00217         h = srch;
00218         w = Q_INT32(double(srch) / h * w);
00219     }
00220 
00221     if (srcw > srch)
00222         h = Q_INT32(double(srch) / srcw * w);
00223     else if (srch > srcw)
00224         w = Q_INT32(double(srcw) / srch * h);
00225 
00226     QColor c;
00227     Q_UINT8 opacity;
00228     QImage img(w,h,32);
00229 
00230     for (Q_INT32 y=0; y < h; ++y) {
00231         Q_INT32 iY = (y * srch ) / h;
00232         for (Q_INT32 x=0; x < w; ++x) {
00233             Q_INT32 iX = (x * srcw ) / w;
00234             m_selection->pixel(iX, iY, &c, &opacity);
00235             img.setPixel(x, y, qRgb(opacity, opacity, opacity));
00236         }
00237     }
00238 
00239     return img;
00240 }
00241 
00242 void KisAdjustmentLayer::slotSelectionChanged(KisImageSP image) {
00243     image->setModified();
00244 }
00245 
00246 #include "kis_adjustment_layer.moc"
KDE Home | KDE Accessibility Home | Description of Access Keys