Commit afc8658b authored by Wolthera van Hövell's avatar Wolthera van Hövell 🛍

Merge branch 'master' into krita-testing-wolthera

parents 27d4034e 91bdcfe3
......@@ -83,12 +83,12 @@ endif()
# define common versions of Krita applications, used to generate kritaversion.h
# update these version for every release:
set(KRITA_VERSION_STRING "3.0.1 Beta")
set(KRITA_VERSION_STRING "3.0.2 Alpha")
set(KRITA_STABLE_VERSION_MAJOR 3) # 3 for 3.x, 4 for 4.x, etc.
set(KRITA_STABLE_VERSION_MINOR 0) # 0 for 3.0, 1 for 3.1, etc.
set(KRITA_VERSION_RELEASE 90) # 89 for Alpha, increase for next test releases, set 0 for first Stable, etc.
#set(KRITA_ALPHA 1) # uncomment only for Alpha
set(KRITA_BETA 1) # uncomment only for Beta
set(KRITA_VERSION_RELEASE 2) # 89 for Alpha, increase for next test releases, set 0 for first Stable, etc.
set(KRITA_ALPHA 1) # uncomment only for Alpha
#set(KRITA_BETA 1) # uncomment only for Beta
#set(KRITA_RC 1) # uncomment only for RC
set(KRITA_YEAR 2016) # update every year
......
......@@ -2,7 +2,7 @@
<kpartgui xmlns="http://www.kde.org/standards/kxmlgui/1.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
name="Krita"
version="94"
version="95"
xsi:schemaLocation="http://www.kde.org/standards/kxmlgui/1.0 http://www.kde.org/standards/kxmlgui/1.0/kxmlgui.xsd">
<MenuBar>
<Menu name="file" noMerge="1">
......
......@@ -284,6 +284,27 @@ void KisPaintOpSettings::setSavedBrushSize(qreal value)
setPropertyNotSaved("SavedBrushSize");
}
qreal KisPaintOpSettings::savedEraserOpacity() const
{
return getDouble("SavedEraserOpacity", 0.0);
}
void KisPaintOpSettings::setSavedEraserOpacity(qreal value)
{
setProperty("SavedEraserOpacity", value);
setPropertyNotSaved("SavedEraserOpacity");
}
qreal KisPaintOpSettings::savedBrushOpacity() const
{
return getDouble("SavedBrushOpacity", 0.0);
}
void KisPaintOpSettings::setSavedBrushOpacity(qreal value)
{
setProperty("SavedBrushOpacity", value);
setPropertyNotSaved("SavedBrushOpacity");
}
QString KisPaintOpSettings::modelName() const
{
......
......@@ -208,6 +208,11 @@ public:
qreal savedBrushSize() const;
void setSavedBrushSize(qreal value);
qreal savedEraserOpacity() const;
void setSavedEraserOpacity(qreal value);
qreal savedBrushOpacity() const;
void setSavedBrushOpacity(qreal value);
QString effectivePaintOpCompositeOp() const;
void setPreset(KisPaintOpPresetWSP preset);
......
......@@ -153,12 +153,12 @@ public:
double yres = 1.0;
const KoColorSpace * colorSpace;
KisProofingConfiguration *proofingConfig = 0;
KisProofingConfigurationSP proofingConfig;
KisSelectionSP deselectedGlobalSelection;
KisGroupLayerSP rootLayer; // The layers are contained in here
QList<KisLayer*> dirtyLayers; // for thumbnails
QList<KisLayerComposition*> compositions;
QList<KisLayerCompositionSP> compositions;
KisNodeSP isolatedRootNode;
bool wrapAroundModePermitted = false;
......@@ -1481,20 +1481,19 @@ void KisImage::requestTimeSwitch(int time)
m_d->animationInterface->requestTimeSwitchNonGUI(time);
}
QList<KisLayerComposition*> KisImage::compositions()
QList<KisLayerCompositionSP> KisImage::compositions()
{
return m_d->compositions;
}
void KisImage::addComposition(KisLayerComposition* composition)
void KisImage::addComposition(KisLayerCompositionSP composition)
{
m_d->compositions.append(composition);
}
void KisImage::removeComposition(KisLayerComposition* composition)
void KisImage::removeComposition(KisLayerCompositionSP composition)
{
m_d->compositions.removeAll(composition);
delete composition;
}
bool checkMasksNeedConversion(KisNodeSP root, const QRect &bounds)
......@@ -1604,13 +1603,13 @@ KisImageAnimationInterface* KisImage::animationInterface() const
return m_d->animationInterface;
}
void KisImage::setProofingConfiguration(KisProofingConfiguration *proofingConfig)
void KisImage::setProofingConfiguration(KisProofingConfigurationSP proofingConfig)
{
m_d->proofingConfig = proofingConfig;
emit sigProofingConfigChanged();
}
KisProofingConfiguration *KisImage::proofingConfiguration() const
KisProofingConfigurationSP KisImage::proofingConfiguration() const
{
if (!m_d->proofingConfig) {
KisImageConfig cfg;
......
......@@ -480,17 +480,17 @@ public:
/**
* Returns the layer compositions for the image
*/
QList<KisLayerComposition*> compositions();
QList<KisLayerCompositionSP> compositions();
/**
* Adds a new layer composition, will be saved with the image
*/
void addComposition(KisLayerComposition* composition);
void addComposition(KisLayerCompositionSP composition);
/**
* Remove the layer compostion
*/
void removeComposition(KisLayerComposition* composition);
void removeComposition(KisLayerCompositionSP composition);
/**
* Permit or deny the wrap-around mode for all the paint devices
......@@ -568,12 +568,12 @@ public:
* the proofingConfiguration has changed.
* @param proofingConfig - the kis proofing config that will be used instead.
*/
void setProofingConfiguration(KisProofingConfiguration *proofingConfig);
void setProofingConfiguration(KisProofingConfigurationSP proofingConfig);
/**
* @brief proofingConfiguration
* @return the proofing configuration of the image.
*/
KisProofingConfiguration *proofingConfiguration() const;
KisProofingConfigurationSP proofingConfiguration() const;
public:
bool startIsolatedMode(KisNodeSP node);
......
......@@ -398,7 +398,7 @@ void KisImageConfig::setShowAdditionalOnionSkinsSettings(bool value)
m_config.writeEntry("showAdditionalOnionSkinsSettings", value);
}
KisProofingConfiguration *KisImageConfig::defaultProofingconfiguration()
KisProofingConfigurationSP KisImageConfig::defaultProofingconfiguration()
{
KisProofingConfiguration *proofingConfig= new KisProofingConfiguration();
proofingConfig->proofingProfile = m_config.readEntry("defaultProofingProfileName", "Chemical proof");
......@@ -417,7 +417,7 @@ KisProofingConfiguration *KisImageConfig::defaultProofingconfiguration()
col.setOpacity(1.0);
proofingConfig->warningColor = col;
proofingConfig->adaptationState = (double)m_config.readEntry("defaultProofingAdaptationState", 1.0);
return proofingConfig;
return toQShared(proofingConfig);
}
void KisImageConfig::setDefaultProofingConfig(const KoColorSpace *proofingSpace, int proofingIntent, bool blackPointCompensation, KoColor warningColor, double adaptationState)
......
......@@ -22,7 +22,7 @@
#include <kconfiggroup.h>
#include "kritaimage_export.h"
#include "KisProofingConfiguration.h"
#include "kis_types.h"
class KRITAIMAGE_EXPORT KisImageConfig
{
......@@ -102,7 +102,7 @@ public:
bool showAdditionalOnionSkinsSettings(bool requestDefault = false) const;
void setShowAdditionalOnionSkinsSettings(bool value);
KisProofingConfiguration *defaultProofingconfiguration();
KisProofingConfigurationSP defaultProofingconfiguration();
void setDefaultProofingConfig(const KoColorSpace *proofingSpace, int proofingIntent, bool blackPointCompensation, KoColor warningColor, double adaptationState);
......
......@@ -265,6 +265,15 @@ class KisKeyframe;
typedef QSharedPointer<KisKeyframe> KisKeyframeSP;
typedef QWeakPointer<KisKeyframe> KisKeyframeWSP;
class KisProofingConfiguration;
typedef QSharedPointer<KisProofingConfiguration> KisProofingConfigurationSP;
typedef QWeakPointer<KisProofingConfiguration> KisProofingConfigurationWSP;
class KisLayerComposition;
typedef QSharedPointer<KisLayerComposition> KisLayerCompositionSP;
typedef QWeakPointer<KisLayerComposition> KisLayerCompositionWSP;
#include <QSharedPointer>
#include <QWeakPointer>
#include <kis_shared_ptr.h>
......
......@@ -55,6 +55,7 @@ struct Q_DECL_HIDDEN KisUpdateScheduler::Private {
KisSimpleUpdateQueue updatesQueue;
KisStrokesQueue strokesQueue;
KisUpdaterContext updaterContext;
bool processingBlocked = false;
qreal balancingRatio = 1.0; // updates-queue-size/strokes-queue-size
KisProjectionUpdateListener *projectionUpdateListener;
......@@ -63,11 +64,6 @@ struct Q_DECL_HIDDEN KisUpdateScheduler::Private {
QAtomicInt updatesLockCounter;
QReadWriteLock updatesStartLock;
KisLazyWaitCondition updatesFinishedCondition;
// KisUpdaterContext can emit signals to KisUpdateScheduler in the dtor, so it
// must to be deleted before anything else.
// That means updaterContext must be declared last.
KisUpdaterContext updaterContext;
};
KisUpdateScheduler::KisUpdateScheduler(KisProjectionUpdateListener *projectionUpdateListener)
......@@ -167,11 +163,9 @@ void KisUpdateScheduler::fullRefresh(KisNodeSP root, const QRect& rc, const QRec
Q_ASSERT(m_d->updaterContext.isJobAllowed(walker));
m_d->updaterContext.addMergeJob(walker);
m_d->updaterContext.unlock();
m_d->updaterContext.waitForDone();
m_d->updaterContext.unlock();
if(needLock) unlock(true);
}
......@@ -414,9 +408,7 @@ bool KisUpdateScheduler::haveUpdatesRunning()
QWriteLocker locker(&m_d->updatesStartLock);
qint32 numMergeJobs, numStrokeJobs;
m_d->updaterContext.lock();
m_d->updaterContext.getJobsSnapshot(numMergeJobs, numStrokeJobs);
m_d->updaterContext.unlock();
return numMergeJobs;
}
......
......@@ -21,14 +21,18 @@
#include <QThread>
#include <QThreadPool>
#include "kis_safe_read_list.h"
#include "kis_update_job_item.h"
#include "kis_stroke_job.h"
KisUpdaterContext::KisUpdaterContext(qint32 threadCount):
m_jobs(threadCount > 0 ? threadCount : defaultThreadCount())
KisUpdaterContext::KisUpdaterContext(qint32 threadCount)
{
if(threadCount <= 0) {
threadCount = QThread::idealThreadCount();
threadCount = threadCount > 0 ? threadCount : 1;
}
m_jobs.resize(threadCount);
for(qint32 i = 0; i < m_jobs.size(); i++) {
m_jobs[i] = new KisUpdateJobItem(&m_exclusiveJobLock);
connect(m_jobs[i], SIGNAL(sigContinueUpdate(const QRect&)),
......@@ -41,10 +45,6 @@ KisUpdaterContext::KisUpdaterContext(qint32 threadCount):
connect(m_jobs[i], SIGNAL(sigJobFinished()),
SLOT(slotJobFinished()), Qt::DirectConnection);
}
#ifdef SANITY_CHECK_CONTEXT_LOCKING
m_lockedBy = (Qt::HANDLE) -1;
#endif
}
KisUpdaterContext::~KisUpdaterContext()
......@@ -54,19 +54,9 @@ KisUpdaterContext::~KisUpdaterContext()
delete m_jobs[i];
}
qint32 KisUpdaterContext::defaultThreadCount() const
{
int threadCount = QThread::idealThreadCount();
return threadCount > 0 ? threadCount : 1;
}
void KisUpdaterContext::getJobsSnapshot(qint32 &numMergeJobs,
qint32 &numStrokeJobs)
{
#ifdef SANITY_CHECK_CONTEXT_LOCKING
KIS_ASSERT(m_lockedBy == QThread::currentThreadId());
#endif
numMergeJobs = 0;
numStrokeJobs = 0;
......@@ -101,10 +91,6 @@ bool KisUpdaterContext::hasSpareThread()
bool KisUpdaterContext::isJobAllowed(KisBaseRectsWalkerSP walker)
{
#ifdef SANITY_CHECK_CONTEXT_LOCKING
KIS_ASSERT(m_lockedBy == QThread::currentThreadId());
#endif
int lod = this->currentLevelOfDetail();
if (lod >= 0 && walker->levelOfDetail() != lod) return false;
......@@ -130,13 +116,9 @@ bool KisUpdaterContext::isJobAllowed(KisBaseRectsWalkerSP walker)
*/
void KisUpdaterContext::addMergeJob(KisBaseRectsWalkerSP walker)
{
#ifdef SANITY_CHECK_CONTEXT_LOCKING
KIS_ASSERT(m_lockedBy == QThread::currentThreadId());
#endif
m_lodCounter.addLod(walker->levelOfDetail());
qint32 jobIndex = findSpareThread();
KIS_ASSERT(jobIndex >= 0);
Q_ASSERT(jobIndex >= 0);
m_jobs[jobIndex]->setWalker(walker);
m_threadPool.start(m_jobs[jobIndex]);
......@@ -147,13 +129,9 @@ void KisUpdaterContext::addMergeJob(KisBaseRectsWalkerSP walker)
*/
void KisTestableUpdaterContext::addMergeJob(KisBaseRectsWalkerSP walker)
{
#ifdef SANITY_CHECK_CONTEXT_LOCKING
KIS_ASSERT(m_lockedBy == QThread::currentThreadId());
#endif
m_lodCounter.addLod(walker->levelOfDetail());
qint32 jobIndex = findSpareThread();
KIS_ASSERT(jobIndex >= 0);
Q_ASSERT(jobIndex >= 0);
m_jobs[jobIndex]->setWalker(walker);
// HINT: Not calling start() here
......@@ -161,13 +139,9 @@ void KisTestableUpdaterContext::addMergeJob(KisBaseRectsWalkerSP walker)
void KisUpdaterContext::addStrokeJob(KisStrokeJob *strokeJob)
{
#ifdef SANITY_CHECK_CONTEXT_LOCKING
KIS_ASSERT(m_lockedBy == QThread::currentThreadId());
#endif
m_lodCounter.addLod(strokeJob->levelOfDetail());
qint32 jobIndex = findSpareThread();
KIS_ASSERT(jobIndex >= 0);
Q_ASSERT(jobIndex >= 0);
m_jobs[jobIndex]->setStrokeJob(strokeJob);
m_threadPool.start(m_jobs[jobIndex]);
......@@ -178,13 +152,9 @@ void KisUpdaterContext::addStrokeJob(KisStrokeJob *strokeJob)
*/
void KisTestableUpdaterContext::addStrokeJob(KisStrokeJob *strokeJob)
{
#ifdef SANITY_CHECK_CONTEXT_LOCKING
KIS_ASSERT(m_lockedBy == QThread::currentThreadId());
#endif
m_lodCounter.addLod(strokeJob->levelOfDetail());
qint32 jobIndex = findSpareThread();
KIS_ASSERT(jobIndex >= 0);
Q_ASSERT(jobIndex >= 0);
m_jobs[jobIndex]->setStrokeJob(strokeJob);
// HINT: Not calling start() here
......@@ -192,13 +162,9 @@ void KisTestableUpdaterContext::addStrokeJob(KisStrokeJob *strokeJob)
void KisUpdaterContext::addSpontaneousJob(KisSpontaneousJob *spontaneousJob)
{
#ifdef SANITY_CHECK_CONTEXT_LOCKING
KIS_ASSERT(m_lockedBy == QThread::currentThreadId());
#endif
m_lodCounter.addLod(spontaneousJob->levelOfDetail());
qint32 jobIndex = findSpareThread();
KIS_ASSERT(jobIndex >= 0);
Q_ASSERT(jobIndex >= 0);
m_jobs[jobIndex]->setSpontaneousJob(spontaneousJob);
m_threadPool.start(m_jobs[jobIndex]);
......@@ -211,7 +177,7 @@ void KisTestableUpdaterContext::addSpontaneousJob(KisSpontaneousJob *spontaneous
{
m_lodCounter.addLod(spontaneousJob->levelOfDetail());
qint32 jobIndex = findSpareThread();
KIS_ASSERT(jobIndex >= 0);
Q_ASSERT(jobIndex >= 0);
m_jobs[jobIndex]->setSpontaneousJob(spontaneousJob);
// HINT: Not calling start() here
......@@ -219,35 +185,7 @@ void KisTestableUpdaterContext::addSpontaneousJob(KisSpontaneousJob *spontaneous
void KisUpdaterContext::waitForDone()
{
lock();
while(true) {
bool allDone = true;
QVector<KisUpdateJobItem*>::const_iterator iter;
FOREACH_SAFE(iter, m_jobs) {
if ((*iter)->isRunning()) {
allDone = false;
break;
}
}
if (!allDone) {
#ifdef SANITY_CHECK_CONTEXT_LOCKING
m_lockedBy = (Qt::HANDLE) -1;
#endif
m_waitAllCond.wait(&m_lock);
#ifdef SANITY_CHECK_CONTEXT_LOCKING
m_lockedBy = QThread::currentThreadId();
#endif
} else {
break;
}
}
unlock();
m_threadPool.waitForDone();
}
bool KisUpdaterContext::walkerIntersectsJob(KisBaseRectsWalkerSP walker,
......@@ -270,7 +208,6 @@ void KisUpdaterContext::slotJobFinished()
{
m_lodCounter.removeLod();
m_waitAllCond.wakeOne();
// Be careful. This slot can be called asynchronously without locks.
emit sigSpareThreadAppeared();
}
......@@ -278,22 +215,10 @@ void KisUpdaterContext::slotJobFinished()
void KisUpdaterContext::lock()
{
m_lock.lock();
#ifdef SANITY_CHECK_CONTEXT_LOCKING
KIS_ASSERT_X(m_lockedBy == (Qt::HANDLE) -1, "KisUpdaterContext",
"context is already locked");
m_lockedBy = QThread::currentThreadId();
#endif
}
void KisUpdaterContext::unlock()
{
#ifdef SANITY_CHECK_CONTEXT_LOCKING
KIS_ASSERT(m_lockedBy == QThread::currentThreadId());
m_lockedBy = (Qt::HANDLE) -1;
#endif
m_lock.unlock();
}
......
......@@ -23,16 +23,11 @@
#include <QMutex>
#include <QReadWriteLock>
#include <QThreadPool>
#include <QWaitCondition>
#include "kis_base_rects_walker.h"
#include "kis_async_merger.h"
#include "kis_lock_free_lod_counter.h"
// TODO: uncomment ifndef for release on 3.0.1
// #ifndef QT_NO_DEBUG
#define SANITY_CHECK_CONTEXT_LOCKING
// #endif // QT_NO_DEBUG
class KisUpdateJobItem;
class KisSpontaneousJob;
......@@ -133,9 +128,6 @@ protected Q_SLOTS:
protected:
static bool walkerIntersectsJob(KisBaseRectsWalkerSP walker,
const KisUpdateJobItem* job);
qint32 defaultThreadCount() const;
qint32 findSpareThread();
protected:
......@@ -149,14 +141,8 @@ protected:
QMutex m_lock;
QVector<KisUpdateJobItem*> m_jobs;
QWaitCondition m_waitAllCond;
QThreadPool m_threadPool;
KisLockFreeLodCounter m_lodCounter;
#ifdef SANITY_CHECK_CONTEXT_LOCKING
// Thread ID of the owner or -1 if not locked
volatile Qt::HANDLE m_lockedBy;
#endif
};
class KRITAIMAGE_EXPORT KisTestableUpdaterContext : public KisUpdaterContext
......
......@@ -114,9 +114,7 @@ void KisStrokesQueueTest::testExclusiveStrokes()
KisTestableUpdaterContext context(2);
QVector<KisUpdateJobItem*> jobs;
context.lock();
context.addMergeJob(walker);
context.unlock();
queue.processQueue(context, false);
jobs = context.getJobs();
......@@ -141,9 +139,7 @@ void KisStrokesQueueTest::testExclusiveStrokes()
QCOMPARE(queue.needsExclusiveAccess(), true);
context.clear();
context.lock();
context.addMergeJob(walker);
context.unlock();
queue.processQueue(context, false);
COMPARE_WALKER(jobs[0], walker);
......@@ -205,9 +201,7 @@ void KisStrokesQueueTest::testBarrierStrokeJobs()
VERIFY_EMPTY(jobs[2]);
// Now some updates has come...
context.lock();
context.addMergeJob(walker);
context.unlock();
jobs = context.getJobs();
COMPARE_NAME(jobs[0], "nor_dab");
......@@ -245,9 +239,7 @@ void KisStrokesQueueTest::testBarrierStrokeJobs()
VERIFY_EMPTY(jobs[2]);
// Process the last update...
context.lock();
context.addMergeJob(walker);
context.unlock();
externalJobsPending = false;
// Yep, the queue is still waiting
......@@ -424,9 +416,7 @@ void KisStrokesQueueTest::testStrokesLevelOfDetail()
KisTestableUpdaterContext context(2);
QVector<KisUpdateJobItem*> jobs;
context.lock();
context.addMergeJob(walker);
context.unlock();
queue.processQueue(context, false);
jobs = context.getJobs();
......@@ -449,14 +439,10 @@ void KisStrokesQueueTest::testStrokesLevelOfDetail()
QCOMPARE(queue.needsExclusiveAccess(), false);
// walker of a different LOD must not be allowed
context.lock();
QCOMPARE(context.isJobAllowed(walker), false);
context.unlock();
context.clear();
context.lock();
context.addMergeJob(walker);
context.unlock();
queue.processQueue(context, false);
jobs = context.getJobs();
......
......@@ -223,9 +223,7 @@ void KisUpdaterContextTest::stressTestExclusiveJobs()
KisStrokeJobStrategy *strategy =
new ExclusivenessCheckerStrategy(counter, hadConcurrency);
context.lock();
context.addStrokeJob(new KisStrokeJob(strategy, data, 0, true));
context.unlock();
}
else {
QTest::qSleep(CHECK_DELAY);
......
......@@ -113,7 +113,7 @@ public:
QRect savedUpdateRect;
QBitArray channelFlags;
KisProofingConfiguration *proofingConfig = 0;
KisProofingConfigurationSP proofingConfig;
bool softProofing = false;
bool gamutCheck = false;
bool proofingConfigUpdated = false;
......@@ -605,7 +605,7 @@ bool KisCanvas2::proofingConfigUpdated()
return m_d->proofingConfigUpdated;
}
KisProofingConfiguration *KisCanvas2::proofingConfiguration() const
KisProofingConfigurationSP KisCanvas2::proofingConfiguration() const
{
if (!m_d->proofingConfig) {
m_d->proofingConfig = this->image()->proofingConfiguration();
......
......@@ -171,7 +171,7 @@ public: // KisCanvas2 methods
* set the options for softproofing, without affecting the proofing options as stored inside the image.
*/
void setProofingOptions(bool softProof, bool gamutCheck);
KisProofingConfiguration *proofingConfiguration() const;
KisProofingConfigurationSP proofingConfiguration() const;
/**
* @brief setProofingConfigUpdated This function is to set whether the proofing config is updated,
* this is needed for determining whether or not to generate a new proofing transform.
......
......@@ -56,7 +56,7 @@ private:
WdgImageProperties * m_page;
KisImageWSP m_image;
KisProofingConfiguration *m_proofingConfig;
KisProofingConfigurationSP m_proofingConfig;
};
......
......@@ -342,7 +342,7 @@ ColorSettingsTab::ColorSettingsTab(QWidget *parent, const char *name)
KisImageConfig cfgImage;
KisProofingConfiguration *proofingConfig = cfgImage.defaultProofingconfiguration();
KisProofingConfigurationSP proofingConfig = cfgImage.defaultProofingconfiguration();
m_page->sldAdaptationState->setMaximum(20);
m_page->sldAdaptationState->setMinimum(0);
m_page->sldAdaptationState->setValue((int)proofingConfig->adaptationState*20);
......@@ -443,7 +443,7 @@ void ColorSettingsTab::setDefault()
KisConfig cfg;
KisImageConfig cfgImage;
KisProofingConfiguration *proofingConfig = cfgImage.defaultProofingconfiguration();
KisProofingConfigurationSP proofingConfig = cfgImage.defaultProofingconfiguration();
const KoColorSpace *proofingSpace = KoColorSpaceRegistry::instance()->colorSpace(proofingConfig->proofingModel,proofingConfig->proofingDepth,proofingConfig->proofingProfile);
m_page->proofingSpaceSelector->setCurrentColorSpace(proofingSpace);
m_page->cmbProofingIntent->setCurrentIndex((int)proofingConfig->intent);
......
......@@ -258,14 +258,14 @@
<property name="text">
<string/>
</property>
<property name="color" stdset="0">
<property name="color">
<color>
<red>0</red>
<green>0</green>
<blue>0</blue>
</color>
</property>
<property name="defaultColor" stdset="0">
<property name="defaultColor">
<color>
<red>0</red>
<green>0</green>
......@@ -708,6 +708,11 @@
<extends>QPushButton</extends>
<header>kis_color_button.h</header>
</customwidget>
<customwidget>
<class>KisIntParseSpinBox</class>
<extends>QSpinBox</extends>
<header>kis_int_parse_spin_box.h</header>
</customwidget>
</customwidgets>
<resources/>
<connections/>
......
......@@ -275,6 +275,25 @@
</property>
</widget>
</item>
<item>
<widget class="QCheckBox" name="eraserBrushOpacityCheckBox">
<property name="sizePolicy">
<sizepolicy hsizetype="Minimum" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="toolTip">
<string>Erase mode will use a separate brush opacity</string>
</property>
<property name="text">
<string>Eraser switch opacity</string>
</property>
<property name="checked">
<bool>false</bool>
</property>
</widget>
</item>
<item>
<widget class="KisLodAvailabilityWidget" name="wdgLodAvailability" native="true">
<property name="minimumSize">
......
......@@ -357,6 +357,18 @@ void KisConfig::setUseEraserBrushSize(bool value)
KisConfigNotifier::instance()->notifyConfigChanged();
}
bool KisConfig::useEraserBrushOpacity(bool defaultValue) const
{
return (defaultValue ? false : m_cfg.readEntry("useEraserBrushOpacity",false));
}
void KisConfig::setUseEraserBrushOpacity(bool value)
{
m_cfg.writeEntry("useEraserBrushOpacity",value);
KisConfigNotifier::instance()->notifyConfigChanged();
}
QColor KisConfig::getMDIBackgroundColor(bool defaultValue) const
{
QColor col(77, 77, 77);
......
......@@ -436,6 +436,9 @@ public: