comparison widgets/IconLoader.cpp @ 957:4b5efd76a55c scalable-icons

Experiment with loading SVGs
author Chris Cannam
date Wed, 06 May 2015 10:08:28 +0100
parents e4773943c9c1
children 85b39667e9cf
comparison
equal deleted inserted replaced
947:e53a87a5efb2 957:4b5efd76a55c
17 17
18 #include <QPixmap> 18 #include <QPixmap>
19 #include <QApplication> 19 #include <QApplication>
20 #include <QPainter> 20 #include <QPainter>
21 #include <QPalette> 21 #include <QPalette>
22 #include <QFile>
23 #include <QSvgRenderer>
22 24
23 static const char *autoInvertExceptions[] = { 25 #include <vector>
26 #include <set>
27
28 #include "base/Debug.h"
29
30 using namespace std;
31
32 static set<QString> autoInvertExceptions {
24 // These are the icons that look OK in their default colours, even 33 // These are the icons that look OK in their default colours, even
25 // in a colour scheme with a black background. (They may also be 34 // in a colour scheme with a black background. (They may also be
26 // icons that would look worse if we tried to auto-invert them.) 35 // icons that would look worse if we tried to auto-invert them.)
27 // If we have icons that look bad when auto-inverted but that are 36 // If we have icons that look bad when auto-inverted but that are
28 // not suitable for use without being inverted, we'll need to 37 // not suitable for use without being inverted, we'll need to
29 // supply inverted versions -- the loader will load xx_inverse.png 38 // supply inverted versions -- the loader will load xx_inverse.png
30 // in preference to xx.png if a dark background is found.) 39 // in preference to xx.png if a dark background is found.)
31 "fileclose", 40 "fileclose",
32 "filenew-22",
33 "filenew", 41 "filenew",
34 "fileopen-22",
35 "fileopen", 42 "fileopen",
36 "fileopenaudio", 43 "fileopenaudio",
37 "fileopensession", 44 "fileopensession",
38 "filesave-22",
39 "filesave", 45 "filesave",
40 "filesaveas-22",
41 "filesaveas", 46 "filesaveas",
47 "filesaveas-sv",
42 "help", 48 "help",
43 "editcut", 49 "editcut",
44 "editcopy", 50 "editcopy",
45 "editpaste", 51 "editpaste",
46 "editdelete", 52 "editdelete",
49 "zoom-in", 55 "zoom-in",
50 "zoom-out", 56 "zoom-out",
51 "zoom" 57 "zoom"
52 }; 58 };
53 59
60 static vector<int> sizes { 0, 16, 22, 24, 32, 48, 64, 128 };
61
54 QIcon 62 QIcon
55 IconLoader::load(QString name) 63 IconLoader::load(QString name)
56 { 64 {
57 QPixmap pmap(loadPixmap(name)); 65 QIcon icon;
58 if (pmap.isNull()) return QIcon(); 66 for (int sz: sizes) {
59 else return QIcon(pmap); 67 QPixmap pmap(loadPixmap(name, sz));
68 if (!pmap.isNull()) icon.addPixmap(pmap);
69 }
70 return icon;
71 }
72
73 bool
74 IconLoader::shouldInvert() const
75 {
76 QColor bg = QApplication::palette().window().color();
77 bool darkBackground = (bg.red() + bg.green() + bg.blue() <= 384);
78 return darkBackground;
79 }
80
81 bool
82 IconLoader::shouldAutoInvert(QString name) const
83 {
84 if (shouldInvert()) {
85 return (autoInvertExceptions.find(name) == autoInvertExceptions.end());
86 } else {
87 return false;
88 }
60 } 89 }
61 90
62 QPixmap 91 QPixmap
63 IconLoader::loadPixmap(QString name) 92 IconLoader::loadPixmap(QString name, int size)
64 { 93 {
65 QColor bg = QApplication::palette().window().color(); 94 bool invert = shouldInvert();
66 if (bg.red() + bg.green() + bg.blue() > 384) { // light background 95 /*
67 QPixmap pmap(QString(":icons/%1").arg(name)); 96 QString nonScalableName = makeNonScalableFilename(name, size, invert);
68 if (pmap.isNull()) { 97 QPixmap pmap(nonScalableName);
69 pmap = QPixmap(QString(":icons/%1.png").arg(name)); 98 if (!pmap.isNull()) return pmap;
99 */
100 QString scalableName = makeScalableFilename(name, invert);
101 QPixmap pmap = loadScalable(scalableName, size);
102 if (!pmap.isNull()) return pmap;
103 /*
104 if (invert && shouldAutoInvert(name)) {
105
106 nonScalableName = makeNonScalableFilename(name, size, false);
107 pmap = QPixmap(nonScalableName);
108 if (!pmap.isNull()) return invertPixmap(pmap);
109
110 scalableName = makeScalableFilename(name, false);
111 pmap = loadScalable(scalableName, size);
112 if (!pmap.isNull()) return invertPixmap(pmap);
113 }
114 */
115 return QPixmap();
116 }
117
118 QPixmap
119 IconLoader::loadScalable(QString name, int size)
120 {
121 if (!QFile(name).exists()) {
122 cerr << "loadScalable: no such file as: \"" << name << "\"" << endl;
123 return QPixmap();
124 }
125 QPixmap pmap(size, size);
126 pmap.fill(Qt::transparent);
127 QPainter painter(&pmap);
128 QSvgRenderer renderer(name);
129 renderer.render(&painter);
130 return pmap;
131 }
132
133 QString
134 IconLoader::makeNonScalableFilename(QString name, int size, bool invert)
135 {
136 if (invert) {
137 if (size == 0) {
138 return QString(":icons/%1_inverse.png").arg(name);
139 } else {
140 return QString(":icons/%1-%2_inverse.png").arg(name).arg(size);
70 } 141 }
71 return pmap; 142 } else {
72 } 143 if (size == 0) {
73 144 return QString(":icons/%1.png").arg(name);
74 QPixmap pmap(QString(":icons/%1").arg(name)); 145 } else {
75 if (pmap.isNull()) { 146 return QString(":icons/%1-%2.png").arg(name).arg(size);
76 pmap = QPixmap(QString(":icons/%1_inverse.png").arg(name));
77 if (pmap.isNull()) {
78 pmap = QPixmap(QString(":icons/%1.png").arg(name));
79 } 147 }
80 } 148 }
81 if (pmap.isNull()) return pmap; 149 }
82 150
83 for (int i = 0; i < int(sizeof(autoInvertExceptions)/ 151 QString
84 sizeof(autoInvertExceptions[0])); ++i) { 152 IconLoader::makeScalableFilename(QString name, bool invert)
85 if (autoInvertExceptions[i] == name) { 153 {
86 return pmap; 154 if (invert) {
87 } 155 return QString(":icons/scalable/%1_inverse.svg").arg(name);
156 } else {
157 return QString(":icons/scalable/%1.svg").arg(name);
88 } 158 }
159 }
89 160
161 QPixmap
162 IconLoader::invertPixmap(QPixmap pmap)
163 {
90 // No suitable inverted icon found for black background; try to 164 // No suitable inverted icon found for black background; try to
91 // auto-invert the default one 165 // auto-invert the default one
92 166
93 QImage img = pmap.toImage().convertToFormat(QImage::Format_ARGB32); 167 QImage img = pmap.toImage().convertToFormat(QImage::Format_ARGB32);
94 168