blob: 1f7aa613b53f630ece17d4d4a35a1d3283bc6980 [file] [log] [blame]
finnur@chromium.org1e0a8cf2011-02-14 18:24:36 +09001// Copyright (c) 2011 The Chromium Authors. All rights reserved.
license.botf003cfe2008-08-24 09:55:55 +09002// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
initial.commit3f4a7322008-07-27 06:49:38 +09004
5#ifndef BASE_EVENT_RECORDER_H_
6#define BASE_EVENT_RECORDER_H_
thakis@chromium.org01d14522010-07-27 08:08:24 +09007#pragma once
initial.commit3f4a7322008-07-27 06:49:38 +09008
rvargas@google.comc3b65182011-03-29 08:48:44 +09009#include "base/base_api.h"
initial.commit3f4a7322008-07-27 06:49:38 +090010#include "base/basictypes.h"
jhawkins@chromium.org8e73d062011-04-05 03:04:37 +090011#include "build/build_config.h"
12
13#if defined(OS_WIN)
14#include <stdio.h>
15#include <string.h>
16#include <windows.h>
17#endif
initial.commit3f4a7322008-07-27 06:49:38 +090018
thestig@chromium.org1c939cf2009-05-01 13:31:22 +090019class FilePath;
20
initial.commit3f4a7322008-07-27 06:49:38 +090021namespace base {
22
23// A class for recording and playing back keyboard and mouse input events.
24//
25// Note - if you record events, and the playback with the windows in
26// different sizes or positions, the playback will fail. When
27// recording and playing, you should move the relevant windows
28// to constant sizes and locations.
29// TODO(mbelshe) For now this is a singleton. I believe that this class
30// could be easily modified to:
31// support two simultaneous recorders
32// be playing back events while already recording events.
33// Why? Imagine if the product had a "record a macro" feature.
34// You might be recording globally, while recording or playing back
35// a macro. I don't think two playbacks make sense.
rvargas@google.comc3b65182011-03-29 08:48:44 +090036class BASE_API EventRecorder {
initial.commit3f4a7322008-07-27 06:49:38 +090037 public:
38 // Get the singleton EventRecorder.
39 // We can only handle one recorder/player at a time.
40 static EventRecorder* current() {
41 if (!current_)
42 current_ = new EventRecorder();
43 return current_;
44 }
45
46 // Starts recording events.
47 // Will clobber the file if it already exists.
48 // Returns true on success, or false if an error occurred.
thestig@chromium.org1c939cf2009-05-01 13:31:22 +090049 bool StartRecording(const FilePath& filename);
initial.commit3f4a7322008-07-27 06:49:38 +090050
51 // Stops recording.
52 void StopRecording();
53
54 // Is the EventRecorder currently recording.
55 bool is_recording() const { return is_recording_; }
56
57 // Plays events previously recorded.
58 // Returns true on success, or false if an error occurred.
thestig@chromium.org1c939cf2009-05-01 13:31:22 +090059 bool StartPlayback(const FilePath& filename);
initial.commit3f4a7322008-07-27 06:49:38 +090060
61 // Stops playback.
62 void StopPlayback();
63
64 // Is the EventRecorder currently playing.
65 bool is_playing() const { return is_playing_; }
66
amanda@chromium.org5c44f992009-01-27 01:33:29 +090067#if defined(OS_WIN)
initial.commit3f4a7322008-07-27 06:49:38 +090068 // C-style callbacks for the EventRecorder.
69 // Used for internal purposes only.
70 LRESULT RecordWndProc(int nCode, WPARAM wParam, LPARAM lParam);
71 LRESULT PlaybackWndProc(int nCode, WPARAM wParam, LPARAM lParam);
amanda@chromium.org5c44f992009-01-27 01:33:29 +090072#endif
initial.commit3f4a7322008-07-27 06:49:38 +090073
74 private:
75 // Create a new EventRecorder. Events are saved to the file filename.
76 // If the file already exists, it will be deleted before recording
77 // starts.
78 explicit EventRecorder()
79 : is_recording_(false),
80 is_playing_(false),
amanda@chromium.org5c44f992009-01-27 01:33:29 +090081#if defined(OS_WIN)
initial.commit3f4a7322008-07-27 06:49:38 +090082 journal_hook_(NULL),
maruel@google.comfc903372008-10-01 05:50:51 +090083 file_(NULL),
amanda@chromium.org5c44f992009-01-27 01:33:29 +090084#endif
maruel@google.comfc903372008-10-01 05:50:51 +090085 playback_first_msg_time_(0),
86 playback_start_time_(0) {
finnur@chromium.org1e0a8cf2011-02-14 18:24:36 +090087#if defined(OS_WIN)
88 memset(&playback_msg_, 0, sizeof(playback_msg_));
89#endif
initial.commit3f4a7322008-07-27 06:49:38 +090090 }
91 ~EventRecorder();
92
93 static EventRecorder* current_; // Our singleton.
94
95 bool is_recording_;
96 bool is_playing_;
amanda@chromium.org5c44f992009-01-27 01:33:29 +090097#if defined(OS_WIN)
initial.commit3f4a7322008-07-27 06:49:38 +090098 HHOOK journal_hook_;
99 FILE* file_;
100 EVENTMSG playback_msg_;
amanda@chromium.org5c44f992009-01-27 01:33:29 +0900101#endif
initial.commit3f4a7322008-07-27 06:49:38 +0900102 int playback_first_msg_time_;
103 int playback_start_time_;
104
tfarina@chromium.org0aad8422010-06-05 01:13:51 +0900105 DISALLOW_COPY_AND_ASSIGN(EventRecorder);
initial.commit3f4a7322008-07-27 06:49:38 +0900106};
107
108} // namespace base
109
110#endif // BASE_EVENT_RECORDER_H_