/* * This file is part of Chalk * * Copyright (c) 2006 Frederic Coiffier * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ // C++ includes. #include #include // TQt includes. #include #include #include #include // Local includes. #include "kgradientslider.h" KGradientSlider::KGradientSlider(TQWidget *tqparent, const char *name, WFlags f) : TQWidget(tqparent, name, f) { m_dragging = false; setMouseTracking(true); setPaletteBackgroundColor(TQt::NoBackground); setMaximumSize(255, 28); m_blackcursor = 0; m_whitecursor = 255; m_gamma = 1.0; m_gammaEnabled = false; setFocusPolicy(TQ_StrongFocus); } KGradientSlider::~KGradientSlider() { } void KGradientSlider::paintEvent(TQPaintEvent *) { int x, y; int wWidth = width(); int wHeight = height(); int gradientHeight = (wHeight / 3); // A TQPixmap is used for enable the double buffering. /*if (!m_dragging) {*/ TQPixmap pm(size()); TQPainter p1; p1.tqbegin(TQT_TQPAINTDEVICE(&pm), this); pm.fill(); // Draw first gradient y = 0; p1.setPen(TQPen::TQPen(TQColor(0,0,0),1, TQt::SolidLine)); for( x=0; x<255; ++x ) { int gray = (255 * x) / wWidth; p1.setPen(TQColor(gray, gray, gray)); p1.drawLine(x, y, x, y + gradientHeight - 1); } // Draw second gradient y = (wHeight / 3); if (m_blackcursor > 0) { p1.fillRect(0, y, (int)m_blackcursor, gradientHeight, TQBrush(TQt::black)); } if (m_whitecursor < 255) { p1.fillRect((int)m_whitecursor, y, 255, gradientHeight, TQBrush(TQt::white)); } for(x = (int)m_blackcursor; x < (int)m_whitecursor; ++x ) { double inten = (double)(x - m_blackcursor) / (double)(m_whitecursor - m_blackcursor); inten = pow (inten, (1.0 / m_gamma)); int gray = (int)(255 * inten); p1.setPen(TQColor(gray, gray, gray)); p1.drawLine(x, y, x, y + gradientHeight - 1); } // Draw cursors y = (2 * wHeight / 3); TQPointArray *a = new TQPointArray(3); p1.setPen(TQt::black); a->setPoint(0, m_blackcursor, y); a->setPoint(1, m_blackcursor + 3, wHeight - 1); a->setPoint(2, m_blackcursor - 3, wHeight - 1); p1.setBrush(TQt::black); p1.drawPolygon(*a); if (m_gammaEnabled) { a->setPoint(0, m_gammacursor, y); a->setPoint(1, m_gammacursor + 3, wHeight - 1); a->setPoint(2, m_gammacursor - 3, wHeight - 1); p1.setBrush(TQt::gray); p1.drawPolygon(*a); } a->setPoint(0, m_whitecursor, y); a->setPoint(1, m_whitecursor + 3, wHeight - 1); a->setPoint(2, m_whitecursor - 3, wHeight - 1); p1.setBrush(TQt::white); p1.drawPolygon(*a); p1.end(); bitBlt(this, 0, 0, &pm); } void KGradientSlider::mousePressEvent ( TQMouseEvent * e ) { eCursor closest_cursor; int distance; if (e->button() != Qt::LeftButton) return; unsigned int x = e->pos().x(); distance = 1000; // just a big number if (abs((int)(x - m_blackcursor)) < distance) { distance = abs((int)(x - m_blackcursor)); closest_cursor = BlackCursor; } if (abs((int)(x - m_whitecursor)) < distance) { distance = abs((int)(x - m_whitecursor)); closest_cursor = WhiteCursor; } if (m_gammaEnabled && (abs((int)(x - m_gammacursor)) < distance)) { distance = abs((int)(x - m_gammacursor)); closest_cursor = GammaCursor; } if (distance > 20) { return; } m_dragging = true; // Determine cursor values and the leftmost and rightmost points. switch (closest_cursor) { case BlackCursor: m_blackcursor = x; m_grab_cursor = closest_cursor; m_leftmost = 0; m_rightmost = m_whitecursor; if (m_gammaEnabled) { double delta = (double) (m_whitecursor - m_blackcursor) / 2.0; double mid = (double)m_blackcursor + delta; double tmp = log10 (1.0 / m_gamma); m_gammacursor = (unsigned int)tqRound(mid + delta * tmp); } break; case WhiteCursor: m_whitecursor = x; m_grab_cursor = closest_cursor; m_leftmost = m_blackcursor; m_rightmost = 255; if (m_gammaEnabled) { double delta = (double) (m_whitecursor - m_blackcursor) / 2.0; double mid = (double)m_blackcursor + delta; double tmp = log10 (1.0 / m_gamma); m_gammacursor = (unsigned int)tqRound(mid + delta * tmp); } break; case GammaCursor: m_gammacursor = x; m_grab_cursor = closest_cursor; m_leftmost = m_blackcursor; m_rightmost = m_whitecursor; double delta = (double) (m_whitecursor - m_blackcursor) / 2.0; double mid = (double)m_blackcursor + delta; double tmp = (x - mid) / delta; m_gamma = 1.0 / pow (10, tmp); break; } tqrepaint(false); } void KGradientSlider::mouseReleaseEvent ( TQMouseEvent * e ) { if (e->button() != Qt::LeftButton) return; m_dragging = false; tqrepaint(false); switch (m_grab_cursor) { case BlackCursor: emit modifiedBlack(m_blackcursor); break; case WhiteCursor: emit modifiedWhite(m_whitecursor); break; case GammaCursor: emit modifiedGamma(m_gamma); break; } } void KGradientSlider::mouseMoveEvent ( TQMouseEvent * e ) { unsigned int x = abs(e->pos().x()); if (m_dragging == true) // Else, drag the selected point { if (x <= m_leftmost) x = m_leftmost; if(x >= m_rightmost) x = m_rightmost; /*if(x > 255) x = 255; if(x < 0) x = 0;*/ switch (m_grab_cursor) { case BlackCursor: if (m_blackcursor != x) { m_blackcursor = x; if (m_gammaEnabled) { double delta = (double) (m_whitecursor - m_blackcursor) / 2.0; double mid = (double)m_blackcursor + delta; double tmp = log10 (1.0 / m_gamma); m_gammacursor = (unsigned int)tqRound(mid + delta * tmp); } } break; case WhiteCursor: if (m_whitecursor != x) { m_whitecursor = x; if (m_gammaEnabled) { double delta = (double) (m_whitecursor - m_blackcursor) / 2.0; double mid = (double)m_blackcursor + delta; double tmp = log10 (1.0 / m_gamma); m_gammacursor = (unsigned int)tqRound(mid + delta * tmp); } } break; case GammaCursor: if (m_gammacursor != x) { m_gammacursor = x; double delta = (double) (m_whitecursor - m_blackcursor) / 2.0; double mid = (double)m_blackcursor + delta; double tmp = (x - mid) / delta; m_gamma = 1.0 / pow (10, tmp); } break; } } tqrepaint(false); } void KGradientSlider::leaveEvent( TQEvent * ) { } void KGradientSlider::enableGamma(bool b) { m_gammaEnabled = b; tqrepaint(false); } double KGradientSlider::getGamma(void) { return m_gamma; } void KGradientSlider::modifyBlack(int v) { if (v >= 0 && v <= (int)m_whitecursor) { m_blackcursor = (unsigned int)v; if (m_gammaEnabled) { double delta = (double) (m_whitecursor - m_blackcursor) / 2.0; double mid = (double)m_blackcursor + delta; double tmp = log10 (1.0 / m_gamma); m_gammacursor = (unsigned int)tqRound(mid + delta * tmp); } tqrepaint(false); } } void KGradientSlider::modifyWhite(int v) { if (v >= (int)m_blackcursor && v <= 255) { m_whitecursor = (unsigned int)v; if (m_gammaEnabled) { double delta = (double) (m_whitecursor - m_blackcursor) / 2.0; double mid = (double)m_blackcursor + delta; double tmp = log10 (1.0 / m_gamma); m_gammacursor = (unsigned int)tqRound(mid + delta * tmp); } tqrepaint(false); } } void KGradientSlider::modifyGamma(double v) { m_gamma = v; double delta = (double) (m_whitecursor - m_blackcursor) / 2.0; double mid = (double)m_blackcursor + delta; double tmp = log10 (1.0 / m_gamma); m_gammacursor = (unsigned int)tqRound(mid + delta * tmp); tqrepaint(false); } #include "kgradientslider.moc"