0
0
mirror of https://github.com/yse/easy_profiler.git synced 2024-12-27 08:41:02 +08:00

(profiler_gui) Added events indicators (like context switch events at the bottom of each thread)

This commit is contained in:
Victor Zarubkin 2016-09-23 23:50:43 +03:00
parent 30de452113
commit 583410c929
7 changed files with 93 additions and 17 deletions

View File

@ -178,6 +178,7 @@ namespace profiler {
BlocksTree::children_t children; ///< List of children indexes
BlocksTree::children_t sync; ///< List of context-switch events
BlocksTree::children_t events; ///< List of events indexes
std::string thread_name; ///< Name of this thread
::profiler::timestamp_t active_time; ///< Active time of this thread (sum of all children duration)
::profiler::thread_id_t thread_id; ///< System Id of this thread
@ -190,6 +191,7 @@ namespace profiler {
BlocksTreeRoot(This&& that)
: children(::std::move(that.children))
, sync(::std::move(that.sync))
, events(::std::move(that.events))
, thread_name(::std::move(that.thread_name))
, active_time(that.active_time)
, thread_id(that.thread_id)
@ -201,6 +203,7 @@ namespace profiler {
{
children = ::std::move(that.children);
sync = ::std::move(that.sync);
events = ::std::move(that.events);
thread_name = ::std::move(that.thread_name);
active_time = that.active_time;
thread_id = that.thread_id;

View File

@ -522,6 +522,72 @@ void EasyGraphicsItem::paint(QPainter* _painter, const QStyleOptionGraphicsItem*
}
if (EASY_GLOBALS.enable_event_indicators && !m_pRoot->events.empty())
{
auto first = ::std::lower_bound(m_pRoot->events.begin(), m_pRoot->events.end(), offset, [&sceneView](::profiler::block_index_t _index, qreal _value)
{
return sceneView->time2position(blocksTree(_index).node->begin()) < _value;
});
if (first != m_pRoot->events.end())
{
if (first != m_pRoot->events.begin())
--first;
}
else if (!m_pRoot->events.empty())
{
first = m_pRoot->events.begin() + m_pRoot->events.size() - 1;
}
previousColor = 0;
qreal prevRight = -1e100, top = y() + boundingRect().height() - 1, h = 3;
if (top + h < visibleBottom)
{
for (auto it = first, end = m_pRoot->events.end(); it != end; ++it)
{
const auto& item = blocksTree(*it);
auto left = sceneView->time2position(item.node->begin());
if (left > sceneRight)
break; // This is first totally invisible item. No need to check other items.
decltype(left) width = 0.25;
if (left + width < sceneLeft) // This item is not visible
continue;
left *= currentScale;
left -= dx;
width *= currentScale;
if (left + width <= prevRight) // This item is not visible
continue;
if (left < prevRight)
{
width -= prevRight - left;
left = prevRight;
}
if (width < 2)
width = 2;
::profiler::color_t color = easyDescriptor(item.node->id()).color();
if (previousColor != color)
{
previousColor = color;
_painter->setBrush(QColor::fromRgb(color));
_painter->setPen(QColor::fromRgb(BORDERS_COLOR & (0xffffffff - color)));
}
rect.setRect(left, top, width, h);
_painter->drawRect(rect);
prevRight = left + width;
}
}
}
_painter->restore();
}

View File

@ -47,6 +47,7 @@ namespace profiler_gui {
: selected_thread(0U)
, selected_block(::profiler_gui::numeric_max<decltype(selected_block)>())
, chrono_text_position(ChronoTextPosition_Center)
, enable_event_indicators(true)
, enable_statistics(true)
, draw_graphics_items_borders(true)
, display_only_relevant_stats(true)

View File

@ -96,7 +96,8 @@ namespace profiler_gui {
EasyBlocks gui_blocks; ///< Profiler graphics blocks builded by GUI
::profiler::thread_id_t selected_thread; ///< Current selected thread id
::profiler::block_index_t selected_block; ///< Current selected profiler block index
ChronometerTextPosition chrono_text_position; ///<
ChronometerTextPosition chrono_text_position; ///< Selected interval text position
bool enable_event_indicators; ///< Enable event indicators painting (These are narrow rectangles at the bottom of each thread)
bool enable_statistics; ///< Enable gathering and using statistics (Disable if you want to consume less memory)
bool draw_graphics_items_borders; ///< Draw borders for graphics blocks or not
bool display_only_relevant_stats; ///< Display only relevant information in ProfTreeWidget (excludes min, max, average times if there are only 1 calls number)

View File

@ -226,6 +226,11 @@ EasyMainWindow::EasyMainWindow() : Parent()
action->setChecked(EASY_GLOBALS.bind_scene_and_tree_expand_status);
connect(action, &QAction::triggered, this, &This::onBindExpandStatusChange);
action = menu->addAction("Paint event indicators");
action->setCheckable(true);
action->setChecked(EASY_GLOBALS.enable_event_indicators);
connect(action, &QAction::triggered, this, &This::onEventIndicatorsChange);
menu->addSeparator();
auto submenu = menu->addMenu("Chronometer text");
auto actionGroup = new QActionGroup(this);
@ -579,6 +584,12 @@ void EasyMainWindow::onChronoTextPosChanged(bool)
emit EASY_GLOBALS.events.chronoPositionChanged();
}
void EasyMainWindow::onEventIndicatorsChange(bool _checked)
{
EASY_GLOBALS.enable_event_indicators = _checked;
static_cast<EasyGraphicsViewWidget*>(m_graphicsView->widget())->view()->scene()->update();
}
void EasyMainWindow::onEnableDisableStatistics(bool _checked)
{
EASY_GLOBALS.enable_statistics = _checked;
@ -700,47 +711,37 @@ void EasyMainWindow::loadSettings()
auto last_file = settings.value("last_file");
if (!last_file.isNull())
{
m_lastFile = last_file.toString();
}
auto val = settings.value("chrono_text_position");
if (!val.isNull())
{
EASY_GLOBALS.chrono_text_position = static_cast<::profiler_gui::ChronometerTextPosition>(val.toInt());
}
auto flag = settings.value("draw_graphics_items_borders");
if (!flag.isNull())
{
EASY_GLOBALS.draw_graphics_items_borders = flag.toBool();
}
flag = settings.value("collapse_items_on_tree_close");
if (!flag.isNull())
{
EASY_GLOBALS.collapse_items_on_tree_close = flag.toBool();
}
flag = settings.value("all_items_expanded_by_default");
if (!flag.isNull())
{
EASY_GLOBALS.all_items_expanded_by_default = flag.toBool();
}
flag = settings.value("bind_scene_and_tree_expand_status");
if (!flag.isNull())
{
EASY_GLOBALS.bind_scene_and_tree_expand_status = flag.toBool();
}
flag = settings.value("enable_event_indicators");
if (!flag.isNull())
EASY_GLOBALS.enable_event_indicators = flag.toBool();
flag = settings.value("enable_statistics");
if (!flag.isNull())
{
EASY_GLOBALS.enable_statistics = flag.toBool();
}
QString encoding = settings.value("encoding", "UTF-8").toString();
auto default_codec_mib = QTextCodec::codecForName(encoding.toStdString().c_str())->mibEnum();
@ -779,6 +780,7 @@ void EasyMainWindow::saveSettingsAndGeometry()
settings.setValue("collapse_items_on_tree_close", EASY_GLOBALS.collapse_items_on_tree_close);
settings.setValue("all_items_expanded_by_default", EASY_GLOBALS.all_items_expanded_by_default);
settings.setValue("bind_scene_and_tree_expand_status", EASY_GLOBALS.bind_scene_and_tree_expand_status);
settings.setValue("enable_event_indicators", EASY_GLOBALS.enable_event_indicators);
settings.setValue("enable_statistics", EASY_GLOBALS.enable_statistics);
settings.setValue("encoding", QTextCodec::codecForLocale()->name());

View File

@ -157,6 +157,7 @@ protected slots:
void onExitClicked(bool);
void onEncodingChanged(bool);
void onChronoTextPosChanged(bool);
void onEventIndicatorsChange(bool);
void onEnableDisableStatistics(bool);
void onDrawBordersChanged(bool);
void onCollapseItemsAfterCloseChanged(bool);

View File

@ -402,7 +402,8 @@ extern "C" PROFILER_API::profiler::block_index_t fillTreesFromFile(::std::atomic
inFile.read(data, sz);
i += sz;
auto baseData = reinterpret_cast<::profiler::SerializedBlock*>(data);
if (descriptors[baseData->id()] == nullptr)
auto desc = descriptors[baseData->id()];
if (desc == nullptr)
return 0;
auto t_begin = reinterpret_cast<::profiler::timestamp_t*>(data);
@ -507,7 +508,8 @@ extern "C" PROFILER_API::profiler::block_index_t fillTreesFromFile(::std::atomic
}
root.children.emplace_back(block_index);// ::std::move(tree));
if (desc->type() == ::profiler::BLOCK_TYPE_EVENT)
root.events.emplace_back(block_index);
if (gather_statistics)