/* This file is part of the Gudhi Library. The Gudhi library
* (Geometric Understanding in Higher Dimensions) is a generic C++
* library for computational topology.
*
* Author(s): David Salinas
*
* Copyright (C) 2014 Inria
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*
*/
#include // isfinite
#include
#include
#include
#include
#include
#include
#include
#include
#include // NaN, infinity
#include // for pair
#include
#ifndef UTILS_BAR_CODE_PERSISTENCE_H_
#define UTILS_BAR_CODE_PERSISTENCE_H_
class Bar_code_persistence {
private:
typedef std::vector> Persistence;
Persistence persistence_vector;
double min_birth;
double max_death;
public:
Bar_code_persistence()
: min_birth(std::numeric_limits::quiet_NaN()),
max_death(std::numeric_limits::quiet_NaN()) { }
void insert(double birth, double death) {
persistence_vector.push_back(std::make_pair(birth, death));
if (std::isfinite(birth)) {
if ((birth < min_birth) || (std::isnan(min_birth)))
min_birth = birth;
if ((birth > max_death) || (std::isnan(max_death)))
max_death = birth;
}
if (std::isfinite(death))
if ((death > max_death) || (std::isnan(max_death)))
max_death = death;
}
void show(const std::string& window_title) {
// Create a view, put a scene in it
QGraphicsView * view = new QGraphicsView();
QGraphicsScene * scene = new QGraphicsScene();
view->setScene(scene);
double ratio = 600.0 / (max_death - min_birth);
// std::cout << "min_birth=" << min_birth << " - max_death=" << max_death << " - ratio=" << ratio << std::endl;
double height = 0.0, birth = 0.0, death = 0.0;
int pers_num = 1;
for (auto& persistence : persistence_vector) {
height = 5.0 * pers_num;
// std::cout << "[" << pers_num << "] birth=" << persistence.first << " - death=" << persistence.second << std::endl;
if (std::isfinite(persistence.first))
birth = ((persistence.first - min_birth) * ratio) + 50.0;
else
birth = 0.0;
if (std::isfinite(persistence.second))
death = ((persistence.second - min_birth) * ratio) + 50.0;
else
death = 700.0;
scene->addLine(birth, height, death, height, QPen(Qt::blue, 2));
pers_num++;
}
height += 10.0;
// scale line
scene->addLine(0, height, 700.0, height, QPen(Qt::black, 1));
int modulo = 0;
for (double scale = 50.0; scale < 700.0; scale += 50.0) {
modulo++;
// scale small dash
scene->addLine(scale, height - 3.0, scale, height + 3.0, QPen(Qt::black, 1));
// scale text
QString scale_value = QString::number(((scale - 50.0) / ratio) + min_birth);
QGraphicsTextItem* dimText = scene->addText(scale_value, QFont("Helvetica", 8));
dimText->setPos(scale - (3.0 * scale_value.size()), height + 9.0 * (modulo % 2));
}
view->setWindowTitle(window_title.c_str());
// Show the view
view->show();
}
};
#endif // UTILS_BAR_CODE_PERSISTENCE_H_