1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "remoting/protocol/mouse_input_filter.h"
6
7 #include <algorithm>
8
9 #include "base/logging.h"
10 #include "base/numerics/ranges.h"
11 #include "remoting/proto/event.pb.h"
12
13 namespace remoting {
14 namespace protocol {
15
MouseInputFilter()16 MouseInputFilter::MouseInputFilter()
17 : x_input_(0), y_input_(0), x_output_(0), y_output_(0) {}
18
MouseInputFilter(InputStub * input_stub)19 MouseInputFilter::MouseInputFilter(InputStub* input_stub)
20 : InputFilter(input_stub),
21 x_input_(0),
22 y_input_(0),
23 x_output_(0),
24 y_output_(0) {}
25
26 MouseInputFilter::~MouseInputFilter() = default;
27
InjectMouseEvent(const MouseEvent & event)28 void MouseInputFilter::InjectMouseEvent(const MouseEvent& event) {
29 if (x_input_ == 0 || y_input_ == 0 || x_output_ == 0 || y_output_ == 0) {
30 return;
31 }
32
33 // We scale based on the max input and output coordinates (which are equal
34 // to size-1), rather than the input and output sizes, so that it's possible
35 // to reach the edge of the output when up-scaling. We also take care to
36 // round up or down correctly, which is important when down-scaling.
37 // After scaling, we offset by the output rect origin. This is normally
38 // (0,0), but may be non-zero when there are multiple displays and we are
39 // showing a single display.
40
41 MouseEvent out_event(event);
42 if (out_event.has_x()) {
43 int x = out_event.x();
44 if (x_output_ != x_input_)
45 x = ((x * x_output_) + (x_input_ / 2)) / x_input_;
46 out_event.set_x(output_offset_.x() + base::ClampToRange(x, 0, x_output_));
47 }
48 if (out_event.has_y()) {
49 int y = out_event.y();
50 if (y_output_ != y_input_)
51 y = ((y * y_output_) + (y_input_ / 2)) / y_input_;
52 out_event.set_y(output_offset_.y() + base::ClampToRange(y, 0, y_output_));
53 }
54 InputFilter::InjectMouseEvent(out_event);
55 }
56
set_input_size(const int32_t x,const int32_t y)57 void MouseInputFilter::set_input_size(const int32_t x, const int32_t y) {
58 x_input_ = x - 1;
59 y_input_ = y - 1;
60 LOG(INFO) << "Setting MouseInputFilter input_size to " << x_input_ << ","
61 << y_input_;
62 }
63
set_output_size(const int32_t x,const int32_t y)64 void MouseInputFilter::set_output_size(const int32_t x, const int32_t y) {
65 x_output_ = x - 1;
66 y_output_ = y - 1;
67 LOG(INFO) << "Setting MouseInputFilter output_size to " << x_output_ << ","
68 << y_output_;
69 }
70
set_output_offset(const webrtc::DesktopVector & v)71 void MouseInputFilter::set_output_offset(const webrtc::DesktopVector& v) {
72 output_offset_ = webrtc::DesktopVector(v.x(), v.y());
73 LOG(INFO) << "Setting MouseInputFilter output_offset to "
74 << output_offset_.x() << "," << output_offset_.y();
75 }
76
77 } // namespace protocol
78 } // namespace remoting
79