Graphic fast autofit for addPoint
git-svn-id: svn://db.shs.com.ru/libs@347 a8b55f48-bf90-11e4-a774-851b48703e85
This commit is contained in:
@@ -94,8 +94,8 @@ Graphic::Graphic(QWidget * parent): QFrame(parent), line_x_min(this), line_x_max
|
||||
mdm = 10.;
|
||||
visible_time = -1.;
|
||||
pause_phase = 0.;
|
||||
selrect.setRect(0., 0., 1., 1.);
|
||||
def_rect = selrect;
|
||||
def_rect.setRect(0., 0., 1., 1.);
|
||||
selrect = def_rect;
|
||||
margins_.setRect(4, 4, 4, 4);
|
||||
curaction = gaMove;
|
||||
selbrush.setStyle(Qt::SolidPattern);
|
||||
@@ -457,6 +457,7 @@ void Graphic::clear() {
|
||||
graphics[i].polyline.clear();
|
||||
graphics[i].polyline_pause.clear();
|
||||
graphics[i].max_x = 0.;
|
||||
graphics[i].cvrect = QRectF();
|
||||
}
|
||||
on_buttonAutofit_clicked();
|
||||
}
|
||||
@@ -487,6 +488,7 @@ void Graphic::setPaused(bool yes) {
|
||||
graphics[i].polyline_pause = graphics[i].polyline;
|
||||
graphics[i].polyline_pause.detach();
|
||||
graphics[i].max_x_pause = graphics[i].max_x;
|
||||
graphics[i].cvrect = QRectF();
|
||||
}
|
||||
timer_pause = startTimer(40);
|
||||
}
|
||||
@@ -498,6 +500,7 @@ void Graphic::setHistorySize(double val) {
|
||||
for (int i = 0; i < graphics.size(); ++i) {
|
||||
QPolygonF & pol(graphics[i].polyline);
|
||||
if (pol.isEmpty() || history <= 0.) continue;
|
||||
graphics[i].cvrect = QRectF();
|
||||
x = pol.back().x() - history;
|
||||
for (int j = pol.size() - 2; j >= 0 ; --j)
|
||||
if (pol[j].x() < x) {
|
||||
@@ -585,26 +588,37 @@ void Graphic::setButtonsPosition(Graphic::Alignment a) {
|
||||
|
||||
void Graphic::addPoint(const QPointF & p, int graphic, bool update_) {
|
||||
if (graphic >= graphics.size() || graphic < 0) return;
|
||||
if (graphics.at(graphic).polyline.size() == 0) graphics[graphic].max_x = p.x();
|
||||
graphics[graphic].polyline << p;
|
||||
if (graphics.at(graphic).max_x < p.x()) graphics[graphic].max_x = p.x();
|
||||
GraphicType & t(graphics[graphic]);
|
||||
if (!t.cvrect.isNull()) {
|
||||
// if (graphics[graphic].cvrect.contains(p))
|
||||
// graphics[graphic].cvrect = QRectF();
|
||||
if (t.cvrect.top() < p.y()) t.cvrect.setTop(p.y());
|
||||
if (t.cvrect.bottom() > p.y()) t.cvrect.setBottom(p.y());
|
||||
if (t.cvrect.right() < p.x()) t.cvrect.setRight(p.x());
|
||||
if (t.cvrect.left() > p.x()) t.cvrect.setLeft(p.x());
|
||||
}
|
||||
if (t.polyline.size() == 0) t.max_x = p.x();
|
||||
t.polyline << p;
|
||||
if (t.max_x < p.x()) t.max_x = p.x();
|
||||
tick(graphic, true, update_);
|
||||
}
|
||||
|
||||
|
||||
void Graphic::setGraphicData(const QVector<QPointF> & g, int graphic, bool update_) {
|
||||
if (graphic >= graphics.size() || graphic < 0) return;
|
||||
graphics[graphic].polyline.clear();
|
||||
graphics[graphic].polyline = g;
|
||||
if (graphics.at(graphic).polyline.size() == 0) {
|
||||
graphics[graphic].max_x = 0.;
|
||||
GraphicType & t(graphics[graphic]);
|
||||
t.cvrect = QRectF();
|
||||
t.polyline.clear();
|
||||
t.polyline = g;
|
||||
if (t.polyline.size() == 0) {
|
||||
t.max_x = 0.;
|
||||
tick(graphic, false, update_);
|
||||
return;
|
||||
}
|
||||
graphics[graphic].max_x = graphics.at(graphic).polyline[0].x();
|
||||
for (int i = 1; i < graphics.at(graphic).polyline.size(); ++i)
|
||||
if (graphics.at(graphic).max_x < graphics.at(graphic).polyline[i].x())
|
||||
graphics[graphic].max_x = graphics.at(graphic).polyline[i].x();
|
||||
t.max_x = t.polyline[0].x();
|
||||
for (int i = 1; i < t.polyline.size(); ++i)
|
||||
if (t.max_x < t.polyline[i].x())
|
||||
t.max_x = t.polyline[i].x();
|
||||
tick(graphic, false, update_);
|
||||
}
|
||||
|
||||
@@ -694,7 +708,7 @@ void Graphic::setGraphicsCount(int arg, bool update) {
|
||||
}
|
||||
|
||||
|
||||
void Graphic::setHistogramData(const QVector<float> & g, int graphic) {
|
||||
/*void Graphic::setHistogramData(const QVector<float> & g, int graphic) {
|
||||
graphics[graphic].polyline.clear();
|
||||
if (g.isEmpty()) {
|
||||
return;
|
||||
@@ -739,25 +753,29 @@ void Graphic::setHistogramData(const QVector<float> & g, int graphic) {
|
||||
cpol << QPointF(range + min, 0.);
|
||||
}
|
||||
updateGraphics();
|
||||
}
|
||||
}*/
|
||||
|
||||
|
||||
void Graphic::findGraphicsRect(double start_x, double end_x, double start_y, double end_y) {
|
||||
double cx, cy, maxX, minX, maxY, minY, vx = DBL_MIN;
|
||||
double cx, cy, maxX, minX, maxY, minY, vx;
|
||||
bool isRangeX = (start_x != end_x), isRangeY = (start_y != end_y);
|
||||
bool isEmpty = true, anyVisible = false, isTimeLimit = (visible_time > 0.) && !(isRangeX || isRangeY);
|
||||
foreach (const GraphicType & t, graphics) {
|
||||
const QPolygonF & pol(pause_ ? t.polyline_pause : t.polyline);
|
||||
if (!pol.isEmpty()) {
|
||||
isEmpty = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (isEmpty) {
|
||||
grect = def_rect;
|
||||
setRectToLines();
|
||||
return;
|
||||
}
|
||||
// bool isEmpty = true;
|
||||
bool fast = true, can_fast = (start_x == 0 && end_x == 0 && start_y == 0 && end_y == 0);
|
||||
bool anyVisible = false, isTimeLimit = (visible_time > 0.) && !(isRangeX || isRangeY);
|
||||
// foreach (const GraphicType & t, graphics) {
|
||||
// const QPolygonF & pol(pause_ ? t.polyline_pause : t.polyline);
|
||||
// if (!pol.isEmpty()) {
|
||||
// isEmpty = false;
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// if (isEmpty) {
|
||||
// grect = def_rect;
|
||||
// setRectToLines();
|
||||
// return;
|
||||
// }
|
||||
// can_fast = false;
|
||||
vx = DBL_MIN;
|
||||
minY = minX = DBL_MAX;
|
||||
maxY = maxX = -DBL_MAX;
|
||||
foreach (const GraphicType & t, graphics) {
|
||||
@@ -765,27 +783,50 @@ void Graphic::findGraphicsRect(double start_x, double end_x, double start_y, dou
|
||||
if (vx < (pause_ ? t.max_x_pause : t.max_x)) vx = (pause_ ? t.max_x_pause : t.max_x);
|
||||
}
|
||||
vx -= visible_time;
|
||||
foreach (const GraphicType & t, graphics) {
|
||||
// qDebug() << "[Graphic]" << "can_fast" << can_fast;
|
||||
for (int g = 0; g < graphics.size(); g++) {
|
||||
GraphicType & t(graphics[g]);
|
||||
if (!t.visible) continue;
|
||||
const QPolygonF & pol(pause_ ? t.polyline_pause : t.polyline);
|
||||
for (int i = 0; i < pol.size(); i++) {
|
||||
cx = pol[i].x();
|
||||
cy = pol[i].y();
|
||||
if ((start_x > cx || end_x < cx) && isRangeX) continue;
|
||||
if ((start_y > cy || end_y < cy) && isRangeY) continue;
|
||||
if ((cx < vx) && isTimeLimit) continue;
|
||||
if (maxY < cy) maxY = cy;
|
||||
if (minY > cy) minY = cy;
|
||||
if (maxX < cx) maxX = cx;
|
||||
if (minX > cx) minX = cx;
|
||||
if (pol.isEmpty()) continue;
|
||||
bool f = true;
|
||||
//qDebug() << "[Graphic]" << "cvrect:" << t.cvrect << t.cvrect.isNull();
|
||||
if (t.cvrect.isNull() || !can_fast) {
|
||||
for (int i = 0; i < pol.size(); i++) {
|
||||
cx = pol[i].x();
|
||||
cy = pol[i].y();
|
||||
if ((start_x > cx || end_x < cx) && isRangeX) continue;
|
||||
if ((start_y > cy || end_y < cy) && isRangeY) continue;
|
||||
if ((cx < vx) && isTimeLimit) continue;
|
||||
if (f) {
|
||||
t.cvrect.setRect(cx, cy, 0, 0);
|
||||
f = false;
|
||||
} else {
|
||||
if (t.cvrect.top() < cy) t.cvrect.setTop(cy);
|
||||
if (t.cvrect.bottom() > cy) t.cvrect.setBottom(cy);
|
||||
if (t.cvrect.right() < cx) t.cvrect.setRight(cx);
|
||||
if (t.cvrect.left() > cx) t.cvrect.setLeft(cx);
|
||||
}
|
||||
fast = false;
|
||||
}
|
||||
if (f) continue;
|
||||
//qDebug() << "[Graphic]" << "2 cvrect:" << t.cvrect;
|
||||
}
|
||||
if (!pol.isEmpty()) anyVisible = true;
|
||||
anyVisible = true;
|
||||
if (maxY < t.cvrect.top()) maxY = t.cvrect.top();
|
||||
if (minY > t.cvrect.bottom()) minY = t.cvrect.bottom();
|
||||
if (maxX < t.cvrect.right()) maxX = t.cvrect.right();
|
||||
if (minX > t.cvrect.left()) minX = t.cvrect.left();
|
||||
if (!can_fast) t.cvrect = QRectF();
|
||||
}
|
||||
if (!anyVisible) {
|
||||
grect.setRect(0., 0., 1., 1.);
|
||||
//qDebug() << "[Graphic]" << "empty autofit";
|
||||
grect = def_rect;
|
||||
setRectToLines();
|
||||
return;
|
||||
}
|
||||
// if (fast) qDebug() << "[Graphic]" << "FAST autofit";
|
||||
// else qDebug() << "[Graphic]" << "autofit";
|
||||
if (maxX > limit_.right()) maxX = limit_.right();
|
||||
if (minX > limit_.right()) minX = limit_.right();
|
||||
if (minX < limit_.left()) minX = limit_.left();
|
||||
@@ -796,8 +837,8 @@ void Graphic::findGraphicsRect(double start_x, double end_x, double start_y, dou
|
||||
if (maxY < limit_.top()) maxY = limit_.top();
|
||||
if (minX > maxX) qSwap<double>(minX, maxX);
|
||||
if (minY > maxY) qSwap<double>(minY, maxY);
|
||||
if (qAbs<double>(minX - maxX) < 1E-60) {minX -= 1E-20; maxX += 1E-20;}
|
||||
if (qAbs<double>(minY - maxY) < 1E-60) {minY -= 1E-20; maxY += 1E-20;}
|
||||
if (qAbs<double>(minX - maxX) < 1E-60) {minX -= defaultRect().width()/2; maxX += defaultRect().width()/2;}
|
||||
if (qAbs<double>(minY - maxY) < 1E-60) {minY -= defaultRect().height()/2; maxY += defaultRect().height()/2;}
|
||||
if (only_expand_x) {
|
||||
if (minX > eminx) minX = eminx;
|
||||
if (maxX < emaxx) maxX = emaxx;
|
||||
@@ -1279,6 +1320,12 @@ void Graphic::tick(int index, bool slide, bool update_) {
|
||||
if (history > 0.)
|
||||
while (t.polyline.size() > 1) {
|
||||
if (fabs(t.polyline.back().x() - t.polyline.front().x()) <= history) break;
|
||||
if (!t.cvrect.isNull()) {
|
||||
if (!t.cvrect.contains(t.polyline.first())) {
|
||||
/// TODO: [Graphic] add smart remove for fast autofit
|
||||
t.cvrect = QRectF();
|
||||
}
|
||||
}
|
||||
t.polyline.pop_front();
|
||||
}
|
||||
}
|
||||
@@ -1530,7 +1577,7 @@ QByteArray Graphic::save() {
|
||||
void Graphic::load(QByteArray ba) {
|
||||
if (ba.isEmpty()) return;
|
||||
char ver = ba[0];
|
||||
qDebug() << "load" << (int)ver;
|
||||
//qDebug() << "load" << (int)ver;
|
||||
switch(ver) {
|
||||
case '2': {// version '2':
|
||||
ba.remove(0, 1);
|
||||
|
||||
Reference in New Issue
Block a user