Warning, file /education/kalzium/src/kalziumgradienttype.cpp was not indexed or was modified since last indexation (in which case cross-reference links may be missing, inaccurate or erroneous).
0001 /* 0002 SPDX-FileCopyrightText: 2005, 2006 Pino Toscano <toscano.pino@tiscali.it> 0003 0004 SPDX-License-Identifier: GPL-2.0-or-later 0005 */ 0006 0007 #include "kalziumgradienttype.h" 0008 0009 #include "element.h" 0010 #include "kalziumdataobject.h" 0011 #include "prefs.h" 0012 0013 #include "kalzium_debug.h" 0014 #include <QVariant> 0015 0016 #include <KLocalizedString> 0017 #include <KUnitConversion/Converter> 0018 0019 #include <cmath> 0020 0021 KalziumGradientTypeFactory::KalziumGradientTypeFactory() 0022 { 0023 m_gradients << KalziumSOMGradientType::instance(); 0024 m_gradients << KalziumCovalentRadiusGradientType::instance(); 0025 m_gradients << KalziumVanDerWaalsRadiusGradientType::instance(); 0026 m_gradients << KalziumMassGradientType::instance(); 0027 m_gradients << KalziumBoilingPointGradientType::instance(); 0028 m_gradients << KalziumMeltingPointGradientType::instance(); 0029 m_gradients << KalziumElectronegativityGradientType::instance(); 0030 m_gradients << KalziumElectronaffinityGradientType::instance(); 0031 m_gradients << KalziumDiscoverydateGradientType::instance(); 0032 m_gradients << KalziumIonizationGradientType::instance(); 0033 } 0034 0035 KalziumGradientTypeFactory *KalziumGradientTypeFactory::instance() 0036 { 0037 static KalziumGradientTypeFactory kttf; 0038 return &kttf; 0039 } 0040 0041 KalziumGradientType *KalziumGradientTypeFactory::build(int id) const 0042 { 0043 if ((id < 0) || (id >= m_gradients.count())) 0044 return nullptr; 0045 0046 return m_gradients.at(id); 0047 } 0048 0049 KalziumGradientType *KalziumGradientTypeFactory::build(const QByteArray &id) const 0050 { 0051 for (int i = 0; i < m_gradients.count(); ++i) { 0052 if (m_gradients.at(i)->name() == id) { 0053 return m_gradients.at(i); 0054 } 0055 } 0056 0057 return nullptr; 0058 } 0059 0060 QStringList KalziumGradientTypeFactory::gradients() const 0061 { 0062 QStringList l; 0063 for (int i = 0; i < m_gradients.count(); ++i) { 0064 l << m_gradients.at(i)->description(); 0065 } 0066 return l; 0067 } 0068 0069 KalziumGradientType::KalziumGradientType() = default; 0070 0071 KalziumGradientType::~KalziumGradientType() = default; 0072 0073 KalziumGradientType *KalziumGradientType::instance() 0074 { 0075 return nullptr; 0076 } 0077 0078 double KalziumGradientType::elementCoeff(int el) const 0079 { 0080 double val = value(el); 0081 if (val == -1) { 0082 return val; 0083 } 0084 0085 if (logarithmicGradient()) { 0086 double minVal = minValue(); 0087 double maxVal = maxValue(); 0088 0089 // Fixing negative values for log calculation (no negative values allowed -> NaN) 0090 if (minVal < 0) { 0091 minVal = abs(minVal) + 1; // make sure it's bigger than 0 0092 maxVal += minVal; 0093 val += minVal; 0094 minVal = 0.01; 0095 } 0096 0097 double result = (log(val) - log(minVal)) / (log(maxVal) - log(minVal)); 0098 0099 // now we perform a "gamma-correction" on the result. Indeed, logarithmic gradients 0100 // often have the problem that all high values have roughly the same color. Note that 0101 // as firstColor() is not necessarily black and secondColor() is not necessarily white, 0102 // this is not exactly a "gamma-correction" in the usual sense. 0103 const double gamma = 1.4; 0104 result = exp(gamma * log(result)); 0105 return result; 0106 } else { 0107 return (val - minValue()) / (maxValue() - minValue()); 0108 } 0109 } 0110 0111 QColor KalziumGradientType::firstColor() const 0112 { 0113 return Prefs::minColor(); 0114 } 0115 0116 QColor KalziumGradientType::secondColor() const 0117 { 0118 return Prefs::maxColor(); 0119 } 0120 0121 QColor KalziumGradientType::notAvailableColor() const 0122 { 0123 return Qt::lightGray; 0124 } 0125 0126 QColor KalziumGradientType::calculateColor(const double coeff) const 0127 { 0128 if ((coeff < 0.0) || (coeff > 1.0)) 0129 return notAvailableColor(); 0130 0131 QColor color2 = secondColor(); 0132 QColor color1 = firstColor(); 0133 0134 int red = static_cast<int>((color2.red() - color1.red()) * coeff + color1.red()); 0135 int green = static_cast<int>((color2.green() - color1.green()) * coeff + color1.green()); 0136 int blue = static_cast<int>((color2.blue() - color1.blue()) * coeff + color1.blue()); 0137 0138 return {red, green, blue}; 0139 } 0140 0141 KalziumCovalentRadiusGradientType *KalziumCovalentRadiusGradientType::instance() 0142 { 0143 static KalziumCovalentRadiusGradientType kcrgt; 0144 return &kcrgt; 0145 } 0146 0147 KalziumCovalentRadiusGradientType::KalziumCovalentRadiusGradientType() 0148 : KalziumGradientType() 0149 { 0150 } 0151 0152 QByteArray KalziumCovalentRadiusGradientType::name() const 0153 { 0154 return "CovalentRadius"; 0155 } 0156 0157 QString KalziumCovalentRadiusGradientType::description() const 0158 { 0159 return i18n("Covalent Radius"); 0160 } 0161 0162 double KalziumCovalentRadiusGradientType::value(int el) const 0163 { 0164 QVariant v = KalziumDataObject::instance()->element(el)->dataAsVariant(ChemicalDataObject::radiusCovalent, Prefs::lengthUnit()); 0165 if (v.type() != QVariant::Double) 0166 return -1; 0167 return v.toDouble(); 0168 } 0169 0170 QString KalziumCovalentRadiusGradientType::unit() const 0171 { 0172 return KalziumDataObject::instance()->unitAsString(Prefs::lengthUnit()); 0173 } 0174 0175 int KalziumCovalentRadiusGradientType::decimals() const 0176 { 0177 return 2; 0178 } 0179 0180 double KalziumCovalentRadiusGradientType::minValue() const 0181 { 0182 KUnitConversion::Value minValue(0.32, KUnitConversion::Angstrom); 0183 return minValue.convertTo(KUnitConversion::UnitId(Prefs::lengthUnit())).number(); 0184 } 0185 0186 double KalziumCovalentRadiusGradientType::maxValue() const 0187 { 0188 KUnitConversion::Value minValue(2.25, KUnitConversion::Angstrom); 0189 return minValue.convertTo(KUnitConversion::UnitId(Prefs::lengthUnit())).number(); 0190 } 0191 0192 bool KalziumCovalentRadiusGradientType::logarithmicGradient() const 0193 { 0194 return Prefs::logarithmicCovalentRadiusGradient(); 0195 } 0196 0197 KalziumVanDerWaalsRadiusGradientType *KalziumVanDerWaalsRadiusGradientType::instance() 0198 { 0199 static KalziumVanDerWaalsRadiusGradientType kvdwrgt; 0200 return &kvdwrgt; 0201 } 0202 0203 KalziumVanDerWaalsRadiusGradientType::KalziumVanDerWaalsRadiusGradientType() 0204 : KalziumGradientType() 0205 { 0206 } 0207 0208 QByteArray KalziumVanDerWaalsRadiusGradientType::name() const 0209 { 0210 return "KalziumVanDerWaalsRadiusGradientType"; 0211 } 0212 0213 QString KalziumVanDerWaalsRadiusGradientType::description() const 0214 { 0215 return i18n("Van Der Waals"); 0216 } 0217 0218 double KalziumVanDerWaalsRadiusGradientType::value(int el) const 0219 { 0220 QVariant v = KalziumDataObject::instance()->element(el)->dataAsVariant(ChemicalDataObject::radiusVDW, Prefs::lengthUnit()); 0221 if (v.type() != QVariant::Double) 0222 return -1; 0223 return v.toDouble(); 0224 } 0225 0226 QString KalziumVanDerWaalsRadiusGradientType::unit() const 0227 { 0228 return KalziumDataObject::instance()->unitAsString(Prefs::lengthUnit()); 0229 } 0230 0231 int KalziumVanDerWaalsRadiusGradientType::decimals() const 0232 { 0233 return 1; 0234 } 0235 0236 double KalziumVanDerWaalsRadiusGradientType::minValue() const 0237 { 0238 KUnitConversion::Value minValue(1.2, KUnitConversion::Angstrom); 0239 return minValue.convertTo(KUnitConversion::UnitId(Prefs::lengthUnit())).number(); 0240 } 0241 0242 double KalziumVanDerWaalsRadiusGradientType::maxValue() const 0243 { 0244 KUnitConversion::Value minValue(3.0, KUnitConversion::Angstrom); 0245 return minValue.convertTo(KUnitConversion::UnitId(Prefs::lengthUnit())).number(); 0246 } 0247 0248 bool KalziumVanDerWaalsRadiusGradientType::logarithmicGradient() const 0249 { 0250 return Prefs::logarithmicVanDerWaalsRadiusGradient(); 0251 } 0252 0253 KalziumMassGradientType *KalziumMassGradientType::instance() 0254 { 0255 static KalziumMassGradientType kargt; 0256 return &kargt; 0257 } 0258 0259 KalziumMassGradientType::KalziumMassGradientType() 0260 : KalziumGradientType() 0261 { 0262 } 0263 0264 QByteArray KalziumMassGradientType::name() const 0265 { 0266 return "AtomicMass"; 0267 } 0268 0269 QString KalziumMassGradientType::description() const 0270 { 0271 return i18n("Atomic Mass"); 0272 } 0273 0274 double KalziumMassGradientType::value(int el) const 0275 { 0276 QVariant v = KalziumDataObject::instance()->element(el)->dataAsVariant(ChemicalDataObject::mass); 0277 if (v.type() != QVariant::Double) 0278 return -1; 0279 return v.toDouble(); 0280 } 0281 0282 QString KalziumMassGradientType::unit() const 0283 { 0284 return i18n("u"); 0285 } 0286 0287 int KalziumMassGradientType::decimals() const 0288 { 0289 return 5; 0290 } 0291 0292 double KalziumMassGradientType::minValue() const 0293 { 0294 return 1.00794; 0295 } 0296 0297 double KalziumMassGradientType::maxValue() const 0298 { 0299 return 294.0; 0300 } 0301 0302 bool KalziumMassGradientType::logarithmicGradient() const 0303 { 0304 return Prefs::logarithmicMassGradient(); 0305 } 0306 0307 KalziumBoilingPointGradientType *KalziumBoilingPointGradientType::instance() 0308 { 0309 static KalziumBoilingPointGradientType kbpgt; 0310 return &kbpgt; 0311 } 0312 0313 KalziumBoilingPointGradientType::KalziumBoilingPointGradientType() 0314 : KalziumGradientType() 0315 { 0316 } 0317 0318 QByteArray KalziumBoilingPointGradientType::name() const 0319 { 0320 return "BoilingPoint"; 0321 } 0322 0323 QString KalziumBoilingPointGradientType::description() const 0324 { 0325 return i18n("Boiling Point"); 0326 } 0327 0328 double KalziumBoilingPointGradientType::value(int el) const 0329 { 0330 QVariant v = KalziumDataObject::instance()->element(el)->dataAsVariant(ChemicalDataObject::boilingpoint, Prefs::temperatureUnit()); 0331 if (v.type() != QVariant::Double) 0332 return -1; 0333 return v.toDouble(); 0334 } 0335 0336 QString KalziumBoilingPointGradientType::unit() const 0337 { 0338 return KalziumDataObject::instance()->unitAsString(Prefs::temperatureUnit()); 0339 } 0340 0341 int KalziumBoilingPointGradientType::decimals() const 0342 { 0343 return 3; 0344 } 0345 0346 double KalziumBoilingPointGradientType::minValue() const 0347 { 0348 KUnitConversion::Value minValue(4.216, KUnitConversion::Kelvin); 0349 return minValue.convertTo(KUnitConversion::UnitId(Prefs::temperatureUnit())).number(); 0350 } 0351 0352 double KalziumBoilingPointGradientType::maxValue() const 0353 { 0354 KUnitConversion::Value minValue(5870.0, KUnitConversion::Kelvin); 0355 return minValue.convertTo(KUnitConversion::UnitId(Prefs::temperatureUnit())).number(); 0356 } 0357 0358 bool KalziumBoilingPointGradientType::logarithmicGradient() const 0359 { 0360 return Prefs::logarithmicBoilingPointGradient(); 0361 } 0362 0363 KalziumMeltingPointGradientType *KalziumMeltingPointGradientType::instance() 0364 { 0365 static KalziumMeltingPointGradientType kmpgt; 0366 return &kmpgt; 0367 } 0368 0369 KalziumMeltingPointGradientType::KalziumMeltingPointGradientType() 0370 : KalziumGradientType() 0371 { 0372 } 0373 0374 QByteArray KalziumMeltingPointGradientType::name() const 0375 { 0376 return "MeltingPoint"; 0377 } 0378 0379 QString KalziumMeltingPointGradientType::description() const 0380 { 0381 return i18n("Melting Point"); 0382 } 0383 0384 double KalziumMeltingPointGradientType::value(int el) const 0385 { 0386 QVariant v = KalziumDataObject::instance()->element(el)->dataAsVariant(ChemicalDataObject::meltingpoint, Prefs::temperatureUnit()); 0387 if (v.type() != QVariant::Double) 0388 return -1; 0389 return v.toDouble(); 0390 } 0391 0392 QString KalziumMeltingPointGradientType::unit() const 0393 { 0394 return KalziumDataObject::instance()->unitAsString(Prefs::temperatureUnit()); 0395 } 0396 0397 int KalziumMeltingPointGradientType::decimals() const 0398 { 0399 return 2; 0400 } 0401 0402 double KalziumMeltingPointGradientType::minValue() const 0403 { 0404 KUnitConversion::Value minValue(0.94, KUnitConversion::Kelvin); 0405 return minValue.convertTo(KUnitConversion::UnitId(Prefs::temperatureUnit())).number(); 0406 } 0407 0408 double KalziumMeltingPointGradientType::maxValue() const 0409 { 0410 KUnitConversion::Value minValue(3825.0, KUnitConversion::Kelvin); 0411 return minValue.convertTo(KUnitConversion::UnitId(Prefs::temperatureUnit())).number(); 0412 } 0413 0414 bool KalziumMeltingPointGradientType::logarithmicGradient() const 0415 { 0416 return Prefs::logarithmicMeltingPointGradient(); 0417 } 0418 0419 KalziumSOMGradientType *KalziumSOMGradientType::instance() 0420 { 0421 static KalziumSOMGradientType kargt; 0422 return &kargt; 0423 } 0424 0425 KalziumSOMGradientType::KalziumSOMGradientType() 0426 : KalziumGradientType() 0427 { 0428 } 0429 0430 QByteArray KalziumSOMGradientType::name() const 0431 { 0432 return "SOM"; 0433 } 0434 0435 QString KalziumSOMGradientType::description() const 0436 { 0437 return i18n("State of matter"); 0438 } 0439 0440 double KalziumSOMGradientType::value(int el) const 0441 { 0442 Q_UNUSED(el); 0443 return -1000; 0444 } 0445 0446 QString KalziumSOMGradientType::unit() const 0447 { 0448 return KalziumDataObject::instance()->unitAsString(Prefs::temperatureUnit()); 0449 ; 0450 } 0451 0452 int KalziumSOMGradientType::decimals() const 0453 { 0454 return 2; 0455 } 0456 0457 double KalziumSOMGradientType::minValue() const 0458 { 0459 KUnitConversion::Value minValue(0.94, KUnitConversion::Kelvin); 0460 return minValue.convertTo(KUnitConversion::UnitId(Prefs::temperatureUnit())).number(); 0461 } 0462 0463 double KalziumSOMGradientType::maxValue() const 0464 { 0465 KUnitConversion::Value minValue(5870.0, KUnitConversion::Kelvin); 0466 return minValue.convertTo(KUnitConversion::UnitId(Prefs::temperatureUnit())).number(); 0467 } 0468 0469 bool KalziumSOMGradientType::logarithmicGradient() const 0470 { 0471 return true; 0472 // return Prefs::logarithmicSOMGradient(); 0473 } 0474 0475 KalziumElectronegativityGradientType *KalziumElectronegativityGradientType::instance() 0476 { 0477 static KalziumElectronegativityGradientType kegt; 0478 return &kegt; 0479 } 0480 0481 KalziumElectronegativityGradientType::KalziumElectronegativityGradientType() 0482 : KalziumGradientType() 0483 { 0484 } 0485 0486 QByteArray KalziumElectronegativityGradientType::name() const 0487 { 0488 return "Electronegativity"; 0489 } 0490 0491 QString KalziumElectronegativityGradientType::description() const 0492 { 0493 return i18n("Electronegativity (Pauling)"); 0494 } 0495 0496 double KalziumElectronegativityGradientType::value(int el) const 0497 { 0498 QVariant v = KalziumDataObject::instance()->element(el)->dataAsVariant(ChemicalDataObject::electronegativityPauling); 0499 if (v.type() != QVariant::Double) 0500 return -1; 0501 return v.toDouble(); 0502 } 0503 0504 QString KalziumElectronegativityGradientType::unit() const 0505 { 0506 return {}; 0507 } 0508 0509 int KalziumElectronaffinityGradientType::decimals() const 0510 { 0511 return 2; 0512 } 0513 0514 double KalziumElectronegativityGradientType::minValue() const 0515 { 0516 return 0.7; 0517 } 0518 0519 double KalziumElectronegativityGradientType::maxValue() const 0520 { 0521 return 3.98; 0522 } 0523 0524 bool KalziumElectronegativityGradientType::logarithmicGradient() const 0525 { 0526 return Prefs::logarithmicElectronegativityGradient(); 0527 } 0528 0529 /// DISCOVERYDATE/// 0530 0531 KalziumDiscoverydateGradientType *KalziumDiscoverydateGradientType::instance() 0532 { 0533 static KalziumDiscoverydateGradientType kegt; 0534 return &kegt; 0535 } 0536 0537 KalziumDiscoverydateGradientType::KalziumDiscoverydateGradientType() 0538 : KalziumGradientType() 0539 { 0540 } 0541 0542 QByteArray KalziumDiscoverydateGradientType::name() const 0543 { 0544 return "Discoverydate"; 0545 } 0546 0547 QString KalziumDiscoverydateGradientType::description() const 0548 { 0549 return i18n("Discovery date"); 0550 } 0551 0552 double KalziumDiscoverydateGradientType::value(int el) const 0553 { 0554 QVariant v = KalziumDataObject::instance()->element(el)->dataAsVariant(ChemicalDataObject::date); 0555 if (v.value<int>() == 0) 0556 return -1; 0557 return v.toDouble(); 0558 } 0559 0560 QString KalziumDiscoverydateGradientType::unit() const 0561 { 0562 return {}; 0563 } 0564 0565 int KalziumDiscoverydateGradientType::decimals() const 0566 { 0567 return 0; 0568 } 0569 0570 double KalziumDiscoverydateGradientType::minValue() const 0571 { 0572 return 1669.0; 0573 } 0574 0575 double KalziumDiscoverydateGradientType::maxValue() const 0576 { 0577 return QDate::currentDate().year(); 0578 } 0579 0580 bool KalziumDiscoverydateGradientType::logarithmicGradient() const 0581 { 0582 return Prefs::logarithmicDiscoverydateGradient(); 0583 } 0584 0585 /// ELECTRONAFFINITY/// 0586 0587 KalziumElectronaffinityGradientType *KalziumElectronaffinityGradientType::instance() 0588 { 0589 static KalziumElectronaffinityGradientType kegt; 0590 return &kegt; 0591 } 0592 0593 KalziumElectronaffinityGradientType::KalziumElectronaffinityGradientType() 0594 : KalziumGradientType() 0595 { 0596 } 0597 0598 QByteArray KalziumElectronaffinityGradientType::name() const 0599 { 0600 return "Electronaffinity"; 0601 } 0602 0603 QString KalziumElectronaffinityGradientType::description() const 0604 { 0605 return i18n("Electronaffinity"); 0606 } 0607 0608 double KalziumElectronaffinityGradientType::value(int el) const 0609 { 0610 QVariant v = KalziumDataObject::instance()->element(el)->dataAsVariant(ChemicalDataObject::electronAffinity, Prefs::energiesUnit()); 0611 return v.toDouble(); 0612 } 0613 0614 QString KalziumElectronaffinityGradientType::unit() const 0615 { 0616 return KalziumDataObject::instance()->unitAsString(Prefs::energiesUnit()); 0617 } 0618 0619 int KalziumElectronegativityGradientType::decimals() const 0620 { 0621 return 2; 0622 } 0623 0624 double KalziumElectronaffinityGradientType::minValue() const 0625 { 0626 KUnitConversion::Value minValue(-0.07, KUnitConversion::Electronvolt); 0627 return minValue.convertTo(KUnitConversion::UnitId(Prefs::energiesUnit())).number(); 0628 } 0629 0630 double KalziumElectronaffinityGradientType::maxValue() const 0631 { 0632 KUnitConversion::Value minValue(3.7, KUnitConversion::Electronvolt); 0633 return minValue.convertTo(KUnitConversion::UnitId(Prefs::energiesUnit())).number(); 0634 } 0635 0636 bool KalziumElectronaffinityGradientType::logarithmicGradient() const 0637 { 0638 return Prefs::logarithmicElectronaffinityGradient(); 0639 } 0640 0641 /// FIRST IONIZATINO/// 0642 0643 KalziumIonizationGradientType *KalziumIonizationGradientType::instance() 0644 { 0645 static KalziumIonizationGradientType kegt; 0646 return &kegt; 0647 } 0648 0649 KalziumIonizationGradientType::KalziumIonizationGradientType() 0650 : KalziumGradientType() 0651 { 0652 } 0653 0654 QByteArray KalziumIonizationGradientType::name() const 0655 { 0656 return "Ionization"; 0657 } 0658 0659 QString KalziumIonizationGradientType::description() const 0660 { 0661 return i18n("First Ionization"); 0662 } 0663 0664 double KalziumIonizationGradientType::value(int el) const 0665 { 0666 QVariant v = KalziumDataObject::instance()->element(el)->dataAsVariant(ChemicalDataObject::ionization, Prefs::energiesUnit()); 0667 return v.toDouble(); 0668 } 0669 0670 QString KalziumIonizationGradientType::unit() const 0671 { 0672 return KalziumDataObject::instance()->unitAsString(Prefs::energiesUnit()); 0673 } 0674 0675 int KalziumIonizationGradientType::decimals() const 0676 { 0677 return 2; 0678 } 0679 0680 double KalziumIonizationGradientType::minValue() const 0681 { 0682 KUnitConversion::Value minValue(3.89, KUnitConversion::Electronvolt); 0683 return minValue.convertTo(KUnitConversion::UnitId(Prefs::energiesUnit())).number(); 0684 } 0685 0686 double KalziumIonizationGradientType::maxValue() const 0687 { 0688 KUnitConversion::Value minValue(25.0, KUnitConversion::Electronvolt); 0689 return minValue.convertTo(KUnitConversion::UnitId(Prefs::energiesUnit())).number(); 0690 } 0691 0692 bool KalziumIonizationGradientType::logarithmicGradient() const 0693 { 0694 return Prefs::logarithmicIonizationGradient(); 0695 }