21 static const int default_strip_chart_width = 400;
22 static const int default_strip_chart_height = 100;
27 size_t WinStatsStripChart::_check_box_height = 13;
28 size_t WinStatsStripChart::_check_box_width = 13;
30 bool WinStatsStripChart::_window_class_registered =
false;
31 const char *
const WinStatsStripChart::_window_class_name =
"strip";
38 int collector_index,
bool show_level) :
40 show_level ? monitor->get_level_view(collector_index, thread_index) : monitor->get_view(thread_index),
43 default_strip_chart_width,
44 default_strip_chart_height),
56 if (_unit_name.empty()) {
57 set_guide_bar_units(GBU_named);
59 set_guide_bar_units(GBU_named | GBU_show_units);
64 set_guide_bar_units(get_guide_bar_units() | GBU_show_units);
67 _smooth_check_box = 0;
77 ~WinStatsStripChart() {
99 SetWindowText(_window, window_title.c_str());
107 if (_net_value_text != text) {
108 _net_value_text = text;
110 GetClientRect(_window, &rect);
111 rect.bottom = _top_margin;
112 InvalidateRect(_window, &rect, TRUE);
122 PStatStripChart::force_redraw();
130 PStatStripChart::changed_size(graph_xsize, graph_ysize);
141 if ((old_unit_mask & (GBU_hz | GBU_ms)) != 0) {
142 unit_mask = unit_mask & (GBU_hz | GBU_ms);
143 unit_mask |= (old_unit_mask & GBU_show_units);
147 GetClientRect(_window, &rect);
148 rect.left = _right_margin;
149 InvalidateRect(_window, &rect, TRUE);
151 GetClientRect(_window, &rect);
152 rect.bottom = _top_margin;
153 InvalidateRect(_window, &rect, TRUE);
164 if (scroll_speed != 0.0f) {
174 if (collector_index < 0) {
187 if (def._parent_index == 0 &&
get_view().get_show_level()) {
209 GetClientRect(_window, &rect);
210 rect.left = _right_margin;
211 InvalidateRect(_window, &rect, TRUE);
217 void WinStatsStripChart::
219 PStatStripChart::update_labels();
221 _label_stack.clear_labels();
223 _label_stack.add_label(WinStatsGraph::_monitor,
this, _thread_index,
226 _labels_changed =
false;
232 void WinStatsStripChart::
235 FillRect(_bitmap_dc, &rect, (HBRUSH)GetStockObject(WHITE_BRUSH));
242 void WinStatsStripChart::
243 copy_region(
int start_x,
int end_x,
int dest_x) {
244 BitBlt(_bitmap_dc, dest_x, 0,
246 _bitmap_dc, start_x, 0,
250 _brush_origin += (dest_x - start_x);
251 SetBrushOrgEx(_bitmap_dc, _brush_origin, 0,
nullptr);
254 dest_x, 0, dest_x + end_x - start_x,
get_ysize()
256 InvalidateRect(_graph_window, &rect, FALSE);
263 void WinStatsStripChart::
266 RECT rect = { x, 0, x + w,
get_ysize() };
267 FillRect(_bitmap_dc, &rect, (HBRUSH)GetStockObject(WHITE_BRUSH));
269 double overall_time = 0.0;
272 FrameData::const_iterator fi;
273 for (fi = fdata.begin(); fi != fdata.end(); ++fi) {
274 const ColorData &cd = (*fi);
275 overall_time += cd._net_value;
276 HBRUSH brush = get_collector_brush(cd._collector_index);
283 FillRect(_bitmap_dc, &rect, brush);
291 FillRect(_bitmap_dc, &rect, brush);
299 void WinStatsStripChart::
300 draw_empty(
int x,
int w) {
301 RECT rect = { x, 0, x + w,
get_ysize() };
302 FillRect(_bitmap_dc, &rect, (HBRUSH)GetStockObject(WHITE_BRUSH));
308 void WinStatsStripChart::
310 RECT rect = { x, 0, x + 1,
get_ysize() };
311 FillRect(_bitmap_dc, &rect, (HBRUSH)GetStockObject(BLACK_BRUSH));
319 void WinStatsStripChart::
320 end_draw(
int from_x,
int to_x) {
323 for (
int i = 0; i < num_guide_bars; i++) {
330 InvalidateRect(_graph_window, &rect, FALSE);
336 LONG WinStatsStripChart::
337 window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) {
340 if (_potential_drag_mode == DM_new_guide_bar) {
341 set_drag_mode(DM_new_guide_bar);
342 SetCapture(_graph_window);
348 switch (LOWORD(wparam)) {
350 if ((HWND)lparam == _smooth_check_box) {
351 int result = SendMessage(_smooth_check_box, BM_GETCHECK, 0, 0);
363 return WinStatsGraph::window_proc(hwnd, msg, wparam, lparam);
369 LONG WinStatsStripChart::
370 graph_window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) {
373 if (_potential_drag_mode == DM_none) {
374 set_drag_mode(DM_scale);
375 int16_t y = HIWORD(lparam);
377 SetCapture(_graph_window);
380 }
else if (_potential_drag_mode == DM_guide_bar && _drag_guide_bar >= 0) {
381 set_drag_mode(DM_guide_bar);
382 int16_t y = HIWORD(lparam);
384 SetCapture(_graph_window);
390 if (_drag_mode == DM_none && _potential_drag_mode == DM_none) {
392 int16_t x = LOWORD(lparam);
393 int16_t y = HIWORD(lparam);
398 TRACKMOUSEEVENT tme = {
399 sizeof(TRACKMOUSEEVENT),
404 TrackMouseEvent(&tme);
408 _label_stack.highlight_label(-1);
411 if (_drag_mode == DM_scale) {
412 int16_t y = HIWORD(lparam);
413 double ratio = 1.0f - ((double)y / (
double)
get_ysize());
419 }
else if (_drag_mode == DM_new_guide_bar) {
422 int16_t y = HIWORD(lparam);
424 set_drag_mode(DM_guide_bar);
429 }
else if (_drag_mode == DM_guide_bar) {
430 int16_t y = HIWORD(lparam);
438 _label_stack.highlight_label(-1);
442 if (_drag_mode == DM_scale) {
443 set_drag_mode(DM_none);
447 }
else if (_drag_mode == DM_guide_bar) {
448 int16_t y = HIWORD(lparam);
454 set_drag_mode(DM_none);
460 case WM_LBUTTONDBLCLK:
464 int16_t x = LOWORD(lparam);
465 int16_t y = HIWORD(lparam);
475 return WinStatsGraph::graph_window_proc(hwnd, msg, wparam, lparam);
483 void WinStatsStripChart::
484 additional_window_paint(HDC hdc) {
486 HFONT hfnt = (HFONT)GetStockObject(ANSI_VAR_FONT);
487 SelectObject(hdc, hfnt);
488 SetTextAlign(hdc, TA_LEFT | TA_TOP);
489 SetBkMode(hdc, TRANSPARENT);
492 GetClientRect(_window, &rect);
493 int x = rect.right - _right_margin + 2;
498 for (i = 0; i < num_guide_bars; i++) {
503 draw_guide_label(hdc, x, top_value, last_y);
507 for (i = 0; i < num_user_guide_bars; i++) {
512 SetTextAlign(hdc, TA_RIGHT | TA_BOTTOM);
513 SetTextColor(hdc, RGB(0, 0, 0));
514 TextOut(hdc, rect.right - _right_margin, _top_margin,
515 _net_value_text.data(), _net_value_text.length());
521 SetTextAlign(hdc, TA_LEFT | TA_BOTTOM);
522 TextOut(hdc, _left_margin + _check_box_width + 2, _top_margin,
"Smooth", 6);
530 void WinStatsStripChart::
531 additional_graph_window_paint(HDC hdc) {
533 for (
int i = 0; i < num_user_guide_bars; i++) {
543 WinStatsGraph::DragMode WinStatsStripChart::
544 consider_drag_start(
int mouse_x,
int mouse_y,
int width,
int height) {
545 if (mouse_x >= _graph_left && mouse_x < _graph_left +
get_xsize()) {
546 if (mouse_y >= _graph_top && mouse_y < _graph_top +
get_ysize()) {
548 int y = mouse_y - _graph_top;
552 if (_drag_guide_bar >= 0) {
558 return DM_new_guide_bar;
562 return WinStatsGraph::consider_drag_start(mouse_x, mouse_y, width, height);
569 void WinStatsStripChart::
570 set_drag_mode(WinStatsGraph::DragMode drag_mode) {
571 WinStatsGraph::set_drag_mode(drag_mode);
573 switch (_drag_mode) {
576 case DM_right_margin:
584 int result = SendMessage(_smooth_check_box, BM_GETCHECK, 0, 0);
593 void WinStatsStripChart::
594 move_graph_window(
int graph_left,
int graph_top,
int graph_xsize,
int graph_ysize) {
595 WinStatsGraph::move_graph_window(graph_left, graph_top, graph_xsize, graph_ysize);
596 if (_smooth_check_box != 0) {
597 SetWindowPos(_smooth_check_box, 0,
598 _left_margin, _top_margin - _check_box_height - 1,
600 SWP_NOZORDER | SWP_NOSIZE | SWP_SHOWWINDOW);
601 InvalidateRect(_smooth_check_box,
nullptr, TRUE);
608 void WinStatsStripChart::
609 draw_guide_bar(HDC hdc,
int from_x,
int to_x,
615 switch (bar._style) {
617 SelectObject(hdc, _light_pen);
621 SelectObject(hdc, _user_guide_bar_pen);
625 SelectObject(hdc, _dark_pen);
628 MoveToEx(hdc, from_x, y,
nullptr);
629 LineTo(hdc, to_x + 1, y);
638 int WinStatsStripChart::
640 switch (bar._style) {
642 SetTextColor(hdc, _light_color);
646 SetTextColor(hdc, _user_guide_bar_color);
650 SetTextColor(hdc, _dark_color);
655 const string &label = bar._label;
657 GetTextExtentPoint32(hdc, label.data(), label.length(), &size);
659 if (bar._style != GBS_user) {
668 int this_y = _graph_top + y - size.cy / 2;
670 (last_y < this_y || last_y > this_y + size.cy)) {
671 TextOut(hdc, x, this_y,
672 label.data(), label.length());
683 void WinStatsStripChart::
689 HINSTANCE application = GetModuleHandle(
nullptr);
690 register_window_class(application);
696 _left_margin +
get_xsize() + _right_margin,
697 _top_margin +
get_ysize() + _bottom_margin
701 AdjustWindowRect(&win_rect, graph_window_style, FALSE);
704 CreateWindow(_window_class_name, window_title.c_str(), graph_window_style,
705 CW_USEDEFAULT, CW_USEDEFAULT,
706 win_rect.right - win_rect.left,
707 win_rect.bottom - win_rect.top,
708 WinStatsGraph::_monitor->get_window(),
nullptr, application, 0);
710 nout <<
"Could not create StripChart window!\n";
714 SetWindowLongPtr(_window, 0, (LONG_PTR)
this);
718 CreateWindow(
"BUTTON",
"",
719 WS_CHILD | BS_AUTOCHECKBOX,
720 0, 0, _check_box_width, _check_box_height,
721 _window,
nullptr, application, 0);
724 SetWindowPos(_window, HWND_TOP, 0, 0, 0, 0,
725 SWP_NOMOVE | SWP_NOSIZE | SWP_SHOWWINDOW);
732 void WinStatsStripChart::
733 register_window_class(HINSTANCE application) {
734 if (_window_class_registered) {
740 ZeroMemory(&wc,
sizeof(WNDCLASS));
742 wc.lpfnWndProc = (WNDPROC)static_window_proc;
743 wc.hInstance = application;
744 wc.hCursor = LoadCursor(
nullptr, IDC_ARROW);
745 wc.hbrBackground = (HBRUSH)COLOR_BACKGROUND;
746 wc.lpszMenuName =
nullptr;
747 wc.lpszClassName = _window_class_name;
752 if (!RegisterClass(&wc)) {
753 nout <<
"Could not register StripChart window class!\n";
757 _window_class_registered =
true;
763 LONG WINAPI WinStatsStripChart::
764 static_window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) {
766 if (
self !=
nullptr && self->_window == hwnd) {
767 return self->window_proc(hwnd, msg, wparam, lparam);
769 return DefWindowProc(hwnd, msg, wparam, lparam);