File: touch_ui_controller_stats_tracker.cc

package info (click to toggle)
chromium 140.0.7339.127-1
  • links: PTS, VCS
  • area: main
  • in suites: sid
  • size: 6,192,880 kB
  • sloc: cpp: 35,093,808; ansic: 7,161,670; javascript: 4,199,694; python: 1,441,797; asm: 949,904; xml: 747,503; pascal: 187,748; perl: 88,691; sh: 88,248; objc: 79,953; sql: 52,714; cs: 44,599; fortran: 24,137; makefile: 22,114; tcl: 15,277; php: 13,980; yacc: 9,000; ruby: 7,485; awk: 3,720; lisp: 3,096; lex: 1,327; ada: 727; jsp: 228; sed: 36
file content (138 lines) | stat: -rw-r--r-- 5,447 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
// Copyright 2020 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "chrome/browser/metrics/desktop_session_duration/touch_ui_controller_stats_tracker.h"

#include "base/functional/bind.h"
#include "base/logging.h"
#include "base/metrics/histogram_functions.h"
#include "base/no_destructor.h"
#include "chrome/browser/metrics/desktop_session_duration/desktop_session_duration_tracker.h"
#include "ui/base/pointer/touch_ui_controller.h"

// static
void TouchUIControllerStatsTracker::Initialize(
    metrics::DesktopSessionDurationTracker* session_duration_tracker,
    ui::TouchUiController* touch_ui_controller) {
  static base::NoDestructor<TouchUIControllerStatsTracker> stats_tracker(
      session_duration_tracker, touch_ui_controller);
}

TouchUIControllerStatsTracker::TouchUIControllerStatsTracker(
    metrics::DesktopSessionDurationTracker* session_duration_tracker,
    ui::TouchUiController* touch_ui_controller)
    : touch_ui_controller_(touch_ui_controller) {
  session_duration_tracker->AddObserver(this);

  // If this instance is destroyed, |touch_mode_change_subscription_|'s
  // destructor will unregister the callback. Hence Unretained is safe.
  touch_mode_change_subscription_ = touch_ui_controller->RegisterCallback(
      base::BindRepeating(&TouchUIControllerStatsTracker::TouchModeChanged,
                          base::Unretained(this)));
#if BUILDFLAG(IS_WIN)
  tablet_mode_change_subscription_ =
      touch_ui_controller->RegisterTabletModeCallback(
          base::BindRepeating(&TouchUIControllerStatsTracker::TabletModeChanged,
                              base::Unretained(this)));
#endif  // BUILDFLAG(IS_WIN)
}

TouchUIControllerStatsTracker::~TouchUIControllerStatsTracker() = default;

// static
const char TouchUIControllerStatsTracker::kSessionTouchDurationHistogramName[] =
    "Session.TotalDuration.TouchMode";
#if BUILDFLAG(IS_WIN)
const char
    TouchUIControllerStatsTracker::kSessionTabletDurationHistogramName[] =
        "Session.TotalDuration.TabletMode";
#endif  // BUILDFLAG(IS_WIN)

void TouchUIControllerStatsTracker::TouchModeChanged() {
  if (session_start_time_.is_null()) {
    return;
  }

  auto switch_time = base::TimeTicks::Now();
  DCHECK_GE(switch_time, last_touch_mode_switch_in_session_);

  // If we changed to non-touch mode, we were in touch mode in the span
  // of time from last_touch_mode_switch_in_session_ to switch_time.
  if (!touch_ui_controller_->touch_ui()) {
    touch_mode_duration_in_session_ +=
        switch_time - last_touch_mode_switch_in_session_;
  }

  last_touch_mode_switch_in_session_ = switch_time;
}

#if BUILDFLAG(IS_WIN)
void TouchUIControllerStatsTracker::TabletModeChanged() {
  if (session_start_time_.is_null()) {
    return;
  }

  auto switch_time = base::TimeTicks::Now();
  DCHECK_GE(switch_time, last_tablet_mode_switch_in_session_);

  // If we changed to desktop mode, we were in tablet mode in the span
  // of time from last_tablet_mode_switch_in_session_ to switch_time.
  if (!touch_ui_controller_->tablet_mode()) {
    tablet_mode_duration_in_session_ +=
        switch_time - last_tablet_mode_switch_in_session_;
  }

  last_tablet_mode_switch_in_session_ = switch_time;
}
#endif  // BUILDFLAG(IS_WIN)

void TouchUIControllerStatsTracker::OnSessionStarted(
    base::TimeTicks session_start) {
  session_start_time_ = session_start;
  last_touch_mode_switch_in_session_ = session_start_time_;
  touch_mode_duration_in_session_ = base::TimeDelta();
#if BUILDFLAG(IS_WIN)
  last_tablet_mode_switch_in_session_ = session_start_time_;
  tablet_mode_duration_in_session_ = base::TimeDelta();
#endif  // BUILDFLAG(IS_WIN)
}

void TouchUIControllerStatsTracker::OnSessionEnded(
    base::TimeDelta session_length,
    base::TimeTicks session_end) {
  // If we end in touch mode, we must count the time from
  // last_touch_mode_switch_in_session_ to session_end.
  //
  // |session_end| may be slightly less than
  // |last_touch_mode_switch_in_session_| because an OnSessionEnded()
  // call may happen slightly after the session end time. Assuming the
  // difference is small, the touch mode time left unaccounted for is small.
  // Accept this error and ignore this time. See crbug.com/1165462.
  if (touch_ui_controller_->touch_ui() &&
      session_end >= last_touch_mode_switch_in_session_) {
    touch_mode_duration_in_session_ +=
        session_end - last_touch_mode_switch_in_session_;
  }
#if BUILDFLAG(IS_WIN)
  if (touch_ui_controller_->tablet_mode() &&
      session_end >= last_tablet_mode_switch_in_session_) {
    tablet_mode_duration_in_session_ +=
        session_end - last_tablet_mode_switch_in_session_;
  }
#endif  // BUILDFLAG(IS_WIN)
  // The samples here correspond 1:1 with Session.TotalDuration, so the
  // bucketing matches too.
  base::UmaHistogramLongTimes(kSessionTouchDurationHistogramName,
                              touch_mode_duration_in_session_);

  session_start_time_ = base::TimeTicks();
  last_touch_mode_switch_in_session_ = base::TimeTicks();
  touch_mode_duration_in_session_ = base::TimeDelta();
#if BUILDFLAG(IS_WIN)
  base::UmaHistogramLongTimes(kSessionTabletDurationHistogramName,
                              tablet_mode_duration_in_session_);
  last_tablet_mode_switch_in_session_ = base::TimeTicks();
  tablet_mode_duration_in_session_ = base::TimeDelta();
#endif  // BUILDFLAG(IS_WIN)
}