1 /*
2 * Copyright (C) 2021 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "input_method_agent_stub.h"
17
18 #include "global.h"
19 #include "input_method_ability.h"
20 #include "ipc_skeleton.h"
21 #include "itypes_util.h"
22 #include "message.h"
23 #include "message_handler.h"
24
25 namespace OHOS {
26 namespace MiscServices {
27 using namespace MessageID;
28
InputMethodAgentStub()29 InputMethodAgentStub::InputMethodAgentStub()
30 {
31 msgHandler_ = nullptr;
32 }
33
~InputMethodAgentStub()34 InputMethodAgentStub::~InputMethodAgentStub()
35 {
36 }
37
OnRemoteRequest(uint32_t code,MessageParcel & data,MessageParcel & reply,MessageOption & option)38 int32_t InputMethodAgentStub::OnRemoteRequest(
39 uint32_t code, MessageParcel &data, MessageParcel &reply, MessageOption &option)
40 {
41 IMSA_HILOGD("InputMethodAgentStub, code = %{public}u, callingPid: %{public}d, callingUid: %{public}d.", code,
42 IPCSkeleton::GetCallingPid(), IPCSkeleton::GetCallingUid());
43 auto descriptorToken = data.ReadInterfaceToken();
44 if (descriptorToken != GetDescriptor()) {
45 return ErrorCode::ERROR_STATUS_UNKNOWN_TRANSACTION;
46 }
47
48 switch (code) {
49 case DISPATCH_KEY_EVENT: {
50 return DispatchKeyEventOnRemote(data, reply);
51 }
52 case SET_CALLING_WINDOW_ID: {
53 SetCallingWindow(data.ReadUint32());
54 break;
55 }
56 case ON_CURSOR_UPDATE: {
57 int32_t positionX = data.ReadInt32();
58 int32_t positionY = data.ReadInt32();
59 int32_t height = data.ReadInt32();
60 OnCursorUpdate(positionX, positionY, height);
61 reply.WriteNoException();
62 return ErrorCode::NO_ERROR;
63 }
64 case ON_SELECTION_CHANGE: {
65 std::u16string text = data.ReadString16();
66 int32_t oldBegin = data.ReadInt32();
67 int32_t oldEnd = data.ReadInt32();
68 int32_t newBegin = data.ReadInt32();
69 int32_t newEnd = data.ReadInt32();
70 OnSelectionChange(text, oldBegin, oldEnd, newBegin, newEnd);
71 reply.WriteNoException();
72 return ErrorCode::NO_ERROR;
73 }
74 case SEND_PRIVATE_COMMAND: {
75 return SendPrivateCommandOnRemote(data, reply);
76 }
77 case ON_ATTRIBUTE_CHANGE: {
78 return OnAttributeChangeOnRemote(data, reply);
79 }
80 default: {
81 return IRemoteStub::OnRemoteRequest(code, data, reply, option);
82 }
83 }
84 return ErrorCode::NO_ERROR;
85 }
86
DispatchKeyEventOnRemote(MessageParcel & data,MessageParcel & reply)87 int32_t InputMethodAgentStub::DispatchKeyEventOnRemote(MessageParcel &data, MessageParcel &reply)
88 {
89 std::shared_ptr<MMI::KeyEvent> keyEvent = MMI::KeyEvent::Create();
90 if (keyEvent == nullptr) {
91 IMSA_HILOGE("keyEvent is nullptr!");
92 return ErrorCode::ERROR_NULL_POINTER;
93 }
94 if (!keyEvent->ReadFromParcel(data)) {
95 IMSA_HILOGE("failed to read key event from parcel!");
96 return ErrorCode::ERROR_EX_PARCELABLE;
97 }
98 auto consumerObject = data.ReadRemoteObject();
99 if (consumerObject == nullptr) {
100 IMSA_HILOGE("consumerObject is nullptr!");
101 return ErrorCode::ERROR_EX_PARCELABLE;
102 }
103 sptr<KeyEventConsumerProxy> consumer = new (std::nothrow) KeyEventConsumerProxy(consumerObject);
104 auto ret = InputMethodAbility::GetInstance()->DispatchKeyEvent(keyEvent, consumer);
105 return reply.WriteInt32(ret) ? ErrorCode::NO_ERROR : ErrorCode::ERROR_EX_PARCELABLE;
106 }
107
SendPrivateCommandOnRemote(MessageParcel & data,MessageParcel & reply)108 int32_t InputMethodAgentStub::SendPrivateCommandOnRemote(MessageParcel &data, MessageParcel &reply)
109 {
110 std::unordered_map<std::string, PrivateDataValue> privateCommand;
111 if (!ITypesUtil::Unmarshal(data, privateCommand)) {
112 IMSA_HILOGE("failed to read message parcel!");
113 return ErrorCode::ERROR_EX_PARCELABLE;
114 }
115 auto ret = InputMethodAbility::GetInstance()->ReceivePrivateCommand(privateCommand);
116 return reply.WriteInt32(ret) ? ErrorCode::NO_ERROR : ErrorCode::ERROR_EX_PARCELABLE;
117 }
118
OnAttributeChangeOnRemote(MessageParcel & data,MessageParcel & reply)119 int32_t InputMethodAgentStub::OnAttributeChangeOnRemote(MessageParcel &data, MessageParcel &reply)
120 {
121 InputAttribute attribute;
122 if (!ITypesUtil::Unmarshal(data, attribute)) {
123 IMSA_HILOGE("failed to read attribute from parcel!");
124 return ErrorCode::ERROR_EX_PARCELABLE;
125 }
126 OnAttributeChange(attribute);
127 reply.WriteNoException();
128 return ErrorCode::NO_ERROR;
129 }
130
DispatchKeyEvent(const std::shared_ptr<MMI::KeyEvent> & keyEvent,sptr<IKeyEventConsumer> & consumer)131 int32_t InputMethodAgentStub::DispatchKeyEvent(
132 const std::shared_ptr<MMI::KeyEvent> &keyEvent, sptr<IKeyEventConsumer> &consumer)
133 {
134 return false;
135 }
136
SetCallingWindow(uint32_t windowId)137 void InputMethodAgentStub::SetCallingWindow(uint32_t windowId)
138 {
139 InputMethodAbility::GetInstance()->SetCallingWindow(windowId);
140 }
141
OnCursorUpdate(int32_t positionX,int32_t positionY,int height)142 void InputMethodAgentStub::OnCursorUpdate(int32_t positionX, int32_t positionY, int height)
143 {
144 if (msgHandler_ == nullptr) {
145 return;
146 }
147 MessageParcel *data = new MessageParcel();
148 data->WriteInt32(positionX);
149 data->WriteInt32(positionY);
150 data->WriteInt32(height);
151 Message *message = new Message(MessageID::MSG_ID_ON_CURSOR_UPDATE, data);
152 msgHandler_->SendMessage(message);
153 }
154
OnSelectionChange(std::u16string text,int32_t oldBegin,int32_t oldEnd,int32_t newBegin,int32_t newEnd)155 void InputMethodAgentStub::OnSelectionChange(
156 std::u16string text, int32_t oldBegin, int32_t oldEnd, int32_t newBegin, int32_t newEnd)
157 {
158 if (msgHandler_ == nullptr) {
159 return;
160 }
161 MessageParcel *data = new MessageParcel();
162 data->WriteString16(text);
163 data->WriteInt32(oldBegin);
164 data->WriteInt32(oldEnd);
165 data->WriteInt32(newBegin);
166 data->WriteInt32(newEnd);
167 Message *message = new Message(MessageID::MSG_ID_ON_SELECTION_CHANGE, data);
168 msgHandler_->SendMessage(message);
169 }
170
SendPrivateCommand(const std::unordered_map<std::string,PrivateDataValue> & privateCommand)171 int32_t InputMethodAgentStub::SendPrivateCommand(
172 const std::unordered_map<std::string, PrivateDataValue> &privateCommand)
173 {
174 return ErrorCode::NO_ERROR;
175 }
176
OnAttributeChange(const InputAttribute & attribute)177 void InputMethodAgentStub::OnAttributeChange(const InputAttribute &attribute)
178 {
179 if (msgHandler_ == nullptr) {
180 IMSA_HILOGE("msgHandler_ is nullptr!");
181 return;
182 }
183 auto data = new (std::nothrow) MessageParcel();
184 if (data == nullptr) {
185 IMSA_HILOGE("failed to create message parcel!");
186 return;
187 }
188 if (!ITypesUtil::Marshal(*data, attribute)) {
189 IMSA_HILOGE("failed to write attribute!");
190 delete data;
191 return;
192 }
193 auto message = new (std::nothrow) Message(MessageID::MSG_ID_ON_ATTRIBUTE_CHANGE, data);
194 if (message == nullptr) {
195 IMSA_HILOGE("failed to create Message!");
196 delete data;
197 return;
198 }
199 msgHandler_->SendMessage(message);
200 }
201
SetMessageHandler(MessageHandler * msgHandler)202 void InputMethodAgentStub::SetMessageHandler(MessageHandler *msgHandler)
203 {
204 msgHandler_ = msgHandler;
205 }
206 } // namespace MiscServices
207 } // namespace OHOS