463 lines
11 KiB
C++
463 lines
11 KiB
C++
#include "utils.h"
|
|
#include <qpixmap.h>
|
|
#include <stdlib.h>
|
|
#include <sys/time.h>
|
|
#include <assert.h>
|
|
|
|
void SetEraseColor(QWidget *widget, QWidget *from, bool inclBgr) {
|
|
const QPixmap *p;
|
|
p = from->erasePixmap();
|
|
if (p) {
|
|
widget->setErasePixmap(*p);
|
|
if (inclBgr) {
|
|
widget->setPaletteBackgroundPixmap(*p);
|
|
}
|
|
} else {
|
|
widget->setEraseColor(from->eraseColor());
|
|
if (inclBgr) {
|
|
widget->setPaletteBackgroundColor(from->eraseColor());
|
|
}
|
|
}
|
|
}
|
|
|
|
FlatButton::FlatButton(const QString &label, QWidget *parent, const char *name)
|
|
: QLabel(label, parent, name) {
|
|
x = -1;
|
|
}
|
|
|
|
void FlatButton::mousePressEvent(QMouseEvent *e) {
|
|
x = e->x();
|
|
y = e->y();
|
|
mousePressed();
|
|
}
|
|
|
|
void FlatButton::mouseReleaseEvent(QMouseEvent *e) {
|
|
if (x >= 0 && abs(e->x() - x) + abs(e->y() - y) < 5) {
|
|
clicked();
|
|
}
|
|
x = -1;
|
|
}
|
|
|
|
void ShrinkButton(QPushButton *b) {
|
|
int margin;
|
|
QString text(b->text());
|
|
b->setText("This is a long text");
|
|
margin = b->sizeHint().width() - b->fontMetrics().width(b->text());
|
|
b->setText(text);
|
|
b->setFixedWidth(b->fontMetrics().width(text) + margin);
|
|
}
|
|
|
|
double DoubleTime(void)
|
|
{
|
|
struct timeval now;
|
|
/* the resolution of this function is usec, if the machine supports this
|
|
and the mantissa of a double is 51 bits or more (31 for sec and 20 for milliseconds)
|
|
*/
|
|
gettimeofday(&now, NULL);
|
|
return now.tv_sec + now.tv_usec / 1e6;
|
|
}
|
|
|
|
static char *coltab[N_SEACOLORS*2] = {
|
|
"X c #FFFFFF", "white",
|
|
"X c #FF0000", "red",
|
|
"X c #00FF00", "lime", // was green
|
|
"X c #0000FF", "blue",
|
|
"X c #FF00FF", "magenta", // fuchsia
|
|
"X c #FFFF00", "yellow",
|
|
"X c #00FFFF", "cyan", // aqua
|
|
"X c #000000", "black",
|
|
"X c #FFA500", "orange",
|
|
"X c #006400", "dark_green",
|
|
"X c #9400D3", "dark_violet",
|
|
"X c #A52A2A", "brown",
|
|
"X c #87CEEB", "sky_blue",
|
|
"X c #808080", "gray",
|
|
"X c #FF69B4", "hot_pink",
|
|
"X c #FFFFE0", "light_yellow",
|
|
"X c #00FF7F", "spring_green",
|
|
"X c #000080", "navy",
|
|
"X c #1E90FF", "dodger_blue",
|
|
"X c #9ACD32", "yellow_green",
|
|
"X c #008B8B", "dark_cyan",
|
|
"X c #808000", "olive",
|
|
"X c #DEB887", "burly_wood",
|
|
"X c #7B68EE", "medium_slate_blue",
|
|
"X c #483D8B", "dark_slate_blue",
|
|
"X c #98FB98", "pale_green",
|
|
"X c #FF1493", "deep_pink",
|
|
"X c #FF6347", "tomato",
|
|
"X c #32CD32", "lime_green",
|
|
"X c #DDA0DD", "plum",
|
|
"X c #7FFF00", "chartreuse",
|
|
"X c #800080", "purple",
|
|
"X c #00CED1", "dark_turquoise",
|
|
"X c #8FBC8F", "dark_sea_green",
|
|
"X c #4682B4", "steel_blue",
|
|
"X c #800000", "maroon",
|
|
"X c #3CB371", "medium_sea_green",
|
|
"X c #FF4500", "orange_red",
|
|
"X c #BA55D3", "medium_orchid",
|
|
"X c #2F4F4F", "dark_slate_gray",
|
|
"X c #CD853F", "peru",
|
|
"X c #228B22", "forest_green",
|
|
"X c #48D1CC", "medium_turquoise",
|
|
"X c #DC143C", "crimson",
|
|
"X c #D3D3D3", "light_gray",
|
|
"X c #ADFF2F", "green_yellow",
|
|
"X c #7FFFD4", "aquamarine",
|
|
"X c #BC8F8F", "rosy_brown",
|
|
"X c #20B2AA", "light_sea_green",
|
|
"X c #C71585", "medium_violet_red",
|
|
"X c #F0E68C", "khaki",
|
|
"X c #6495ED", "cornflower_blue",
|
|
"X c #556B2F", "dark_olive_green",
|
|
"X c #CD5C5C", "indian_red",
|
|
"X c #2E8B57", "sea_green",
|
|
"X c #F08080", "light_coral",
|
|
"X c #8A2BE2", "blue_violet",
|
|
"X c #AFEEEE", "pale_turquoise",
|
|
"X c #4169E1", "royal_blue",
|
|
"X c #0000CD", "medium_blue",
|
|
"X c #B8860B", "dark_goldenrod",
|
|
"X c #00BFFF", "deep_sky_blue",
|
|
"X c #FFC0CB", "pink",
|
|
"X c #4B0082", "indigo",
|
|
"X c #A0522D", "sienna",
|
|
"X c #FFD700", "gold",
|
|
"X c #F4A460", "sandy_brown",
|
|
"X c #DAA520", "goldenrod",
|
|
"X c #DA70D6", "orchid",
|
|
"X c #E6E6FA", "lavender",
|
|
"X c #5F9EA0", "cadet_blue",
|
|
"X c #D2691E", "chocolate",
|
|
"X c #66CDAA", "medium_aquamarine",
|
|
"X c #6B8E23", "olive_drab",
|
|
"X c #A9A9A9", "dark_gray",
|
|
"X c #BDB76B", "dark_khaki",
|
|
"X c #696969", "dim_gray",
|
|
"X c #B0C4DE", "light_steel_blue",
|
|
"X c #191970", "midnight_blue",
|
|
"X c #FFE4C4", "bisque",
|
|
"X c #6A5ACD", "slate_blue",
|
|
"X c #EE82EE", "violet",
|
|
"X c #8B4513", "saddle_brown",
|
|
"X c #FF7F50", "coral",
|
|
"X c #008000", "mid_green",
|
|
"X c #DB7093", "pale_violet_red",
|
|
"X c #C0C0C0", "silver",
|
|
"X c #E0FFFF", "light_cyan",
|
|
"X c #9370DB", "medium_purple",
|
|
"X c #FF8C00", "dark_orange",
|
|
"X c #00FA9A", "medium_spring_green",
|
|
"X c #E9967A", "dark_salmon",
|
|
"X c #778899", "light_slate_gray",
|
|
"X c #9932CC", "dark_orchid",
|
|
"X c #EEE8AA", "pale_goldenrod",
|
|
"X c #F8F8FF", "ghost_white",
|
|
"X c #FFA07A", "light_salmon",
|
|
"X c #ADD8E6", "light_blue",
|
|
"X c #D8BFD8", "thistle",
|
|
"X c #FFE4E1", "misty_rose",
|
|
"X c #FFDEAD", "navajo_white",
|
|
"X c #40E0D0", "turquoise",
|
|
"X c #90EE90", "light_green",
|
|
"X c #B22222", "fire_brick",
|
|
"X c #008080", "teal",
|
|
"X c #F0FFF0", "honeydew",
|
|
"X c #FFFACD", "lemon_chiffon",
|
|
"X c #FFF5EE", "seashell",
|
|
"X c #F5F5DC", "beige",
|
|
"X c #DCDCDC", "gainsboro",
|
|
"X c #FA8072", "salmon",
|
|
"X c #8B008B", "dark_magenta",
|
|
"X c #FFB6C1", "light_pink",
|
|
"X c #708090", "slate_gray",
|
|
"X c #87CEFA", "light_sky_blue",
|
|
"X c #FFEFD5", "papaya_whip",
|
|
"X c #D2B48C", "tan",
|
|
"X c #FFFFF0", "ivory",
|
|
"X c #F0FFFF", "azure",
|
|
"X c #F5DEB3", "wheat",
|
|
"X c #00008B", "dark_blue",
|
|
"X c #FFDAB9", "peach_puff",
|
|
"X c #8B0000", "dark_red",
|
|
"X c #FAF0E6", "linen",
|
|
"X c #B0E0E6", "powder_blue",
|
|
"X c #FFE4B5", "moccasin",
|
|
"X c #F5F5F5", "white_smoke",
|
|
"X c #FFF8DC", "cornsilk",
|
|
"X c #FFFAFA", "snow",
|
|
"X c #FFF0F5", "lavender_blush",
|
|
"X c #FFEBCD", "blanched_almond",
|
|
"X c #F0F8FF", "alice_blue",
|
|
"X c #FAEBD7", "antique_white",
|
|
"X c #FDF5E6", "old_lace",
|
|
"X c #FAFAD2", "light_goldenrod_yellow",
|
|
"X c #F5FFFA", "mint_cream",
|
|
"X c #FFFAF0", "floral_white",
|
|
"X c #7CFC00", "lawn_green"
|
|
};
|
|
|
|
static long seaColors[N_SEACOLORS]={0};
|
|
|
|
static void getRGB(long i, long &r, long &g, long &b) {
|
|
long code;
|
|
char *k;
|
|
|
|
if (i >= 0x1000000 && i < 0x2000000) {
|
|
code = i - 0x1000000;
|
|
} else {
|
|
if (i < 0 || i >= N_SEACOLORS) {
|
|
r = 0;
|
|
g = 0;
|
|
b = 0;
|
|
return;
|
|
}
|
|
if (seaColors[i] == 0) {
|
|
k = strchr(coltab[i*2], '#');
|
|
if (k) {
|
|
seaColors[i] = strtol(k+1, NULL, 16);
|
|
}
|
|
}
|
|
code = seaColors[i];
|
|
}
|
|
b = code % 256; code = code / 256;
|
|
g = code % 256; code = code / 256;
|
|
r = code % 256;
|
|
}
|
|
|
|
QPen thisPen(long i, int w) {
|
|
long r,g,b;
|
|
|
|
getRGB(i, r, g, b);
|
|
if (w == 0) {
|
|
w = (3 * r + 5 * g + b) / 460; /* make pen larger for bright colors, 0 <= w <= 4 */
|
|
if (w < 2) {
|
|
w = 2;
|
|
}
|
|
}
|
|
return QPen(QColor(r,g,b), w, Qt::SolidLine, Qt::FlatCap, Qt::BevelJoin);
|
|
};
|
|
|
|
static const char *miniPix[] = {
|
|
"1 1 1 1",
|
|
" c None",
|
|
" "
|
|
};
|
|
|
|
|
|
// the following routine is for a color widget
|
|
const QPixmap *thisPixmap(long i, int w) {
|
|
char *penpix[3+11];
|
|
long l, j, k;
|
|
|
|
if (i < 0) {
|
|
return new QPixmap(miniPix);
|
|
}
|
|
if (i >= N_SEACOLORS) {
|
|
return NULL;
|
|
}
|
|
l = thisPen(i, w).width();
|
|
if (l > 11) l = 11;
|
|
penpix[0] = "20 11 2 1";
|
|
penpix[1] = coltab[i*2];
|
|
penpix[2] = " c None";
|
|
k = (11 - l) / 2;
|
|
for (j = 0; j < k; j++) {
|
|
penpix[j+3] = " ";
|
|
}
|
|
for (j = k; j < k + l; j++) {
|
|
penpix[j+3] = "XXXXXXXXXXXXXXXXXXXX";
|
|
}
|
|
for (j = k + l; j < 11; j++) {
|
|
penpix[j+3] = " ";
|
|
}
|
|
return new QPixmap((const char **)penpix);
|
|
};
|
|
|
|
long Convert2ColorIndex(const QString &color) {
|
|
QString s=color.stripWhiteSpace();
|
|
long rgb;
|
|
bool ok;
|
|
long r,g,b,rr,gg,bb,d;
|
|
long dist;
|
|
long index;
|
|
long i;
|
|
const char *ccol;
|
|
|
|
if (s[0] == '#') { // hexadecimal color
|
|
s.remove(0,1);
|
|
rgb = s.toLong(&ok, 16);
|
|
if (!ok) {
|
|
return -2;
|
|
}
|
|
if (s.length() == 3) { // short form: find closest index
|
|
bb = rgb % 16 * 17; rgb = rgb / 16;
|
|
gg = rgb % 16 * 17; rgb = rgb / 16;
|
|
rr = rgb % 16 * 17;
|
|
dist = 9999999;
|
|
index = -2;
|
|
for (i = 0; i < N_SEACOLORS; i++) {
|
|
getRGB(i, r, g, b);
|
|
r -= rr;
|
|
g -= gg;
|
|
b -= bb;
|
|
d = 5*r*r + 8*g*g + 5*b*b;
|
|
if (d < dist) {
|
|
dist = d;
|
|
index = i;
|
|
}
|
|
}
|
|
} else if (s.length() == 6) { // long form: keep rgb code
|
|
index = 0x1000000 + rgb;
|
|
} else {
|
|
return -2;
|
|
}
|
|
return index;
|
|
}
|
|
index = s.toLong(&ok);
|
|
if (ok) { // color index
|
|
return index;
|
|
}
|
|
i = s.find("grey");
|
|
if (i >= 0) {
|
|
s.replace(i+2, 1, "a");
|
|
}
|
|
ccol = s.latin1();
|
|
if (strcasecmp(ccol, "auto") == 0) {
|
|
return -1;
|
|
}
|
|
for (i = 0; i < N_SEACOLORS; i++) {
|
|
if (strcasecmp(coltab[i*2+1], ccol) == 0) {
|
|
return i;
|
|
}
|
|
}
|
|
if (strcasecmp(ccol, "green") == 0) {
|
|
return 2;
|
|
}
|
|
if (strcasecmp(ccol, "fuchsia") == 0) {
|
|
return 4;
|
|
}
|
|
if (strcasecmp(ccol, "aqua") == 0) {
|
|
return 6;
|
|
}
|
|
return -2;
|
|
}
|
|
|
|
bool Convert2ColorName(long i, QString &result) {
|
|
if (i >= 0x1000000 && i < 0x2000000) {
|
|
result.sprintf("#%6.6lX", i - 0x1000000);
|
|
return true;
|
|
}
|
|
if (i < 0 || i >= N_SEACOLORS) {
|
|
result = "auto";
|
|
return false;
|
|
} else {
|
|
result = coltab[i*2+1];
|
|
return true;
|
|
}
|
|
}
|
|
|
|
QString toRichText(QString &txt, bool *finished) {
|
|
QString result("");
|
|
QChar ch;
|
|
int i, l;
|
|
bool wasspace;
|
|
|
|
if (txt == "" || txt == " ") {
|
|
return " ";
|
|
}
|
|
l = txt.length();
|
|
wasspace = true;
|
|
for (i = 0; i < l; i++) {
|
|
ch = txt[i];
|
|
if (ch == ' ') {
|
|
if (wasspace) {
|
|
result.append(" ");
|
|
} else {
|
|
result.append(' ');
|
|
wasspace = true;
|
|
}
|
|
} else {
|
|
wasspace = false;
|
|
if (ch == '&') {
|
|
result.append("&");
|
|
} else if (ch == '<') {
|
|
result.append("<");
|
|
} else {
|
|
result.append(ch);
|
|
}
|
|
}
|
|
}
|
|
return result;
|
|
}
|
|
|
|
MyTextEdit::MyTextEdit(QWidget * parent, const char *name) : QTextEdit(parent, name)
|
|
{
|
|
QFont monospace("Courier");
|
|
|
|
setTextFormat(Qt::RichText);
|
|
setWordWrap(QTextEdit::WidgetWidth);
|
|
setWrapPolicy(QTextEdit::Anywhere);
|
|
monospace.setStyleHint(QFont::TypeWriter);
|
|
setFont(monospace);
|
|
linebuffer = "";
|
|
buffered = false;
|
|
buffer = QStringList();
|
|
}
|
|
|
|
void MyTextEdit::appendHtml(QString text) {
|
|
linebuffer.append(text);
|
|
}
|
|
|
|
void MyTextEdit::setBuffered(bool arg) {
|
|
if (buffered) {
|
|
hide();
|
|
for (QStringList::Iterator it = buffer.begin(); it != buffer.end(); ++it ) {
|
|
append(*it);
|
|
}
|
|
show();
|
|
buffer.clear();
|
|
}
|
|
buffered = arg;
|
|
}
|
|
|
|
void MyTextEdit::appendText(QString text) {
|
|
QChar ch;
|
|
int i, l;
|
|
bool wasspace;
|
|
|
|
l = text.length();
|
|
wasspace = true;
|
|
for (i = 0; i < l; i++) {
|
|
ch = text[i];
|
|
if (ch == ' ') {
|
|
if (wasspace) {
|
|
linebuffer.append(" ");
|
|
} else {
|
|
linebuffer.append(' ');
|
|
wasspace = true;
|
|
}
|
|
} else {
|
|
wasspace = false;
|
|
if (ch == '\n') {
|
|
if (linebuffer == "" || linebuffer == " ") {
|
|
linebuffer="<br>";
|
|
}
|
|
if (buffered) {
|
|
buffer.append(linebuffer);
|
|
} else {
|
|
append(linebuffer);
|
|
}
|
|
linebuffer = "";
|
|
} else if (ch == '&') {
|
|
linebuffer.append("&");
|
|
} else if (ch == '<') {
|
|
linebuffer.append("<");
|
|
} else {
|
|
linebuffer.append(ch);
|
|
}
|
|
}
|
|
}
|
|
}
|