* Copyright (c) 2021-2025 Huawei Device Co., Ltd.
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "input_event.h"
#include <algorithm>
#include "axis_event.h"
#include "event_log_helper.h"
#undef MMI_LOG_TAG
#define MMI_LOG_TAG "InputEvent"
namespace OHOS {
namespace MMI {
namespace {
int64_t g_nextEventId = 1;
constexpr uint32_t DATA_LENGTH_LIMIT { 1024 };
}
std::string EventLogHelper::userType_ = "";
std::once_flag EventLogHelper::betaFlag_;
InputEvent::InputEvent(int32_t eventType) : eventType_(eventType)
{
Reset();
}
InputEvent::InputEvent(const InputEvent& other)
: eventType_(other.eventType_), id_(other.id_), actionTime_(other.actionTime_),
sensorInputTime_(other.sensorInputTime_), action_(other.action_), actionStartTime_(other.actionStartTime_),
deviceId_(other.deviceId_), sourceType_(other.sourceType_), targetDisplayId_(other.targetDisplayId_),
targetWindowId_(other.targetWindowId_), agentWindowId_(other.agentWindowId_),
bitwise_(other.bitwise_), markEnabled_(other.markEnabled_),
extraData_(other.extraData_), extraDataLength_(other.extraDataLength_) {}
InputEvent::~InputEvent() {}
void InputEvent::Reset()
{
struct timespec ts = { 0, 0 };
if (clock_gettime(CLOCK_MONOTONIC, &ts) != 0) {
actionTime_ = 0;
}
id_ = -1;
if (!AddInt64(ts.tv_sec * 1000000, ts.tv_nsec / 1000, actionTime_)) {
MMI_HILOGE("The addition of actionTime_ overflows");
return;
}
action_ = ACTION_UNKNOWN;
actionStartTime_ = actionTime_;
deviceId_ = -1;
sourceType_ = SOURCE_TYPE_UNKNOWN;
targetDisplayId_ = -1;
targetWindowId_ = -1;
agentWindowId_ = -1;
bitwise_ = EVENT_FLAG_NONE;
markEnabled_ = true;
}
std::string InputEvent::ToString()
{
std::string eventStr = "Id:";
eventStr += std::to_string(id_);
eventStr += "eventType:";
eventStr += std::to_string(eventType_);
eventStr += ",actionTime:";
eventStr += std::to_string(actionTime_);
eventStr += ",deviceId:";
eventStr += std::to_string(deviceId_);
eventStr += ",sourceType:";
eventStr += std::to_string(sourceType_);
return eventStr;
}
size_t InputEvent::Hash()
{
std::hash<std::string> hasher;
return hasher(ToString());
}
std::shared_ptr<InputEvent> InputEvent::Create()
{
auto event = std::shared_ptr<InputEvent>(new (std::nothrow) InputEvent(InputEvent::EVENT_TYPE_BASE));
CHKPP(event);
return event;
}
const char* InputEvent::EventTypeToString(int32_t eventType)
{
switch (eventType) {
case InputEvent::EVENT_TYPE_BASE: {
return "base";
}
case InputEvent::EVENT_TYPE_KEY: {
return "key";
}
case InputEvent::EVENT_TYPE_POINTER: {
return "pointer";
}
case InputEvent::EVENT_TYPE_AXIS: {
return "axis";
}
case InputEvent::EVENT_TYPE_FINGERPRINT: {
return "fingerprint";
}
default: {
MMI_HILOGW("Unknown EVENT_TYPE");
return "unknown";
}
}
}
int32_t InputEvent::GetId() const
{
return id_;
}
void InputEvent::SetId(int32_t id)
{
id_ = id;
}
void InputEvent::UpdateId()
{
if (g_nextEventId >= INT32_MAX) {
g_nextEventId = 1;
}
id_ = g_nextEventId++;
}
int64_t InputEvent::GetActionTime() const
{
return actionTime_;
}
void InputEvent::SetActionTime(int64_t actionTime)
{
actionTime_ = actionTime;
}
void InputEvent::SetSensorInputTime(uint64_t sensorInputTime)
{
sensorInputTime_ = sensorInputTime;
}
uint64_t InputEvent::GetSensorInputTime() const
{
return sensorInputTime_;
}
int32_t InputEvent::GetAction() const
{
return action_;
}
void InputEvent::SetAction(int32_t action)
{
action_ = action;
}
int64_t InputEvent::GetActionStartTime() const
{
return actionStartTime_;
}
void InputEvent::SetActionStartTime(int64_t actionStartTime)
{
actionStartTime_ = actionStartTime;
}
int32_t InputEvent::GetDeviceId() const
{
return deviceId_;
}
void InputEvent::SetDeviceId(int32_t deviceId)
{
deviceId_ = deviceId;
}
int32_t InputEvent::GetSourceType() const
{
return sourceType_;
}
void InputEvent::SetSourceType(int32_t sourceType)
{
sourceType_ = sourceType;
}
const char* InputEvent::DumpSourceType() const
{
switch (sourceType_) {
case InputEvent::SOURCE_TYPE_MOUSE: {
return "mouse";
}
case InputEvent::SOURCE_TYPE_TOUCHSCREEN: {
return "touch-screen";
}
case InputEvent::SOURCE_TYPE_TOUCHPAD: {
return "touch-pad";
}
case InputEvent::SOURCE_TYPE_JOYSTICK: {
return "joystick";
}
case InputEvent::SOURCE_TYPE_FINGERPRINT: {
return "fingerprint";
}
case InputEvent::SOURCE_TYPE_CROWN: {
return "crown";
}
default: {
break;
}
}
return "unknown";
}
int32_t InputEvent::GetTargetDisplayId() const
{
return targetDisplayId_;
}
void InputEvent::SetTargetDisplayId(int32_t displayId)
{
targetDisplayId_ = displayId;
}
int32_t InputEvent::GetAgentWindowId() const
{
return agentWindowId_;
}
void InputEvent::SetAgentWindowId(int32_t windowId)
{
agentWindowId_ = windowId;
}
int32_t InputEvent::GetTargetWindowId() const
{
return targetWindowId_;
}
void InputEvent::SetTargetWindowId(int32_t windowId)
{
targetWindowId_ = windowId;
}
int32_t InputEvent::GetEventType() const
{
return eventType_;
}
uint32_t InputEvent::GetFlag() const
{
return bitwise_;
}
bool InputEvent::HasFlag(uint32_t flag)
{
return (bitwise_ & flag) != 0;
}
bool InputEvent::IsFlag(uint32_t flag)
{
return (bitwise_ & flag) == flag;
}
void InputEvent::AddFlag(uint32_t flag)
{
bitwise_ |= flag;
}
void InputEvent::ClearFlag()
{
bitwise_ = EVENT_FLAG_NONE;
}
void InputEvent::ClearFlag(uint32_t flag)
{
bitwise_ &= ~flag;
}
bool InputEvent::IsMarkEnabled() const
{
return markEnabled_;
}
void InputEvent::SetMarkEnabled(bool markEnabled)
{
markEnabled_ = markEnabled;
}
void InputEvent::SetProcessedCallback(std::function<void(int32_t, int64_t)> callback)
{
processedCallback_ = callback;
}
void InputEvent::MarkProcessed()
{
if (!processedCallback_) {
return;
}
if (!markEnabled_) {
MMI_HILOGD("Skip MarkProcessed eventId:%{public}d, eventType:%{public}d", id_, eventType_);
return;
}
auto func = processedCallback_;
processedCallback_ = std::function<void(int32_t, int64_t)>();
func(id_, actionTime_);
}
void InputEvent::SetExtraData(const std::shared_ptr<const uint8_t[]> data, uint32_t length)
{
if (data && (length > 0) && (length <= DATA_LENGTH_LIMIT)) {
extraData_ = data;
extraDataLength_ = length;
}
}
void InputEvent::GetExtraData(std::shared_ptr<const uint8_t[]> &data, uint32_t &length) const
{
if (extraData_ && extraDataLength_ != 0) {
data = extraData_;
length = extraDataLength_;
} else {
length = 0;
}
}
bool InputEvent::WriteToParcel(Parcel &out) const
{
WRITEINT32(out, eventType_);
WRITEINT32(out, id_);
WRITEINT64(out, actionTime_);
WRITEUINT64(out, sensorInputTime_);
WRITEINT32(out, action_);
WRITEINT64(out, actionStartTime_);
WRITEINT32(out, deviceId_);
WRITEINT32(out, sourceType_);
WRITEINT32(out, targetDisplayId_);
WRITEINT32(out, targetWindowId_);
WRITEINT32(out, agentWindowId_);
WRITEUINT32(out, bitwise_);
WRITEBOOL(out, markEnabled_);
if (extraData_ && extraDataLength_ != 0) {
WRITEUINT32(out, extraDataLength_);
WRITEBUFFER(out, (void *)extraData_.get(), extraDataLength_);
} else {
WRITEUINT32(out, 0);
}
return true;
}
bool InputEvent::Marshalling(Parcel &out) const
{
return WriteToParcel(out);
}
bool InputEvent::ReadFromParcel(Parcel &in)
{
#if defined(ANDROID_PLATFORM) || defined(IOS_PLATFORM)
return false;
#else
READINT32(in, eventType_);
READINT32(in, id_);
READINT64(in, actionTime_);
READUINT64(in, sensorInputTime_);
READINT32(in, action_);
READINT64(in, actionStartTime_);
READINT32(in, deviceId_);
READINT32(in, sourceType_);
READINT32(in, targetDisplayId_);
READINT32(in, targetWindowId_);
READINT32(in, agentWindowId_);
READUINT32(in, bitwise_);
READBOOL(in, markEnabled_);
READUINT32(in, extraDataLength_);
if (extraDataLength_ == 0) {
return true;
}
if (extraDataLength_ > DATA_LENGTH_LIMIT) {
extraDataLength_ = 0;
return false;
}
const uint8_t *buffer = in.ReadBuffer(extraDataLength_);
std::shared_ptr<uint8_t[]> sp(new uint8_t[extraDataLength_], [](uint8_t* ptr) { delete[] ptr; });
if ((buffer == nullptr) || (sp == nullptr)) {
extraDataLength_ = 0;
return false;
}
std::copy(buffer, buffer + extraDataLength_, sp.get());
extraData_ = sp;
return true;
#endif
}
InputEvent *InputEvent::Unmarshalling(Parcel &parcel)
{
InputEvent *data = new (std::nothrow) InputEvent(InputEvent::EVENT_TYPE_BASE);
if (data && !data->ReadFromParcel(parcel)) {
delete data;
data = nullptr;
}
return data;
}
std::string_view InputEvent::ActionToShortStr(int32_t action)
{
switch (action) {
case InputEvent::ACTION_CANCEL:
return "B:C:";
case InputEvent::ACTION_UNKNOWN:
return "B:UK:";
default:
return "B:?:";
}
}
int32_t OHOS::MMI::EventLogHelper::infoDictCount_ = 0;
int32_t OHOS::MMI::EventLogHelper::debugDictCount_ = 0;
}
}