1 /*
2 * Copyright (c) 2023 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 "notification_local_live_view_button.h"
17
18 #include <cstdint>
19 #include <string> // for basic_string, operator+, basic_string<>...
20 #include <memory> // for shared_ptr, shared_ptr<>::element_type
21 #include <vector>
22
23 #include "ans_image_util.h"
24 #include "ans_log_wrapper.h"
25 #include "nlohmann/json.hpp" // for json, basic_json<>::object_t, basic_json
26 #include "notification_button_option.h"
27 #include "notification_json_convert.h"
28 #include "parcel.h" // for Parcel
29 #include "pixel_map.h" // for PixelMap
30
31 namespace OHOS {
32 namespace Notification {
33 const uint32_t BUTTON_MAX_SIZE = 3;
34
GetAllButtonNames() const35 std::vector<std::string> NotificationLocalLiveViewButton::GetAllButtonNames() const
36 {
37 return buttonNames_;
38 }
39
addSingleButtonName(const std::string & buttonName)40 void NotificationLocalLiveViewButton::addSingleButtonName(const std::string &buttonName)
41 {
42 if (buttonNames_.size() >= BUTTON_MAX_SIZE) {
43 ANS_LOGW("already added 3 buttonOption");
44 return;
45 }
46
47 buttonNames_.emplace_back(buttonName);
48 }
49
GetAllButtonIcons() const50 std::vector<std::shared_ptr<Media::PixelMap>> NotificationLocalLiveViewButton::GetAllButtonIcons() const
51 {
52 return buttonIcons_;
53 }
54
addSingleButtonIcon(std::shared_ptr<Media::PixelMap> & icon)55 void NotificationLocalLiveViewButton::addSingleButtonIcon(std::shared_ptr<Media::PixelMap> &icon)
56 {
57 if (buttonIcons_.size() >= BUTTON_MAX_SIZE) {
58 ANS_LOGW("already added 3 buttonIcon");
59 return;
60 }
61
62 buttonIcons_.emplace_back(icon);
63 }
64
Dump()65 std::string NotificationLocalLiveViewButton::Dump()
66 {
67 return "";
68 }
69
ToJson(nlohmann::json & jsonObject) const70 bool NotificationLocalLiveViewButton::ToJson(nlohmann::json &jsonObject) const
71 {
72 nlohmann::json buttonsArr = nlohmann::json::array();
73
74 jsonObject["names"] = nlohmann::json(buttonNames_);
75
76 nlohmann::json iconsArr = nlohmann::json::array();
77 for (auto &btn : buttonIcons_) {
78 if (!btn) {
79 continue;
80 }
81 nlohmann::json btnObj = AnsImageUtil::PackImage(btn);
82 iconsArr.emplace_back(btnObj);
83 }
84 jsonObject["icons"] = iconsArr;
85
86 return true;
87 }
88
FromJson(const nlohmann::json & jsonObject)89 NotificationLocalLiveViewButton *NotificationLocalLiveViewButton::FromJson(const nlohmann::json &jsonObject)
90 {
91 if (jsonObject.is_null() or !jsonObject.is_object()) {
92 ANS_LOGE("Invalid JSON object");
93 return nullptr;
94 }
95
96 NotificationLocalLiveViewButton *button = new (std::nothrow) NotificationLocalLiveViewButton();
97 if (button == nullptr) {
98 ANS_LOGE("Failed to create capsule instance");
99 return nullptr;
100 }
101
102 const auto &jsonEnd = jsonObject.cend();
103
104 if (jsonObject.find("names") != jsonEnd && jsonObject.at("names").is_array()) {
105 button->buttonNames_ = jsonObject.at("names").get<std::vector<std::string>>();
106 }
107
108 if (jsonObject.find("icons") != jsonEnd) {
109 auto iconArr = jsonObject.at("icons");
110 for (auto &iconObj : iconArr) {
111 auto pIcon = AnsImageUtil::UnPackImage(iconObj.get<std::string>());
112 if (pIcon == nullptr) {
113 ANS_LOGE("Failed to parse button icon");
114 return nullptr;
115 }
116 button->buttonIcons_.emplace_back(pIcon);
117 }
118 }
119
120 return button;
121 }
122
Marshalling(Parcel & parcel) const123 bool NotificationLocalLiveViewButton::Marshalling(Parcel &parcel) const
124 {
125 if (!parcel.WriteStringVector(buttonNames_)) {
126 ANS_LOGE("Failed to write buttonNames");
127 return false;
128 }
129
130 if (!parcel.WriteUint64(buttonIcons_.size())) {
131 ANS_LOGE("Failed to write the size of buttonIcons");
132 return false;
133 }
134
135 for (auto it = buttonIcons_.begin(); it != buttonIcons_.end(); ++it) {
136 if (!parcel.WriteParcelable(it->get())) {
137 ANS_LOGE("Failed to write buttonIcons");
138 return false;
139 }
140 }
141
142 return true;
143 }
144
ReadFromParcel(Parcel & parcel)145 bool NotificationLocalLiveViewButton::ReadFromParcel(Parcel &parcel)
146 {
147 if (!parcel.ReadStringVector(&buttonNames_)) {
148 ANS_LOGE("Failed to read button names");
149 return false;
150 }
151
152 auto vsize = parcel.ReadUint64();
153 vsize = (vsize < BUTTON_MAX_SIZE) ? vsize : BUTTON_MAX_SIZE;
154 for (uint64_t it = 0; it < vsize; ++it) {
155 auto member = std::shared_ptr<Media::PixelMap>(parcel.ReadParcelable<Media::PixelMap>());
156 if (member == nullptr) {
157 buttonIcons_.clear();
158 ANS_LOGE("Failed to read LocalLiveViewButton");
159 return false;
160 }
161
162 buttonIcons_.emplace_back(member);
163 }
164
165 return true;
166 }
167
Unmarshalling(Parcel & parcel)168 NotificationLocalLiveViewButton *NotificationLocalLiveViewButton::Unmarshalling(Parcel &parcel)
169 {
170 NotificationLocalLiveViewButton *button = new (std::nothrow) NotificationLocalLiveViewButton();
171
172 if (button && !button->ReadFromParcel(parcel)) {
173 delete button;
174 button = nullptr;
175 }
176
177 return button;
178 }
179 } // namespace Notification
180 } // namespace OHOS
181