diff options
| author | 2023-09-13 09:39:16 -0400 | |
|---|---|---|
| committer | 2023-09-13 09:39:16 -0400 | |
| commit | 5b5c69b8f61fbcff2ac72441857750068d585816 (patch) | |
| tree | 071d9db0793abfa5e7cf2f1544d81a10f66596d3 /src | |
| parent | Merge pull request #11473 from liamwhite/fix-launch-param (diff) | |
| parent | service: mii: Remove most magic values (diff) | |
| download | yuzu-5b5c69b8f61fbcff2ac72441857750068d585816.tar.gz yuzu-5b5c69b8f61fbcff2ac72441857750068d585816.tar.xz yuzu-5b5c69b8f61fbcff2ac72441857750068d585816.zip | |
Merge pull request #11480 from german77/mii_service
service: mii: Update implementation Part1
Diffstat (limited to '')
24 files changed, 4466 insertions, 1943 deletions
diff --git a/src/core/CMakeLists.txt b/src/core/CMakeLists.txt index 012648d69..c33910ade 100644 --- a/src/core/CMakeLists.txt +++ b/src/core/CMakeLists.txt | |||
| @@ -584,13 +584,23 @@ add_library(core STATIC | |||
| 584 | hle/service/lm/lm.h | 584 | hle/service/lm/lm.h |
| 585 | hle/service/mig/mig.cpp | 585 | hle/service/mig/mig.cpp |
| 586 | hle/service/mig/mig.h | 586 | hle/service/mig/mig.h |
| 587 | hle/service/mii/types/char_info.cpp | ||
| 588 | hle/service/mii/types/char_info.h | ||
| 589 | hle/service/mii/types/core_data.cpp | ||
| 590 | hle/service/mii/types/core_data.h | ||
| 591 | hle/service/mii/types/raw_data.cpp | ||
| 592 | hle/service/mii/types/raw_data.h | ||
| 593 | hle/service/mii/types/store_data.cpp | ||
| 594 | hle/service/mii/types/store_data.h | ||
| 595 | hle/service/mii/types/ver3_store_data.cpp | ||
| 596 | hle/service/mii/types/ver3_store_data.h | ||
| 587 | hle/service/mii/mii.cpp | 597 | hle/service/mii/mii.cpp |
| 588 | hle/service/mii/mii.h | 598 | hle/service/mii/mii.h |
| 589 | hle/service/mii/mii_manager.cpp | 599 | hle/service/mii/mii_manager.cpp |
| 590 | hle/service/mii/mii_manager.h | 600 | hle/service/mii/mii_manager.h |
| 591 | hle/service/mii/raw_data.cpp | 601 | hle/service/mii/mii_result.h |
| 592 | hle/service/mii/raw_data.h | 602 | hle/service/mii/mii_types.h |
| 593 | hle/service/mii/types.h | 603 | hle/service/mii/mii_util.h |
| 594 | hle/service/mm/mm_u.cpp | 604 | hle/service/mm/mm_u.cpp |
| 595 | hle/service/mm/mm_u.h | 605 | hle/service/mm/mm_u.h |
| 596 | hle/service/mnpp/mnpp_app.cpp | 606 | hle/service/mnpp/mnpp_app.cpp |
diff --git a/src/core/hle/service/am/applets/applet_mii_edit.cpp b/src/core/hle/service/am/applets/applet_mii_edit.cpp index f8e2bac32..350a90818 100644 --- a/src/core/hle/service/am/applets/applet_mii_edit.cpp +++ b/src/core/hle/service/am/applets/applet_mii_edit.cpp | |||
| @@ -85,15 +85,18 @@ void MiiEdit::Execute() { | |||
| 85 | break; | 85 | break; |
| 86 | case MiiEditAppletMode::CreateMii: | 86 | case MiiEditAppletMode::CreateMii: |
| 87 | case MiiEditAppletMode::EditMii: { | 87 | case MiiEditAppletMode::EditMii: { |
| 88 | Service::Mii::MiiManager mii_manager; | 88 | Mii::CharInfo char_info{}; |
| 89 | Mii::StoreData store_data{}; | ||
| 90 | store_data.BuildBase(Mii::Gender::Male); | ||
| 91 | char_info.SetFromStoreData(store_data); | ||
| 89 | 92 | ||
| 90 | const MiiEditCharInfo char_info{ | 93 | const MiiEditCharInfo edit_char_info{ |
| 91 | .mii_info{applet_input_common.applet_mode == MiiEditAppletMode::EditMii | 94 | .mii_info{applet_input_common.applet_mode == MiiEditAppletMode::EditMii |
| 92 | ? applet_input_v4.char_info.mii_info | 95 | ? applet_input_v4.char_info.mii_info |
| 93 | : mii_manager.BuildBase(Mii::Gender::Male)}, | 96 | : char_info}, |
| 94 | }; | 97 | }; |
| 95 | 98 | ||
| 96 | MiiEditOutputForCharInfoEditing(MiiEditResult::Success, char_info); | 99 | MiiEditOutputForCharInfoEditing(MiiEditResult::Success, edit_char_info); |
| 97 | break; | 100 | break; |
| 98 | } | 101 | } |
| 99 | default: | 102 | default: |
diff --git a/src/core/hle/service/am/applets/applet_mii_edit_types.h b/src/core/hle/service/am/applets/applet_mii_edit_types.h index 4705d019f..f3d764073 100644 --- a/src/core/hle/service/am/applets/applet_mii_edit_types.h +++ b/src/core/hle/service/am/applets/applet_mii_edit_types.h | |||
| @@ -7,7 +7,8 @@ | |||
| 7 | 7 | ||
| 8 | #include "common/common_funcs.h" | 8 | #include "common/common_funcs.h" |
| 9 | #include "common/common_types.h" | 9 | #include "common/common_types.h" |
| 10 | #include "core/hle/service/mii/types.h" | 10 | #include "common/uuid.h" |
| 11 | #include "core/hle/service/mii/types/char_info.h" | ||
| 11 | 12 | ||
| 12 | namespace Service::AM::Applets { | 13 | namespace Service::AM::Applets { |
| 13 | 14 | ||
diff --git a/src/core/hle/service/mii/mii.cpp b/src/core/hle/service/mii/mii.cpp index 65c11a2f3..3b83c5ed7 100644 --- a/src/core/hle/service/mii/mii.cpp +++ b/src/core/hle/service/mii/mii.cpp | |||
| @@ -7,17 +7,16 @@ | |||
| 7 | #include "core/hle/service/ipc_helpers.h" | 7 | #include "core/hle/service/ipc_helpers.h" |
| 8 | #include "core/hle/service/mii/mii.h" | 8 | #include "core/hle/service/mii/mii.h" |
| 9 | #include "core/hle/service/mii/mii_manager.h" | 9 | #include "core/hle/service/mii/mii_manager.h" |
| 10 | #include "core/hle/service/mii/mii_result.h" | ||
| 10 | #include "core/hle/service/server_manager.h" | 11 | #include "core/hle/service/server_manager.h" |
| 11 | #include "core/hle/service/service.h" | 12 | #include "core/hle/service/service.h" |
| 12 | 13 | ||
| 13 | namespace Service::Mii { | 14 | namespace Service::Mii { |
| 14 | 15 | ||
| 15 | constexpr Result ERROR_INVALID_ARGUMENT{ErrorModule::Mii, 1}; | ||
| 16 | |||
| 17 | class IDatabaseService final : public ServiceFramework<IDatabaseService> { | 16 | class IDatabaseService final : public ServiceFramework<IDatabaseService> { |
| 18 | public: | 17 | public: |
| 19 | explicit IDatabaseService(Core::System& system_) | 18 | explicit IDatabaseService(Core::System& system_, bool is_system_) |
| 20 | : ServiceFramework{system_, "IDatabaseService"} { | 19 | : ServiceFramework{system_, "IDatabaseService"}, is_system{is_system_} { |
| 21 | // clang-format off | 20 | // clang-format off |
| 22 | static const FunctionInfo functions[] = { | 21 | static const FunctionInfo functions[] = { |
| 23 | {0, &IDatabaseService::IsUpdated, "IsUpdated"}, | 22 | {0, &IDatabaseService::IsUpdated, "IsUpdated"}, |
| @@ -54,34 +53,27 @@ public: | |||
| 54 | } | 53 | } |
| 55 | 54 | ||
| 56 | private: | 55 | private: |
| 57 | template <typename T> | ||
| 58 | std::vector<u8> SerializeArray(const std::vector<T>& values) { | ||
| 59 | std::vector<u8> out(values.size() * sizeof(T)); | ||
| 60 | std::size_t offset{}; | ||
| 61 | for (const auto& value : values) { | ||
| 62 | std::memcpy(out.data() + offset, &value, sizeof(T)); | ||
| 63 | offset += sizeof(T); | ||
| 64 | } | ||
| 65 | return out; | ||
| 66 | } | ||
| 67 | |||
| 68 | void IsUpdated(HLERequestContext& ctx) { | 56 | void IsUpdated(HLERequestContext& ctx) { |
| 69 | IPC::RequestParser rp{ctx}; | 57 | IPC::RequestParser rp{ctx}; |
| 70 | const auto source_flag{rp.PopRaw<SourceFlag>()}; | 58 | const auto source_flag{rp.PopRaw<SourceFlag>()}; |
| 71 | 59 | ||
| 72 | LOG_DEBUG(Service_Mii, "called with source_flag={}", source_flag); | 60 | LOG_DEBUG(Service_Mii, "called with source_flag={}", source_flag); |
| 73 | 61 | ||
| 62 | const bool is_updated = manager.IsUpdated(metadata, source_flag); | ||
| 63 | |||
| 74 | IPC::ResponseBuilder rb{ctx, 3}; | 64 | IPC::ResponseBuilder rb{ctx, 3}; |
| 75 | rb.Push(ResultSuccess); | 65 | rb.Push(ResultSuccess); |
| 76 | rb.Push(manager.CheckAndResetUpdateCounter(source_flag, current_update_counter)); | 66 | rb.Push<u8>(is_updated); |
| 77 | } | 67 | } |
| 78 | 68 | ||
| 79 | void IsFullDatabase(HLERequestContext& ctx) { | 69 | void IsFullDatabase(HLERequestContext& ctx) { |
| 80 | LOG_DEBUG(Service_Mii, "called"); | 70 | LOG_DEBUG(Service_Mii, "called"); |
| 81 | 71 | ||
| 72 | const bool is_full_database = manager.IsFullDatabase(); | ||
| 73 | |||
| 82 | IPC::ResponseBuilder rb{ctx, 3}; | 74 | IPC::ResponseBuilder rb{ctx, 3}; |
| 83 | rb.Push(ResultSuccess); | 75 | rb.Push(ResultSuccess); |
| 84 | rb.Push(manager.IsFullDatabase()); | 76 | rb.Push<u8>(is_full_database); |
| 85 | } | 77 | } |
| 86 | 78 | ||
| 87 | void GetCount(HLERequestContext& ctx) { | 79 | void GetCount(HLERequestContext& ctx) { |
| @@ -90,57 +82,63 @@ private: | |||
| 90 | 82 | ||
| 91 | LOG_DEBUG(Service_Mii, "called with source_flag={}", source_flag); | 83 | LOG_DEBUG(Service_Mii, "called with source_flag={}", source_flag); |
| 92 | 84 | ||
| 85 | const u32 mii_count = manager.GetCount(metadata, source_flag); | ||
| 86 | |||
| 93 | IPC::ResponseBuilder rb{ctx, 3}; | 87 | IPC::ResponseBuilder rb{ctx, 3}; |
| 94 | rb.Push(ResultSuccess); | 88 | rb.Push(ResultSuccess); |
| 95 | rb.Push<u32>(manager.GetCount(source_flag)); | 89 | rb.Push(mii_count); |
| 96 | } | 90 | } |
| 97 | 91 | ||
| 98 | void Get(HLERequestContext& ctx) { | 92 | void Get(HLERequestContext& ctx) { |
| 99 | IPC::RequestParser rp{ctx}; | 93 | IPC::RequestParser rp{ctx}; |
| 100 | const auto source_flag{rp.PopRaw<SourceFlag>()}; | 94 | const auto source_flag{rp.PopRaw<SourceFlag>()}; |
| 95 | const auto output_size{ctx.GetWriteBufferNumElements<CharInfoElement>()}; | ||
| 101 | 96 | ||
| 102 | LOG_DEBUG(Service_Mii, "called with source_flag={}", source_flag); | 97 | LOG_DEBUG(Service_Mii, "called with source_flag={}, out_size={}", source_flag, output_size); |
| 98 | |||
| 99 | u32 mii_count{}; | ||
| 100 | std::vector<CharInfoElement> char_info_elements(output_size); | ||
| 101 | Result result = manager.Get(metadata, char_info_elements, mii_count, source_flag); | ||
| 103 | 102 | ||
| 104 | const auto default_miis{manager.GetDefault(source_flag)}; | 103 | if (mii_count != 0) { |
| 105 | if (default_miis.size() > 0) { | 104 | ctx.WriteBuffer(char_info_elements); |
| 106 | ctx.WriteBuffer(SerializeArray(default_miis)); | ||
| 107 | } | 105 | } |
| 108 | 106 | ||
| 109 | IPC::ResponseBuilder rb{ctx, 3}; | 107 | IPC::ResponseBuilder rb{ctx, 3}; |
| 110 | rb.Push(ResultSuccess); | 108 | rb.Push(result); |
| 111 | rb.Push<u32>(static_cast<u32>(default_miis.size())); | 109 | rb.Push(mii_count); |
| 112 | } | 110 | } |
| 113 | 111 | ||
| 114 | void Get1(HLERequestContext& ctx) { | 112 | void Get1(HLERequestContext& ctx) { |
| 115 | IPC::RequestParser rp{ctx}; | 113 | IPC::RequestParser rp{ctx}; |
| 116 | const auto source_flag{rp.PopRaw<SourceFlag>()}; | 114 | const auto source_flag{rp.PopRaw<SourceFlag>()}; |
| 115 | const auto output_size{ctx.GetWriteBufferNumElements<CharInfo>()}; | ||
| 117 | 116 | ||
| 118 | LOG_DEBUG(Service_Mii, "called with source_flag={}", source_flag); | 117 | LOG_DEBUG(Service_Mii, "called with source_flag={}, out_size={}", source_flag, output_size); |
| 119 | 118 | ||
| 120 | const auto default_miis{manager.GetDefault(source_flag)}; | 119 | u32 mii_count{}; |
| 120 | std::vector<CharInfo> char_info(output_size); | ||
| 121 | Result result = manager.Get(metadata, char_info, mii_count, source_flag); | ||
| 121 | 122 | ||
| 122 | std::vector<CharInfo> values; | 123 | if (mii_count != 0) { |
| 123 | for (const auto& element : default_miis) { | 124 | ctx.WriteBuffer(char_info); |
| 124 | values.emplace_back(element.info); | ||
| 125 | } | 125 | } |
| 126 | 126 | ||
| 127 | ctx.WriteBuffer(SerializeArray(values)); | ||
| 128 | |||
| 129 | IPC::ResponseBuilder rb{ctx, 3}; | 127 | IPC::ResponseBuilder rb{ctx, 3}; |
| 130 | rb.Push(ResultSuccess); | 128 | rb.Push(result); |
| 131 | rb.Push<u32>(static_cast<u32>(default_miis.size())); | 129 | rb.Push(mii_count); |
| 132 | } | 130 | } |
| 133 | 131 | ||
| 134 | void UpdateLatest(HLERequestContext& ctx) { | 132 | void UpdateLatest(HLERequestContext& ctx) { |
| 135 | IPC::RequestParser rp{ctx}; | 133 | IPC::RequestParser rp{ctx}; |
| 136 | const auto info{rp.PopRaw<CharInfo>()}; | 134 | const auto char_info{rp.PopRaw<CharInfo>()}; |
| 137 | const auto source_flag{rp.PopRaw<SourceFlag>()}; | 135 | const auto source_flag{rp.PopRaw<SourceFlag>()}; |
| 138 | 136 | ||
| 139 | LOG_DEBUG(Service_Mii, "called with source_flag={}", source_flag); | 137 | LOG_DEBUG(Service_Mii, "called with source_flag={}", source_flag); |
| 140 | 138 | ||
| 141 | CharInfo new_char_info{}; | 139 | CharInfo new_char_info{}; |
| 142 | const auto result{manager.UpdateLatest(&new_char_info, info, source_flag)}; | 140 | const auto result = manager.UpdateLatest(metadata, new_char_info, char_info, source_flag); |
| 143 | if (result != ResultSuccess) { | 141 | if (result.IsFailure()) { |
| 144 | IPC::ResponseBuilder rb{ctx, 2}; | 142 | IPC::ResponseBuilder rb{ctx, 2}; |
| 145 | rb.Push(result); | 143 | rb.Push(result); |
| 146 | return; | 144 | return; |
| @@ -153,7 +151,6 @@ private: | |||
| 153 | 151 | ||
| 154 | void BuildRandom(HLERequestContext& ctx) { | 152 | void BuildRandom(HLERequestContext& ctx) { |
| 155 | IPC::RequestParser rp{ctx}; | 153 | IPC::RequestParser rp{ctx}; |
| 156 | |||
| 157 | const auto age{rp.PopRaw<Age>()}; | 154 | const auto age{rp.PopRaw<Age>()}; |
| 158 | const auto gender{rp.PopRaw<Gender>()}; | 155 | const auto gender{rp.PopRaw<Gender>()}; |
| 159 | const auto race{rp.PopRaw<Race>()}; | 156 | const auto race{rp.PopRaw<Race>()}; |
| @@ -162,47 +159,48 @@ private: | |||
| 162 | 159 | ||
| 163 | if (age > Age::All) { | 160 | if (age > Age::All) { |
| 164 | IPC::ResponseBuilder rb{ctx, 2}; | 161 | IPC::ResponseBuilder rb{ctx, 2}; |
| 165 | rb.Push(ERROR_INVALID_ARGUMENT); | 162 | rb.Push(ResultInvalidArgument); |
| 166 | LOG_ERROR(Service_Mii, "invalid age={}", age); | ||
| 167 | return; | 163 | return; |
| 168 | } | 164 | } |
| 169 | 165 | ||
| 170 | if (gender > Gender::All) { | 166 | if (gender > Gender::All) { |
| 171 | IPC::ResponseBuilder rb{ctx, 2}; | 167 | IPC::ResponseBuilder rb{ctx, 2}; |
| 172 | rb.Push(ERROR_INVALID_ARGUMENT); | 168 | rb.Push(ResultInvalidArgument); |
| 173 | LOG_ERROR(Service_Mii, "invalid gender={}", gender); | ||
| 174 | return; | 169 | return; |
| 175 | } | 170 | } |
| 176 | 171 | ||
| 177 | if (race > Race::All) { | 172 | if (race > Race::All) { |
| 178 | IPC::ResponseBuilder rb{ctx, 2}; | 173 | IPC::ResponseBuilder rb{ctx, 2}; |
| 179 | rb.Push(ERROR_INVALID_ARGUMENT); | 174 | rb.Push(ResultInvalidArgument); |
| 180 | LOG_ERROR(Service_Mii, "invalid race={}", race); | ||
| 181 | return; | 175 | return; |
| 182 | } | 176 | } |
| 183 | 177 | ||
| 178 | CharInfo char_info{}; | ||
| 179 | manager.BuildRandom(char_info, age, gender, race); | ||
| 180 | |||
| 184 | IPC::ResponseBuilder rb{ctx, 2 + sizeof(CharInfo) / sizeof(u32)}; | 181 | IPC::ResponseBuilder rb{ctx, 2 + sizeof(CharInfo) / sizeof(u32)}; |
| 185 | rb.Push(ResultSuccess); | 182 | rb.Push(ResultSuccess); |
| 186 | rb.PushRaw<CharInfo>(manager.BuildRandom(age, gender, race)); | 183 | rb.PushRaw<CharInfo>(char_info); |
| 187 | } | 184 | } |
| 188 | 185 | ||
| 189 | void BuildDefault(HLERequestContext& ctx) { | 186 | void BuildDefault(HLERequestContext& ctx) { |
| 190 | IPC::RequestParser rp{ctx}; | 187 | IPC::RequestParser rp{ctx}; |
| 191 | const auto index{rp.Pop<u32>()}; | 188 | const auto index{rp.Pop<u32>()}; |
| 192 | 189 | ||
| 193 | LOG_DEBUG(Service_Mii, "called with index={}", index); | 190 | LOG_INFO(Service_Mii, "called with index={}", index); |
| 194 | 191 | ||
| 195 | if (index > 5) { | 192 | if (index > 5) { |
| 196 | LOG_ERROR(Service_Mii, "invalid argument, index cannot be greater than 5 but is {:08X}", | ||
| 197 | index); | ||
| 198 | IPC::ResponseBuilder rb{ctx, 2}; | 193 | IPC::ResponseBuilder rb{ctx, 2}; |
| 199 | rb.Push(ERROR_INVALID_ARGUMENT); | 194 | rb.Push(ResultInvalidArgument); |
| 200 | return; | 195 | return; |
| 201 | } | 196 | } |
| 202 | 197 | ||
| 198 | CharInfo char_info{}; | ||
| 199 | manager.BuildDefault(char_info, index); | ||
| 200 | |||
| 203 | IPC::ResponseBuilder rb{ctx, 2 + sizeof(CharInfo) / sizeof(u32)}; | 201 | IPC::ResponseBuilder rb{ctx, 2 + sizeof(CharInfo) / sizeof(u32)}; |
| 204 | rb.Push(ResultSuccess); | 202 | rb.Push(ResultSuccess); |
| 205 | rb.PushRaw<CharInfo>(manager.BuildDefault(index)); | 203 | rb.PushRaw<CharInfo>(char_info); |
| 206 | } | 204 | } |
| 207 | 205 | ||
| 208 | void GetIndex(HLERequestContext& ctx) { | 206 | void GetIndex(HLERequestContext& ctx) { |
| @@ -211,19 +209,21 @@ private: | |||
| 211 | 209 | ||
| 212 | LOG_DEBUG(Service_Mii, "called"); | 210 | LOG_DEBUG(Service_Mii, "called"); |
| 213 | 211 | ||
| 214 | u32 index{}; | 212 | s32 index{}; |
| 213 | const auto result = manager.GetIndex(metadata, info, index); | ||
| 214 | |||
| 215 | IPC::ResponseBuilder rb{ctx, 3}; | 215 | IPC::ResponseBuilder rb{ctx, 3}; |
| 216 | rb.Push(manager.GetIndex(info, index)); | 216 | rb.Push(result); |
| 217 | rb.Push(index); | 217 | rb.Push(index); |
| 218 | } | 218 | } |
| 219 | 219 | ||
| 220 | void SetInterfaceVersion(HLERequestContext& ctx) { | 220 | void SetInterfaceVersion(HLERequestContext& ctx) { |
| 221 | IPC::RequestParser rp{ctx}; | 221 | IPC::RequestParser rp{ctx}; |
| 222 | current_interface_version = rp.PopRaw<u32>(); | 222 | const auto interface_version{rp.PopRaw<u32>()}; |
| 223 | 223 | ||
| 224 | LOG_DEBUG(Service_Mii, "called, interface_version={:08X}", current_interface_version); | 224 | LOG_INFO(Service_Mii, "called, interface_version={:08X}", interface_version); |
| 225 | 225 | ||
| 226 | UNIMPLEMENTED_IF(current_interface_version != 1); | 226 | manager.SetInterfaceVersion(metadata, interface_version); |
| 227 | 227 | ||
| 228 | IPC::ResponseBuilder rb{ctx, 2}; | 228 | IPC::ResponseBuilder rb{ctx, 2}; |
| 229 | rb.Push(ResultSuccess); | 229 | rb.Push(ResultSuccess); |
| @@ -231,30 +231,27 @@ private: | |||
| 231 | 231 | ||
| 232 | void Convert(HLERequestContext& ctx) { | 232 | void Convert(HLERequestContext& ctx) { |
| 233 | IPC::RequestParser rp{ctx}; | 233 | IPC::RequestParser rp{ctx}; |
| 234 | |||
| 235 | const auto mii_v3{rp.PopRaw<Ver3StoreData>()}; | 234 | const auto mii_v3{rp.PopRaw<Ver3StoreData>()}; |
| 236 | 235 | ||
| 237 | LOG_INFO(Service_Mii, "called"); | 236 | LOG_INFO(Service_Mii, "called"); |
| 238 | 237 | ||
| 238 | CharInfo char_info{}; | ||
| 239 | manager.ConvertV3ToCharInfo(char_info, mii_v3); | ||
| 240 | |||
| 239 | IPC::ResponseBuilder rb{ctx, 2 + sizeof(CharInfo) / sizeof(u32)}; | 241 | IPC::ResponseBuilder rb{ctx, 2 + sizeof(CharInfo) / sizeof(u32)}; |
| 240 | rb.Push(ResultSuccess); | 242 | rb.Push(ResultSuccess); |
| 241 | rb.PushRaw<CharInfo>(manager.ConvertV3ToCharInfo(mii_v3)); | 243 | rb.PushRaw<CharInfo>(char_info); |
| 242 | } | ||
| 243 | |||
| 244 | constexpr bool IsInterfaceVersionSupported(u32 interface_version) const { | ||
| 245 | return current_interface_version >= interface_version; | ||
| 246 | } | 244 | } |
| 247 | 245 | ||
| 248 | MiiManager manager; | 246 | MiiManager manager{}; |
| 249 | 247 | DatabaseSessionMetadata metadata{}; | |
| 250 | u32 current_interface_version{}; | 248 | bool is_system{}; |
| 251 | u64 current_update_counter{}; | ||
| 252 | }; | 249 | }; |
| 253 | 250 | ||
| 254 | class MiiDBModule final : public ServiceFramework<MiiDBModule> { | 251 | class MiiDBModule final : public ServiceFramework<MiiDBModule> { |
| 255 | public: | 252 | public: |
| 256 | explicit MiiDBModule(Core::System& system_, const char* name_) | 253 | explicit MiiDBModule(Core::System& system_, const char* name_, bool is_system_) |
| 257 | : ServiceFramework{system_, name_} { | 254 | : ServiceFramework{system_, name_}, is_system{is_system_} { |
| 258 | // clang-format off | 255 | // clang-format off |
| 259 | static const FunctionInfo functions[] = { | 256 | static const FunctionInfo functions[] = { |
| 260 | {0, &MiiDBModule::GetDatabaseService, "GetDatabaseService"}, | 257 | {0, &MiiDBModule::GetDatabaseService, "GetDatabaseService"}, |
| @@ -268,10 +265,12 @@ private: | |||
| 268 | void GetDatabaseService(HLERequestContext& ctx) { | 265 | void GetDatabaseService(HLERequestContext& ctx) { |
| 269 | IPC::ResponseBuilder rb{ctx, 2, 0, 1}; | 266 | IPC::ResponseBuilder rb{ctx, 2, 0, 1}; |
| 270 | rb.Push(ResultSuccess); | 267 | rb.Push(ResultSuccess); |
| 271 | rb.PushIpcInterface<IDatabaseService>(system); | 268 | rb.PushIpcInterface<IDatabaseService>(system, is_system); |
| 272 | 269 | ||
| 273 | LOG_DEBUG(Service_Mii, "called"); | 270 | LOG_DEBUG(Service_Mii, "called"); |
| 274 | } | 271 | } |
| 272 | |||
| 273 | bool is_system{}; | ||
| 275 | }; | 274 | }; |
| 276 | 275 | ||
| 277 | class MiiImg final : public ServiceFramework<MiiImg> { | 276 | class MiiImg final : public ServiceFramework<MiiImg> { |
| @@ -303,8 +302,10 @@ public: | |||
| 303 | void LoopProcess(Core::System& system) { | 302 | void LoopProcess(Core::System& system) { |
| 304 | auto server_manager = std::make_unique<ServerManager>(system); | 303 | auto server_manager = std::make_unique<ServerManager>(system); |
| 305 | 304 | ||
| 306 | server_manager->RegisterNamedService("mii:e", std::make_shared<MiiDBModule>(system, "mii:e")); | 305 | server_manager->RegisterNamedService("mii:e", |
| 307 | server_manager->RegisterNamedService("mii:u", std::make_shared<MiiDBModule>(system, "mii:u")); | 306 | std::make_shared<MiiDBModule>(system, "mii:e", true)); |
| 307 | server_manager->RegisterNamedService("mii:u", | ||
| 308 | std::make_shared<MiiDBModule>(system, "mii:u", false)); | ||
| 308 | server_manager->RegisterNamedService("miiimg", std::make_shared<MiiImg>(system)); | 309 | server_manager->RegisterNamedService("miiimg", std::make_shared<MiiImg>(system)); |
| 309 | ServerManager::RunServer(std::move(server_manager)); | 310 | ServerManager::RunServer(std::move(server_manager)); |
| 310 | } | 311 | } |
diff --git a/src/core/hle/service/mii/mii_manager.cpp b/src/core/hle/service/mii/mii_manager.cpp index dd632df50..292d63777 100644 --- a/src/core/hle/service/mii/mii_manager.cpp +++ b/src/core/hle/service/mii/mii_manager.cpp | |||
| @@ -10,385 +10,24 @@ | |||
| 10 | 10 | ||
| 11 | #include "core/hle/service/acc/profile_manager.h" | 11 | #include "core/hle/service/acc/profile_manager.h" |
| 12 | #include "core/hle/service/mii/mii_manager.h" | 12 | #include "core/hle/service/mii/mii_manager.h" |
| 13 | #include "core/hle/service/mii/raw_data.h" | 13 | #include "core/hle/service/mii/mii_result.h" |
| 14 | #include "core/hle/service/mii/mii_util.h" | ||
| 15 | #include "core/hle/service/mii/types/core_data.h" | ||
| 16 | #include "core/hle/service/mii/types/raw_data.h" | ||
| 14 | 17 | ||
| 15 | namespace Service::Mii { | 18 | namespace Service::Mii { |
| 16 | |||
| 17 | namespace { | ||
| 18 | |||
| 19 | constexpr Result ERROR_CANNOT_FIND_ENTRY{ErrorModule::Mii, 4}; | ||
| 20 | |||
| 21 | constexpr std::size_t DefaultMiiCount{RawData::DefaultMii.size()}; | 19 | constexpr std::size_t DefaultMiiCount{RawData::DefaultMii.size()}; |
| 22 | 20 | ||
| 23 | constexpr MiiStoreData::Name DefaultMiiName{u'n', u'o', u' ', u'n', u'a', u'm', u'e'}; | 21 | MiiManager::MiiManager() {} |
| 24 | constexpr std::array<u8, 8> HairColorLookup{8, 1, 2, 3, 4, 5, 6, 7}; | ||
| 25 | constexpr std::array<u8, 6> EyeColorLookup{8, 9, 10, 11, 12, 13}; | ||
| 26 | constexpr std::array<u8, 5> MouthColorLookup{19, 20, 21, 22, 23}; | ||
| 27 | constexpr std::array<u8, 7> GlassesColorLookup{8, 14, 15, 16, 17, 18, 0}; | ||
| 28 | constexpr std::array<u8, 62> EyeRotateLookup{ | ||
| 29 | {0x03, 0x04, 0x04, 0x04, 0x03, 0x04, 0x04, 0x04, 0x03, 0x04, 0x04, 0x04, 0x04, 0x03, 0x03, 0x04, | ||
| 30 | 0x04, 0x04, 0x03, 0x03, 0x04, 0x03, 0x04, 0x03, 0x03, 0x04, 0x03, 0x04, 0x04, 0x03, 0x04, 0x04, | ||
| 31 | 0x04, 0x03, 0x03, 0x03, 0x04, 0x04, 0x03, 0x03, 0x03, 0x04, 0x04, 0x03, 0x03, 0x03, 0x03, 0x03, | ||
| 32 | 0x03, 0x03, 0x03, 0x03, 0x04, 0x04, 0x04, 0x04, 0x03, 0x04, 0x04, 0x03, 0x04, 0x04}}; | ||
| 33 | constexpr std::array<u8, 24> EyebrowRotateLookup{{0x06, 0x06, 0x05, 0x07, 0x06, 0x07, 0x06, 0x07, | ||
| 34 | 0x04, 0x07, 0x06, 0x08, 0x05, 0x05, 0x06, 0x06, | ||
| 35 | 0x07, 0x07, 0x06, 0x06, 0x05, 0x06, 0x07, 0x05}}; | ||
| 36 | |||
| 37 | template <typename T, std::size_t SourceArraySize, std::size_t DestArraySize> | ||
| 38 | std::array<T, DestArraySize> ResizeArray(const std::array<T, SourceArraySize>& in) { | ||
| 39 | std::array<T, DestArraySize> out{}; | ||
| 40 | std::memcpy(out.data(), in.data(), sizeof(T) * std::min(SourceArraySize, DestArraySize)); | ||
| 41 | return out; | ||
| 42 | } | ||
| 43 | |||
| 44 | CharInfo ConvertStoreDataToInfo(const MiiStoreData& data) { | ||
| 45 | MiiStoreBitFields bf; | ||
| 46 | std::memcpy(&bf, data.data.data.data(), sizeof(MiiStoreBitFields)); | ||
| 47 | |||
| 48 | return { | ||
| 49 | .uuid = data.data.uuid, | ||
| 50 | .name = ResizeArray<char16_t, 10, 11>(data.data.name), | ||
| 51 | .font_region = static_cast<u8>(bf.font_region.Value()), | ||
| 52 | .favorite_color = static_cast<u8>(bf.favorite_color.Value()), | ||
| 53 | .gender = static_cast<u8>(bf.gender.Value()), | ||
| 54 | .height = static_cast<u8>(bf.height.Value()), | ||
| 55 | .build = static_cast<u8>(bf.build.Value()), | ||
| 56 | .type = static_cast<u8>(bf.type.Value()), | ||
| 57 | .region_move = static_cast<u8>(bf.region_move.Value()), | ||
| 58 | .faceline_type = static_cast<u8>(bf.faceline_type.Value()), | ||
| 59 | .faceline_color = static_cast<u8>(bf.faceline_color.Value()), | ||
| 60 | .faceline_wrinkle = static_cast<u8>(bf.faceline_wrinkle.Value()), | ||
| 61 | .faceline_make = static_cast<u8>(bf.faceline_makeup.Value()), | ||
| 62 | .hair_type = static_cast<u8>(bf.hair_type.Value()), | ||
| 63 | .hair_color = static_cast<u8>(bf.hair_color.Value()), | ||
| 64 | .hair_flip = static_cast<u8>(bf.hair_flip.Value()), | ||
| 65 | .eye_type = static_cast<u8>(bf.eye_type.Value()), | ||
| 66 | .eye_color = static_cast<u8>(bf.eye_color.Value()), | ||
| 67 | .eye_scale = static_cast<u8>(bf.eye_scale.Value()), | ||
| 68 | .eye_aspect = static_cast<u8>(bf.eye_aspect.Value()), | ||
| 69 | .eye_rotate = static_cast<u8>(bf.eye_rotate.Value()), | ||
| 70 | .eye_x = static_cast<u8>(bf.eye_x.Value()), | ||
| 71 | .eye_y = static_cast<u8>(bf.eye_y.Value()), | ||
| 72 | .eyebrow_type = static_cast<u8>(bf.eyebrow_type.Value()), | ||
| 73 | .eyebrow_color = static_cast<u8>(bf.eyebrow_color.Value()), | ||
| 74 | .eyebrow_scale = static_cast<u8>(bf.eyebrow_scale.Value()), | ||
| 75 | .eyebrow_aspect = static_cast<u8>(bf.eyebrow_aspect.Value()), | ||
| 76 | .eyebrow_rotate = static_cast<u8>(bf.eyebrow_rotate.Value()), | ||
| 77 | .eyebrow_x = static_cast<u8>(bf.eyebrow_x.Value()), | ||
| 78 | .eyebrow_y = static_cast<u8>(bf.eyebrow_y.Value() + 3), | ||
| 79 | .nose_type = static_cast<u8>(bf.nose_type.Value()), | ||
| 80 | .nose_scale = static_cast<u8>(bf.nose_scale.Value()), | ||
| 81 | .nose_y = static_cast<u8>(bf.nose_y.Value()), | ||
| 82 | .mouth_type = static_cast<u8>(bf.mouth_type.Value()), | ||
| 83 | .mouth_color = static_cast<u8>(bf.mouth_color.Value()), | ||
| 84 | .mouth_scale = static_cast<u8>(bf.mouth_scale.Value()), | ||
| 85 | .mouth_aspect = static_cast<u8>(bf.mouth_aspect.Value()), | ||
| 86 | .mouth_y = static_cast<u8>(bf.mouth_y.Value()), | ||
| 87 | .beard_color = static_cast<u8>(bf.beard_color.Value()), | ||
| 88 | .beard_type = static_cast<u8>(bf.beard_type.Value()), | ||
| 89 | .mustache_type = static_cast<u8>(bf.mustache_type.Value()), | ||
| 90 | .mustache_scale = static_cast<u8>(bf.mustache_scale.Value()), | ||
| 91 | .mustache_y = static_cast<u8>(bf.mustache_y.Value()), | ||
| 92 | .glasses_type = static_cast<u8>(bf.glasses_type.Value()), | ||
| 93 | .glasses_color = static_cast<u8>(bf.glasses_color.Value()), | ||
| 94 | .glasses_scale = static_cast<u8>(bf.glasses_scale.Value()), | ||
| 95 | .glasses_y = static_cast<u8>(bf.glasses_y.Value()), | ||
| 96 | .mole_type = static_cast<u8>(bf.mole_type.Value()), | ||
| 97 | .mole_scale = static_cast<u8>(bf.mole_scale.Value()), | ||
| 98 | .mole_x = static_cast<u8>(bf.mole_x.Value()), | ||
| 99 | .mole_y = static_cast<u8>(bf.mole_y.Value()), | ||
| 100 | .padding = 0, | ||
| 101 | }; | ||
| 102 | } | ||
| 103 | |||
| 104 | u16 GenerateCrc16(const void* data, std::size_t size) { | ||
| 105 | s32 crc{}; | ||
| 106 | for (std::size_t i = 0; i < size; i++) { | ||
| 107 | crc ^= static_cast<const u8*>(data)[i] << 8; | ||
| 108 | for (std::size_t j = 0; j < 8; j++) { | ||
| 109 | crc <<= 1; | ||
| 110 | if ((crc & 0x10000) != 0) { | ||
| 111 | crc = (crc ^ 0x1021) & 0xFFFF; | ||
| 112 | } | ||
| 113 | } | ||
| 114 | } | ||
| 115 | return Common::swap16(static_cast<u16>(crc)); | ||
| 116 | } | ||
| 117 | |||
| 118 | template <typename T> | ||
| 119 | T GetRandomValue(T min, T max) { | ||
| 120 | std::random_device device; | ||
| 121 | std::mt19937 gen(device()); | ||
| 122 | std::uniform_int_distribution<u64> distribution(static_cast<u64>(min), static_cast<u64>(max)); | ||
| 123 | return static_cast<T>(distribution(gen)); | ||
| 124 | } | ||
| 125 | |||
| 126 | template <typename T> | ||
| 127 | T GetRandomValue(T max) { | ||
| 128 | return GetRandomValue<T>({}, max); | ||
| 129 | } | ||
| 130 | |||
| 131 | MiiStoreData BuildRandomStoreData(Age age, Gender gender, Race race, const Common::UUID& user_id) { | ||
| 132 | MiiStoreBitFields bf{}; | ||
| 133 | |||
| 134 | if (gender == Gender::All) { | ||
| 135 | gender = GetRandomValue<Gender>(Gender::Maximum); | ||
| 136 | } | ||
| 137 | |||
| 138 | bf.gender.Assign(gender); | ||
| 139 | bf.favorite_color.Assign(GetRandomValue<u8>(11)); | ||
| 140 | bf.region_move.Assign(0); | ||
| 141 | bf.font_region.Assign(FontRegion::Standard); | ||
| 142 | bf.type.Assign(0); | ||
| 143 | bf.height.Assign(64); | ||
| 144 | bf.build.Assign(64); | ||
| 145 | |||
| 146 | if (age == Age::All) { | ||
| 147 | const auto temp{GetRandomValue<int>(10)}; | ||
| 148 | if (temp >= 8) { | ||
| 149 | age = Age::Old; | ||
| 150 | } else if (temp >= 4) { | ||
| 151 | age = Age::Normal; | ||
| 152 | } else { | ||
| 153 | age = Age::Young; | ||
| 154 | } | ||
| 155 | } | ||
| 156 | |||
| 157 | if (race == Race::All) { | ||
| 158 | const auto temp{GetRandomValue<int>(10)}; | ||
| 159 | if (temp >= 8) { | ||
| 160 | race = Race::Black; | ||
| 161 | } else if (temp >= 4) { | ||
| 162 | race = Race::White; | ||
| 163 | } else { | ||
| 164 | race = Race::Asian; | ||
| 165 | } | ||
| 166 | } | ||
| 167 | |||
| 168 | u32 axis_y{}; | ||
| 169 | if (gender == Gender::Female && age == Age::Young) { | ||
| 170 | axis_y = GetRandomValue<u32>(3); | ||
| 171 | } | ||
| 172 | |||
| 173 | const std::size_t index{3 * static_cast<std::size_t>(age) + | ||
| 174 | 9 * static_cast<std::size_t>(gender) + static_cast<std::size_t>(race)}; | ||
| 175 | |||
| 176 | const auto faceline_type_info{RawData::RandomMiiFaceline.at(index)}; | ||
| 177 | const auto faceline_color_info{RawData::RandomMiiFacelineColor.at( | ||
| 178 | 3 * static_cast<std::size_t>(gender) + static_cast<std::size_t>(race))}; | ||
| 179 | const auto faceline_wrinkle_info{RawData::RandomMiiFacelineWrinkle.at(index)}; | ||
| 180 | const auto faceline_makeup_info{RawData::RandomMiiFacelineMakeup.at(index)}; | ||
| 181 | const auto hair_type_info{RawData::RandomMiiHairType.at(index)}; | ||
| 182 | const auto hair_color_info{RawData::RandomMiiHairColor.at(3 * static_cast<std::size_t>(race) + | ||
| 183 | static_cast<std::size_t>(age))}; | ||
| 184 | const auto eye_type_info{RawData::RandomMiiEyeType.at(index)}; | ||
| 185 | const auto eye_color_info{RawData::RandomMiiEyeColor.at(static_cast<std::size_t>(race))}; | ||
| 186 | const auto eyebrow_type_info{RawData::RandomMiiEyebrowType.at(index)}; | ||
| 187 | const auto nose_type_info{RawData::RandomMiiNoseType.at(index)}; | ||
| 188 | const auto mouth_type_info{RawData::RandomMiiMouthType.at(index)}; | ||
| 189 | const auto glasses_type_info{RawData::RandomMiiGlassType.at(static_cast<std::size_t>(age))}; | ||
| 190 | |||
| 191 | bf.faceline_type.Assign( | ||
| 192 | faceline_type_info.values[GetRandomValue<std::size_t>(faceline_type_info.values_count)]); | ||
| 193 | bf.faceline_color.Assign( | ||
| 194 | faceline_color_info.values[GetRandomValue<std::size_t>(faceline_color_info.values_count)]); | ||
| 195 | bf.faceline_wrinkle.Assign( | ||
| 196 | faceline_wrinkle_info | ||
| 197 | .values[GetRandomValue<std::size_t>(faceline_wrinkle_info.values_count)]); | ||
| 198 | bf.faceline_makeup.Assign( | ||
| 199 | faceline_makeup_info | ||
| 200 | .values[GetRandomValue<std::size_t>(faceline_makeup_info.values_count)]); | ||
| 201 | |||
| 202 | bf.hair_type.Assign( | ||
| 203 | hair_type_info.values[GetRandomValue<std::size_t>(hair_type_info.values_count)]); | ||
| 204 | bf.hair_color.Assign( | ||
| 205 | HairColorLookup[hair_color_info | ||
| 206 | .values[GetRandomValue<std::size_t>(hair_color_info.values_count)]]); | ||
| 207 | bf.hair_flip.Assign(GetRandomValue<HairFlip>(HairFlip::Maximum)); | ||
| 208 | |||
| 209 | bf.eye_type.Assign( | ||
| 210 | eye_type_info.values[GetRandomValue<std::size_t>(eye_type_info.values_count)]); | ||
| 211 | |||
| 212 | const auto eye_rotate_1{gender != Gender::Male ? 4 : 2}; | ||
| 213 | const auto eye_rotate_2{gender != Gender::Male ? 3 : 4}; | ||
| 214 | const auto eye_rotate_offset{32 - EyeRotateLookup[eye_rotate_1] + eye_rotate_2}; | ||
| 215 | const auto eye_rotate{32 - EyeRotateLookup[bf.eye_type]}; | ||
| 216 | |||
| 217 | bf.eye_color.Assign( | ||
| 218 | EyeColorLookup[eye_color_info | ||
| 219 | .values[GetRandomValue<std::size_t>(eye_color_info.values_count)]]); | ||
| 220 | bf.eye_scale.Assign(4); | ||
| 221 | bf.eye_aspect.Assign(3); | ||
| 222 | bf.eye_rotate.Assign(eye_rotate_offset - eye_rotate); | ||
| 223 | bf.eye_x.Assign(2); | ||
| 224 | bf.eye_y.Assign(axis_y + 12); | ||
| 225 | |||
| 226 | bf.eyebrow_type.Assign( | ||
| 227 | eyebrow_type_info.values[GetRandomValue<std::size_t>(eyebrow_type_info.values_count)]); | ||
| 228 | |||
| 229 | const auto eyebrow_rotate_1{race == Race::Asian ? 6 : 0}; | ||
| 230 | const auto eyebrow_y{race == Race::Asian ? 9 : 10}; | ||
| 231 | const auto eyebrow_rotate_offset{32 - EyebrowRotateLookup[eyebrow_rotate_1] + 6}; | ||
| 232 | const auto eyebrow_rotate{ | ||
| 233 | 32 - EyebrowRotateLookup[static_cast<std::size_t>(bf.eyebrow_type.Value())]}; | ||
| 234 | |||
| 235 | bf.eyebrow_color.Assign(bf.hair_color); | ||
| 236 | bf.eyebrow_scale.Assign(4); | ||
| 237 | bf.eyebrow_aspect.Assign(3); | ||
| 238 | bf.eyebrow_rotate.Assign(eyebrow_rotate_offset - eyebrow_rotate); | ||
| 239 | bf.eyebrow_x.Assign(2); | ||
| 240 | bf.eyebrow_y.Assign(axis_y + eyebrow_y); | ||
| 241 | |||
| 242 | const auto nose_scale{gender == Gender::Female ? 3 : 4}; | ||
| 243 | |||
| 244 | bf.nose_type.Assign( | ||
| 245 | nose_type_info.values[GetRandomValue<std::size_t>(nose_type_info.values_count)]); | ||
| 246 | bf.nose_scale.Assign(nose_scale); | ||
| 247 | bf.nose_y.Assign(axis_y + 9); | ||
| 248 | |||
| 249 | const auto mouth_color{gender == Gender::Female ? GetRandomValue<int>(4) : 0}; | ||
| 250 | |||
| 251 | bf.mouth_type.Assign( | ||
| 252 | mouth_type_info.values[GetRandomValue<std::size_t>(mouth_type_info.values_count)]); | ||
| 253 | bf.mouth_color.Assign(MouthColorLookup[mouth_color]); | ||
| 254 | bf.mouth_scale.Assign(4); | ||
| 255 | bf.mouth_aspect.Assign(3); | ||
| 256 | bf.mouth_y.Assign(axis_y + 13); | ||
| 257 | |||
| 258 | bf.beard_color.Assign(bf.hair_color); | ||
| 259 | bf.mustache_scale.Assign(4); | ||
| 260 | |||
| 261 | if (gender == Gender::Male && age != Age::Young && GetRandomValue<int>(10) < 2) { | ||
| 262 | const auto mustache_and_beard_flag{ | ||
| 263 | GetRandomValue<BeardAndMustacheFlag>(BeardAndMustacheFlag::All)}; | ||
| 264 | |||
| 265 | auto beard_type{BeardType::None}; | ||
| 266 | auto mustache_type{MustacheType::None}; | ||
| 267 | |||
| 268 | if ((mustache_and_beard_flag & BeardAndMustacheFlag::Beard) == | ||
| 269 | BeardAndMustacheFlag::Beard) { | ||
| 270 | beard_type = GetRandomValue<BeardType>(BeardType::Beard1, BeardType::Beard5); | ||
| 271 | } | ||
| 272 | |||
| 273 | if ((mustache_and_beard_flag & BeardAndMustacheFlag::Mustache) == | ||
| 274 | BeardAndMustacheFlag::Mustache) { | ||
| 275 | mustache_type = | ||
| 276 | GetRandomValue<MustacheType>(MustacheType::Mustache1, MustacheType::Mustache5); | ||
| 277 | } | ||
| 278 | |||
| 279 | bf.mustache_type.Assign(mustache_type); | ||
| 280 | bf.beard_type.Assign(beard_type); | ||
| 281 | bf.mustache_y.Assign(10); | ||
| 282 | } else { | ||
| 283 | bf.mustache_type.Assign(MustacheType::None); | ||
| 284 | bf.beard_type.Assign(BeardType::None); | ||
| 285 | bf.mustache_y.Assign(axis_y + 10); | ||
| 286 | } | ||
| 287 | |||
| 288 | const auto glasses_type_start{GetRandomValue<std::size_t>(100)}; | ||
| 289 | u8 glasses_type{}; | ||
| 290 | while (glasses_type_start < glasses_type_info.values[glasses_type]) { | ||
| 291 | if (++glasses_type >= glasses_type_info.values_count) { | ||
| 292 | ASSERT(false); | ||
| 293 | break; | ||
| 294 | } | ||
| 295 | } | ||
| 296 | |||
| 297 | bf.glasses_type.Assign(glasses_type); | ||
| 298 | bf.glasses_color.Assign(GlassesColorLookup[0]); | ||
| 299 | bf.glasses_scale.Assign(4); | ||
| 300 | bf.glasses_y.Assign(axis_y + 10); | ||
| 301 | |||
| 302 | bf.mole_type.Assign(0); | ||
| 303 | bf.mole_scale.Assign(4); | ||
| 304 | bf.mole_x.Assign(2); | ||
| 305 | bf.mole_y.Assign(20); | ||
| 306 | 22 | ||
| 307 | return {DefaultMiiName, bf, user_id}; | 23 | bool MiiManager::IsUpdated(DatabaseSessionMetadata& metadata, SourceFlag source_flag) const { |
| 308 | } | ||
| 309 | |||
| 310 | MiiStoreData BuildDefaultStoreData(const DefaultMii& info, const Common::UUID& user_id) { | ||
| 311 | MiiStoreBitFields bf{}; | ||
| 312 | |||
| 313 | bf.font_region.Assign(info.font_region); | ||
| 314 | bf.favorite_color.Assign(info.favorite_color); | ||
| 315 | bf.gender.Assign(info.gender); | ||
| 316 | bf.height.Assign(info.height); | ||
| 317 | bf.build.Assign(info.weight); | ||
| 318 | bf.type.Assign(info.type); | ||
| 319 | bf.region_move.Assign(info.region); | ||
| 320 | bf.faceline_type.Assign(info.face_type); | ||
| 321 | bf.faceline_color.Assign(info.face_color); | ||
| 322 | bf.faceline_wrinkle.Assign(info.face_wrinkle); | ||
| 323 | bf.faceline_makeup.Assign(info.face_makeup); | ||
| 324 | bf.hair_type.Assign(info.hair_type); | ||
| 325 | bf.hair_color.Assign(HairColorLookup[info.hair_color]); | ||
| 326 | bf.hair_flip.Assign(static_cast<HairFlip>(info.hair_flip)); | ||
| 327 | bf.eye_type.Assign(info.eye_type); | ||
| 328 | bf.eye_color.Assign(EyeColorLookup[info.eye_color]); | ||
| 329 | bf.eye_scale.Assign(info.eye_scale); | ||
| 330 | bf.eye_aspect.Assign(info.eye_aspect); | ||
| 331 | bf.eye_rotate.Assign(info.eye_rotate); | ||
| 332 | bf.eye_x.Assign(info.eye_x); | ||
| 333 | bf.eye_y.Assign(info.eye_y); | ||
| 334 | bf.eyebrow_type.Assign(info.eyebrow_type); | ||
| 335 | bf.eyebrow_color.Assign(HairColorLookup[info.eyebrow_color]); | ||
| 336 | bf.eyebrow_scale.Assign(info.eyebrow_scale); | ||
| 337 | bf.eyebrow_aspect.Assign(info.eyebrow_aspect); | ||
| 338 | bf.eyebrow_rotate.Assign(info.eyebrow_rotate); | ||
| 339 | bf.eyebrow_x.Assign(info.eyebrow_x); | ||
| 340 | bf.eyebrow_y.Assign(info.eyebrow_y - 3); | ||
| 341 | bf.nose_type.Assign(info.nose_type); | ||
| 342 | bf.nose_scale.Assign(info.nose_scale); | ||
| 343 | bf.nose_y.Assign(info.nose_y); | ||
| 344 | bf.mouth_type.Assign(info.mouth_type); | ||
| 345 | bf.mouth_color.Assign(MouthColorLookup[info.mouth_color]); | ||
| 346 | bf.mouth_scale.Assign(info.mouth_scale); | ||
| 347 | bf.mouth_aspect.Assign(info.mouth_aspect); | ||
| 348 | bf.mouth_y.Assign(info.mouth_y); | ||
| 349 | bf.beard_color.Assign(HairColorLookup[info.beard_color]); | ||
| 350 | bf.beard_type.Assign(static_cast<BeardType>(info.beard_type)); | ||
| 351 | bf.mustache_type.Assign(static_cast<MustacheType>(info.mustache_type)); | ||
| 352 | bf.mustache_scale.Assign(info.mustache_scale); | ||
| 353 | bf.mustache_y.Assign(info.mustache_y); | ||
| 354 | bf.glasses_type.Assign(info.glasses_type); | ||
| 355 | bf.glasses_color.Assign(GlassesColorLookup[info.glasses_color]); | ||
| 356 | bf.glasses_scale.Assign(info.glasses_scale); | ||
| 357 | bf.glasses_y.Assign(info.glasses_y); | ||
| 358 | bf.mole_type.Assign(info.mole_type); | ||
| 359 | bf.mole_scale.Assign(info.mole_scale); | ||
| 360 | bf.mole_x.Assign(info.mole_x); | ||
| 361 | bf.mole_y.Assign(info.mole_y); | ||
| 362 | |||
| 363 | return {DefaultMiiName, bf, user_id}; | ||
| 364 | } | ||
| 365 | |||
| 366 | } // namespace | ||
| 367 | |||
| 368 | MiiStoreData::MiiStoreData() = default; | ||
| 369 | |||
| 370 | MiiStoreData::MiiStoreData(const MiiStoreData::Name& name, const MiiStoreBitFields& bit_fields, | ||
| 371 | const Common::UUID& user_id) { | ||
| 372 | data.name = name; | ||
| 373 | data.uuid = Common::UUID::MakeRandomRFC4122V4(); | ||
| 374 | |||
| 375 | std::memcpy(data.data.data(), &bit_fields, sizeof(MiiStoreBitFields)); | ||
| 376 | data_crc = GenerateCrc16(data.data.data(), sizeof(data)); | ||
| 377 | device_crc = GenerateCrc16(&user_id, sizeof(Common::UUID)); | ||
| 378 | } | ||
| 379 | |||
| 380 | MiiManager::MiiManager() : user_id{Service::Account::ProfileManager().GetLastOpenedUser()} {} | ||
| 381 | |||
| 382 | bool MiiManager::CheckAndResetUpdateCounter(SourceFlag source_flag, u64& current_update_counter) { | ||
| 383 | if ((source_flag & SourceFlag::Database) == SourceFlag::None) { | 24 | if ((source_flag & SourceFlag::Database) == SourceFlag::None) { |
| 384 | return false; | 25 | return false; |
| 385 | } | 26 | } |
| 386 | 27 | ||
| 387 | const bool result{current_update_counter != update_counter}; | 28 | const auto metadata_update_counter = metadata.update_counter; |
| 388 | 29 | metadata.update_counter = update_counter; | |
| 389 | current_update_counter = update_counter; | 30 | return metadata_update_counter != update_counter; |
| 390 | |||
| 391 | return result; | ||
| 392 | } | 31 | } |
| 393 | 32 | ||
| 394 | bool MiiManager::IsFullDatabase() const { | 33 | bool MiiManager::IsFullDatabase() const { |
| @@ -396,306 +35,138 @@ bool MiiManager::IsFullDatabase() const { | |||
| 396 | return false; | 35 | return false; |
| 397 | } | 36 | } |
| 398 | 37 | ||
| 399 | u32 MiiManager::GetCount(SourceFlag source_flag) const { | 38 | u32 MiiManager::GetCount(const DatabaseSessionMetadata& metadata, SourceFlag source_flag) const { |
| 400 | std::size_t count{}; | 39 | u32 mii_count{}; |
| 40 | if ((source_flag & SourceFlag::Default) != SourceFlag::None) { | ||
| 41 | mii_count += DefaultMiiCount; | ||
| 42 | } | ||
| 401 | if ((source_flag & SourceFlag::Database) != SourceFlag::None) { | 43 | if ((source_flag & SourceFlag::Database) != SourceFlag::None) { |
| 402 | // TODO(bunnei): We don't implement the Mii database, but when we do, update this | 44 | // TODO(bunnei): We don't implement the Mii database, but when we do, update this |
| 403 | count += 0; | ||
| 404 | } | 45 | } |
| 405 | if ((source_flag & SourceFlag::Default) != SourceFlag::None) { | 46 | return mii_count; |
| 406 | count += DefaultMiiCount; | ||
| 407 | } | ||
| 408 | return static_cast<u32>(count); | ||
| 409 | } | 47 | } |
| 410 | 48 | ||
| 411 | Result MiiManager::UpdateLatest(CharInfo* out_info, const CharInfo& info, SourceFlag source_flag) { | 49 | Result MiiManager::UpdateLatest(DatabaseSessionMetadata& metadata, CharInfo& out_char_info, |
| 50 | const CharInfo& char_info, SourceFlag source_flag) { | ||
| 412 | if ((source_flag & SourceFlag::Database) == SourceFlag::None) { | 51 | if ((source_flag & SourceFlag::Database) == SourceFlag::None) { |
| 413 | return ERROR_CANNOT_FIND_ENTRY; | 52 | return ResultNotFound; |
| 414 | } | 53 | } |
| 415 | 54 | ||
| 416 | // TODO(bunnei): We don't implement the Mii database, so we can't have an entry | 55 | // TODO(bunnei): We don't implement the Mii database, so we can't have an entry |
| 417 | return ERROR_CANNOT_FIND_ENTRY; | 56 | return ResultNotFound; |
| 418 | } | 57 | } |
| 419 | 58 | ||
| 420 | CharInfo MiiManager::BuildRandom(Age age, Gender gender, Race race) { | 59 | void MiiManager::BuildDefault(CharInfo& out_char_info, u32 index) const { |
| 421 | return ConvertStoreDataToInfo(BuildRandomStoreData(age, gender, race, user_id)); | 60 | StoreData store_data{}; |
| 61 | store_data.BuildDefault(index); | ||
| 62 | out_char_info.SetFromStoreData(store_data); | ||
| 422 | } | 63 | } |
| 423 | 64 | ||
| 424 | CharInfo MiiManager::BuildBase(Gender gender) { | 65 | void MiiManager::BuildBase(CharInfo& out_char_info, Gender gender) const { |
| 425 | const std::size_t index = gender == Gender::Female ? 1 : 0; | 66 | StoreData store_data{}; |
| 426 | return ConvertStoreDataToInfo(BuildDefaultStoreData(RawData::BaseMii.at(index), user_id)); | 67 | store_data.BuildBase(gender); |
| 68 | out_char_info.SetFromStoreData(store_data); | ||
| 427 | } | 69 | } |
| 428 | 70 | ||
| 429 | CharInfo MiiManager::BuildDefault(std::size_t index) { | 71 | void MiiManager::BuildRandom(CharInfo& out_char_info, Age age, Gender gender, Race race) const { |
| 430 | return ConvertStoreDataToInfo(BuildDefaultStoreData(RawData::DefaultMii.at(index), user_id)); | 72 | StoreData store_data{}; |
| 73 | store_data.BuildRandom(age, gender, race); | ||
| 74 | out_char_info.SetFromStoreData(store_data); | ||
| 431 | } | 75 | } |
| 432 | 76 | ||
| 433 | CharInfo MiiManager::ConvertV3ToCharInfo(const Ver3StoreData& mii_v3) const { | 77 | void MiiManager::ConvertV3ToCharInfo(CharInfo& out_char_info, const Ver3StoreData& mii_v3) const { |
| 434 | Service::Mii::MiiManager manager; | 78 | StoreData store_data{}; |
| 435 | auto mii = manager.BuildBase(Mii::Gender::Male); | 79 | mii_v3.BuildToStoreData(store_data); |
| 80 | out_char_info.SetFromStoreData(store_data); | ||
| 81 | } | ||
| 436 | 82 | ||
| 437 | if (!ValidateV3Info(mii_v3)) { | 83 | Result MiiManager::Get(const DatabaseSessionMetadata& metadata, |
| 438 | return mii; | 84 | std::span<CharInfoElement> out_elements, u32& out_count, |
| 85 | SourceFlag source_flag) { | ||
| 86 | if ((source_flag & SourceFlag::Database) == SourceFlag::None) { | ||
| 87 | return BuildDefault(out_elements, out_count, source_flag); | ||
| 439 | } | 88 | } |
| 440 | 89 | ||
| 441 | // TODO: We are ignoring a bunch of data from the mii_v3 | 90 | // TODO(bunnei): We don't implement the Mii database, so we can't have an entry |
| 442 | |||
| 443 | mii.gender = static_cast<u8>(mii_v3.mii_information.gender); | ||
| 444 | mii.favorite_color = static_cast<u8>(mii_v3.mii_information.favorite_color); | ||
| 445 | mii.height = mii_v3.height; | ||
| 446 | mii.build = mii_v3.build; | ||
| 447 | |||
| 448 | // Copy name until string terminator | ||
| 449 | mii.name = {}; | ||
| 450 | for (std::size_t index = 0; index < mii.name.size() - 1; index++) { | ||
| 451 | mii.name[index] = mii_v3.mii_name[index]; | ||
| 452 | if (mii.name[index] == 0) { | ||
| 453 | break; | ||
| 454 | } | ||
| 455 | } | ||
| 456 | 91 | ||
| 457 | mii.font_region = mii_v3.region_information.character_set; | 92 | // Include default Mii at the end of the list |
| 458 | 93 | return BuildDefault(out_elements, out_count, source_flag); | |
| 459 | mii.faceline_type = mii_v3.appearance_bits1.face_shape; | ||
| 460 | mii.faceline_color = mii_v3.appearance_bits1.skin_color; | ||
| 461 | mii.faceline_wrinkle = mii_v3.appearance_bits2.wrinkles; | ||
| 462 | mii.faceline_make = mii_v3.appearance_bits2.makeup; | ||
| 463 | |||
| 464 | mii.hair_type = mii_v3.hair_style; | ||
| 465 | mii.hair_color = mii_v3.appearance_bits3.hair_color; | ||
| 466 | mii.hair_flip = mii_v3.appearance_bits3.flip_hair; | ||
| 467 | |||
| 468 | mii.eye_type = static_cast<u8>(mii_v3.appearance_bits4.eye_type); | ||
| 469 | mii.eye_color = static_cast<u8>(mii_v3.appearance_bits4.eye_color); | ||
| 470 | mii.eye_scale = static_cast<u8>(mii_v3.appearance_bits4.eye_scale); | ||
| 471 | mii.eye_aspect = static_cast<u8>(mii_v3.appearance_bits4.eye_vertical_stretch); | ||
| 472 | mii.eye_rotate = static_cast<u8>(mii_v3.appearance_bits4.eye_rotation); | ||
| 473 | mii.eye_x = static_cast<u8>(mii_v3.appearance_bits4.eye_spacing); | ||
| 474 | mii.eye_y = static_cast<u8>(mii_v3.appearance_bits4.eye_y_position); | ||
| 475 | |||
| 476 | mii.eyebrow_type = static_cast<u8>(mii_v3.appearance_bits5.eyebrow_style); | ||
| 477 | mii.eyebrow_color = static_cast<u8>(mii_v3.appearance_bits5.eyebrow_color); | ||
| 478 | mii.eyebrow_scale = static_cast<u8>(mii_v3.appearance_bits5.eyebrow_scale); | ||
| 479 | mii.eyebrow_aspect = static_cast<u8>(mii_v3.appearance_bits5.eyebrow_yscale); | ||
| 480 | mii.eyebrow_rotate = static_cast<u8>(mii_v3.appearance_bits5.eyebrow_rotation); | ||
| 481 | mii.eyebrow_x = static_cast<u8>(mii_v3.appearance_bits5.eyebrow_spacing); | ||
| 482 | mii.eyebrow_y = static_cast<u8>(mii_v3.appearance_bits5.eyebrow_y_position); | ||
| 483 | |||
| 484 | mii.nose_type = static_cast<u8>(mii_v3.appearance_bits6.nose_type); | ||
| 485 | mii.nose_scale = static_cast<u8>(mii_v3.appearance_bits6.nose_scale); | ||
| 486 | mii.nose_y = static_cast<u8>(mii_v3.appearance_bits6.nose_y_position); | ||
| 487 | |||
| 488 | mii.mouth_type = static_cast<u8>(mii_v3.appearance_bits7.mouth_type); | ||
| 489 | mii.mouth_color = static_cast<u8>(mii_v3.appearance_bits7.mouth_color); | ||
| 490 | mii.mouth_scale = static_cast<u8>(mii_v3.appearance_bits7.mouth_scale); | ||
| 491 | mii.mouth_aspect = static_cast<u8>(mii_v3.appearance_bits7.mouth_horizontal_stretch); | ||
| 492 | mii.mouth_y = static_cast<u8>(mii_v3.appearance_bits8.mouth_y_position); | ||
| 493 | |||
| 494 | mii.mustache_type = static_cast<u8>(mii_v3.appearance_bits8.mustache_type); | ||
| 495 | mii.mustache_scale = static_cast<u8>(mii_v3.appearance_bits9.mustache_scale); | ||
| 496 | mii.mustache_y = static_cast<u8>(mii_v3.appearance_bits9.mustache_y_position); | ||
| 497 | |||
| 498 | mii.beard_type = static_cast<u8>(mii_v3.appearance_bits9.bear_type); | ||
| 499 | mii.beard_color = static_cast<u8>(mii_v3.appearance_bits9.facial_hair_color); | ||
| 500 | |||
| 501 | mii.glasses_type = static_cast<u8>(mii_v3.appearance_bits10.glasses_type); | ||
| 502 | mii.glasses_color = static_cast<u8>(mii_v3.appearance_bits10.glasses_color); | ||
| 503 | mii.glasses_scale = static_cast<u8>(mii_v3.appearance_bits10.glasses_scale); | ||
| 504 | mii.glasses_y = static_cast<u8>(mii_v3.appearance_bits10.glasses_y_position); | ||
| 505 | |||
| 506 | mii.mole_type = static_cast<u8>(mii_v3.appearance_bits11.mole_enabled); | ||
| 507 | mii.mole_scale = static_cast<u8>(mii_v3.appearance_bits11.mole_scale); | ||
| 508 | mii.mole_x = static_cast<u8>(mii_v3.appearance_bits11.mole_x_position); | ||
| 509 | mii.mole_y = static_cast<u8>(mii_v3.appearance_bits11.mole_y_position); | ||
| 510 | |||
| 511 | // TODO: Validate mii data | ||
| 512 | |||
| 513 | return mii; | ||
| 514 | } | 94 | } |
| 515 | 95 | ||
| 516 | Ver3StoreData MiiManager::BuildFromStoreData(const CharInfo& mii) const { | 96 | Result MiiManager::Get(const DatabaseSessionMetadata& metadata, std::span<CharInfo> out_char_info, |
| 517 | Service::Mii::MiiManager manager; | 97 | u32& out_count, SourceFlag source_flag) { |
| 518 | Ver3StoreData mii_v3{}; | 98 | if ((source_flag & SourceFlag::Database) == SourceFlag::None) { |
| 519 | 99 | return BuildDefault(out_char_info, out_count, source_flag); | |
| 520 | // TODO: We are ignoring a bunch of data from the mii_v3 | ||
| 521 | |||
| 522 | mii_v3.version = 1; | ||
| 523 | mii_v3.mii_information.gender.Assign(mii.gender); | ||
| 524 | mii_v3.mii_information.favorite_color.Assign(mii.favorite_color); | ||
| 525 | mii_v3.height = mii.height; | ||
| 526 | mii_v3.build = mii.build; | ||
| 527 | |||
| 528 | // Copy name until string terminator | ||
| 529 | mii_v3.mii_name = {}; | ||
| 530 | for (std::size_t index = 0; index < mii.name.size() - 1; index++) { | ||
| 531 | mii_v3.mii_name[index] = mii.name[index]; | ||
| 532 | if (mii_v3.mii_name[index] == 0) { | ||
| 533 | break; | ||
| 534 | } | ||
| 535 | } | 100 | } |
| 536 | 101 | ||
| 537 | mii_v3.region_information.character_set.Assign(mii.font_region); | 102 | // TODO(bunnei): We don't implement the Mii database, so we can't have an entry |
| 538 | |||
| 539 | mii_v3.appearance_bits1.face_shape.Assign(mii.faceline_type); | ||
| 540 | mii_v3.appearance_bits2.wrinkles.Assign(mii.faceline_wrinkle); | ||
| 541 | mii_v3.appearance_bits2.makeup.Assign(mii.faceline_make); | ||
| 542 | |||
| 543 | mii_v3.hair_style = mii.hair_type; | ||
| 544 | mii_v3.appearance_bits3.flip_hair.Assign(mii.hair_flip); | ||
| 545 | 103 | ||
| 546 | mii_v3.appearance_bits4.eye_type.Assign(mii.eye_type); | 104 | // Include default Mii at the end of the list |
| 547 | mii_v3.appearance_bits4.eye_scale.Assign(mii.eye_scale); | 105 | return BuildDefault(out_char_info, out_count, source_flag); |
| 548 | mii_v3.appearance_bits4.eye_vertical_stretch.Assign(mii.eye_aspect); | 106 | } |
| 549 | mii_v3.appearance_bits4.eye_rotation.Assign(mii.eye_rotate); | ||
| 550 | mii_v3.appearance_bits4.eye_spacing.Assign(mii.eye_x); | ||
| 551 | mii_v3.appearance_bits4.eye_y_position.Assign(mii.eye_y); | ||
| 552 | 107 | ||
| 553 | mii_v3.appearance_bits5.eyebrow_style.Assign(mii.eyebrow_type); | 108 | Result MiiManager::BuildDefault(std::span<CharInfoElement> out_elements, u32& out_count, |
| 554 | mii_v3.appearance_bits5.eyebrow_scale.Assign(mii.eyebrow_scale); | 109 | SourceFlag source_flag) { |
| 555 | mii_v3.appearance_bits5.eyebrow_yscale.Assign(mii.eyebrow_aspect); | 110 | if ((source_flag & SourceFlag::Default) == SourceFlag::None) { |
| 556 | mii_v3.appearance_bits5.eyebrow_rotation.Assign(mii.eyebrow_rotate); | 111 | return ResultSuccess; |
| 557 | mii_v3.appearance_bits5.eyebrow_spacing.Assign(mii.eyebrow_x); | 112 | } |
| 558 | mii_v3.appearance_bits5.eyebrow_y_position.Assign(mii.eyebrow_y); | ||
| 559 | 113 | ||
| 560 | mii_v3.appearance_bits6.nose_type.Assign(mii.nose_type); | 114 | StoreData store_data{}; |
| 561 | mii_v3.appearance_bits6.nose_scale.Assign(mii.nose_scale); | ||
| 562 | mii_v3.appearance_bits6.nose_y_position.Assign(mii.nose_y); | ||
| 563 | 115 | ||
| 564 | mii_v3.appearance_bits7.mouth_type.Assign(mii.mouth_type); | 116 | for (std::size_t index = 0; index < DefaultMiiCount; ++index) { |
| 565 | mii_v3.appearance_bits7.mouth_scale.Assign(mii.mouth_scale); | 117 | if (out_elements.size() <= static_cast<std::size_t>(out_count)) { |
| 566 | mii_v3.appearance_bits7.mouth_horizontal_stretch.Assign(mii.mouth_aspect); | 118 | return ResultInvalidArgumentSize; |
| 567 | mii_v3.appearance_bits8.mouth_y_position.Assign(mii.mouth_y); | 119 | } |
| 568 | 120 | ||
| 569 | mii_v3.appearance_bits8.mustache_type.Assign(mii.mustache_type); | 121 | store_data.BuildDefault(static_cast<u32>(index)); |
| 570 | mii_v3.appearance_bits9.mustache_scale.Assign(mii.mustache_scale); | ||
| 571 | mii_v3.appearance_bits9.mustache_y_position.Assign(mii.mustache_y); | ||
| 572 | 122 | ||
| 573 | mii_v3.appearance_bits9.bear_type.Assign(mii.beard_type); | 123 | out_elements[out_count].source = Source::Default; |
| 124 | out_elements[out_count].char_info.SetFromStoreData(store_data); | ||
| 125 | out_count++; | ||
| 126 | } | ||
| 574 | 127 | ||
| 575 | mii_v3.appearance_bits10.glasses_scale.Assign(mii.glasses_scale); | 128 | return ResultSuccess; |
| 576 | mii_v3.appearance_bits10.glasses_y_position.Assign(mii.glasses_y); | 129 | } |
| 577 | 130 | ||
| 578 | mii_v3.appearance_bits11.mole_enabled.Assign(mii.mole_type); | 131 | Result MiiManager::BuildDefault(std::span<CharInfo> out_char_info, u32& out_count, |
| 579 | mii_v3.appearance_bits11.mole_scale.Assign(mii.mole_scale); | 132 | SourceFlag source_flag) { |
| 580 | mii_v3.appearance_bits11.mole_x_position.Assign(mii.mole_x); | 133 | if ((source_flag & SourceFlag::Default) == SourceFlag::None) { |
| 581 | mii_v3.appearance_bits11.mole_y_position.Assign(mii.mole_y); | 134 | return ResultSuccess; |
| 135 | } | ||
| 582 | 136 | ||
| 583 | // These types are converted to V3 from a table | 137 | StoreData store_data{}; |
| 584 | mii_v3.appearance_bits1.skin_color.Assign(Ver3FacelineColorTable[mii.faceline_color]); | ||
| 585 | mii_v3.appearance_bits3.hair_color.Assign(Ver3HairColorTable[mii.hair_color]); | ||
| 586 | mii_v3.appearance_bits4.eye_color.Assign(Ver3EyeColorTable[mii.eye_color]); | ||
| 587 | mii_v3.appearance_bits5.eyebrow_color.Assign(Ver3HairColorTable[mii.eyebrow_color]); | ||
| 588 | mii_v3.appearance_bits7.mouth_color.Assign(Ver3MouthlineColorTable[mii.mouth_color]); | ||
| 589 | mii_v3.appearance_bits9.facial_hair_color.Assign(Ver3HairColorTable[mii.beard_color]); | ||
| 590 | mii_v3.appearance_bits10.glasses_color.Assign(Ver3GlassColorTable[mii.glasses_color]); | ||
| 591 | mii_v3.appearance_bits10.glasses_type.Assign(Ver3GlassTypeTable[mii.glasses_type]); | ||
| 592 | 138 | ||
| 593 | mii_v3.crc = GenerateCrc16(&mii_v3, sizeof(Ver3StoreData) - sizeof(u16)); | 139 | for (std::size_t index = 0; index < DefaultMiiCount; ++index) { |
| 140 | if (out_char_info.size() <= static_cast<std::size_t>(out_count)) { | ||
| 141 | return ResultInvalidArgumentSize; | ||
| 142 | } | ||
| 594 | 143 | ||
| 595 | // TODO: Validate mii_v3 data | 144 | store_data.BuildDefault(static_cast<u32>(index)); |
| 596 | 145 | ||
| 597 | return mii_v3; | 146 | out_char_info[out_count].SetFromStoreData(store_data); |
| 598 | } | 147 | out_count++; |
| 599 | 148 | } | |
| 600 | NfpStoreDataExtension MiiManager::SetFromStoreData(const CharInfo& mii) const { | ||
| 601 | return { | ||
| 602 | .faceline_color = static_cast<u8>(mii.faceline_color & 0xf), | ||
| 603 | .hair_color = static_cast<u8>(mii.hair_color & 0x7f), | ||
| 604 | .eye_color = static_cast<u8>(mii.eyebrow_color & 0x7f), | ||
| 605 | .eyebrow_color = static_cast<u8>(mii.eyebrow_color & 0x7f), | ||
| 606 | .mouth_color = static_cast<u8>(mii.mouth_color & 0x7f), | ||
| 607 | .beard_color = static_cast<u8>(mii.beard_color & 0x7f), | ||
| 608 | .glass_color = static_cast<u8>(mii.glasses_color & 0x7f), | ||
| 609 | .glass_type = static_cast<u8>(mii.glasses_type & 0x1f), | ||
| 610 | }; | ||
| 611 | } | ||
| 612 | 149 | ||
| 613 | bool MiiManager::ValidateV3Info(const Ver3StoreData& mii_v3) const { | 150 | return ResultSuccess; |
| 614 | bool is_valid = mii_v3.version == 0 || mii_v3.version == 3; | ||
| 615 | |||
| 616 | is_valid = is_valid && (mii_v3.mii_name[0] != 0); | ||
| 617 | |||
| 618 | is_valid = is_valid && (mii_v3.mii_information.birth_month < 13); | ||
| 619 | is_valid = is_valid && (mii_v3.mii_information.birth_day < 32); | ||
| 620 | is_valid = is_valid && (mii_v3.mii_information.favorite_color < 12); | ||
| 621 | is_valid = is_valid && (mii_v3.height < 128); | ||
| 622 | is_valid = is_valid && (mii_v3.build < 128); | ||
| 623 | |||
| 624 | is_valid = is_valid && (mii_v3.appearance_bits1.face_shape < 12); | ||
| 625 | is_valid = is_valid && (mii_v3.appearance_bits1.skin_color < 7); | ||
| 626 | is_valid = is_valid && (mii_v3.appearance_bits2.wrinkles < 12); | ||
| 627 | is_valid = is_valid && (mii_v3.appearance_bits2.makeup < 12); | ||
| 628 | |||
| 629 | is_valid = is_valid && (mii_v3.hair_style < 132); | ||
| 630 | is_valid = is_valid && (mii_v3.appearance_bits3.hair_color < 8); | ||
| 631 | |||
| 632 | is_valid = is_valid && (mii_v3.appearance_bits4.eye_type < 60); | ||
| 633 | is_valid = is_valid && (mii_v3.appearance_bits4.eye_color < 6); | ||
| 634 | is_valid = is_valid && (mii_v3.appearance_bits4.eye_scale < 8); | ||
| 635 | is_valid = is_valid && (mii_v3.appearance_bits4.eye_vertical_stretch < 7); | ||
| 636 | is_valid = is_valid && (mii_v3.appearance_bits4.eye_rotation < 8); | ||
| 637 | is_valid = is_valid && (mii_v3.appearance_bits4.eye_spacing < 13); | ||
| 638 | is_valid = is_valid && (mii_v3.appearance_bits4.eye_y_position < 19); | ||
| 639 | |||
| 640 | is_valid = is_valid && (mii_v3.appearance_bits5.eyebrow_style < 25); | ||
| 641 | is_valid = is_valid && (mii_v3.appearance_bits5.eyebrow_color < 8); | ||
| 642 | is_valid = is_valid && (mii_v3.appearance_bits5.eyebrow_scale < 9); | ||
| 643 | is_valid = is_valid && (mii_v3.appearance_bits5.eyebrow_yscale < 7); | ||
| 644 | is_valid = is_valid && (mii_v3.appearance_bits5.eyebrow_rotation < 12); | ||
| 645 | is_valid = is_valid && (mii_v3.appearance_bits5.eyebrow_spacing < 12); | ||
| 646 | is_valid = is_valid && (mii_v3.appearance_bits5.eyebrow_y_position < 19); | ||
| 647 | |||
| 648 | is_valid = is_valid && (mii_v3.appearance_bits6.nose_type < 18); | ||
| 649 | is_valid = is_valid && (mii_v3.appearance_bits6.nose_scale < 9); | ||
| 650 | is_valid = is_valid && (mii_v3.appearance_bits6.nose_y_position < 19); | ||
| 651 | |||
| 652 | is_valid = is_valid && (mii_v3.appearance_bits7.mouth_type < 36); | ||
| 653 | is_valid = is_valid && (mii_v3.appearance_bits7.mouth_color < 5); | ||
| 654 | is_valid = is_valid && (mii_v3.appearance_bits7.mouth_scale < 9); | ||
| 655 | is_valid = is_valid && (mii_v3.appearance_bits7.mouth_horizontal_stretch < 7); | ||
| 656 | is_valid = is_valid && (mii_v3.appearance_bits8.mouth_y_position < 19); | ||
| 657 | |||
| 658 | is_valid = is_valid && (mii_v3.appearance_bits8.mustache_type < 6); | ||
| 659 | is_valid = is_valid && (mii_v3.appearance_bits9.mustache_scale < 7); | ||
| 660 | is_valid = is_valid && (mii_v3.appearance_bits9.mustache_y_position < 17); | ||
| 661 | |||
| 662 | is_valid = is_valid && (mii_v3.appearance_bits9.bear_type < 6); | ||
| 663 | is_valid = is_valid && (mii_v3.appearance_bits9.facial_hair_color < 8); | ||
| 664 | |||
| 665 | is_valid = is_valid && (mii_v3.appearance_bits10.glasses_type < 9); | ||
| 666 | is_valid = is_valid && (mii_v3.appearance_bits10.glasses_color < 6); | ||
| 667 | is_valid = is_valid && (mii_v3.appearance_bits10.glasses_scale < 8); | ||
| 668 | is_valid = is_valid && (mii_v3.appearance_bits10.glasses_y_position < 21); | ||
| 669 | |||
| 670 | is_valid = is_valid && (mii_v3.appearance_bits11.mole_enabled < 2); | ||
| 671 | is_valid = is_valid && (mii_v3.appearance_bits11.mole_scale < 9); | ||
| 672 | is_valid = is_valid && (mii_v3.appearance_bits11.mole_x_position < 17); | ||
| 673 | is_valid = is_valid && (mii_v3.appearance_bits11.mole_y_position < 31); | ||
| 674 | |||
| 675 | return is_valid; | ||
| 676 | } | 151 | } |
| 677 | 152 | ||
| 678 | std::vector<MiiInfoElement> MiiManager::GetDefault(SourceFlag source_flag) { | 153 | Result MiiManager::GetIndex(const DatabaseSessionMetadata& metadata, const CharInfo& char_info, |
| 679 | std::vector<MiiInfoElement> result; | 154 | s32& out_index) { |
| 680 | |||
| 681 | if ((source_flag & SourceFlag::Default) == SourceFlag::None) { | ||
| 682 | return result; | ||
| 683 | } | ||
| 684 | 155 | ||
| 685 | for (std::size_t index = 0; index < DefaultMiiCount; index++) { | 156 | if (char_info.Verify() != ValidationResult::NoErrors) { |
| 686 | result.emplace_back(BuildDefault(index), Source::Default); | 157 | return ResultInvalidCharInfo; |
| 687 | } | 158 | } |
| 688 | 159 | ||
| 689 | return result; | ||
| 690 | } | ||
| 691 | |||
| 692 | Result MiiManager::GetIndex([[maybe_unused]] const CharInfo& info, u32& index) { | ||
| 693 | constexpr u32 INVALID_INDEX{0xFFFFFFFF}; | 160 | constexpr u32 INVALID_INDEX{0xFFFFFFFF}; |
| 694 | 161 | ||
| 695 | index = INVALID_INDEX; | 162 | out_index = INVALID_INDEX; |
| 696 | 163 | ||
| 697 | // TODO(bunnei): We don't implement the Mii database, so we can't have an index | 164 | // TODO(bunnei): We don't implement the Mii database, so we can't have an index |
| 698 | return ERROR_CANNOT_FIND_ENTRY; | 165 | return ResultNotFound; |
| 166 | } | ||
| 167 | |||
| 168 | void MiiManager::SetInterfaceVersion(DatabaseSessionMetadata& metadata, u32 version) { | ||
| 169 | metadata.interface_version = version; | ||
| 699 | } | 170 | } |
| 700 | 171 | ||
| 701 | } // namespace Service::Mii | 172 | } // namespace Service::Mii |
diff --git a/src/core/hle/service/mii/mii_manager.h b/src/core/hle/service/mii/mii_manager.h index 0c8295ebe..a2e7a6d73 100644 --- a/src/core/hle/service/mii/mii_manager.h +++ b/src/core/hle/service/mii/mii_manager.h | |||
| @@ -6,7 +6,10 @@ | |||
| 6 | #include <vector> | 6 | #include <vector> |
| 7 | 7 | ||
| 8 | #include "core/hle/result.h" | 8 | #include "core/hle/result.h" |
| 9 | #include "core/hle/service/mii/types.h" | 9 | #include "core/hle/service/mii/mii_types.h" |
| 10 | #include "core/hle/service/mii/types/char_info.h" | ||
| 11 | #include "core/hle/service/mii/types/store_data.h" | ||
| 12 | #include "core/hle/service/mii/types/ver3_store_data.h" | ||
| 10 | 13 | ||
| 11 | namespace Service::Mii { | 14 | namespace Service::Mii { |
| 12 | 15 | ||
| @@ -16,26 +19,30 @@ class MiiManager { | |||
| 16 | public: | 19 | public: |
| 17 | MiiManager(); | 20 | MiiManager(); |
| 18 | 21 | ||
| 19 | bool CheckAndResetUpdateCounter(SourceFlag source_flag, u64& current_update_counter); | 22 | bool IsUpdated(DatabaseSessionMetadata& metadata, SourceFlag source_flag) const; |
| 23 | |||
| 20 | bool IsFullDatabase() const; | 24 | bool IsFullDatabase() const; |
| 21 | u32 GetCount(SourceFlag source_flag) const; | 25 | u32 GetCount(const DatabaseSessionMetadata& metadata, SourceFlag source_flag) const; |
| 22 | Result UpdateLatest(CharInfo* out_info, const CharInfo& info, SourceFlag source_flag); | 26 | Result UpdateLatest(DatabaseSessionMetadata& metadata, CharInfo& out_char_info, |
| 23 | CharInfo BuildRandom(Age age, Gender gender, Race race); | 27 | const CharInfo& char_info, SourceFlag source_flag); |
| 24 | CharInfo BuildBase(Gender gender); | 28 | Result Get(const DatabaseSessionMetadata& metadata, std::span<CharInfoElement> out_elements, |
| 25 | CharInfo BuildDefault(std::size_t index); | 29 | u32& out_count, SourceFlag source_flag); |
| 26 | CharInfo ConvertV3ToCharInfo(const Ver3StoreData& mii_v3) const; | 30 | Result Get(const DatabaseSessionMetadata& metadata, std::span<CharInfo> out_char_info, |
| 27 | bool ValidateV3Info(const Ver3StoreData& mii_v3) const; | 31 | u32& out_count, SourceFlag source_flag); |
| 28 | std::vector<MiiInfoElement> GetDefault(SourceFlag source_flag); | 32 | void BuildDefault(CharInfo& out_char_info, u32 index) const; |
| 29 | Result GetIndex(const CharInfo& info, u32& index); | 33 | void BuildBase(CharInfo& out_char_info, Gender gender) const; |
| 30 | 34 | void BuildRandom(CharInfo& out_char_info, Age age, Gender gender, Race race) const; | |
| 31 | // This is nn::mii::detail::Ver::StoreDataRaw::BuildFromStoreData | 35 | void ConvertV3ToCharInfo(CharInfo& out_char_info, const Ver3StoreData& mii_v3) const; |
| 32 | Ver3StoreData BuildFromStoreData(const CharInfo& mii) const; | 36 | std::vector<CharInfoElement> GetDefault(SourceFlag source_flag); |
| 33 | 37 | Result GetIndex(const DatabaseSessionMetadata& metadata, const CharInfo& char_info, | |
| 34 | // This is nn::mii::detail::NfpStoreDataExtentionRaw::SetFromStoreData | 38 | s32& out_index); |
| 35 | NfpStoreDataExtension SetFromStoreData(const CharInfo& mii) const; | 39 | void SetInterfaceVersion(DatabaseSessionMetadata& metadata, u32 version); |
| 36 | 40 | ||
| 37 | private: | 41 | private: |
| 38 | const Common::UUID user_id{}; | 42 | Result BuildDefault(std::span<CharInfoElement> out_elements, u32& out_count, |
| 43 | SourceFlag source_flag); | ||
| 44 | Result BuildDefault(std::span<CharInfo> out_char_info, u32& out_count, SourceFlag source_flag); | ||
| 45 | |||
| 39 | u64 update_counter{}; | 46 | u64 update_counter{}; |
| 40 | }; | 47 | }; |
| 41 | 48 | ||
diff --git a/src/core/hle/service/mii/mii_result.h b/src/core/hle/service/mii/mii_result.h new file mode 100644 index 000000000..021cb76da --- /dev/null +++ b/src/core/hle/service/mii/mii_result.h | |||
| @@ -0,0 +1,20 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include "core/hle/result.h" | ||
| 7 | |||
| 8 | namespace Service::Mii { | ||
| 9 | |||
| 10 | constexpr Result ResultInvalidArgument{ErrorModule::Mii, 1}; | ||
| 11 | constexpr Result ResultInvalidArgumentSize{ErrorModule::Mii, 2}; | ||
| 12 | constexpr Result ResultNotUpdated{ErrorModule::Mii, 3}; | ||
| 13 | constexpr Result ResultNotFound{ErrorModule::Mii, 4}; | ||
| 14 | constexpr Result ResultDatabaseFull{ErrorModule::Mii, 5}; | ||
| 15 | constexpr Result ResultInvalidCharInfo{ErrorModule::Mii, 100}; | ||
| 16 | constexpr Result ResultInvalidStoreData{ErrorModule::Mii, 109}; | ||
| 17 | constexpr Result ResultInvalidOperation{ErrorModule::Mii, 202}; | ||
| 18 | constexpr Result ResultPermissionDenied{ErrorModule::Mii, 203}; | ||
| 19 | |||
| 20 | }; // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/mii_types.h b/src/core/hle/service/mii/mii_types.h new file mode 100644 index 000000000..95476f745 --- /dev/null +++ b/src/core/hle/service/mii/mii_types.h | |||
| @@ -0,0 +1,694 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include <array> | ||
| 7 | #include <type_traits> | ||
| 8 | |||
| 9 | #include "common/bit_field.h" | ||
| 10 | #include "common/common_funcs.h" | ||
| 11 | #include "common/common_types.h" | ||
| 12 | #include "common/uuid.h" | ||
| 13 | |||
| 14 | namespace Service::Mii { | ||
| 15 | |||
| 16 | constexpr u8 MaxHeight = 127; | ||
| 17 | constexpr u8 MaxBuild = 127; | ||
| 18 | constexpr u8 MaxType = 1; | ||
| 19 | constexpr u8 MaxRegionMove = 3; | ||
| 20 | constexpr u8 MaxEyeScale = 7; | ||
| 21 | constexpr u8 MaxEyeAspect = 6; | ||
| 22 | constexpr u8 MaxEyeRotate = 7; | ||
| 23 | constexpr u8 MaxEyeX = 12; | ||
| 24 | constexpr u8 MaxEyeY = 18; | ||
| 25 | constexpr u8 MaxEyebrowScale = 8; | ||
| 26 | constexpr u8 MaxEyebrowAspect = 6; | ||
| 27 | constexpr u8 MaxEyebrowRotate = 11; | ||
| 28 | constexpr u8 MaxEyebrowX = 12; | ||
| 29 | constexpr u8 MaxEyebrowY = 18; | ||
| 30 | constexpr u8 MaxNoseScale = 8; | ||
| 31 | constexpr u8 MaxNoseY = 18; | ||
| 32 | constexpr u8 MaxMouthScale = 8; | ||
| 33 | constexpr u8 MaxMoutAspect = 6; | ||
| 34 | constexpr u8 MaxMouthY = 18; | ||
| 35 | constexpr u8 MaxMustacheScale = 8; | ||
| 36 | constexpr u8 MasMustacheY = 16; | ||
| 37 | constexpr u8 MaxGlassScale = 7; | ||
| 38 | constexpr u8 MaxGlassY = 20; | ||
| 39 | constexpr u8 MaxMoleScale = 8; | ||
| 40 | constexpr u8 MaxMoleX = 16; | ||
| 41 | constexpr u8 MaxMoleY = 30; | ||
| 42 | constexpr u8 MaxVer3CommonColor = 7; | ||
| 43 | constexpr u8 MaxVer3GlassType = 8; | ||
| 44 | |||
| 45 | enum class Age : u8 { | ||
| 46 | Young, | ||
| 47 | Normal, | ||
| 48 | Old, | ||
| 49 | All, // Default | ||
| 50 | |||
| 51 | Max = All, | ||
| 52 | }; | ||
| 53 | |||
| 54 | enum class Gender : u8 { | ||
| 55 | Male, | ||
| 56 | Female, | ||
| 57 | All, // Default | ||
| 58 | |||
| 59 | Max = Female, | ||
| 60 | }; | ||
| 61 | |||
| 62 | enum class Race : u8 { | ||
| 63 | Black, | ||
| 64 | White, | ||
| 65 | Asian, | ||
| 66 | All, // Default | ||
| 67 | |||
| 68 | Max = All, | ||
| 69 | }; | ||
| 70 | |||
| 71 | enum class HairType : u8 { | ||
| 72 | NormalLong, // Default | ||
| 73 | NormalShort, | ||
| 74 | NormalMedium, | ||
| 75 | NormalExtraLong, | ||
| 76 | NormalLongBottom, | ||
| 77 | NormalTwoPeaks, | ||
| 78 | PartingLong, | ||
| 79 | FrontLock, | ||
| 80 | PartingShort, | ||
| 81 | PartingExtraLongCurved, | ||
| 82 | PartingExtraLong, | ||
| 83 | PartingMiddleLong, | ||
| 84 | PartingSquared, | ||
| 85 | PartingLongBottom, | ||
| 86 | PeaksTop, | ||
| 87 | PeaksSquared, | ||
| 88 | PartingPeaks, | ||
| 89 | PeaksLongBottom, | ||
| 90 | Peaks, | ||
| 91 | PeaksRounded, | ||
| 92 | PeaksSide, | ||
| 93 | PeaksMedium, | ||
| 94 | PeaksLong, | ||
| 95 | PeaksRoundedLong, | ||
| 96 | PartingFrontPeaks, | ||
| 97 | PartingLongFront, | ||
| 98 | PartingLongRounded, | ||
| 99 | PartingFrontPeaksLong, | ||
| 100 | PartingExtraLongRounded, | ||
| 101 | LongRounded, | ||
| 102 | NormalUnknown1, | ||
| 103 | NormalUnknown2, | ||
| 104 | NormalUnknown3, | ||
| 105 | NormalUnknown4, | ||
| 106 | NormalUnknown5, | ||
| 107 | NormalUnknown6, | ||
| 108 | DreadLocks, | ||
| 109 | PlatedMats, | ||
| 110 | Caps, | ||
| 111 | Afro, | ||
| 112 | PlatedMatsLong, | ||
| 113 | Beanie, | ||
| 114 | Short, | ||
| 115 | ShortTopLongSide, | ||
| 116 | ShortUnknown1, | ||
| 117 | ShortUnknown2, | ||
| 118 | MilitaryParting, | ||
| 119 | Military, | ||
| 120 | ShortUnknown3, | ||
| 121 | ShortUnknown4, | ||
| 122 | ShortUnknown5, | ||
| 123 | ShortUnknown6, | ||
| 124 | NoneTop, | ||
| 125 | None, | ||
| 126 | LongUnknown1, | ||
| 127 | LongUnknown2, | ||
| 128 | LongUnknown3, | ||
| 129 | LongUnknown4, | ||
| 130 | LongUnknown5, | ||
| 131 | LongUnknown6, | ||
| 132 | LongUnknown7, | ||
| 133 | LongUnknown8, | ||
| 134 | LongUnknown9, | ||
| 135 | LongUnknown10, | ||
| 136 | LongUnknown11, | ||
| 137 | LongUnknown12, | ||
| 138 | LongUnknown13, | ||
| 139 | LongUnknown14, | ||
| 140 | LongUnknown15, | ||
| 141 | LongUnknown16, | ||
| 142 | LongUnknown17, | ||
| 143 | LongUnknown18, | ||
| 144 | LongUnknown19, | ||
| 145 | LongUnknown20, | ||
| 146 | LongUnknown21, | ||
| 147 | LongUnknown22, | ||
| 148 | LongUnknown23, | ||
| 149 | LongUnknown24, | ||
| 150 | LongUnknown25, | ||
| 151 | LongUnknown26, | ||
| 152 | LongUnknown27, | ||
| 153 | LongUnknown28, | ||
| 154 | LongUnknown29, | ||
| 155 | LongUnknown30, | ||
| 156 | LongUnknown31, | ||
| 157 | LongUnknown32, | ||
| 158 | LongUnknown33, | ||
| 159 | LongUnknown34, | ||
| 160 | LongUnknown35, | ||
| 161 | LongUnknown36, | ||
| 162 | LongUnknown37, | ||
| 163 | LongUnknown38, | ||
| 164 | LongUnknown39, | ||
| 165 | LongUnknown40, | ||
| 166 | LongUnknown41, | ||
| 167 | LongUnknown42, | ||
| 168 | LongUnknown43, | ||
| 169 | LongUnknown44, | ||
| 170 | LongUnknown45, | ||
| 171 | LongUnknown46, | ||
| 172 | LongUnknown47, | ||
| 173 | LongUnknown48, | ||
| 174 | LongUnknown49, | ||
| 175 | LongUnknown50, | ||
| 176 | LongUnknown51, | ||
| 177 | LongUnknown52, | ||
| 178 | LongUnknown53, | ||
| 179 | LongUnknown54, | ||
| 180 | LongUnknown55, | ||
| 181 | LongUnknown56, | ||
| 182 | LongUnknown57, | ||
| 183 | LongUnknown58, | ||
| 184 | LongUnknown59, | ||
| 185 | LongUnknown60, | ||
| 186 | LongUnknown61, | ||
| 187 | LongUnknown62, | ||
| 188 | LongUnknown63, | ||
| 189 | LongUnknown64, | ||
| 190 | LongUnknown65, | ||
| 191 | LongUnknown66, | ||
| 192 | TwoMediumFrontStrandsOneLongBackPonyTail, | ||
| 193 | TwoFrontStrandsLongBackPonyTail, | ||
| 194 | PartingFrontTwoLongBackPonyTails, | ||
| 195 | TwoFrontStrandsOneLongBackPonyTail, | ||
| 196 | LongBackPonyTail, | ||
| 197 | LongFrontTwoLongBackPonyTails, | ||
| 198 | StrandsTwoShortSidedPonyTails, | ||
| 199 | TwoMediumSidedPonyTails, | ||
| 200 | ShortFrontTwoBackPonyTails, | ||
| 201 | TwoShortSidedPonyTails, | ||
| 202 | TwoLongSidedPonyTails, | ||
| 203 | LongFrontTwoBackPonyTails, | ||
| 204 | |||
| 205 | Max = LongFrontTwoBackPonyTails, | ||
| 206 | }; | ||
| 207 | |||
| 208 | enum class MoleType : u8 { | ||
| 209 | None, // Default | ||
| 210 | OneDot, | ||
| 211 | |||
| 212 | Max = OneDot, | ||
| 213 | }; | ||
| 214 | |||
| 215 | enum class HairFlip : u8 { | ||
| 216 | Left, // Default | ||
| 217 | Right, | ||
| 218 | |||
| 219 | Max = Right, | ||
| 220 | }; | ||
| 221 | |||
| 222 | enum class CommonColor : u8 { | ||
| 223 | // For simplicity common colors aren't listed | ||
| 224 | Max = 99, | ||
| 225 | Count = 100, | ||
| 226 | }; | ||
| 227 | |||
| 228 | enum class FavoriteColor : u8 { | ||
| 229 | Red, // Default | ||
| 230 | Orange, | ||
| 231 | Yellow, | ||
| 232 | LimeGreen, | ||
| 233 | Green, | ||
| 234 | Blue, | ||
| 235 | LightBlue, | ||
| 236 | Pink, | ||
| 237 | Purple, | ||
| 238 | Brown, | ||
| 239 | White, | ||
| 240 | Black, | ||
| 241 | |||
| 242 | Max = Black, | ||
| 243 | }; | ||
| 244 | |||
| 245 | enum class EyeType : u8 { | ||
| 246 | Normal, // Default | ||
| 247 | NormalLash, | ||
| 248 | WhiteLash, | ||
| 249 | WhiteNoBottom, | ||
| 250 | OvalAngledWhite, | ||
| 251 | AngryWhite, | ||
| 252 | DotLashType1, | ||
| 253 | Line, | ||
| 254 | DotLine, | ||
| 255 | OvalWhite, | ||
| 256 | RoundedWhite, | ||
| 257 | NormalShadow, | ||
| 258 | CircleWhite, | ||
| 259 | Circle, | ||
| 260 | CircleWhiteStroke, | ||
| 261 | NormalOvalNoBottom, | ||
| 262 | NormalOvalLarge, | ||
| 263 | NormalRoundedNoBottom, | ||
| 264 | SmallLash, | ||
| 265 | Small, | ||
| 266 | TwoSmall, | ||
| 267 | NormalLongLash, | ||
| 268 | WhiteTwoLashes, | ||
| 269 | WhiteThreeLashes, | ||
| 270 | DotAngry, | ||
| 271 | DotAngled, | ||
| 272 | Oval, | ||
| 273 | SmallWhite, | ||
| 274 | WhiteAngledNoBottom, | ||
| 275 | WhiteAngledNoLeft, | ||
| 276 | SmallWhiteTwoLashes, | ||
| 277 | LeafWhiteLash, | ||
| 278 | WhiteLargeNoBottom, | ||
| 279 | Dot, | ||
| 280 | DotLashType2, | ||
| 281 | DotThreeLashes, | ||
| 282 | WhiteOvalTop, | ||
| 283 | WhiteOvalBottom, | ||
| 284 | WhiteOvalBottomFlat, | ||
| 285 | WhiteOvalTwoLashes, | ||
| 286 | WhiteOvalThreeLashes, | ||
| 287 | WhiteOvalNoBottomTwoLashes, | ||
| 288 | DotWhite, | ||
| 289 | WhiteOvalTopFlat, | ||
| 290 | WhiteThinLeaf, | ||
| 291 | StarThreeLashes, | ||
| 292 | LineTwoLashes, | ||
| 293 | CrowsFeet, | ||
| 294 | WhiteNoBottomFlat, | ||
| 295 | WhiteNoBottomRounded, | ||
| 296 | WhiteSmallBottomLine, | ||
| 297 | WhiteNoBottomLash, | ||
| 298 | WhiteNoPartialBottomLash, | ||
| 299 | WhiteOvalBottomLine, | ||
| 300 | WhiteNoBottomLashTopLine, | ||
| 301 | WhiteNoPartialBottomTwoLashes, | ||
| 302 | NormalTopLine, | ||
| 303 | WhiteOvalLash, | ||
| 304 | RoundTired, | ||
| 305 | WhiteLarge, | ||
| 306 | |||
| 307 | Max = WhiteLarge, | ||
| 308 | }; | ||
| 309 | |||
| 310 | enum class MouthType : u8 { | ||
| 311 | Neutral, // Default | ||
| 312 | NeutralLips, | ||
| 313 | Smile, | ||
| 314 | SmileStroke, | ||
| 315 | SmileTeeth, | ||
| 316 | LipsSmall, | ||
| 317 | LipsLarge, | ||
| 318 | Wave, | ||
| 319 | WaveAngrySmall, | ||
| 320 | NeutralStrokeLarge, | ||
| 321 | TeethSurprised, | ||
| 322 | LipsExtraLarge, | ||
| 323 | LipsUp, | ||
| 324 | NeutralDown, | ||
| 325 | Surprised, | ||
| 326 | TeethMiddle, | ||
| 327 | NeutralStroke, | ||
| 328 | LipsExtraSmall, | ||
| 329 | Malicious, | ||
| 330 | LipsDual, | ||
| 331 | NeutralComma, | ||
| 332 | NeutralUp, | ||
| 333 | TeethLarge, | ||
| 334 | WaveAngry, | ||
| 335 | LipsSexy, | ||
| 336 | SmileInverted, | ||
| 337 | LipsSexyOutline, | ||
| 338 | SmileRounded, | ||
| 339 | LipsTeeth, | ||
| 340 | NeutralOpen, | ||
| 341 | TeethRounded, | ||
| 342 | WaveAngrySmallInverted, | ||
| 343 | NeutralCommaInverted, | ||
| 344 | TeethFull, | ||
| 345 | SmileDownLine, | ||
| 346 | Kiss, | ||
| 347 | |||
| 348 | Max = Kiss, | ||
| 349 | }; | ||
| 350 | |||
| 351 | enum class FontRegion : u8 { | ||
| 352 | Standard, // Default | ||
| 353 | China, | ||
| 354 | Korea, | ||
| 355 | Taiwan, | ||
| 356 | |||
| 357 | Max = Taiwan, | ||
| 358 | }; | ||
| 359 | |||
| 360 | enum class FacelineType : u8 { | ||
| 361 | Sharp, // Default | ||
| 362 | Rounded, | ||
| 363 | SharpRounded, | ||
| 364 | SharpRoundedSmall, | ||
| 365 | Large, | ||
| 366 | LargeRounded, | ||
| 367 | SharpSmall, | ||
| 368 | Flat, | ||
| 369 | Bump, | ||
| 370 | Angular, | ||
| 371 | FlatRounded, | ||
| 372 | AngularSmall, | ||
| 373 | |||
| 374 | Max = AngularSmall, | ||
| 375 | }; | ||
| 376 | |||
| 377 | enum class FacelineColor : u8 { | ||
| 378 | Beige, // Default | ||
| 379 | WarmBeige, | ||
| 380 | Natural, | ||
| 381 | Honey, | ||
| 382 | Chestnut, | ||
| 383 | Porcelain, | ||
| 384 | Ivory, | ||
| 385 | WarmIvory, | ||
| 386 | Almond, | ||
| 387 | Espresso, | ||
| 388 | |||
| 389 | Max = Espresso, | ||
| 390 | Count = Max + 1, | ||
| 391 | }; | ||
| 392 | |||
| 393 | enum class FacelineWrinkle : u8 { | ||
| 394 | None, // Default | ||
| 395 | TearTroughs, | ||
| 396 | FacialPain, | ||
| 397 | Cheeks, | ||
| 398 | Folds, | ||
| 399 | UnderTheEyes, | ||
| 400 | SplitChin, | ||
| 401 | Chin, | ||
| 402 | BrowDroop, | ||
| 403 | MouthFrown, | ||
| 404 | CrowsFeet, | ||
| 405 | FoldsCrowsFrown, | ||
| 406 | |||
| 407 | Max = FoldsCrowsFrown, | ||
| 408 | }; | ||
| 409 | |||
| 410 | enum class FacelineMake : u8 { | ||
| 411 | None, // Default | ||
| 412 | CheekPorcelain, | ||
| 413 | CheekNatural, | ||
| 414 | EyeShadowBlue, | ||
| 415 | CheekBlushPorcelain, | ||
| 416 | CheekBlushNatural, | ||
| 417 | CheekPorcelainEyeShadowBlue, | ||
| 418 | CheekPorcelainEyeShadowNatural, | ||
| 419 | CheekBlushPorcelainEyeShadowEspresso, | ||
| 420 | Freckles, | ||
| 421 | LionsManeBeard, | ||
| 422 | StubbleBeard, | ||
| 423 | |||
| 424 | Max = StubbleBeard, | ||
| 425 | }; | ||
| 426 | |||
| 427 | enum class EyebrowType : u8 { | ||
| 428 | FlatAngledLarge, // Default | ||
| 429 | LowArchRoundedThin, | ||
| 430 | SoftAngledLarge, | ||
| 431 | MediumArchRoundedThin, | ||
| 432 | RoundedMedium, | ||
| 433 | LowArchMedium, | ||
| 434 | RoundedThin, | ||
| 435 | UpThin, | ||
| 436 | MediumArchRoundedMedium, | ||
| 437 | RoundedLarge, | ||
| 438 | UpLarge, | ||
| 439 | FlatAngledLargeInverted, | ||
| 440 | MediumArchFlat, | ||
| 441 | AngledThin, | ||
| 442 | HorizontalLarge, | ||
| 443 | HighArchFlat, | ||
| 444 | Flat, | ||
| 445 | MediumArchLarge, | ||
| 446 | LowArchThin, | ||
| 447 | RoundedThinInverted, | ||
| 448 | HighArchLarge, | ||
| 449 | Hairy, | ||
| 450 | Dotted, | ||
| 451 | None, | ||
| 452 | |||
| 453 | Max = None, | ||
| 454 | }; | ||
| 455 | |||
| 456 | enum class NoseType : u8 { | ||
| 457 | Normal, // Default | ||
| 458 | Rounded, | ||
| 459 | Dot, | ||
| 460 | Arrow, | ||
| 461 | Roman, | ||
| 462 | Triangle, | ||
| 463 | Button, | ||
| 464 | RoundedInverted, | ||
| 465 | Potato, | ||
| 466 | Grecian, | ||
| 467 | Snub, | ||
| 468 | Aquiline, | ||
| 469 | ArrowLeft, | ||
| 470 | RoundedLarge, | ||
| 471 | Hooked, | ||
| 472 | Fat, | ||
| 473 | Droopy, | ||
| 474 | ArrowLarge, | ||
| 475 | |||
| 476 | Max = ArrowLarge, | ||
| 477 | }; | ||
| 478 | |||
| 479 | enum class BeardType : u8 { | ||
| 480 | None, | ||
| 481 | Goatee, | ||
| 482 | GoateeLong, | ||
| 483 | LionsManeLong, | ||
| 484 | LionsMane, | ||
| 485 | Full, | ||
| 486 | |||
| 487 | Min = Goatee, | ||
| 488 | Max = Full, | ||
| 489 | }; | ||
| 490 | |||
| 491 | enum class MustacheType : u8 { | ||
| 492 | None, | ||
| 493 | Walrus, | ||
| 494 | Pencil, | ||
| 495 | Horseshoe, | ||
| 496 | Normal, | ||
| 497 | Toothbrush, | ||
| 498 | |||
| 499 | Min = Walrus, | ||
| 500 | Max = Toothbrush, | ||
| 501 | }; | ||
| 502 | |||
| 503 | enum class GlassType : u8 { | ||
| 504 | None, | ||
| 505 | Oval, | ||
| 506 | Wayfarer, | ||
| 507 | Rectangle, | ||
| 508 | TopRimless, | ||
| 509 | Rounded, | ||
| 510 | Oversized, | ||
| 511 | CatEye, | ||
| 512 | Square, | ||
| 513 | BottomRimless, | ||
| 514 | SemiOpaqueRounded, | ||
| 515 | SemiOpaqueCatEye, | ||
| 516 | SemiOpaqueOval, | ||
| 517 | SemiOpaqueRectangle, | ||
| 518 | SemiOpaqueAviator, | ||
| 519 | OpaqueRounded, | ||
| 520 | OpaqueCatEye, | ||
| 521 | OpaqueOval, | ||
| 522 | OpaqueRectangle, | ||
| 523 | OpaqueAviator, | ||
| 524 | |||
| 525 | Max = OpaqueAviator, | ||
| 526 | Count = Max + 1, | ||
| 527 | }; | ||
| 528 | |||
| 529 | enum class BeardAndMustacheFlag : u32 { | ||
| 530 | Beard = 1, | ||
| 531 | Mustache, | ||
| 532 | All = Beard | Mustache, | ||
| 533 | }; | ||
| 534 | DECLARE_ENUM_FLAG_OPERATORS(BeardAndMustacheFlag); | ||
| 535 | |||
| 536 | enum class Source : u32 { | ||
| 537 | Database = 0, | ||
| 538 | Default = 1, | ||
| 539 | Account = 2, | ||
| 540 | Friend = 3, | ||
| 541 | }; | ||
| 542 | |||
| 543 | enum class SourceFlag : u32 { | ||
| 544 | None = 0, | ||
| 545 | Database = 1 << 0, | ||
| 546 | Default = 1 << 1, | ||
| 547 | }; | ||
| 548 | DECLARE_ENUM_FLAG_OPERATORS(SourceFlag); | ||
| 549 | |||
| 550 | enum class ValidationResult : u32 { | ||
| 551 | NoErrors = 0x0, | ||
| 552 | InvalidBeardColor = 0x1, | ||
| 553 | InvalidBeardType = 0x2, | ||
| 554 | InvalidBuild = 0x3, | ||
| 555 | InvalidEyeAspect = 0x4, | ||
| 556 | InvalidEyeColor = 0x5, | ||
| 557 | InvalidEyeRotate = 0x6, | ||
| 558 | InvalidEyeScale = 0x7, | ||
| 559 | InvalidEyeType = 0x8, | ||
| 560 | InvalidEyeX = 0x9, | ||
| 561 | InvalidEyeY = 0xa, | ||
| 562 | InvalidEyebrowAspect = 0xb, | ||
| 563 | InvalidEyebrowColor = 0xc, | ||
| 564 | InvalidEyebrowRotate = 0xd, | ||
| 565 | InvalidEyebrowScale = 0xe, | ||
| 566 | InvalidEyebrowType = 0xf, | ||
| 567 | InvalidEyebrowX = 0x10, | ||
| 568 | InvalidEyebrowY = 0x11, | ||
| 569 | InvalidFacelineColor = 0x12, | ||
| 570 | InvalidFacelineMake = 0x13, | ||
| 571 | InvalidFacelineWrinkle = 0x14, | ||
| 572 | InvalidFacelineType = 0x15, | ||
| 573 | InvalidColor = 0x16, | ||
| 574 | InvalidFont = 0x17, | ||
| 575 | InvalidGender = 0x18, | ||
| 576 | InvalidGlassColor = 0x19, | ||
| 577 | InvalidGlassScale = 0x1a, | ||
| 578 | InvalidGlassType = 0x1b, | ||
| 579 | InvalidGlassY = 0x1c, | ||
| 580 | InvalidHairColor = 0x1d, | ||
| 581 | InvalidHairFlip = 0x1e, | ||
| 582 | InvalidHairType = 0x1f, | ||
| 583 | InvalidHeight = 0x20, | ||
| 584 | InvalidMoleScale = 0x21, | ||
| 585 | InvalidMoleType = 0x22, | ||
| 586 | InvalidMoleX = 0x23, | ||
| 587 | InvalidMoleY = 0x24, | ||
| 588 | InvalidMouthAspect = 0x25, | ||
| 589 | InvalidMouthColor = 0x26, | ||
| 590 | InvalidMouthScale = 0x27, | ||
| 591 | InvalidMouthType = 0x28, | ||
| 592 | InvalidMouthY = 0x29, | ||
| 593 | InvalidMustacheScale = 0x2a, | ||
| 594 | InvalidMustacheType = 0x2b, | ||
| 595 | InvalidMustacheY = 0x2c, | ||
| 596 | InvalidNoseScale = 0x2e, | ||
| 597 | InvalidNoseType = 0x2f, | ||
| 598 | InvalidNoseY = 0x30, | ||
| 599 | InvalidRegionMove = 0x31, | ||
| 600 | InvalidCreateId = 0x32, | ||
| 601 | InvalidName = 0x33, | ||
| 602 | InvalidType = 0x35, | ||
| 603 | }; | ||
| 604 | |||
| 605 | struct Nickname { | ||
| 606 | static constexpr std::size_t MaxNameSize = 10; | ||
| 607 | std::array<char16_t, MaxNameSize> data; | ||
| 608 | |||
| 609 | // Checks for null, non-zero terminated or dirty strings | ||
| 610 | bool IsValid() const { | ||
| 611 | if (data[0] == 0) { | ||
| 612 | return false; | ||
| 613 | } | ||
| 614 | |||
| 615 | if (data[MaxNameSize] != 0) { | ||
| 616 | return false; | ||
| 617 | } | ||
| 618 | std::size_t index = 1; | ||
| 619 | while (data[index] != 0) { | ||
| 620 | index++; | ||
| 621 | } | ||
| 622 | while (index < MaxNameSize && data[index] == 0) { | ||
| 623 | index++; | ||
| 624 | } | ||
| 625 | return index == MaxNameSize; | ||
| 626 | } | ||
| 627 | }; | ||
| 628 | static_assert(sizeof(Nickname) == 0x14, "Nickname is an invalid size"); | ||
| 629 | |||
| 630 | struct DefaultMii { | ||
| 631 | u32 face_type{}; | ||
| 632 | u32 face_color{}; | ||
| 633 | u32 face_wrinkle{}; | ||
| 634 | u32 face_makeup{}; | ||
| 635 | u32 hair_type{}; | ||
| 636 | u32 hair_color{}; | ||
| 637 | u32 hair_flip{}; | ||
| 638 | u32 eye_type{}; | ||
| 639 | u32 eye_color{}; | ||
| 640 | u32 eye_scale{}; | ||
| 641 | u32 eye_aspect{}; | ||
| 642 | u32 eye_rotate{}; | ||
| 643 | u32 eye_x{}; | ||
| 644 | u32 eye_y{}; | ||
| 645 | u32 eyebrow_type{}; | ||
| 646 | u32 eyebrow_color{}; | ||
| 647 | u32 eyebrow_scale{}; | ||
| 648 | u32 eyebrow_aspect{}; | ||
| 649 | u32 eyebrow_rotate{}; | ||
| 650 | u32 eyebrow_x{}; | ||
| 651 | u32 eyebrow_y{}; | ||
| 652 | u32 nose_type{}; | ||
| 653 | u32 nose_scale{}; | ||
| 654 | u32 nose_y{}; | ||
| 655 | u32 mouth_type{}; | ||
| 656 | u32 mouth_color{}; | ||
| 657 | u32 mouth_scale{}; | ||
| 658 | u32 mouth_aspect{}; | ||
| 659 | u32 mouth_y{}; | ||
| 660 | u32 mustache_type{}; | ||
| 661 | u32 beard_type{}; | ||
| 662 | u32 beard_color{}; | ||
| 663 | u32 mustache_scale{}; | ||
| 664 | u32 mustache_y{}; | ||
| 665 | u32 glasses_type{}; | ||
| 666 | u32 glasses_color{}; | ||
| 667 | u32 glasses_scale{}; | ||
| 668 | u32 glasses_y{}; | ||
| 669 | u32 mole_type{}; | ||
| 670 | u32 mole_scale{}; | ||
| 671 | u32 mole_x{}; | ||
| 672 | u32 mole_y{}; | ||
| 673 | u32 height{}; | ||
| 674 | u32 weight{}; | ||
| 675 | u32 gender{}; | ||
| 676 | u32 favorite_color{}; | ||
| 677 | u32 region_move{}; | ||
| 678 | u32 font_region{}; | ||
| 679 | u32 type{}; | ||
| 680 | Nickname nickname; | ||
| 681 | }; | ||
| 682 | static_assert(sizeof(DefaultMii) == 0xd8, "DefaultMii has incorrect size."); | ||
| 683 | |||
| 684 | struct DatabaseSessionMetadata { | ||
| 685 | u32 interface_version; | ||
| 686 | u32 magic; | ||
| 687 | u64 update_counter; | ||
| 688 | |||
| 689 | bool IsInterfaceVersionSupported(u32 version) const { | ||
| 690 | return version <= interface_version; | ||
| 691 | } | ||
| 692 | }; | ||
| 693 | |||
| 694 | } // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/mii_util.h b/src/core/hle/service/mii/mii_util.h new file mode 100644 index 000000000..ddb544c23 --- /dev/null +++ b/src/core/hle/service/mii/mii_util.h | |||
| @@ -0,0 +1,59 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include <random> | ||
| 7 | #include <span> | ||
| 8 | |||
| 9 | #include "common/common_types.h" | ||
| 10 | #include "common/swap.h" | ||
| 11 | #include "common/uuid.h" | ||
| 12 | #include "core/hle/service/mii/mii_types.h" | ||
| 13 | |||
| 14 | namespace Service::Mii { | ||
| 15 | class MiiUtil { | ||
| 16 | public: | ||
| 17 | static u16 CalculateCrc16(const void* data, std::size_t size) { | ||
| 18 | s32 crc{}; | ||
| 19 | for (std::size_t i = 0; i < size; i++) { | ||
| 20 | crc ^= static_cast<const u8*>(data)[i] << 8; | ||
| 21 | for (std::size_t j = 0; j < 8; j++) { | ||
| 22 | crc <<= 1; | ||
| 23 | if ((crc & 0x10000) != 0) { | ||
| 24 | crc = (crc ^ 0x1021) & 0xFFFF; | ||
| 25 | } | ||
| 26 | } | ||
| 27 | } | ||
| 28 | return Common::swap16(static_cast<u16>(crc)); | ||
| 29 | } | ||
| 30 | |||
| 31 | static Common::UUID MakeCreateId() { | ||
| 32 | return Common::UUID::MakeRandomRFC4122V4(); | ||
| 33 | } | ||
| 34 | |||
| 35 | static Common::UUID GetDeviceId() { | ||
| 36 | // This should be nn::settings::detail::GetMiiAuthorId() | ||
| 37 | return Common::UUID::MakeDefault(); | ||
| 38 | } | ||
| 39 | |||
| 40 | template <typename T> | ||
| 41 | static T GetRandomValue(T min, T max) { | ||
| 42 | std::random_device device; | ||
| 43 | std::mt19937 gen(device()); | ||
| 44 | std::uniform_int_distribution<u64> distribution(static_cast<u64>(min), | ||
| 45 | static_cast<u64>(max)); | ||
| 46 | return static_cast<T>(distribution(gen)); | ||
| 47 | } | ||
| 48 | |||
| 49 | template <typename T> | ||
| 50 | static T GetRandomValue(T max) { | ||
| 51 | return GetRandomValue<T>({}, max); | ||
| 52 | } | ||
| 53 | |||
| 54 | static bool IsFontRegionValid(FontRegion font, std::span<const char16_t> text) { | ||
| 55 | // TODO: This function needs to check against the font tables | ||
| 56 | return true; | ||
| 57 | } | ||
| 58 | }; | ||
| 59 | } // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/raw_data.h b/src/core/hle/service/mii/raw_data.h deleted file mode 100644 index cdd2337d6..000000000 --- a/src/core/hle/service/mii/raw_data.h +++ /dev/null | |||
| @@ -1,27 +0,0 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include <array> | ||
| 7 | |||
| 8 | #include "core/hle/service/mii/types.h" | ||
| 9 | |||
| 10 | namespace Service::Mii::RawData { | ||
| 11 | |||
| 12 | extern const std::array<Service::Mii::DefaultMii, 2> BaseMii; | ||
| 13 | extern const std::array<Service::Mii::DefaultMii, 6> DefaultMii; | ||
| 14 | extern const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiFaceline; | ||
| 15 | extern const std::array<Service::Mii::RandomMiiData3, 6> RandomMiiFacelineColor; | ||
| 16 | extern const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiFacelineWrinkle; | ||
| 17 | extern const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiFacelineMakeup; | ||
| 18 | extern const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiHairType; | ||
| 19 | extern const std::array<Service::Mii::RandomMiiData3, 9> RandomMiiHairColor; | ||
| 20 | extern const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiEyeType; | ||
| 21 | extern const std::array<Service::Mii::RandomMiiData2, 3> RandomMiiEyeColor; | ||
| 22 | extern const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiEyebrowType; | ||
| 23 | extern const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiNoseType; | ||
| 24 | extern const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiMouthType; | ||
| 25 | extern const std::array<Service::Mii::RandomMiiData2, 3> RandomMiiGlassType; | ||
| 26 | |||
| 27 | } // namespace Service::Mii::RawData | ||
diff --git a/src/core/hle/service/mii/types.h b/src/core/hle/service/mii/types.h deleted file mode 100644 index c48d08d79..000000000 --- a/src/core/hle/service/mii/types.h +++ /dev/null | |||
| @@ -1,553 +0,0 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include <array> | ||
| 7 | #include <type_traits> | ||
| 8 | |||
| 9 | #include "common/bit_field.h" | ||
| 10 | #include "common/common_funcs.h" | ||
| 11 | #include "common/common_types.h" | ||
| 12 | #include "common/uuid.h" | ||
| 13 | |||
| 14 | namespace Service::Mii { | ||
| 15 | |||
| 16 | enum class Age : u32 { | ||
| 17 | Young, | ||
| 18 | Normal, | ||
| 19 | Old, | ||
| 20 | All, | ||
| 21 | }; | ||
| 22 | |||
| 23 | enum class BeardType : u32 { | ||
| 24 | None, | ||
| 25 | Beard1, | ||
| 26 | Beard2, | ||
| 27 | Beard3, | ||
| 28 | Beard4, | ||
| 29 | Beard5, | ||
| 30 | }; | ||
| 31 | |||
| 32 | enum class BeardAndMustacheFlag : u32 { | ||
| 33 | Beard = 1, | ||
| 34 | Mustache, | ||
| 35 | All = Beard | Mustache, | ||
| 36 | }; | ||
| 37 | DECLARE_ENUM_FLAG_OPERATORS(BeardAndMustacheFlag); | ||
| 38 | |||
| 39 | enum class FontRegion : u32 { | ||
| 40 | Standard, | ||
| 41 | China, | ||
| 42 | Korea, | ||
| 43 | Taiwan, | ||
| 44 | }; | ||
| 45 | |||
| 46 | enum class Gender : u32 { | ||
| 47 | Male, | ||
| 48 | Female, | ||
| 49 | All, | ||
| 50 | Maximum = Female, | ||
| 51 | }; | ||
| 52 | |||
| 53 | enum class HairFlip : u32 { | ||
| 54 | Left, | ||
| 55 | Right, | ||
| 56 | Maximum = Right, | ||
| 57 | }; | ||
| 58 | |||
| 59 | enum class MustacheType : u32 { | ||
| 60 | None, | ||
| 61 | Mustache1, | ||
| 62 | Mustache2, | ||
| 63 | Mustache3, | ||
| 64 | Mustache4, | ||
| 65 | Mustache5, | ||
| 66 | }; | ||
| 67 | |||
| 68 | enum class Race : u32 { | ||
| 69 | Black, | ||
| 70 | White, | ||
| 71 | Asian, | ||
| 72 | All, | ||
| 73 | }; | ||
| 74 | |||
| 75 | enum class Source : u32 { | ||
| 76 | Database = 0, | ||
| 77 | Default = 1, | ||
| 78 | Account = 2, | ||
| 79 | Friend = 3, | ||
| 80 | }; | ||
| 81 | |||
| 82 | enum class SourceFlag : u32 { | ||
| 83 | None = 0, | ||
| 84 | Database = 1 << 0, | ||
| 85 | Default = 1 << 1, | ||
| 86 | }; | ||
| 87 | DECLARE_ENUM_FLAG_OPERATORS(SourceFlag); | ||
| 88 | |||
| 89 | // nn::mii::CharInfo | ||
| 90 | struct CharInfo { | ||
| 91 | Common::UUID uuid; | ||
| 92 | std::array<char16_t, 11> name; | ||
| 93 | u8 font_region; | ||
| 94 | u8 favorite_color; | ||
| 95 | u8 gender; | ||
| 96 | u8 height; | ||
| 97 | u8 build; | ||
| 98 | u8 type; | ||
| 99 | u8 region_move; | ||
| 100 | u8 faceline_type; | ||
| 101 | u8 faceline_color; | ||
| 102 | u8 faceline_wrinkle; | ||
| 103 | u8 faceline_make; | ||
| 104 | u8 hair_type; | ||
| 105 | u8 hair_color; | ||
| 106 | u8 hair_flip; | ||
| 107 | u8 eye_type; | ||
| 108 | u8 eye_color; | ||
| 109 | u8 eye_scale; | ||
| 110 | u8 eye_aspect; | ||
| 111 | u8 eye_rotate; | ||
| 112 | u8 eye_x; | ||
| 113 | u8 eye_y; | ||
| 114 | u8 eyebrow_type; | ||
| 115 | u8 eyebrow_color; | ||
| 116 | u8 eyebrow_scale; | ||
| 117 | u8 eyebrow_aspect; | ||
| 118 | u8 eyebrow_rotate; | ||
| 119 | u8 eyebrow_x; | ||
| 120 | u8 eyebrow_y; | ||
| 121 | u8 nose_type; | ||
| 122 | u8 nose_scale; | ||
| 123 | u8 nose_y; | ||
| 124 | u8 mouth_type; | ||
| 125 | u8 mouth_color; | ||
| 126 | u8 mouth_scale; | ||
| 127 | u8 mouth_aspect; | ||
| 128 | u8 mouth_y; | ||
| 129 | u8 beard_color; | ||
| 130 | u8 beard_type; | ||
| 131 | u8 mustache_type; | ||
| 132 | u8 mustache_scale; | ||
| 133 | u8 mustache_y; | ||
| 134 | u8 glasses_type; | ||
| 135 | u8 glasses_color; | ||
| 136 | u8 glasses_scale; | ||
| 137 | u8 glasses_y; | ||
| 138 | u8 mole_type; | ||
| 139 | u8 mole_scale; | ||
| 140 | u8 mole_x; | ||
| 141 | u8 mole_y; | ||
| 142 | u8 padding; | ||
| 143 | }; | ||
| 144 | static_assert(sizeof(CharInfo) == 0x58, "CharInfo has incorrect size."); | ||
| 145 | static_assert(std::has_unique_object_representations_v<CharInfo>, | ||
| 146 | "All bits of CharInfo must contribute to its value."); | ||
| 147 | |||
| 148 | #pragma pack(push, 4) | ||
| 149 | |||
| 150 | struct MiiInfoElement { | ||
| 151 | MiiInfoElement(const CharInfo& info_, Source source_) : info{info_}, source{source_} {} | ||
| 152 | |||
| 153 | CharInfo info{}; | ||
| 154 | Source source{}; | ||
| 155 | }; | ||
| 156 | static_assert(sizeof(MiiInfoElement) == 0x5c, "MiiInfoElement has incorrect size."); | ||
| 157 | |||
| 158 | struct MiiStoreBitFields { | ||
| 159 | union { | ||
| 160 | u32 word_0{}; | ||
| 161 | |||
| 162 | BitField<0, 8, u32> hair_type; | ||
| 163 | BitField<8, 7, u32> height; | ||
| 164 | BitField<15, 1, u32> mole_type; | ||
| 165 | BitField<16, 7, u32> build; | ||
| 166 | BitField<23, 1, HairFlip> hair_flip; | ||
| 167 | BitField<24, 7, u32> hair_color; | ||
| 168 | BitField<31, 1, u32> type; | ||
| 169 | }; | ||
| 170 | |||
| 171 | union { | ||
| 172 | u32 word_1{}; | ||
| 173 | |||
| 174 | BitField<0, 7, u32> eye_color; | ||
| 175 | BitField<7, 1, Gender> gender; | ||
| 176 | BitField<8, 7, u32> eyebrow_color; | ||
| 177 | BitField<16, 7, u32> mouth_color; | ||
| 178 | BitField<24, 7, u32> beard_color; | ||
| 179 | }; | ||
| 180 | |||
| 181 | union { | ||
| 182 | u32 word_2{}; | ||
| 183 | |||
| 184 | BitField<0, 7, u32> glasses_color; | ||
| 185 | BitField<8, 6, u32> eye_type; | ||
| 186 | BitField<14, 2, u32> region_move; | ||
| 187 | BitField<16, 6, u32> mouth_type; | ||
| 188 | BitField<22, 2, FontRegion> font_region; | ||
| 189 | BitField<24, 5, u32> eye_y; | ||
| 190 | BitField<29, 3, u32> glasses_scale; | ||
| 191 | }; | ||
| 192 | |||
| 193 | union { | ||
| 194 | u32 word_3{}; | ||
| 195 | |||
| 196 | BitField<0, 5, u32> eyebrow_type; | ||
| 197 | BitField<5, 3, MustacheType> mustache_type; | ||
| 198 | BitField<8, 5, u32> nose_type; | ||
| 199 | BitField<13, 3, BeardType> beard_type; | ||
| 200 | BitField<16, 5, u32> nose_y; | ||
| 201 | BitField<21, 3, u32> mouth_aspect; | ||
| 202 | BitField<24, 5, u32> mouth_y; | ||
| 203 | BitField<29, 3, u32> eyebrow_aspect; | ||
| 204 | }; | ||
| 205 | |||
| 206 | union { | ||
| 207 | u32 word_4{}; | ||
| 208 | |||
| 209 | BitField<0, 5, u32> mustache_y; | ||
| 210 | BitField<5, 3, u32> eye_rotate; | ||
| 211 | BitField<8, 5, u32> glasses_y; | ||
| 212 | BitField<13, 3, u32> eye_aspect; | ||
| 213 | BitField<16, 5, u32> mole_x; | ||
| 214 | BitField<21, 3, u32> eye_scale; | ||
| 215 | BitField<24, 5, u32> mole_y; | ||
| 216 | }; | ||
| 217 | |||
| 218 | union { | ||
| 219 | u32 word_5{}; | ||
| 220 | |||
| 221 | BitField<0, 5, u32> glasses_type; | ||
| 222 | BitField<8, 4, u32> favorite_color; | ||
| 223 | BitField<12, 4, u32> faceline_type; | ||
| 224 | BitField<16, 4, u32> faceline_color; | ||
| 225 | BitField<20, 4, u32> faceline_wrinkle; | ||
| 226 | BitField<24, 4, u32> faceline_makeup; | ||
| 227 | BitField<28, 4, u32> eye_x; | ||
| 228 | }; | ||
| 229 | |||
| 230 | union { | ||
| 231 | u32 word_6{}; | ||
| 232 | |||
| 233 | BitField<0, 4, u32> eyebrow_scale; | ||
| 234 | BitField<4, 4, u32> eyebrow_rotate; | ||
| 235 | BitField<8, 4, u32> eyebrow_x; | ||
| 236 | BitField<12, 4, u32> eyebrow_y; | ||
| 237 | BitField<16, 4, u32> nose_scale; | ||
| 238 | BitField<20, 4, u32> mouth_scale; | ||
| 239 | BitField<24, 4, u32> mustache_scale; | ||
| 240 | BitField<28, 4, u32> mole_scale; | ||
| 241 | }; | ||
| 242 | }; | ||
| 243 | static_assert(sizeof(MiiStoreBitFields) == 0x1c, "MiiStoreBitFields has incorrect size."); | ||
| 244 | static_assert(std::is_trivially_copyable_v<MiiStoreBitFields>, | ||
| 245 | "MiiStoreBitFields is not trivially copyable."); | ||
| 246 | |||
| 247 | // This is nn::mii::Ver3StoreData | ||
| 248 | // Based on citra HLE::Applets::MiiData and PretendoNetwork. | ||
| 249 | // https://github.com/citra-emu/citra/blob/master/src/core/hle/applets/mii_selector.h#L48 | ||
| 250 | // https://github.com/PretendoNetwork/mii-js/blob/master/mii.js#L299 | ||
| 251 | struct Ver3StoreData { | ||
| 252 | u8 version; | ||
| 253 | union { | ||
| 254 | u8 raw; | ||
| 255 | |||
| 256 | BitField<0, 1, u8> allow_copying; | ||
| 257 | BitField<1, 1, u8> profanity_flag; | ||
| 258 | BitField<2, 2, u8> region_lock; | ||
| 259 | BitField<4, 2, u8> character_set; | ||
| 260 | } region_information; | ||
| 261 | u16_be mii_id; | ||
| 262 | u64_be system_id; | ||
| 263 | u32_be specialness_and_creation_date; | ||
| 264 | std::array<u8, 0x6> creator_mac; | ||
| 265 | u16_be padding; | ||
| 266 | union { | ||
| 267 | u16 raw; | ||
| 268 | |||
| 269 | BitField<0, 1, u16> gender; | ||
| 270 | BitField<1, 4, u16> birth_month; | ||
| 271 | BitField<5, 5, u16> birth_day; | ||
| 272 | BitField<10, 4, u16> favorite_color; | ||
| 273 | BitField<14, 1, u16> favorite; | ||
| 274 | } mii_information; | ||
| 275 | std::array<char16_t, 0xA> mii_name; | ||
| 276 | u8 height; | ||
| 277 | u8 build; | ||
| 278 | union { | ||
| 279 | u8 raw; | ||
| 280 | |||
| 281 | BitField<0, 1, u8> disable_sharing; | ||
| 282 | BitField<1, 4, u8> face_shape; | ||
| 283 | BitField<5, 3, u8> skin_color; | ||
| 284 | } appearance_bits1; | ||
| 285 | union { | ||
| 286 | u8 raw; | ||
| 287 | |||
| 288 | BitField<0, 4, u8> wrinkles; | ||
| 289 | BitField<4, 4, u8> makeup; | ||
| 290 | } appearance_bits2; | ||
| 291 | u8 hair_style; | ||
| 292 | union { | ||
| 293 | u8 raw; | ||
| 294 | |||
| 295 | BitField<0, 3, u8> hair_color; | ||
| 296 | BitField<3, 1, u8> flip_hair; | ||
| 297 | } appearance_bits3; | ||
| 298 | union { | ||
| 299 | u32 raw; | ||
| 300 | |||
| 301 | BitField<0, 6, u32> eye_type; | ||
| 302 | BitField<6, 3, u32> eye_color; | ||
| 303 | BitField<9, 4, u32> eye_scale; | ||
| 304 | BitField<13, 3, u32> eye_vertical_stretch; | ||
| 305 | BitField<16, 5, u32> eye_rotation; | ||
| 306 | BitField<21, 4, u32> eye_spacing; | ||
| 307 | BitField<25, 5, u32> eye_y_position; | ||
| 308 | } appearance_bits4; | ||
| 309 | union { | ||
| 310 | u32 raw; | ||
| 311 | |||
| 312 | BitField<0, 5, u32> eyebrow_style; | ||
| 313 | BitField<5, 3, u32> eyebrow_color; | ||
| 314 | BitField<8, 4, u32> eyebrow_scale; | ||
| 315 | BitField<12, 3, u32> eyebrow_yscale; | ||
| 316 | BitField<16, 4, u32> eyebrow_rotation; | ||
| 317 | BitField<21, 4, u32> eyebrow_spacing; | ||
| 318 | BitField<25, 5, u32> eyebrow_y_position; | ||
| 319 | } appearance_bits5; | ||
| 320 | union { | ||
| 321 | u16 raw; | ||
| 322 | |||
| 323 | BitField<0, 5, u16> nose_type; | ||
| 324 | BitField<5, 4, u16> nose_scale; | ||
| 325 | BitField<9, 5, u16> nose_y_position; | ||
| 326 | } appearance_bits6; | ||
| 327 | union { | ||
| 328 | u16 raw; | ||
| 329 | |||
| 330 | BitField<0, 6, u16> mouth_type; | ||
| 331 | BitField<6, 3, u16> mouth_color; | ||
| 332 | BitField<9, 4, u16> mouth_scale; | ||
| 333 | BitField<13, 3, u16> mouth_horizontal_stretch; | ||
| 334 | } appearance_bits7; | ||
| 335 | union { | ||
| 336 | u8 raw; | ||
| 337 | |||
| 338 | BitField<0, 5, u8> mouth_y_position; | ||
| 339 | BitField<5, 3, u8> mustache_type; | ||
| 340 | } appearance_bits8; | ||
| 341 | u8 allow_copying; | ||
| 342 | union { | ||
| 343 | u16 raw; | ||
| 344 | |||
| 345 | BitField<0, 3, u16> bear_type; | ||
| 346 | BitField<3, 3, u16> facial_hair_color; | ||
| 347 | BitField<6, 4, u16> mustache_scale; | ||
| 348 | BitField<10, 5, u16> mustache_y_position; | ||
| 349 | } appearance_bits9; | ||
| 350 | union { | ||
| 351 | u16 raw; | ||
| 352 | |||
| 353 | BitField<0, 4, u16> glasses_type; | ||
| 354 | BitField<4, 3, u16> glasses_color; | ||
| 355 | BitField<7, 4, u16> glasses_scale; | ||
| 356 | BitField<11, 5, u16> glasses_y_position; | ||
| 357 | } appearance_bits10; | ||
| 358 | union { | ||
| 359 | u16 raw; | ||
| 360 | |||
| 361 | BitField<0, 1, u16> mole_enabled; | ||
| 362 | BitField<1, 4, u16> mole_scale; | ||
| 363 | BitField<5, 5, u16> mole_x_position; | ||
| 364 | BitField<10, 5, u16> mole_y_position; | ||
| 365 | } appearance_bits11; | ||
| 366 | |||
| 367 | std::array<u16_le, 0xA> author_name; | ||
| 368 | INSERT_PADDING_BYTES(0x2); | ||
| 369 | u16_be crc; | ||
| 370 | }; | ||
| 371 | static_assert(sizeof(Ver3StoreData) == 0x60, "Ver3StoreData is an invalid size"); | ||
| 372 | |||
| 373 | struct NfpStoreDataExtension { | ||
| 374 | u8 faceline_color; | ||
| 375 | u8 hair_color; | ||
| 376 | u8 eye_color; | ||
| 377 | u8 eyebrow_color; | ||
| 378 | u8 mouth_color; | ||
| 379 | u8 beard_color; | ||
| 380 | u8 glass_color; | ||
| 381 | u8 glass_type; | ||
| 382 | }; | ||
| 383 | static_assert(sizeof(NfpStoreDataExtension) == 0x8, "NfpStoreDataExtension is an invalid size"); | ||
| 384 | |||
| 385 | constexpr std::array<u8, 0x10> Ver3FacelineColorTable{ | ||
| 386 | 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x0, 0x1, 0x5, 0x5, | ||
| 387 | }; | ||
| 388 | |||
| 389 | constexpr std::array<u8, 100> Ver3HairColorTable{ | ||
| 390 | 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, 0x0, 0x4, 0x3, 0x5, 0x4, 0x4, 0x6, 0x2, 0x0, | ||
| 391 | 0x6, 0x4, 0x3, 0x2, 0x2, 0x7, 0x3, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, | ||
| 392 | 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x0, 0x0, 0x4, | ||
| 393 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x0, 0x0, 0x0, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x5, 0x5, 0x5, | ||
| 394 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x5, 0x7, 0x5, 0x7, 0x7, 0x7, 0x7, 0x7, 0x6, 0x7, | ||
| 395 | 0x7, 0x7, 0x7, 0x7, 0x3, 0x7, 0x7, 0x7, 0x7, 0x7, 0x0, 0x4, 0x4, 0x4, 0x4, | ||
| 396 | }; | ||
| 397 | |||
| 398 | constexpr std::array<u8, 100> Ver3EyeColorTable{ | ||
| 399 | 0x0, 0x2, 0x2, 0x2, 0x1, 0x3, 0x2, 0x3, 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x2, 0x2, 0x4, | ||
| 400 | 0x2, 0x1, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, | ||
| 401 | 0x2, 0x2, 0x2, 0x2, 0x0, 0x0, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x1, 0x0, 0x4, 0x4, | ||
| 402 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x0, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, | ||
| 403 | 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x2, 0x2, | ||
| 404 | 0x3, 0x3, 0x3, 0x3, 0x2, 0x2, 0x2, 0x2, 0x2, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, | ||
| 405 | }; | ||
| 406 | |||
| 407 | constexpr std::array<u8, 100> Ver3MouthlineColorTable{ | ||
| 408 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x3, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x1, 0x4, | ||
| 409 | 0x4, 0x4, 0x0, 0x1, 0x2, 0x3, 0x4, 0x4, 0x2, 0x3, 0x3, 0x4, 0x4, 0x4, 0x4, 0x1, 0x4, | ||
| 410 | 0x4, 0x2, 0x3, 0x3, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x3, 0x3, 0x3, 0x4, 0x4, 0x4, | ||
| 411 | 0x3, 0x3, 0x3, 0x3, 0x3, 0x4, 0x4, 0x4, 0x4, 0x4, 0x3, 0x3, 0x3, 0x3, 0x4, 0x4, 0x4, | ||
| 412 | 0x4, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x4, 0x4, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x4, 0x3, | ||
| 413 | 0x3, 0x3, 0x3, 0x3, 0x4, 0x0, 0x3, 0x3, 0x3, 0x3, 0x4, 0x3, 0x3, 0x3, 0x3, | ||
| 414 | }; | ||
| 415 | |||
| 416 | constexpr std::array<u8, 100> Ver3GlassColorTable{ | ||
| 417 | 0x0, 0x1, 0x1, 0x1, 0x5, 0x1, 0x1, 0x4, 0x0, 0x5, 0x1, 0x1, 0x3, 0x5, 0x1, 0x2, 0x3, | ||
| 418 | 0x4, 0x5, 0x4, 0x2, 0x2, 0x4, 0x4, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, | ||
| 419 | 0x2, 0x2, 0x2, 0x2, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, | ||
| 420 | 0x3, 0x3, 0x3, 0x3, 0x3, 0x0, 0x0, 0x0, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x0, 0x5, 0x5, | ||
| 421 | 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x1, 0x4, | ||
| 422 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, | ||
| 423 | }; | ||
| 424 | |||
| 425 | constexpr std::array<u8, 20> Ver3GlassTypeTable{ | ||
| 426 | 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, 0x8, 0x1, | ||
| 427 | 0x2, 0x1, 0x3, 0x7, 0x7, 0x6, 0x7, 0x8, 0x7, 0x7, | ||
| 428 | }; | ||
| 429 | |||
| 430 | struct MiiStoreData { | ||
| 431 | using Name = std::array<char16_t, 10>; | ||
| 432 | |||
| 433 | MiiStoreData(); | ||
| 434 | MiiStoreData(const Name& name, const MiiStoreBitFields& bit_fields, | ||
| 435 | const Common::UUID& user_id); | ||
| 436 | |||
| 437 | // This corresponds to the above structure MiiStoreBitFields. I did it like this because the | ||
| 438 | // BitField<> type makes this (and any thing that contains it) not trivially copyable, which is | ||
| 439 | // not suitable for our uses. | ||
| 440 | struct { | ||
| 441 | std::array<u8, 0x1C> data{}; | ||
| 442 | static_assert(sizeof(MiiStoreBitFields) == sizeof(data), "data field has incorrect size."); | ||
| 443 | |||
| 444 | Name name{}; | ||
| 445 | Common::UUID uuid{}; | ||
| 446 | } data; | ||
| 447 | |||
| 448 | u16 data_crc{}; | ||
| 449 | u16 device_crc{}; | ||
| 450 | }; | ||
| 451 | static_assert(sizeof(MiiStoreData) == 0x44, "MiiStoreData has incorrect size."); | ||
| 452 | |||
| 453 | struct MiiStoreDataElement { | ||
| 454 | MiiStoreData data{}; | ||
| 455 | Source source{}; | ||
| 456 | }; | ||
| 457 | static_assert(sizeof(MiiStoreDataElement) == 0x48, "MiiStoreDataElement has incorrect size."); | ||
| 458 | |||
| 459 | struct MiiDatabase { | ||
| 460 | u32 magic{}; // 'NFDB' | ||
| 461 | std::array<MiiStoreData, 0x64> miis{}; | ||
| 462 | INSERT_PADDING_BYTES(1); | ||
| 463 | u8 count{}; | ||
| 464 | u16 crc{}; | ||
| 465 | }; | ||
| 466 | static_assert(sizeof(MiiDatabase) == 0x1A98, "MiiDatabase has incorrect size."); | ||
| 467 | |||
| 468 | struct RandomMiiValues { | ||
| 469 | std::array<u8, 0xbc> values{}; | ||
| 470 | }; | ||
| 471 | static_assert(sizeof(RandomMiiValues) == 0xbc, "RandomMiiValues has incorrect size."); | ||
| 472 | |||
| 473 | struct RandomMiiData4 { | ||
| 474 | Gender gender{}; | ||
| 475 | Age age{}; | ||
| 476 | Race race{}; | ||
| 477 | u32 values_count{}; | ||
| 478 | std::array<u32, 47> values{}; | ||
| 479 | }; | ||
| 480 | static_assert(sizeof(RandomMiiData4) == 0xcc, "RandomMiiData4 has incorrect size."); | ||
| 481 | |||
| 482 | struct RandomMiiData3 { | ||
| 483 | u32 arg_1; | ||
| 484 | u32 arg_2; | ||
| 485 | u32 values_count; | ||
| 486 | std::array<u32, 47> values{}; | ||
| 487 | }; | ||
| 488 | static_assert(sizeof(RandomMiiData3) == 0xc8, "RandomMiiData3 has incorrect size."); | ||
| 489 | |||
| 490 | struct RandomMiiData2 { | ||
| 491 | u32 arg_1; | ||
| 492 | u32 values_count; | ||
| 493 | std::array<u32, 47> values{}; | ||
| 494 | }; | ||
| 495 | static_assert(sizeof(RandomMiiData2) == 0xc4, "RandomMiiData2 has incorrect size."); | ||
| 496 | |||
| 497 | struct DefaultMii { | ||
| 498 | u32 face_type{}; | ||
| 499 | u32 face_color{}; | ||
| 500 | u32 face_wrinkle{}; | ||
| 501 | u32 face_makeup{}; | ||
| 502 | u32 hair_type{}; | ||
| 503 | u32 hair_color{}; | ||
| 504 | u32 hair_flip{}; | ||
| 505 | u32 eye_type{}; | ||
| 506 | u32 eye_color{}; | ||
| 507 | u32 eye_scale{}; | ||
| 508 | u32 eye_aspect{}; | ||
| 509 | u32 eye_rotate{}; | ||
| 510 | u32 eye_x{}; | ||
| 511 | u32 eye_y{}; | ||
| 512 | u32 eyebrow_type{}; | ||
| 513 | u32 eyebrow_color{}; | ||
| 514 | u32 eyebrow_scale{}; | ||
| 515 | u32 eyebrow_aspect{}; | ||
| 516 | u32 eyebrow_rotate{}; | ||
| 517 | u32 eyebrow_x{}; | ||
| 518 | u32 eyebrow_y{}; | ||
| 519 | u32 nose_type{}; | ||
| 520 | u32 nose_scale{}; | ||
| 521 | u32 nose_y{}; | ||
| 522 | u32 mouth_type{}; | ||
| 523 | u32 mouth_color{}; | ||
| 524 | u32 mouth_scale{}; | ||
| 525 | u32 mouth_aspect{}; | ||
| 526 | u32 mouth_y{}; | ||
| 527 | u32 mustache_type{}; | ||
| 528 | u32 beard_type{}; | ||
| 529 | u32 beard_color{}; | ||
| 530 | u32 mustache_scale{}; | ||
| 531 | u32 mustache_y{}; | ||
| 532 | u32 glasses_type{}; | ||
| 533 | u32 glasses_color{}; | ||
| 534 | u32 glasses_scale{}; | ||
| 535 | u32 glasses_y{}; | ||
| 536 | u32 mole_type{}; | ||
| 537 | u32 mole_scale{}; | ||
| 538 | u32 mole_x{}; | ||
| 539 | u32 mole_y{}; | ||
| 540 | u32 height{}; | ||
| 541 | u32 weight{}; | ||
| 542 | Gender gender{}; | ||
| 543 | u32 favorite_color{}; | ||
| 544 | u32 region{}; | ||
| 545 | FontRegion font_region{}; | ||
| 546 | u32 type{}; | ||
| 547 | INSERT_PADDING_WORDS(5); | ||
| 548 | }; | ||
| 549 | static_assert(sizeof(DefaultMii) == 0xd8, "MiiStoreData has incorrect size."); | ||
| 550 | |||
| 551 | #pragma pack(pop) | ||
| 552 | |||
| 553 | } // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/types/char_info.cpp b/src/core/hle/service/mii/types/char_info.cpp new file mode 100644 index 000000000..bb948c628 --- /dev/null +++ b/src/core/hle/service/mii/types/char_info.cpp | |||
| @@ -0,0 +1,482 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #include "core/hle/service/mii/types/char_info.h" | ||
| 5 | #include "core/hle/service/mii/types/store_data.h" | ||
| 6 | |||
| 7 | namespace Service::Mii { | ||
| 8 | |||
| 9 | void CharInfo::SetFromStoreData(const StoreData& store_data) { | ||
| 10 | name = store_data.GetNickname(); | ||
| 11 | null_terminator = '\0'; | ||
| 12 | create_id = store_data.GetCreateId(); | ||
| 13 | font_region = store_data.GetFontRegion(); | ||
| 14 | favorite_color = store_data.GetFavoriteColor(); | ||
| 15 | gender = store_data.GetGender(); | ||
| 16 | height = store_data.GetHeight(); | ||
| 17 | build = store_data.GetBuild(); | ||
| 18 | type = store_data.GetType(); | ||
| 19 | region_move = store_data.GetRegionMove(); | ||
| 20 | faceline_type = store_data.GetFacelineType(); | ||
| 21 | faceline_color = store_data.GetFacelineColor(); | ||
| 22 | faceline_wrinkle = store_data.GetFacelineWrinkle(); | ||
| 23 | faceline_make = store_data.GetFacelineMake(); | ||
| 24 | hair_type = store_data.GetHairType(); | ||
| 25 | hair_color = store_data.GetHairColor(); | ||
| 26 | hair_flip = store_data.GetHairFlip(); | ||
| 27 | eye_type = store_data.GetEyeType(); | ||
| 28 | eye_color = store_data.GetEyeColor(); | ||
| 29 | eye_scale = store_data.GetEyeScale(); | ||
| 30 | eye_aspect = store_data.GetEyeAspect(); | ||
| 31 | eye_rotate = store_data.GetEyeRotate(); | ||
| 32 | eye_x = store_data.GetEyeX(); | ||
| 33 | eye_y = store_data.GetEyeY(); | ||
| 34 | eyebrow_type = store_data.GetEyebrowType(); | ||
| 35 | eyebrow_color = store_data.GetEyebrowColor(); | ||
| 36 | eyebrow_scale = store_data.GetEyebrowScale(); | ||
| 37 | eyebrow_aspect = store_data.GetEyebrowAspect(); | ||
| 38 | eyebrow_rotate = store_data.GetEyebrowRotate(); | ||
| 39 | eyebrow_x = store_data.GetEyebrowX(); | ||
| 40 | eyebrow_y = store_data.GetEyebrowY(); | ||
| 41 | nose_type = store_data.GetNoseType(); | ||
| 42 | nose_scale = store_data.GetNoseScale(); | ||
| 43 | nose_y = store_data.GetNoseY(); | ||
| 44 | mouth_type = store_data.GetMouthType(); | ||
| 45 | mouth_color = store_data.GetMouthColor(); | ||
| 46 | mouth_scale = store_data.GetMouthScale(); | ||
| 47 | mouth_aspect = store_data.GetMouthAspect(); | ||
| 48 | mouth_y = store_data.GetMouthY(); | ||
| 49 | beard_color = store_data.GetBeardColor(); | ||
| 50 | beard_type = store_data.GetBeardType(); | ||
| 51 | mustache_type = store_data.GetMustacheType(); | ||
| 52 | mustache_scale = store_data.GetMustacheScale(); | ||
| 53 | mustache_y = store_data.GetMustacheY(); | ||
| 54 | glass_type = store_data.GetGlassType(); | ||
| 55 | glass_color = store_data.GetGlassColor(); | ||
| 56 | glass_scale = store_data.GetGlassScale(); | ||
| 57 | glass_y = store_data.GetGlassY(); | ||
| 58 | mole_type = store_data.GetMoleType(); | ||
| 59 | mole_scale = store_data.GetMoleScale(); | ||
| 60 | mole_x = store_data.GetMoleX(); | ||
| 61 | mole_y = store_data.GetMoleY(); | ||
| 62 | padding = '\0'; | ||
| 63 | } | ||
| 64 | |||
| 65 | ValidationResult CharInfo::Verify() const { | ||
| 66 | if (!create_id.IsValid()) { | ||
| 67 | return ValidationResult::InvalidCreateId; | ||
| 68 | } | ||
| 69 | if (!name.IsValid()) { | ||
| 70 | return ValidationResult::InvalidName; | ||
| 71 | } | ||
| 72 | if (font_region > FontRegion::Max) { | ||
| 73 | return ValidationResult::InvalidFont; | ||
| 74 | } | ||
| 75 | if (favorite_color > FavoriteColor::Max) { | ||
| 76 | return ValidationResult::InvalidColor; | ||
| 77 | } | ||
| 78 | if (gender > Gender::Max) { | ||
| 79 | return ValidationResult::InvalidGender; | ||
| 80 | } | ||
| 81 | if (height > MaxHeight) { | ||
| 82 | return ValidationResult::InvalidHeight; | ||
| 83 | } | ||
| 84 | if (build > MaxBuild) { | ||
| 85 | return ValidationResult::InvalidBuild; | ||
| 86 | } | ||
| 87 | if (type > MaxType) { | ||
| 88 | return ValidationResult::InvalidType; | ||
| 89 | } | ||
| 90 | if (region_move > MaxRegionMove) { | ||
| 91 | return ValidationResult::InvalidRegionMove; | ||
| 92 | } | ||
| 93 | if (faceline_type > FacelineType::Max) { | ||
| 94 | return ValidationResult::InvalidFacelineType; | ||
| 95 | } | ||
| 96 | if (faceline_color > FacelineColor::Max) { | ||
| 97 | return ValidationResult::InvalidFacelineColor; | ||
| 98 | } | ||
| 99 | if (faceline_wrinkle > FacelineWrinkle::Max) { | ||
| 100 | return ValidationResult::InvalidFacelineWrinkle; | ||
| 101 | } | ||
| 102 | if (faceline_make > FacelineMake::Max) { | ||
| 103 | return ValidationResult::InvalidFacelineMake; | ||
| 104 | } | ||
| 105 | if (hair_type > HairType::Max) { | ||
| 106 | return ValidationResult::InvalidHairType; | ||
| 107 | } | ||
| 108 | if (hair_color > CommonColor::Max) { | ||
| 109 | return ValidationResult::InvalidHairColor; | ||
| 110 | } | ||
| 111 | if (hair_flip > HairFlip::Max) { | ||
| 112 | return ValidationResult::InvalidHairFlip; | ||
| 113 | } | ||
| 114 | if (eye_type > EyeType::Max) { | ||
| 115 | return ValidationResult::InvalidEyeType; | ||
| 116 | } | ||
| 117 | if (eye_color > CommonColor::Max) { | ||
| 118 | return ValidationResult::InvalidEyeColor; | ||
| 119 | } | ||
| 120 | if (eye_scale > MaxEyeScale) { | ||
| 121 | return ValidationResult::InvalidEyeScale; | ||
| 122 | } | ||
| 123 | if (eye_aspect > MaxEyeAspect) { | ||
| 124 | return ValidationResult::InvalidEyeAspect; | ||
| 125 | } | ||
| 126 | if (eye_rotate > MaxEyeX) { | ||
| 127 | return ValidationResult::InvalidEyeRotate; | ||
| 128 | } | ||
| 129 | if (eye_x > MaxEyeX) { | ||
| 130 | return ValidationResult::InvalidEyeX; | ||
| 131 | } | ||
| 132 | if (eye_y > MaxEyeY) { | ||
| 133 | return ValidationResult::InvalidEyeY; | ||
| 134 | } | ||
| 135 | if (eyebrow_type > EyebrowType::Max) { | ||
| 136 | return ValidationResult::InvalidEyebrowType; | ||
| 137 | } | ||
| 138 | if (eyebrow_color > CommonColor::Max) { | ||
| 139 | return ValidationResult::InvalidEyebrowColor; | ||
| 140 | } | ||
| 141 | if (eyebrow_scale > MaxEyebrowScale) { | ||
| 142 | return ValidationResult::InvalidEyebrowScale; | ||
| 143 | } | ||
| 144 | if (eyebrow_aspect > MaxEyebrowAspect) { | ||
| 145 | return ValidationResult::InvalidEyebrowAspect; | ||
| 146 | } | ||
| 147 | if (eyebrow_rotate > MaxEyebrowRotate) { | ||
| 148 | return ValidationResult::InvalidEyebrowRotate; | ||
| 149 | } | ||
| 150 | if (eyebrow_x > MaxEyebrowX) { | ||
| 151 | return ValidationResult::InvalidEyebrowX; | ||
| 152 | } | ||
| 153 | if (eyebrow_y > MaxEyebrowY) { | ||
| 154 | return ValidationResult::InvalidEyebrowY; | ||
| 155 | } | ||
| 156 | if (nose_type > NoseType::Max) { | ||
| 157 | return ValidationResult::InvalidNoseType; | ||
| 158 | } | ||
| 159 | if (nose_scale > MaxNoseScale) { | ||
| 160 | return ValidationResult::InvalidNoseScale; | ||
| 161 | } | ||
| 162 | if (nose_y > MaxNoseY) { | ||
| 163 | return ValidationResult::InvalidNoseY; | ||
| 164 | } | ||
| 165 | if (mouth_type > MouthType::Max) { | ||
| 166 | return ValidationResult::InvalidMouthType; | ||
| 167 | } | ||
| 168 | if (mouth_color > CommonColor::Max) { | ||
| 169 | return ValidationResult::InvalidMouthColor; | ||
| 170 | } | ||
| 171 | if (mouth_scale > MaxMouthScale) { | ||
| 172 | return ValidationResult::InvalidMouthScale; | ||
| 173 | } | ||
| 174 | if (mouth_aspect > MaxMoutAspect) { | ||
| 175 | return ValidationResult::InvalidMouthAspect; | ||
| 176 | } | ||
| 177 | if (mouth_y > MaxMouthY) { | ||
| 178 | return ValidationResult::InvalidMoleY; | ||
| 179 | } | ||
| 180 | if (beard_color > CommonColor::Max) { | ||
| 181 | return ValidationResult::InvalidBeardColor; | ||
| 182 | } | ||
| 183 | if (beard_type > BeardType::Max) { | ||
| 184 | return ValidationResult::InvalidBeardType; | ||
| 185 | } | ||
| 186 | if (mustache_type > MustacheType::Max) { | ||
| 187 | return ValidationResult::InvalidMustacheType; | ||
| 188 | } | ||
| 189 | if (mustache_scale > MaxMustacheScale) { | ||
| 190 | return ValidationResult::InvalidMustacheScale; | ||
| 191 | } | ||
| 192 | if (mustache_y > MasMustacheY) { | ||
| 193 | return ValidationResult::InvalidMustacheY; | ||
| 194 | } | ||
| 195 | if (glass_type > GlassType::Max) { | ||
| 196 | return ValidationResult::InvalidGlassType; | ||
| 197 | } | ||
| 198 | if (glass_color > CommonColor::Max) { | ||
| 199 | return ValidationResult::InvalidGlassColor; | ||
| 200 | } | ||
| 201 | if (glass_scale > MaxGlassScale) { | ||
| 202 | return ValidationResult::InvalidGlassScale; | ||
| 203 | } | ||
| 204 | if (glass_y > MaxGlassY) { | ||
| 205 | return ValidationResult::InvalidGlassY; | ||
| 206 | } | ||
| 207 | if (mole_type > MoleType::Max) { | ||
| 208 | return ValidationResult::InvalidMoleType; | ||
| 209 | } | ||
| 210 | if (mole_scale > MaxMoleScale) { | ||
| 211 | return ValidationResult::InvalidMoleScale; | ||
| 212 | } | ||
| 213 | if (mole_x > MaxMoleX) { | ||
| 214 | return ValidationResult::InvalidMoleX; | ||
| 215 | } | ||
| 216 | if (mole_y > MaxMoleY) { | ||
| 217 | return ValidationResult::InvalidMoleY; | ||
| 218 | } | ||
| 219 | return ValidationResult::NoErrors; | ||
| 220 | } | ||
| 221 | |||
| 222 | Common::UUID CharInfo::GetCreateId() const { | ||
| 223 | return create_id; | ||
| 224 | } | ||
| 225 | |||
| 226 | Nickname CharInfo::GetNickname() const { | ||
| 227 | return name; | ||
| 228 | } | ||
| 229 | |||
| 230 | FontRegion CharInfo::GetFontRegion() const { | ||
| 231 | return font_region; | ||
| 232 | } | ||
| 233 | |||
| 234 | FavoriteColor CharInfo::GetFavoriteColor() const { | ||
| 235 | return favorite_color; | ||
| 236 | } | ||
| 237 | |||
| 238 | Gender CharInfo::GetGender() const { | ||
| 239 | return gender; | ||
| 240 | } | ||
| 241 | |||
| 242 | u8 CharInfo::GetHeight() const { | ||
| 243 | return height; | ||
| 244 | } | ||
| 245 | |||
| 246 | u8 CharInfo::GetBuild() const { | ||
| 247 | return build; | ||
| 248 | } | ||
| 249 | |||
| 250 | u8 CharInfo::GetType() const { | ||
| 251 | return type; | ||
| 252 | } | ||
| 253 | |||
| 254 | u8 CharInfo::GetRegionMove() const { | ||
| 255 | return region_move; | ||
| 256 | } | ||
| 257 | |||
| 258 | FacelineType CharInfo::GetFacelineType() const { | ||
| 259 | return faceline_type; | ||
| 260 | } | ||
| 261 | |||
| 262 | FacelineColor CharInfo::GetFacelineColor() const { | ||
| 263 | return faceline_color; | ||
| 264 | } | ||
| 265 | |||
| 266 | FacelineWrinkle CharInfo::GetFacelineWrinkle() const { | ||
| 267 | return faceline_wrinkle; | ||
| 268 | } | ||
| 269 | |||
| 270 | FacelineMake CharInfo::GetFacelineMake() const { | ||
| 271 | return faceline_make; | ||
| 272 | } | ||
| 273 | |||
| 274 | HairType CharInfo::GetHairType() const { | ||
| 275 | return hair_type; | ||
| 276 | } | ||
| 277 | |||
| 278 | CommonColor CharInfo::GetHairColor() const { | ||
| 279 | return hair_color; | ||
| 280 | } | ||
| 281 | |||
| 282 | HairFlip CharInfo::GetHairFlip() const { | ||
| 283 | return hair_flip; | ||
| 284 | } | ||
| 285 | |||
| 286 | EyeType CharInfo::GetEyeType() const { | ||
| 287 | return eye_type; | ||
| 288 | } | ||
| 289 | |||
| 290 | CommonColor CharInfo::GetEyeColor() const { | ||
| 291 | return eye_color; | ||
| 292 | } | ||
| 293 | |||
| 294 | u8 CharInfo::GetEyeScale() const { | ||
| 295 | return eye_scale; | ||
| 296 | } | ||
| 297 | |||
| 298 | u8 CharInfo::GetEyeAspect() const { | ||
| 299 | return eye_aspect; | ||
| 300 | } | ||
| 301 | |||
| 302 | u8 CharInfo::GetEyeRotate() const { | ||
| 303 | return eye_rotate; | ||
| 304 | } | ||
| 305 | |||
| 306 | u8 CharInfo::GetEyeX() const { | ||
| 307 | return eye_x; | ||
| 308 | } | ||
| 309 | |||
| 310 | u8 CharInfo::GetEyeY() const { | ||
| 311 | return eye_y; | ||
| 312 | } | ||
| 313 | |||
| 314 | EyebrowType CharInfo::GetEyebrowType() const { | ||
| 315 | return eyebrow_type; | ||
| 316 | } | ||
| 317 | |||
| 318 | CommonColor CharInfo::GetEyebrowColor() const { | ||
| 319 | return eyebrow_color; | ||
| 320 | } | ||
| 321 | |||
| 322 | u8 CharInfo::GetEyebrowScale() const { | ||
| 323 | return eyebrow_scale; | ||
| 324 | } | ||
| 325 | |||
| 326 | u8 CharInfo::GetEyebrowAspect() const { | ||
| 327 | return eyebrow_aspect; | ||
| 328 | } | ||
| 329 | |||
| 330 | u8 CharInfo::GetEyebrowRotate() const { | ||
| 331 | return eyebrow_rotate; | ||
| 332 | } | ||
| 333 | |||
| 334 | u8 CharInfo::GetEyebrowX() const { | ||
| 335 | return eyebrow_x; | ||
| 336 | } | ||
| 337 | |||
| 338 | u8 CharInfo::GetEyebrowY() const { | ||
| 339 | return eyebrow_y; | ||
| 340 | } | ||
| 341 | |||
| 342 | NoseType CharInfo::GetNoseType() const { | ||
| 343 | return nose_type; | ||
| 344 | } | ||
| 345 | |||
| 346 | u8 CharInfo::GetNoseScale() const { | ||
| 347 | return nose_scale; | ||
| 348 | } | ||
| 349 | |||
| 350 | u8 CharInfo::GetNoseY() const { | ||
| 351 | return nose_y; | ||
| 352 | } | ||
| 353 | |||
| 354 | MouthType CharInfo::GetMouthType() const { | ||
| 355 | return mouth_type; | ||
| 356 | } | ||
| 357 | |||
| 358 | CommonColor CharInfo::GetMouthColor() const { | ||
| 359 | return mouth_color; | ||
| 360 | } | ||
| 361 | |||
| 362 | u8 CharInfo::GetMouthScale() const { | ||
| 363 | return mouth_scale; | ||
| 364 | } | ||
| 365 | |||
| 366 | u8 CharInfo::GetMouthAspect() const { | ||
| 367 | return mouth_aspect; | ||
| 368 | } | ||
| 369 | |||
| 370 | u8 CharInfo::GetMouthY() const { | ||
| 371 | return mouth_y; | ||
| 372 | } | ||
| 373 | |||
| 374 | CommonColor CharInfo::GetBeardColor() const { | ||
| 375 | return beard_color; | ||
| 376 | } | ||
| 377 | |||
| 378 | BeardType CharInfo::GetBeardType() const { | ||
| 379 | return beard_type; | ||
| 380 | } | ||
| 381 | |||
| 382 | MustacheType CharInfo::GetMustacheType() const { | ||
| 383 | return mustache_type; | ||
| 384 | } | ||
| 385 | |||
| 386 | u8 CharInfo::GetMustacheScale() const { | ||
| 387 | return mustache_scale; | ||
| 388 | } | ||
| 389 | |||
| 390 | u8 CharInfo::GetMustacheY() const { | ||
| 391 | return mustache_y; | ||
| 392 | } | ||
| 393 | |||
| 394 | GlassType CharInfo::GetGlassType() const { | ||
| 395 | return glass_type; | ||
| 396 | } | ||
| 397 | |||
| 398 | CommonColor CharInfo::GetGlassColor() const { | ||
| 399 | return glass_color; | ||
| 400 | } | ||
| 401 | |||
| 402 | u8 CharInfo::GetGlassScale() const { | ||
| 403 | return glass_scale; | ||
| 404 | } | ||
| 405 | |||
| 406 | u8 CharInfo::GetGlassY() const { | ||
| 407 | return glass_y; | ||
| 408 | } | ||
| 409 | |||
| 410 | MoleType CharInfo::GetMoleType() const { | ||
| 411 | return mole_type; | ||
| 412 | } | ||
| 413 | |||
| 414 | u8 CharInfo::GetMoleScale() const { | ||
| 415 | return mole_scale; | ||
| 416 | } | ||
| 417 | |||
| 418 | u8 CharInfo::GetMoleX() const { | ||
| 419 | return mole_x; | ||
| 420 | } | ||
| 421 | |||
| 422 | u8 CharInfo::GetMoleY() const { | ||
| 423 | return mole_y; | ||
| 424 | } | ||
| 425 | |||
| 426 | bool CharInfo::operator==(const CharInfo& info) { | ||
| 427 | bool is_identical = info.Verify() == ValidationResult::NoErrors; | ||
| 428 | is_identical &= name.data == info.GetNickname().data; | ||
| 429 | is_identical &= create_id == info.GetCreateId(); | ||
| 430 | is_identical &= font_region == info.GetFontRegion(); | ||
| 431 | is_identical &= favorite_color == info.GetFavoriteColor(); | ||
| 432 | is_identical &= gender == info.GetGender(); | ||
| 433 | is_identical &= height == info.GetHeight(); | ||
| 434 | is_identical &= build == info.GetBuild(); | ||
| 435 | is_identical &= type == info.GetType(); | ||
| 436 | is_identical &= region_move == info.GetRegionMove(); | ||
| 437 | is_identical &= faceline_type == info.GetFacelineType(); | ||
| 438 | is_identical &= faceline_color == info.GetFacelineColor(); | ||
| 439 | is_identical &= faceline_wrinkle == info.GetFacelineWrinkle(); | ||
| 440 | is_identical &= faceline_make == info.GetFacelineMake(); | ||
| 441 | is_identical &= hair_type == info.GetHairType(); | ||
| 442 | is_identical &= hair_color == info.GetHairColor(); | ||
| 443 | is_identical &= hair_flip == info.GetHairFlip(); | ||
| 444 | is_identical &= eye_type == info.GetEyeType(); | ||
| 445 | is_identical &= eye_color == info.GetEyeColor(); | ||
| 446 | is_identical &= eye_scale == info.GetEyeScale(); | ||
| 447 | is_identical &= eye_aspect == info.GetEyeAspect(); | ||
| 448 | is_identical &= eye_rotate == info.GetEyeRotate(); | ||
| 449 | is_identical &= eye_x == info.GetEyeX(); | ||
| 450 | is_identical &= eye_y == info.GetEyeY(); | ||
| 451 | is_identical &= eyebrow_type == info.GetEyebrowType(); | ||
| 452 | is_identical &= eyebrow_color == info.GetEyebrowColor(); | ||
| 453 | is_identical &= eyebrow_scale == info.GetEyebrowScale(); | ||
| 454 | is_identical &= eyebrow_aspect == info.GetEyebrowAspect(); | ||
| 455 | is_identical &= eyebrow_rotate == info.GetEyebrowRotate(); | ||
| 456 | is_identical &= eyebrow_x == info.GetEyebrowX(); | ||
| 457 | is_identical &= eyebrow_y == info.GetEyebrowY(); | ||
| 458 | is_identical &= nose_type == info.GetNoseType(); | ||
| 459 | is_identical &= nose_scale == info.GetNoseScale(); | ||
| 460 | is_identical &= nose_y == info.GetNoseY(); | ||
| 461 | is_identical &= mouth_type == info.GetMouthType(); | ||
| 462 | is_identical &= mouth_color == info.GetMouthColor(); | ||
| 463 | is_identical &= mouth_scale == info.GetMouthScale(); | ||
| 464 | is_identical &= mouth_aspect == info.GetMouthAspect(); | ||
| 465 | is_identical &= mouth_y == info.GetMouthY(); | ||
| 466 | is_identical &= beard_color == info.GetBeardColor(); | ||
| 467 | is_identical &= beard_type == info.GetBeardType(); | ||
| 468 | is_identical &= mustache_type == info.GetMustacheType(); | ||
| 469 | is_identical &= mustache_scale == info.GetMustacheScale(); | ||
| 470 | is_identical &= mustache_y == info.GetMustacheY(); | ||
| 471 | is_identical &= glass_type == info.GetGlassType(); | ||
| 472 | is_identical &= glass_color == info.GetGlassColor(); | ||
| 473 | is_identical &= glass_scale == info.GetGlassScale(); | ||
| 474 | is_identical &= glass_y == info.GetGlassY(); | ||
| 475 | is_identical &= mole_type == info.GetMoleType(); | ||
| 476 | is_identical &= mole_scale == info.GetMoleScale(); | ||
| 477 | is_identical &= mole_x == info.GetMoleX(); | ||
| 478 | is_identical &= mole_y == info.GetMoleY(); | ||
| 479 | return is_identical; | ||
| 480 | } | ||
| 481 | |||
| 482 | } // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/types/char_info.h b/src/core/hle/service/mii/types/char_info.h new file mode 100644 index 000000000..d069b221f --- /dev/null +++ b/src/core/hle/service/mii/types/char_info.h | |||
| @@ -0,0 +1,137 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include "core/hle/service/mii/mii_types.h" | ||
| 7 | |||
| 8 | namespace Service::Mii { | ||
| 9 | class StoreData; | ||
| 10 | |||
| 11 | // This is nn::mii::detail::CharInfoRaw | ||
| 12 | class CharInfo { | ||
| 13 | public: | ||
| 14 | void SetFromStoreData(const StoreData& store_data_raw); | ||
| 15 | |||
| 16 | ValidationResult Verify() const; | ||
| 17 | |||
| 18 | Common::UUID GetCreateId() const; | ||
| 19 | Nickname GetNickname() const; | ||
| 20 | FontRegion GetFontRegion() const; | ||
| 21 | FavoriteColor GetFavoriteColor() const; | ||
| 22 | Gender GetGender() const; | ||
| 23 | u8 GetHeight() const; | ||
| 24 | u8 GetBuild() const; | ||
| 25 | u8 GetType() const; | ||
| 26 | u8 GetRegionMove() const; | ||
| 27 | FacelineType GetFacelineType() const; | ||
| 28 | FacelineColor GetFacelineColor() const; | ||
| 29 | FacelineWrinkle GetFacelineWrinkle() const; | ||
| 30 | FacelineMake GetFacelineMake() const; | ||
| 31 | HairType GetHairType() const; | ||
| 32 | CommonColor GetHairColor() const; | ||
| 33 | HairFlip GetHairFlip() const; | ||
| 34 | EyeType GetEyeType() const; | ||
| 35 | CommonColor GetEyeColor() const; | ||
| 36 | u8 GetEyeScale() const; | ||
| 37 | u8 GetEyeAspect() const; | ||
| 38 | u8 GetEyeRotate() const; | ||
| 39 | u8 GetEyeX() const; | ||
| 40 | u8 GetEyeY() const; | ||
| 41 | EyebrowType GetEyebrowType() const; | ||
| 42 | CommonColor GetEyebrowColor() const; | ||
| 43 | u8 GetEyebrowScale() const; | ||
| 44 | u8 GetEyebrowAspect() const; | ||
| 45 | u8 GetEyebrowRotate() const; | ||
| 46 | u8 GetEyebrowX() const; | ||
| 47 | u8 GetEyebrowY() const; | ||
| 48 | NoseType GetNoseType() const; | ||
| 49 | u8 GetNoseScale() const; | ||
| 50 | u8 GetNoseY() const; | ||
| 51 | MouthType GetMouthType() const; | ||
| 52 | CommonColor GetMouthColor() const; | ||
| 53 | u8 GetMouthScale() const; | ||
| 54 | u8 GetMouthAspect() const; | ||
| 55 | u8 GetMouthY() const; | ||
| 56 | CommonColor GetBeardColor() const; | ||
| 57 | BeardType GetBeardType() const; | ||
| 58 | MustacheType GetMustacheType() const; | ||
| 59 | u8 GetMustacheScale() const; | ||
| 60 | u8 GetMustacheY() const; | ||
| 61 | GlassType GetGlassType() const; | ||
| 62 | CommonColor GetGlassColor() const; | ||
| 63 | u8 GetGlassScale() const; | ||
| 64 | u8 GetGlassY() const; | ||
| 65 | MoleType GetMoleType() const; | ||
| 66 | u8 GetMoleScale() const; | ||
| 67 | u8 GetMoleX() const; | ||
| 68 | u8 GetMoleY() const; | ||
| 69 | |||
| 70 | bool operator==(const CharInfo& info); | ||
| 71 | |||
| 72 | private: | ||
| 73 | Common::UUID create_id; | ||
| 74 | Nickname name; | ||
| 75 | u16 null_terminator; | ||
| 76 | FontRegion font_region; | ||
| 77 | FavoriteColor favorite_color; | ||
| 78 | Gender gender; | ||
| 79 | u8 height; | ||
| 80 | u8 build; | ||
| 81 | u8 type; | ||
| 82 | u8 region_move; | ||
| 83 | FacelineType faceline_type; | ||
| 84 | FacelineColor faceline_color; | ||
| 85 | FacelineWrinkle faceline_wrinkle; | ||
| 86 | FacelineMake faceline_make; | ||
| 87 | HairType hair_type; | ||
| 88 | CommonColor hair_color; | ||
| 89 | HairFlip hair_flip; | ||
| 90 | EyeType eye_type; | ||
| 91 | CommonColor eye_color; | ||
| 92 | u8 eye_scale; | ||
| 93 | u8 eye_aspect; | ||
| 94 | u8 eye_rotate; | ||
| 95 | u8 eye_x; | ||
| 96 | u8 eye_y; | ||
| 97 | EyebrowType eyebrow_type; | ||
| 98 | CommonColor eyebrow_color; | ||
| 99 | u8 eyebrow_scale; | ||
| 100 | u8 eyebrow_aspect; | ||
| 101 | u8 eyebrow_rotate; | ||
| 102 | u8 eyebrow_x; | ||
| 103 | u8 eyebrow_y; | ||
| 104 | NoseType nose_type; | ||
| 105 | u8 nose_scale; | ||
| 106 | u8 nose_y; | ||
| 107 | MouthType mouth_type; | ||
| 108 | CommonColor mouth_color; | ||
| 109 | u8 mouth_scale; | ||
| 110 | u8 mouth_aspect; | ||
| 111 | u8 mouth_y; | ||
| 112 | CommonColor beard_color; | ||
| 113 | BeardType beard_type; | ||
| 114 | MustacheType mustache_type; | ||
| 115 | u8 mustache_scale; | ||
| 116 | u8 mustache_y; | ||
| 117 | GlassType glass_type; | ||
| 118 | CommonColor glass_color; | ||
| 119 | u8 glass_scale; | ||
| 120 | u8 glass_y; | ||
| 121 | MoleType mole_type; | ||
| 122 | u8 mole_scale; | ||
| 123 | u8 mole_x; | ||
| 124 | u8 mole_y; | ||
| 125 | u8 padding; | ||
| 126 | }; | ||
| 127 | static_assert(sizeof(CharInfo) == 0x58, "CharInfo has incorrect size."); | ||
| 128 | static_assert(std::has_unique_object_representations_v<CharInfo>, | ||
| 129 | "All bits of CharInfo must contribute to its value."); | ||
| 130 | |||
| 131 | struct CharInfoElement { | ||
| 132 | CharInfo char_info{}; | ||
| 133 | Source source{}; | ||
| 134 | }; | ||
| 135 | static_assert(sizeof(CharInfoElement) == 0x5c, "CharInfoElement has incorrect size."); | ||
| 136 | |||
| 137 | }; // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/types/core_data.cpp b/src/core/hle/service/mii/types/core_data.cpp new file mode 100644 index 000000000..659288b51 --- /dev/null +++ b/src/core/hle/service/mii/types/core_data.cpp | |||
| @@ -0,0 +1,601 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #include "common/assert.h" | ||
| 5 | #include "core/hle/service/mii/mii_util.h" | ||
| 6 | #include "core/hle/service/mii/types/core_data.h" | ||
| 7 | #include "core/hle/service/mii/types/raw_data.h" | ||
| 8 | |||
| 9 | namespace Service::Mii { | ||
| 10 | |||
| 11 | void CoreData::SetDefault() { | ||
| 12 | data = {}; | ||
| 13 | name = GetDefaultNickname(); | ||
| 14 | } | ||
| 15 | |||
| 16 | void CoreData::BuildRandom(Age age, Gender gender, Race race) { | ||
| 17 | if (gender == Gender::All) { | ||
| 18 | gender = MiiUtil::GetRandomValue(Gender::Max); | ||
| 19 | } | ||
| 20 | |||
| 21 | if (age == Age::All) { | ||
| 22 | const auto random{MiiUtil::GetRandomValue<int>(10)}; | ||
| 23 | if (random >= 8) { | ||
| 24 | age = Age::Old; | ||
| 25 | } else if (random >= 4) { | ||
| 26 | age = Age::Normal; | ||
| 27 | } else { | ||
| 28 | age = Age::Young; | ||
| 29 | } | ||
| 30 | } | ||
| 31 | |||
| 32 | if (race == Race::All) { | ||
| 33 | const auto random{MiiUtil::GetRandomValue<int>(10)}; | ||
| 34 | if (random >= 8) { | ||
| 35 | race = Race::Black; | ||
| 36 | } else if (random >= 4) { | ||
| 37 | race = Race::White; | ||
| 38 | } else { | ||
| 39 | race = Race::Asian; | ||
| 40 | } | ||
| 41 | } | ||
| 42 | |||
| 43 | SetGender(gender); | ||
| 44 | SetFavoriteColor(MiiUtil::GetRandomValue(FavoriteColor::Max)); | ||
| 45 | SetRegionMove(0); | ||
| 46 | SetFontRegion(FontRegion::Standard); | ||
| 47 | SetType(0); | ||
| 48 | SetHeight(64); | ||
| 49 | SetBuild(64); | ||
| 50 | |||
| 51 | u32 axis_y{}; | ||
| 52 | if (gender == Gender::Female && age == Age::Young) { | ||
| 53 | axis_y = MiiUtil::GetRandomValue<u32>(3); | ||
| 54 | } | ||
| 55 | |||
| 56 | const std::size_t index{3 * static_cast<std::size_t>(age) + | ||
| 57 | 9 * static_cast<std::size_t>(gender) + static_cast<std::size_t>(race)}; | ||
| 58 | |||
| 59 | const auto& faceline_type_info{RawData::RandomMiiFaceline.at(index)}; | ||
| 60 | const auto& faceline_color_info{RawData::RandomMiiFacelineColor.at( | ||
| 61 | 3 * static_cast<std::size_t>(gender) + static_cast<std::size_t>(race))}; | ||
| 62 | const auto& faceline_wrinkle_info{RawData::RandomMiiFacelineWrinkle.at(index)}; | ||
| 63 | const auto& faceline_makeup_info{RawData::RandomMiiFacelineMakeup.at(index)}; | ||
| 64 | const auto& hair_type_info{RawData::RandomMiiHairType.at(index)}; | ||
| 65 | const auto& hair_color_info{RawData::RandomMiiHairColor.at(3 * static_cast<std::size_t>(race) + | ||
| 66 | static_cast<std::size_t>(age))}; | ||
| 67 | const auto& eye_type_info{RawData::RandomMiiEyeType.at(index)}; | ||
| 68 | const auto& eye_color_info{RawData::RandomMiiEyeColor.at(static_cast<std::size_t>(race))}; | ||
| 69 | const auto& eyebrow_type_info{RawData::RandomMiiEyebrowType.at(index)}; | ||
| 70 | const auto& nose_type_info{RawData::RandomMiiNoseType.at(index)}; | ||
| 71 | const auto& mouth_type_info{RawData::RandomMiiMouthType.at(index)}; | ||
| 72 | const auto& glasses_type_info{RawData::RandomMiiGlassType.at(static_cast<std::size_t>(age))}; | ||
| 73 | |||
| 74 | data.faceline_type.Assign( | ||
| 75 | faceline_type_info | ||
| 76 | .values[MiiUtil::GetRandomValue<std::size_t>(faceline_type_info.values_count)]); | ||
| 77 | data.faceline_color.Assign( | ||
| 78 | faceline_color_info | ||
| 79 | .values[MiiUtil::GetRandomValue<std::size_t>(faceline_color_info.values_count)]); | ||
| 80 | data.faceline_wrinkle.Assign( | ||
| 81 | faceline_wrinkle_info | ||
| 82 | .values[MiiUtil::GetRandomValue<std::size_t>(faceline_wrinkle_info.values_count)]); | ||
| 83 | data.faceline_makeup.Assign( | ||
| 84 | faceline_makeup_info | ||
| 85 | .values[MiiUtil::GetRandomValue<std::size_t>(faceline_makeup_info.values_count)]); | ||
| 86 | |||
| 87 | data.hair_type.Assign( | ||
| 88 | hair_type_info.values[MiiUtil::GetRandomValue<std::size_t>(hair_type_info.values_count)]); | ||
| 89 | SetHairColor(RawData::GetHairColorFromVer3( | ||
| 90 | hair_color_info | ||
| 91 | .values[MiiUtil::GetRandomValue<std::size_t>(hair_color_info.values_count)])); | ||
| 92 | SetHairFlip(MiiUtil::GetRandomValue(HairFlip::Max)); | ||
| 93 | |||
| 94 | data.eye_type.Assign( | ||
| 95 | eye_type_info.values[MiiUtil::GetRandomValue<std::size_t>(eye_type_info.values_count)]); | ||
| 96 | |||
| 97 | const auto eye_rotate_1{gender != Gender::Male ? 4 : 2}; | ||
| 98 | const auto eye_rotate_2{gender != Gender::Male ? 3 : 4}; | ||
| 99 | const auto eye_rotate_offset{32 - RawData::EyeRotateLookup[eye_rotate_1] + eye_rotate_2}; | ||
| 100 | const auto eye_rotate{32 - RawData::EyeRotateLookup[data.eye_type]}; | ||
| 101 | |||
| 102 | SetEyeColor(RawData::GetEyeColorFromVer3( | ||
| 103 | eye_color_info.values[MiiUtil::GetRandomValue<std::size_t>(eye_color_info.values_count)])); | ||
| 104 | SetEyeScale(4); | ||
| 105 | SetEyeAspect(3); | ||
| 106 | SetEyeRotate(static_cast<u8>(eye_rotate_offset - eye_rotate)); | ||
| 107 | SetEyeX(2); | ||
| 108 | SetEyeY(static_cast<u8>(axis_y + 12)); | ||
| 109 | |||
| 110 | data.eyebrow_type.Assign( | ||
| 111 | eyebrow_type_info | ||
| 112 | .values[MiiUtil::GetRandomValue<std::size_t>(eyebrow_type_info.values_count)]); | ||
| 113 | |||
| 114 | const auto eyebrow_rotate_1{race == Race::Asian ? 6 : 0}; | ||
| 115 | const auto eyebrow_y{race == Race::Asian ? 9 : 10}; | ||
| 116 | const auto eyebrow_rotate_offset{32 - RawData::EyebrowRotateLookup[eyebrow_rotate_1] + 6}; | ||
| 117 | const auto eyebrow_rotate{ | ||
| 118 | 32 - RawData::EyebrowRotateLookup[static_cast<std::size_t>(data.eyebrow_type.Value())]}; | ||
| 119 | |||
| 120 | SetEyebrowColor(GetHairColor()); | ||
| 121 | SetEyebrowScale(4); | ||
| 122 | SetEyebrowAspect(3); | ||
| 123 | SetEyebrowRotate(static_cast<u8>(eyebrow_rotate_offset - eyebrow_rotate)); | ||
| 124 | SetEyebrowX(2); | ||
| 125 | SetEyebrowY(static_cast<u8>(axis_y + eyebrow_y)); | ||
| 126 | |||
| 127 | data.nose_type.Assign( | ||
| 128 | nose_type_info.values[MiiUtil::GetRandomValue<std::size_t>(nose_type_info.values_count)]); | ||
| 129 | SetNoseScale(gender == Gender::Female ? 3 : 4); | ||
| 130 | SetNoseY(static_cast<u8>(axis_y + 9)); | ||
| 131 | |||
| 132 | const auto mouth_color{gender == Gender::Female ? MiiUtil::GetRandomValue<int>(4) : 0}; | ||
| 133 | |||
| 134 | data.mouth_type.Assign( | ||
| 135 | mouth_type_info.values[MiiUtil::GetRandomValue<std::size_t>(mouth_type_info.values_count)]); | ||
| 136 | SetMouthColor(RawData::GetMouthColorFromVer3(mouth_color)); | ||
| 137 | SetMouthScale(4); | ||
| 138 | SetMouthAspect(3); | ||
| 139 | SetMouthY(static_cast<u8>(axis_y + 13)); | ||
| 140 | |||
| 141 | SetBeardColor(GetHairColor()); | ||
| 142 | SetMustacheScale(4); | ||
| 143 | |||
| 144 | if (gender == Gender::Male && age != Age::Young && MiiUtil::GetRandomValue<int>(10) < 2) { | ||
| 145 | const auto mustache_and_beard_flag{MiiUtil::GetRandomValue(BeardAndMustacheFlag::All)}; | ||
| 146 | |||
| 147 | auto beard_type{BeardType::None}; | ||
| 148 | auto mustache_type{MustacheType::None}; | ||
| 149 | |||
| 150 | if ((mustache_and_beard_flag & BeardAndMustacheFlag::Beard) == | ||
| 151 | BeardAndMustacheFlag::Beard) { | ||
| 152 | beard_type = MiiUtil::GetRandomValue(BeardType::Min, BeardType::Max); | ||
| 153 | } | ||
| 154 | |||
| 155 | if ((mustache_and_beard_flag & BeardAndMustacheFlag::Mustache) == | ||
| 156 | BeardAndMustacheFlag::Mustache) { | ||
| 157 | mustache_type = MiiUtil::GetRandomValue(MustacheType::Min, MustacheType::Max); | ||
| 158 | } | ||
| 159 | |||
| 160 | SetMustacheType(mustache_type); | ||
| 161 | SetBeardType(beard_type); | ||
| 162 | SetMustacheY(10); | ||
| 163 | } else { | ||
| 164 | SetMustacheType(MustacheType::None); | ||
| 165 | SetBeardType(BeardType::None); | ||
| 166 | SetMustacheY(static_cast<u8>(axis_y + 10)); | ||
| 167 | } | ||
| 168 | |||
| 169 | const auto glasses_type_start{MiiUtil::GetRandomValue<std::size_t>(100)}; | ||
| 170 | u8 glasses_type{}; | ||
| 171 | while (glasses_type_start < glasses_type_info.values[glasses_type]) { | ||
| 172 | if (++glasses_type >= glasses_type_info.values_count) { | ||
| 173 | ASSERT(false); | ||
| 174 | break; | ||
| 175 | } | ||
| 176 | } | ||
| 177 | |||
| 178 | SetGlassType(static_cast<GlassType>(glasses_type)); | ||
| 179 | SetGlassColor(RawData::GetGlassColorFromVer3(0)); | ||
| 180 | SetGlassScale(4); | ||
| 181 | |||
| 182 | SetMoleType(MoleType::None); | ||
| 183 | SetMoleScale(4); | ||
| 184 | SetMoleX(2); | ||
| 185 | SetMoleY(20); | ||
| 186 | } | ||
| 187 | |||
| 188 | u32 CoreData::IsValid() const { | ||
| 189 | // TODO: Complete this | ||
| 190 | return 0; | ||
| 191 | } | ||
| 192 | |||
| 193 | void CoreData::SetFontRegion(FontRegion value) { | ||
| 194 | data.font_region.Assign(static_cast<u32>(value)); | ||
| 195 | } | ||
| 196 | |||
| 197 | void CoreData::SetFavoriteColor(FavoriteColor value) { | ||
| 198 | data.favorite_color.Assign(static_cast<u32>(value)); | ||
| 199 | } | ||
| 200 | |||
| 201 | void CoreData::SetGender(Gender value) { | ||
| 202 | data.gender.Assign(static_cast<u32>(value)); | ||
| 203 | } | ||
| 204 | |||
| 205 | void CoreData::SetHeight(u8 value) { | ||
| 206 | data.height.Assign(value); | ||
| 207 | } | ||
| 208 | |||
| 209 | void CoreData::SetBuild(u8 value) { | ||
| 210 | data.build.Assign(value); | ||
| 211 | } | ||
| 212 | |||
| 213 | void CoreData::SetType(u8 value) { | ||
| 214 | data.type.Assign(value); | ||
| 215 | } | ||
| 216 | |||
| 217 | void CoreData::SetRegionMove(u8 value) { | ||
| 218 | data.region_move.Assign(value); | ||
| 219 | } | ||
| 220 | |||
| 221 | void CoreData::SetFacelineType(FacelineType value) { | ||
| 222 | data.faceline_type.Assign(static_cast<u32>(value)); | ||
| 223 | } | ||
| 224 | |||
| 225 | void CoreData::SetFacelineColor(FacelineColor value) { | ||
| 226 | data.faceline_color.Assign(static_cast<u32>(value)); | ||
| 227 | } | ||
| 228 | |||
| 229 | void CoreData::SetFacelineWrinkle(FacelineWrinkle value) { | ||
| 230 | data.faceline_wrinkle.Assign(static_cast<u32>(value)); | ||
| 231 | } | ||
| 232 | |||
| 233 | void CoreData::SetFacelineMake(FacelineMake value) { | ||
| 234 | data.faceline_makeup.Assign(static_cast<u32>(value)); | ||
| 235 | } | ||
| 236 | |||
| 237 | void CoreData::SetHairType(HairType value) { | ||
| 238 | data.hair_type.Assign(static_cast<u32>(value)); | ||
| 239 | } | ||
| 240 | |||
| 241 | void CoreData::SetHairColor(CommonColor value) { | ||
| 242 | data.hair_color.Assign(static_cast<u32>(value)); | ||
| 243 | } | ||
| 244 | |||
| 245 | void CoreData::SetHairFlip(HairFlip value) { | ||
| 246 | data.hair_flip.Assign(static_cast<u32>(value)); | ||
| 247 | } | ||
| 248 | |||
| 249 | void CoreData::SetEyeType(EyeType value) { | ||
| 250 | data.eye_type.Assign(static_cast<u32>(value)); | ||
| 251 | } | ||
| 252 | |||
| 253 | void CoreData::SetEyeColor(CommonColor value) { | ||
| 254 | data.eye_color.Assign(static_cast<u32>(value)); | ||
| 255 | } | ||
| 256 | |||
| 257 | void CoreData::SetEyeScale(u8 value) { | ||
| 258 | data.eye_scale.Assign(value); | ||
| 259 | } | ||
| 260 | |||
| 261 | void CoreData::SetEyeAspect(u8 value) { | ||
| 262 | data.eye_aspect.Assign(value); | ||
| 263 | } | ||
| 264 | |||
| 265 | void CoreData::SetEyeRotate(u8 value) { | ||
| 266 | data.eye_rotate.Assign(value); | ||
| 267 | } | ||
| 268 | |||
| 269 | void CoreData::SetEyeX(u8 value) { | ||
| 270 | data.eye_x.Assign(value); | ||
| 271 | } | ||
| 272 | |||
| 273 | void CoreData::SetEyeY(u8 value) { | ||
| 274 | data.eye_y.Assign(value); | ||
| 275 | } | ||
| 276 | |||
| 277 | void CoreData::SetEyebrowType(EyebrowType value) { | ||
| 278 | data.eyebrow_type.Assign(static_cast<u32>(value)); | ||
| 279 | } | ||
| 280 | |||
| 281 | void CoreData::SetEyebrowColor(CommonColor value) { | ||
| 282 | data.eyebrow_color.Assign(static_cast<u32>(value)); | ||
| 283 | } | ||
| 284 | |||
| 285 | void CoreData::SetEyebrowScale(u8 value) { | ||
| 286 | data.eyebrow_scale.Assign(value); | ||
| 287 | } | ||
| 288 | |||
| 289 | void CoreData::SetEyebrowAspect(u8 value) { | ||
| 290 | data.eyebrow_aspect.Assign(value); | ||
| 291 | } | ||
| 292 | |||
| 293 | void CoreData::SetEyebrowRotate(u8 value) { | ||
| 294 | data.eyebrow_rotate.Assign(value); | ||
| 295 | } | ||
| 296 | |||
| 297 | void CoreData::SetEyebrowX(u8 value) { | ||
| 298 | data.eyebrow_x.Assign(value); | ||
| 299 | } | ||
| 300 | |||
| 301 | void CoreData::SetEyebrowY(u8 value) { | ||
| 302 | data.eyebrow_y.Assign(value); | ||
| 303 | } | ||
| 304 | |||
| 305 | void CoreData::SetNoseType(NoseType value) { | ||
| 306 | data.nose_type.Assign(static_cast<u32>(value)); | ||
| 307 | } | ||
| 308 | |||
| 309 | void CoreData::SetNoseScale(u8 value) { | ||
| 310 | data.nose_scale.Assign(value); | ||
| 311 | } | ||
| 312 | |||
| 313 | void CoreData::SetNoseY(u8 value) { | ||
| 314 | data.nose_y.Assign(value); | ||
| 315 | } | ||
| 316 | |||
| 317 | void CoreData::SetMouthType(u8 value) { | ||
| 318 | data.mouth_type.Assign(value); | ||
| 319 | } | ||
| 320 | |||
| 321 | void CoreData::SetMouthColor(CommonColor value) { | ||
| 322 | data.mouth_color.Assign(static_cast<u32>(value)); | ||
| 323 | } | ||
| 324 | |||
| 325 | void CoreData::SetMouthScale(u8 value) { | ||
| 326 | data.mouth_scale.Assign(value); | ||
| 327 | } | ||
| 328 | |||
| 329 | void CoreData::SetMouthAspect(u8 value) { | ||
| 330 | data.mouth_aspect.Assign(value); | ||
| 331 | } | ||
| 332 | |||
| 333 | void CoreData::SetMouthY(u8 value) { | ||
| 334 | data.mouth_y.Assign(value); | ||
| 335 | } | ||
| 336 | |||
| 337 | void CoreData::SetBeardColor(CommonColor value) { | ||
| 338 | data.beard_color.Assign(static_cast<u32>(value)); | ||
| 339 | } | ||
| 340 | |||
| 341 | void CoreData::SetBeardType(BeardType value) { | ||
| 342 | data.beard_type.Assign(static_cast<u32>(value)); | ||
| 343 | } | ||
| 344 | |||
| 345 | void CoreData::SetMustacheType(MustacheType value) { | ||
| 346 | data.mustache_type.Assign(static_cast<u32>(value)); | ||
| 347 | } | ||
| 348 | |||
| 349 | void CoreData::SetMustacheScale(u8 value) { | ||
| 350 | data.mustache_scale.Assign(value); | ||
| 351 | } | ||
| 352 | |||
| 353 | void CoreData::SetMustacheY(u8 value) { | ||
| 354 | data.mustache_y.Assign(value); | ||
| 355 | } | ||
| 356 | |||
| 357 | void CoreData::SetGlassType(GlassType value) { | ||
| 358 | data.glasses_type.Assign(static_cast<u32>(value)); | ||
| 359 | } | ||
| 360 | |||
| 361 | void CoreData::SetGlassColor(CommonColor value) { | ||
| 362 | data.glasses_color.Assign(static_cast<u32>(value)); | ||
| 363 | } | ||
| 364 | |||
| 365 | void CoreData::SetGlassScale(u8 value) { | ||
| 366 | data.glasses_scale.Assign(value); | ||
| 367 | } | ||
| 368 | |||
| 369 | void CoreData::SetGlassY(u8 value) { | ||
| 370 | data.glasses_y.Assign(value); | ||
| 371 | } | ||
| 372 | |||
| 373 | void CoreData::SetMoleType(MoleType value) { | ||
| 374 | data.mole_type.Assign(static_cast<u32>(value)); | ||
| 375 | } | ||
| 376 | |||
| 377 | void CoreData::SetMoleScale(u8 value) { | ||
| 378 | data.mole_scale.Assign(value); | ||
| 379 | } | ||
| 380 | |||
| 381 | void CoreData::SetMoleX(u8 value) { | ||
| 382 | data.mole_x.Assign(value); | ||
| 383 | } | ||
| 384 | |||
| 385 | void CoreData::SetMoleY(u8 value) { | ||
| 386 | data.mole_y.Assign(value); | ||
| 387 | } | ||
| 388 | |||
| 389 | void CoreData::SetNickname(Nickname nickname) { | ||
| 390 | name = nickname; | ||
| 391 | } | ||
| 392 | |||
| 393 | FontRegion CoreData::GetFontRegion() const { | ||
| 394 | return static_cast<FontRegion>(data.font_region.Value()); | ||
| 395 | } | ||
| 396 | |||
| 397 | FavoriteColor CoreData::GetFavoriteColor() const { | ||
| 398 | return static_cast<FavoriteColor>(data.favorite_color.Value()); | ||
| 399 | } | ||
| 400 | |||
| 401 | Gender CoreData::GetGender() const { | ||
| 402 | return static_cast<Gender>(data.gender.Value()); | ||
| 403 | } | ||
| 404 | |||
| 405 | u8 CoreData::GetHeight() const { | ||
| 406 | return static_cast<u8>(data.height.Value()); | ||
| 407 | } | ||
| 408 | |||
| 409 | u8 CoreData::GetBuild() const { | ||
| 410 | return static_cast<u8>(data.build.Value()); | ||
| 411 | } | ||
| 412 | |||
| 413 | u8 CoreData::GetType() const { | ||
| 414 | return static_cast<u8>(data.type.Value()); | ||
| 415 | } | ||
| 416 | |||
| 417 | u8 CoreData::GetRegionMove() const { | ||
| 418 | return static_cast<u8>(data.region_move.Value()); | ||
| 419 | } | ||
| 420 | |||
| 421 | FacelineType CoreData::GetFacelineType() const { | ||
| 422 | return static_cast<FacelineType>(data.faceline_type.Value()); | ||
| 423 | } | ||
| 424 | |||
| 425 | FacelineColor CoreData::GetFacelineColor() const { | ||
| 426 | return static_cast<FacelineColor>(data.faceline_color.Value()); | ||
| 427 | } | ||
| 428 | |||
| 429 | FacelineWrinkle CoreData::GetFacelineWrinkle() const { | ||
| 430 | return static_cast<FacelineWrinkle>(data.faceline_wrinkle.Value()); | ||
| 431 | } | ||
| 432 | |||
| 433 | FacelineMake CoreData::GetFacelineMake() const { | ||
| 434 | return static_cast<FacelineMake>(data.faceline_makeup.Value()); | ||
| 435 | } | ||
| 436 | |||
| 437 | HairType CoreData::GetHairType() const { | ||
| 438 | return static_cast<HairType>(data.hair_type.Value()); | ||
| 439 | } | ||
| 440 | |||
| 441 | CommonColor CoreData::GetHairColor() const { | ||
| 442 | return static_cast<CommonColor>(data.hair_color.Value()); | ||
| 443 | } | ||
| 444 | |||
| 445 | HairFlip CoreData::GetHairFlip() const { | ||
| 446 | return static_cast<HairFlip>(data.hair_flip.Value()); | ||
| 447 | } | ||
| 448 | |||
| 449 | EyeType CoreData::GetEyeType() const { | ||
| 450 | return static_cast<EyeType>(data.eye_type.Value()); | ||
| 451 | } | ||
| 452 | |||
| 453 | CommonColor CoreData::GetEyeColor() const { | ||
| 454 | return static_cast<CommonColor>(data.eye_color.Value()); | ||
| 455 | } | ||
| 456 | |||
| 457 | u8 CoreData::GetEyeScale() const { | ||
| 458 | return static_cast<u8>(data.eye_scale.Value()); | ||
| 459 | } | ||
| 460 | |||
| 461 | u8 CoreData::GetEyeAspect() const { | ||
| 462 | return static_cast<u8>(data.eye_aspect.Value()); | ||
| 463 | } | ||
| 464 | |||
| 465 | u8 CoreData::GetEyeRotate() const { | ||
| 466 | return static_cast<u8>(data.eye_rotate.Value()); | ||
| 467 | } | ||
| 468 | |||
| 469 | u8 CoreData::GetEyeX() const { | ||
| 470 | return static_cast<u8>(data.eye_x.Value()); | ||
| 471 | } | ||
| 472 | |||
| 473 | u8 CoreData::GetEyeY() const { | ||
| 474 | return static_cast<u8>(data.eye_y.Value()); | ||
| 475 | } | ||
| 476 | |||
| 477 | EyebrowType CoreData::GetEyebrowType() const { | ||
| 478 | return static_cast<EyebrowType>(data.eyebrow_type.Value()); | ||
| 479 | } | ||
| 480 | |||
| 481 | CommonColor CoreData::GetEyebrowColor() const { | ||
| 482 | return static_cast<CommonColor>(data.eyebrow_color.Value()); | ||
| 483 | } | ||
| 484 | |||
| 485 | u8 CoreData::GetEyebrowScale() const { | ||
| 486 | return static_cast<u8>(data.eyebrow_scale.Value()); | ||
| 487 | } | ||
| 488 | |||
| 489 | u8 CoreData::GetEyebrowAspect() const { | ||
| 490 | return static_cast<u8>(data.eyebrow_aspect.Value()); | ||
| 491 | } | ||
| 492 | |||
| 493 | u8 CoreData::GetEyebrowRotate() const { | ||
| 494 | return static_cast<u8>(data.eyebrow_rotate.Value()); | ||
| 495 | } | ||
| 496 | |||
| 497 | u8 CoreData::GetEyebrowX() const { | ||
| 498 | return static_cast<u8>(data.eyebrow_x.Value()); | ||
| 499 | } | ||
| 500 | |||
| 501 | u8 CoreData::GetEyebrowY() const { | ||
| 502 | return static_cast<u8>(data.eyebrow_y.Value()); | ||
| 503 | } | ||
| 504 | |||
| 505 | NoseType CoreData::GetNoseType() const { | ||
| 506 | return static_cast<NoseType>(data.nose_type.Value()); | ||
| 507 | } | ||
| 508 | |||
| 509 | u8 CoreData::GetNoseScale() const { | ||
| 510 | return static_cast<u8>(data.nose_scale.Value()); | ||
| 511 | } | ||
| 512 | |||
| 513 | u8 CoreData::GetNoseY() const { | ||
| 514 | return static_cast<u8>(data.nose_y.Value()); | ||
| 515 | } | ||
| 516 | |||
| 517 | MouthType CoreData::GetMouthType() const { | ||
| 518 | return static_cast<MouthType>(data.mouth_type.Value()); | ||
| 519 | } | ||
| 520 | |||
| 521 | CommonColor CoreData::GetMouthColor() const { | ||
| 522 | return static_cast<CommonColor>(data.mouth_color.Value()); | ||
| 523 | } | ||
| 524 | |||
| 525 | u8 CoreData::GetMouthScale() const { | ||
| 526 | return static_cast<u8>(data.mouth_scale.Value()); | ||
| 527 | } | ||
| 528 | |||
| 529 | u8 CoreData::GetMouthAspect() const { | ||
| 530 | return static_cast<u8>(data.mouth_aspect.Value()); | ||
| 531 | } | ||
| 532 | |||
| 533 | u8 CoreData::GetMouthY() const { | ||
| 534 | return static_cast<u8>(data.mouth_y.Value()); | ||
| 535 | } | ||
| 536 | |||
| 537 | CommonColor CoreData::GetBeardColor() const { | ||
| 538 | return static_cast<CommonColor>(data.beard_color.Value()); | ||
| 539 | } | ||
| 540 | |||
| 541 | BeardType CoreData::GetBeardType() const { | ||
| 542 | return static_cast<BeardType>(data.beard_type.Value()); | ||
| 543 | } | ||
| 544 | |||
| 545 | MustacheType CoreData::GetMustacheType() const { | ||
| 546 | return static_cast<MustacheType>(data.mustache_type.Value()); | ||
| 547 | } | ||
| 548 | |||
| 549 | u8 CoreData::GetMustacheScale() const { | ||
| 550 | return static_cast<u8>(data.mustache_scale.Value()); | ||
| 551 | } | ||
| 552 | |||
| 553 | u8 CoreData::GetMustacheY() const { | ||
| 554 | return static_cast<u8>(data.mustache_y.Value()); | ||
| 555 | } | ||
| 556 | |||
| 557 | GlassType CoreData::GetGlassType() const { | ||
| 558 | return static_cast<GlassType>(data.glasses_type.Value()); | ||
| 559 | } | ||
| 560 | |||
| 561 | CommonColor CoreData::GetGlassColor() const { | ||
| 562 | return static_cast<CommonColor>(data.glasses_color.Value()); | ||
| 563 | } | ||
| 564 | |||
| 565 | u8 CoreData::GetGlassScale() const { | ||
| 566 | return static_cast<u8>(data.glasses_scale.Value()); | ||
| 567 | } | ||
| 568 | |||
| 569 | u8 CoreData::GetGlassY() const { | ||
| 570 | return static_cast<u8>(data.glasses_y.Value()); | ||
| 571 | } | ||
| 572 | |||
| 573 | MoleType CoreData::GetMoleType() const { | ||
| 574 | return static_cast<MoleType>(data.mole_type.Value()); | ||
| 575 | } | ||
| 576 | |||
| 577 | u8 CoreData::GetMoleScale() const { | ||
| 578 | return static_cast<u8>(data.mole_scale.Value()); | ||
| 579 | } | ||
| 580 | |||
| 581 | u8 CoreData::GetMoleX() const { | ||
| 582 | return static_cast<u8>(data.mole_x.Value()); | ||
| 583 | } | ||
| 584 | |||
| 585 | u8 CoreData::GetMoleY() const { | ||
| 586 | return static_cast<u8>(data.mole_y.Value()); | ||
| 587 | } | ||
| 588 | |||
| 589 | Nickname CoreData::GetNickname() const { | ||
| 590 | return name; | ||
| 591 | } | ||
| 592 | |||
| 593 | Nickname CoreData::GetDefaultNickname() const { | ||
| 594 | return {u'n', u'o', u' ', u'n', u'a', u'm', u'e'}; | ||
| 595 | } | ||
| 596 | |||
| 597 | Nickname CoreData::GetInvalidNickname() const { | ||
| 598 | return {u'?', u'?', u'?'}; | ||
| 599 | } | ||
| 600 | |||
| 601 | } // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/types/core_data.h b/src/core/hle/service/mii/types/core_data.h new file mode 100644 index 000000000..cebcd2ee4 --- /dev/null +++ b/src/core/hle/service/mii/types/core_data.h | |||
| @@ -0,0 +1,216 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include "core/hle/service/mii/mii_types.h" | ||
| 7 | |||
| 8 | namespace Service::Mii { | ||
| 9 | |||
| 10 | struct StoreDataBitFields { | ||
| 11 | union { | ||
| 12 | u32 word_0{}; | ||
| 13 | |||
| 14 | BitField<0, 8, u32> hair_type; | ||
| 15 | BitField<8, 7, u32> height; | ||
| 16 | BitField<15, 1, u32> mole_type; | ||
| 17 | BitField<16, 7, u32> build; | ||
| 18 | BitField<23, 1, u32> hair_flip; | ||
| 19 | BitField<24, 7, u32> hair_color; | ||
| 20 | BitField<31, 1, u32> type; | ||
| 21 | }; | ||
| 22 | |||
| 23 | union { | ||
| 24 | u32 word_1{}; | ||
| 25 | |||
| 26 | BitField<0, 7, u32> eye_color; | ||
| 27 | BitField<7, 1, u32> gender; | ||
| 28 | BitField<8, 7, u32> eyebrow_color; | ||
| 29 | BitField<16, 7, u32> mouth_color; | ||
| 30 | BitField<24, 7, u32> beard_color; | ||
| 31 | }; | ||
| 32 | |||
| 33 | union { | ||
| 34 | u32 word_2{}; | ||
| 35 | |||
| 36 | BitField<0, 7, u32> glasses_color; | ||
| 37 | BitField<8, 6, u32> eye_type; | ||
| 38 | BitField<14, 2, u32> region_move; | ||
| 39 | BitField<16, 6, u32> mouth_type; | ||
| 40 | BitField<22, 2, u32> font_region; | ||
| 41 | BitField<24, 5, u32> eye_y; | ||
| 42 | BitField<29, 3, u32> glasses_scale; | ||
| 43 | }; | ||
| 44 | |||
| 45 | union { | ||
| 46 | u32 word_3{}; | ||
| 47 | |||
| 48 | BitField<0, 5, u32> eyebrow_type; | ||
| 49 | BitField<5, 3, u32> mustache_type; | ||
| 50 | BitField<8, 5, u32> nose_type; | ||
| 51 | BitField<13, 3, u32> beard_type; | ||
| 52 | BitField<16, 5, u32> nose_y; | ||
| 53 | BitField<21, 3, u32> mouth_aspect; | ||
| 54 | BitField<24, 5, u32> mouth_y; | ||
| 55 | BitField<29, 3, u32> eyebrow_aspect; | ||
| 56 | }; | ||
| 57 | |||
| 58 | union { | ||
| 59 | u32 word_4{}; | ||
| 60 | |||
| 61 | BitField<0, 5, u32> mustache_y; | ||
| 62 | BitField<5, 3, u32> eye_rotate; | ||
| 63 | BitField<8, 5, u32> glasses_y; | ||
| 64 | BitField<13, 3, u32> eye_aspect; | ||
| 65 | BitField<16, 5, u32> mole_x; | ||
| 66 | BitField<21, 3, u32> eye_scale; | ||
| 67 | BitField<24, 5, u32> mole_y; | ||
| 68 | }; | ||
| 69 | |||
| 70 | union { | ||
| 71 | u32 word_5{}; | ||
| 72 | |||
| 73 | BitField<0, 5, u32> glasses_type; | ||
| 74 | BitField<8, 4, u32> favorite_color; | ||
| 75 | BitField<12, 4, u32> faceline_type; | ||
| 76 | BitField<16, 4, u32> faceline_color; | ||
| 77 | BitField<20, 4, u32> faceline_wrinkle; | ||
| 78 | BitField<24, 4, u32> faceline_makeup; | ||
| 79 | BitField<28, 4, u32> eye_x; | ||
| 80 | }; | ||
| 81 | |||
| 82 | union { | ||
| 83 | u32 word_6{}; | ||
| 84 | |||
| 85 | BitField<0, 4, u32> eyebrow_scale; | ||
| 86 | BitField<4, 4, u32> eyebrow_rotate; | ||
| 87 | BitField<8, 4, u32> eyebrow_x; | ||
| 88 | BitField<12, 4, u32> eyebrow_y; | ||
| 89 | BitField<16, 4, u32> nose_scale; | ||
| 90 | BitField<20, 4, u32> mouth_scale; | ||
| 91 | BitField<24, 4, u32> mustache_scale; | ||
| 92 | BitField<28, 4, u32> mole_scale; | ||
| 93 | }; | ||
| 94 | }; | ||
| 95 | static_assert(sizeof(StoreDataBitFields) == 0x1c, "StoreDataBitFields has incorrect size."); | ||
| 96 | static_assert(std::is_trivially_copyable_v<StoreDataBitFields>, | ||
| 97 | "StoreDataBitFields is not trivially copyable."); | ||
| 98 | |||
| 99 | class CoreData { | ||
| 100 | public: | ||
| 101 | void SetDefault(); | ||
| 102 | void BuildRandom(Age age, Gender gender, Race race); | ||
| 103 | |||
| 104 | u32 IsValid() const; | ||
| 105 | |||
| 106 | void SetFontRegion(FontRegion value); | ||
| 107 | void SetFavoriteColor(FavoriteColor value); | ||
| 108 | void SetGender(Gender value); | ||
| 109 | void SetHeight(u8 value); | ||
| 110 | void SetBuild(u8 value); | ||
| 111 | void SetType(u8 value); | ||
| 112 | void SetRegionMove(u8 value); | ||
| 113 | void SetFacelineType(FacelineType value); | ||
| 114 | void SetFacelineColor(FacelineColor value); | ||
| 115 | void SetFacelineWrinkle(FacelineWrinkle value); | ||
| 116 | void SetFacelineMake(FacelineMake value); | ||
| 117 | void SetHairType(HairType value); | ||
| 118 | void SetHairColor(CommonColor value); | ||
| 119 | void SetHairFlip(HairFlip value); | ||
| 120 | void SetEyeType(EyeType value); | ||
| 121 | void SetEyeColor(CommonColor value); | ||
| 122 | void SetEyeScale(u8 value); | ||
| 123 | void SetEyeAspect(u8 value); | ||
| 124 | void SetEyeRotate(u8 value); | ||
| 125 | void SetEyeX(u8 value); | ||
| 126 | void SetEyeY(u8 value); | ||
| 127 | void SetEyebrowType(EyebrowType value); | ||
| 128 | void SetEyebrowColor(CommonColor value); | ||
| 129 | void SetEyebrowScale(u8 value); | ||
| 130 | void SetEyebrowAspect(u8 value); | ||
| 131 | void SetEyebrowRotate(u8 value); | ||
| 132 | void SetEyebrowX(u8 value); | ||
| 133 | void SetEyebrowY(u8 value); | ||
| 134 | void SetNoseType(NoseType value); | ||
| 135 | void SetNoseScale(u8 value); | ||
| 136 | void SetNoseY(u8 value); | ||
| 137 | void SetMouthType(u8 value); | ||
| 138 | void SetMouthColor(CommonColor value); | ||
| 139 | void SetMouthScale(u8 value); | ||
| 140 | void SetMouthAspect(u8 value); | ||
| 141 | void SetMouthY(u8 value); | ||
| 142 | void SetBeardColor(CommonColor value); | ||
| 143 | void SetBeardType(BeardType value); | ||
| 144 | void SetMustacheType(MustacheType value); | ||
| 145 | void SetMustacheScale(u8 value); | ||
| 146 | void SetMustacheY(u8 value); | ||
| 147 | void SetGlassType(GlassType value); | ||
| 148 | void SetGlassColor(CommonColor value); | ||
| 149 | void SetGlassScale(u8 value); | ||
| 150 | void SetGlassY(u8 value); | ||
| 151 | void SetMoleType(MoleType value); | ||
| 152 | void SetMoleScale(u8 value); | ||
| 153 | void SetMoleX(u8 value); | ||
| 154 | void SetMoleY(u8 value); | ||
| 155 | void SetNickname(Nickname nickname); | ||
| 156 | |||
| 157 | FontRegion GetFontRegion() const; | ||
| 158 | FavoriteColor GetFavoriteColor() const; | ||
| 159 | Gender GetGender() const; | ||
| 160 | u8 GetHeight() const; | ||
| 161 | u8 GetBuild() const; | ||
| 162 | u8 GetType() const; | ||
| 163 | u8 GetRegionMove() const; | ||
| 164 | FacelineType GetFacelineType() const; | ||
| 165 | FacelineColor GetFacelineColor() const; | ||
| 166 | FacelineWrinkle GetFacelineWrinkle() const; | ||
| 167 | FacelineMake GetFacelineMake() const; | ||
| 168 | HairType GetHairType() const; | ||
| 169 | CommonColor GetHairColor() const; | ||
| 170 | HairFlip GetHairFlip() const; | ||
| 171 | EyeType GetEyeType() const; | ||
| 172 | CommonColor GetEyeColor() const; | ||
| 173 | u8 GetEyeScale() const; | ||
| 174 | u8 GetEyeAspect() const; | ||
| 175 | u8 GetEyeRotate() const; | ||
| 176 | u8 GetEyeX() const; | ||
| 177 | u8 GetEyeY() const; | ||
| 178 | EyebrowType GetEyebrowType() const; | ||
| 179 | CommonColor GetEyebrowColor() const; | ||
| 180 | u8 GetEyebrowScale() const; | ||
| 181 | u8 GetEyebrowAspect() const; | ||
| 182 | u8 GetEyebrowRotate() const; | ||
| 183 | u8 GetEyebrowX() const; | ||
| 184 | u8 GetEyebrowY() const; | ||
| 185 | NoseType GetNoseType() const; | ||
| 186 | u8 GetNoseScale() const; | ||
| 187 | u8 GetNoseY() const; | ||
| 188 | MouthType GetMouthType() const; | ||
| 189 | CommonColor GetMouthColor() const; | ||
| 190 | u8 GetMouthScale() const; | ||
| 191 | u8 GetMouthAspect() const; | ||
| 192 | u8 GetMouthY() const; | ||
| 193 | CommonColor GetBeardColor() const; | ||
| 194 | BeardType GetBeardType() const; | ||
| 195 | MustacheType GetMustacheType() const; | ||
| 196 | u8 GetMustacheScale() const; | ||
| 197 | u8 GetMustacheY() const; | ||
| 198 | GlassType GetGlassType() const; | ||
| 199 | CommonColor GetGlassColor() const; | ||
| 200 | u8 GetGlassScale() const; | ||
| 201 | u8 GetGlassY() const; | ||
| 202 | MoleType GetMoleType() const; | ||
| 203 | u8 GetMoleScale() const; | ||
| 204 | u8 GetMoleX() const; | ||
| 205 | u8 GetMoleY() const; | ||
| 206 | Nickname GetNickname() const; | ||
| 207 | Nickname GetDefaultNickname() const; | ||
| 208 | Nickname GetInvalidNickname() const; | ||
| 209 | |||
| 210 | private: | ||
| 211 | StoreDataBitFields data{}; | ||
| 212 | Nickname name{}; | ||
| 213 | }; | ||
| 214 | static_assert(sizeof(CoreData) == 0x30, "CoreData has incorrect size."); | ||
| 215 | |||
| 216 | }; // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/raw_data.cpp b/src/core/hle/service/mii/types/raw_data.cpp index e5245b791..5143abcc8 100644 --- a/src/core/hle/service/mii/raw_data.cpp +++ b/src/core/hle/service/mii/types/raw_data.cpp | |||
| @@ -1,10 +1,87 @@ | |||
| 1 | // SPDX-FileCopyrightText: Ryujinx Team and Contributors | 1 | // SPDX-FileCopyrightText: Ryujinx Team and Contributors |
| 2 | // SPDX-License-Identifier: MIT | 2 | // SPDX-License-Identifier: MIT |
| 3 | 3 | ||
| 4 | #include "core/hle/service/mii/raw_data.h" | 4 | #include "core/hle/service/mii/types/raw_data.h" |
| 5 | 5 | ||
| 6 | namespace Service::Mii::RawData { | 6 | namespace Service::Mii::RawData { |
| 7 | 7 | ||
| 8 | constexpr std::array<u8, static_cast<u8>(FacelineColor::Count)> FromVer3FacelineColorTable{ | ||
| 9 | 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x0, 0x1, 0x5, 0x5, | ||
| 10 | }; | ||
| 11 | |||
| 12 | constexpr std::array<u8, static_cast<u8>(CommonColor::Count)> FromVer3HairColorTable{ | ||
| 13 | 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, 0x0, 0x4, 0x3, 0x5, 0x4, 0x4, 0x6, 0x2, 0x0, | ||
| 14 | 0x6, 0x4, 0x3, 0x2, 0x2, 0x7, 0x3, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, | ||
| 15 | 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x0, 0x0, 0x4, | ||
| 16 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x0, 0x0, 0x0, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x5, 0x5, 0x5, | ||
| 17 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x5, 0x7, 0x5, 0x7, 0x7, 0x7, 0x7, 0x7, 0x6, 0x7, | ||
| 18 | 0x7, 0x7, 0x7, 0x7, 0x3, 0x7, 0x7, 0x7, 0x7, 0x7, 0x0, 0x4, 0x4, 0x4, 0x4, | ||
| 19 | }; | ||
| 20 | |||
| 21 | constexpr std::array<u8, static_cast<u8>(CommonColor::Count)> FromVer3EyeColorTable{ | ||
| 22 | 0x0, 0x2, 0x2, 0x2, 0x1, 0x3, 0x2, 0x3, 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x2, 0x2, 0x4, | ||
| 23 | 0x2, 0x1, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, | ||
| 24 | 0x2, 0x2, 0x2, 0x2, 0x0, 0x0, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x1, 0x0, 0x4, 0x4, | ||
| 25 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x0, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, | ||
| 26 | 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x2, 0x2, | ||
| 27 | 0x3, 0x3, 0x3, 0x3, 0x2, 0x2, 0x2, 0x2, 0x2, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, | ||
| 28 | }; | ||
| 29 | |||
| 30 | constexpr std::array<u8, static_cast<u8>(CommonColor::Count)> FromVer3MouthlineColorTable{ | ||
| 31 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x3, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x1, 0x4, | ||
| 32 | 0x4, 0x4, 0x0, 0x1, 0x2, 0x3, 0x4, 0x4, 0x2, 0x3, 0x3, 0x4, 0x4, 0x4, 0x4, 0x1, 0x4, | ||
| 33 | 0x4, 0x2, 0x3, 0x3, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x3, 0x3, 0x3, 0x4, 0x4, 0x4, | ||
| 34 | 0x3, 0x3, 0x3, 0x3, 0x3, 0x4, 0x4, 0x4, 0x4, 0x4, 0x3, 0x3, 0x3, 0x3, 0x4, 0x4, 0x4, | ||
| 35 | 0x4, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x4, 0x4, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x4, 0x3, | ||
| 36 | 0x3, 0x3, 0x3, 0x3, 0x4, 0x0, 0x3, 0x3, 0x3, 0x3, 0x4, 0x3, 0x3, 0x3, 0x3, | ||
| 37 | }; | ||
| 38 | |||
| 39 | constexpr std::array<u8, static_cast<u8>(CommonColor::Count)> FromVer3GlassColorTable{ | ||
| 40 | 0x0, 0x1, 0x1, 0x1, 0x5, 0x1, 0x1, 0x4, 0x0, 0x5, 0x1, 0x1, 0x3, 0x5, 0x1, 0x2, 0x3, | ||
| 41 | 0x4, 0x5, 0x4, 0x2, 0x2, 0x4, 0x4, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, 0x2, | ||
| 42 | 0x2, 0x2, 0x2, 0x2, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, | ||
| 43 | 0x3, 0x3, 0x3, 0x3, 0x3, 0x0, 0x0, 0x0, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x0, 0x5, 0x5, | ||
| 44 | 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, 0x1, 0x4, | ||
| 45 | 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x4, 0x5, 0x5, 0x5, 0x5, 0x5, 0x5, | ||
| 46 | }; | ||
| 47 | |||
| 48 | constexpr std::array<u8, static_cast<u8>(GlassType::Count)> FromVer3GlassTypeTable{ | ||
| 49 | 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, 0x8, 0x1, | ||
| 50 | 0x2, 0x1, 0x3, 0x7, 0x7, 0x6, 0x7, 0x8, 0x7, 0x7, | ||
| 51 | }; | ||
| 52 | |||
| 53 | constexpr std::array<u8, 8> Ver3FacelineColorTable{ | ||
| 54 | 0x0, 0x1, 0x2, 0x3, 0x4, 0x5, | ||
| 55 | }; | ||
| 56 | |||
| 57 | constexpr std::array<u8, 8> Ver3HairColorTable{ | ||
| 58 | 0x8, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, | ||
| 59 | }; | ||
| 60 | |||
| 61 | constexpr std::array<u8, 6> Ver3EyeColorTable{ | ||
| 62 | 0x8, 0x9, 0xa, 0xb, 0xc, 0xd, | ||
| 63 | }; | ||
| 64 | |||
| 65 | constexpr std::array<u8, 5> Ver3MouthColorTable{ | ||
| 66 | 0x13, 0x14, 0x15, 0x16, 0x17, | ||
| 67 | }; | ||
| 68 | |||
| 69 | constexpr std::array<u8, 7> Ver3GlassColorTable{ | ||
| 70 | 0x8, 0xe, 0xf, 0x10, 0x11, 0x12, 0x0, | ||
| 71 | }; | ||
| 72 | |||
| 73 | const std::array<u8, 62> EyeRotateLookup{ | ||
| 74 | 0x03, 0x04, 0x04, 0x04, 0x03, 0x04, 0x04, 0x04, 0x03, 0x04, 0x04, 0x04, 0x04, 0x03, 0x03, 0x04, | ||
| 75 | 0x04, 0x04, 0x03, 0x03, 0x04, 0x03, 0x04, 0x03, 0x03, 0x04, 0x03, 0x04, 0x04, 0x03, 0x04, 0x04, | ||
| 76 | 0x04, 0x03, 0x03, 0x03, 0x04, 0x04, 0x03, 0x03, 0x03, 0x04, 0x04, 0x03, 0x03, 0x03, 0x03, 0x03, | ||
| 77 | 0x03, 0x03, 0x03, 0x03, 0x04, 0x04, 0x04, 0x04, 0x03, 0x04, 0x04, 0x03, 0x04, 0x04, | ||
| 78 | }; | ||
| 79 | |||
| 80 | const std::array<u8, 24> EyebrowRotateLookup{ | ||
| 81 | 0x06, 0x06, 0x05, 0x07, 0x06, 0x07, 0x06, 0x07, 0x04, 0x07, 0x06, 0x08, | ||
| 82 | 0x05, 0x05, 0x06, 0x06, 0x07, 0x07, 0x06, 0x06, 0x05, 0x06, 0x07, 0x05, | ||
| 83 | }; | ||
| 84 | |||
| 8 | const std::array<Service::Mii::DefaultMii, 2> BaseMii{ | 85 | const std::array<Service::Mii::DefaultMii, 2> BaseMii{ |
| 9 | Service::Mii::DefaultMii{ | 86 | Service::Mii::DefaultMii{ |
| 10 | .face_type = 0, | 87 | .face_type = 0, |
| @@ -51,11 +128,12 @@ const std::array<Service::Mii::DefaultMii, 2> BaseMii{ | |||
| 51 | .mole_y = 20, | 128 | .mole_y = 20, |
| 52 | .height = 64, | 129 | .height = 64, |
| 53 | .weight = 64, | 130 | .weight = 64, |
| 54 | .gender = Gender::Male, | 131 | .gender = 0, |
| 55 | .favorite_color = 0, | 132 | .favorite_color = 0, |
| 56 | .region = 0, | 133 | .region_move = 0, |
| 57 | .font_region = FontRegion::Standard, | 134 | .font_region = 0, |
| 58 | .type = 0, | 135 | .type = 0, |
| 136 | .nickname = {u'n', u'o', u' ', u'n', u'a', u'm', u'e'}, | ||
| 59 | }, | 137 | }, |
| 60 | Service::Mii::DefaultMii{ | 138 | Service::Mii::DefaultMii{ |
| 61 | .face_type = 0, | 139 | .face_type = 0, |
| @@ -102,11 +180,12 @@ const std::array<Service::Mii::DefaultMii, 2> BaseMii{ | |||
| 102 | .mole_y = 20, | 180 | .mole_y = 20, |
| 103 | .height = 64, | 181 | .height = 64, |
| 104 | .weight = 64, | 182 | .weight = 64, |
| 105 | .gender = Gender::Female, | 183 | .gender = 1, |
| 106 | .favorite_color = 0, | 184 | .favorite_color = 0, |
| 107 | .region = 0, | 185 | .region_move = 0, |
| 108 | .font_region = FontRegion::Standard, | 186 | .font_region = 0, |
| 109 | .type = 0, | 187 | .type = 0, |
| 188 | .nickname = {u'n', u'o', u' ', u'n', u'a', u'm', u'e'}, | ||
| 110 | }, | 189 | }, |
| 111 | }; | 190 | }; |
| 112 | 191 | ||
| @@ -156,11 +235,12 @@ const std::array<Service::Mii::DefaultMii, 6> DefaultMii{ | |||
| 156 | .mole_y = 20, | 235 | .mole_y = 20, |
| 157 | .height = 64, | 236 | .height = 64, |
| 158 | .weight = 64, | 237 | .weight = 64, |
| 159 | .gender = Gender::Male, | 238 | .gender = 0, |
| 160 | .favorite_color = 4, | 239 | .favorite_color = 4, |
| 161 | .region = 0, | 240 | .region_move = 0, |
| 162 | .font_region = FontRegion::Standard, | 241 | .font_region = 0, |
| 163 | .type = 0, | 242 | .type = 0, |
| 243 | .nickname = {u'n', u'o', u' ', u'n', u'a', u'm', u'e'}, | ||
| 164 | }, | 244 | }, |
| 165 | Service::Mii::DefaultMii{ | 245 | Service::Mii::DefaultMii{ |
| 166 | .face_type = 0, | 246 | .face_type = 0, |
| @@ -207,11 +287,12 @@ const std::array<Service::Mii::DefaultMii, 6> DefaultMii{ | |||
| 207 | .mole_y = 20, | 287 | .mole_y = 20, |
| 208 | .height = 64, | 288 | .height = 64, |
| 209 | .weight = 64, | 289 | .weight = 64, |
| 210 | .gender = Gender::Male, | 290 | .gender = 0, |
| 211 | .favorite_color = 5, | 291 | .favorite_color = 5, |
| 212 | .region = 0, | 292 | .region_move = 0, |
| 213 | .font_region = FontRegion::Standard, | 293 | .font_region = 0, |
| 214 | .type = 0, | 294 | .type = 0, |
| 295 | .nickname = {u'n', u'o', u' ', u'n', u'a', u'm', u'e'}, | ||
| 215 | }, | 296 | }, |
| 216 | Service::Mii::DefaultMii{ | 297 | Service::Mii::DefaultMii{ |
| 217 | .face_type = 0, | 298 | .face_type = 0, |
| @@ -258,11 +339,12 @@ const std::array<Service::Mii::DefaultMii, 6> DefaultMii{ | |||
| 258 | .mole_y = 20, | 339 | .mole_y = 20, |
| 259 | .height = 64, | 340 | .height = 64, |
| 260 | .weight = 64, | 341 | .weight = 64, |
| 261 | .gender = Gender::Male, | 342 | .gender = 0, |
| 262 | .favorite_color = 0, | 343 | .favorite_color = 0, |
| 263 | .region = 0, | 344 | .region_move = 0, |
| 264 | .font_region = FontRegion::Standard, | 345 | .font_region = 0, |
| 265 | .type = 0, | 346 | .type = 0, |
| 347 | .nickname = {u'n', u'o', u' ', u'n', u'a', u'm', u'e'}, | ||
| 266 | }, | 348 | }, |
| 267 | Service::Mii::DefaultMii{ | 349 | Service::Mii::DefaultMii{ |
| 268 | .face_type = 0, | 350 | .face_type = 0, |
| @@ -309,11 +391,12 @@ const std::array<Service::Mii::DefaultMii, 6> DefaultMii{ | |||
| 309 | .mole_y = 20, | 391 | .mole_y = 20, |
| 310 | .height = 64, | 392 | .height = 64, |
| 311 | .weight = 64, | 393 | .weight = 64, |
| 312 | .gender = Gender::Female, | 394 | .gender = 1, |
| 313 | .favorite_color = 2, | 395 | .favorite_color = 2, |
| 314 | .region = 0, | 396 | .region_move = 0, |
| 315 | .font_region = FontRegion::Standard, | 397 | .font_region = 0, |
| 316 | .type = 0, | 398 | .type = 0, |
| 399 | .nickname = {u'n', u'o', u' ', u'n', u'a', u'm', u'e'}, | ||
| 317 | }, | 400 | }, |
| 318 | Service::Mii::DefaultMii{ | 401 | Service::Mii::DefaultMii{ |
| 319 | .face_type = 0, | 402 | .face_type = 0, |
| @@ -360,11 +443,12 @@ const std::array<Service::Mii::DefaultMii, 6> DefaultMii{ | |||
| 360 | .mole_y = 20, | 443 | .mole_y = 20, |
| 361 | .height = 64, | 444 | .height = 64, |
| 362 | .weight = 64, | 445 | .weight = 64, |
| 363 | .gender = Gender::Female, | 446 | .gender = 1, |
| 364 | .favorite_color = 6, | 447 | .favorite_color = 6, |
| 365 | .region = 0, | 448 | .region_move = 0, |
| 366 | .font_region = FontRegion::Standard, | 449 | .font_region = 0, |
| 367 | .type = 0, | 450 | .type = 0, |
| 451 | .nickname = {u'n', u'o', u' ', u'n', u'a', u'm', u'e'}, | ||
| 368 | }, | 452 | }, |
| 369 | Service::Mii::DefaultMii{ | 453 | Service::Mii::DefaultMii{ |
| 370 | .face_type = 0, | 454 | .face_type = 0, |
| @@ -411,176 +495,177 @@ const std::array<Service::Mii::DefaultMii, 6> DefaultMii{ | |||
| 411 | .mole_y = 20, | 495 | .mole_y = 20, |
| 412 | .height = 64, | 496 | .height = 64, |
| 413 | .weight = 64, | 497 | .weight = 64, |
| 414 | .gender = Gender::Female, | 498 | .gender = 1, |
| 415 | .favorite_color = 7, | 499 | .favorite_color = 7, |
| 416 | .region = 0, | 500 | .region_move = 0, |
| 417 | .font_region = FontRegion::Standard, | 501 | .font_region = 0, |
| 418 | .type = 0, | 502 | .type = 0, |
| 503 | .nickname = {u'n', u'o', u' ', u'n', u'a', u'm', u'e'}, | ||
| 419 | }, | 504 | }, |
| 420 | 505 | ||
| 421 | }; | 506 | }; |
| 422 | 507 | ||
| 423 | const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiFaceline{ | 508 | const std::array<RandomMiiData4, 18> RandomMiiFaceline{ |
| 424 | Service::Mii::RandomMiiData4{ | 509 | RandomMiiData4{ |
| 425 | .gender = Gender::Male, | 510 | .gender = static_cast<u32>(Gender::Male), |
| 426 | .age = Age::Young, | 511 | .age = static_cast<u32>(Age::Young), |
| 427 | .race = Race::Black, | 512 | .race = static_cast<u32>(Race::Black), |
| 428 | .values_count = 10, | 513 | .values_count = 10, |
| 429 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, | 514 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, |
| 430 | }, | 515 | }, |
| 431 | Service::Mii::RandomMiiData4{ | 516 | RandomMiiData4{ |
| 432 | .gender = Gender::Male, | 517 | .gender = static_cast<u32>(Gender::Male), |
| 433 | .age = Age::Normal, | 518 | .age = static_cast<u32>(Age::Normal), |
| 434 | .race = Race::Black, | 519 | .race = static_cast<u32>(Race::Black), |
| 435 | .values_count = 10, | 520 | .values_count = 10, |
| 436 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, | 521 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, |
| 437 | }, | 522 | }, |
| 438 | Service::Mii::RandomMiiData4{ | 523 | RandomMiiData4{ |
| 439 | .gender = Gender::Male, | 524 | .gender = static_cast<u32>(Gender::Male), |
| 440 | .age = Age::Old, | 525 | .age = static_cast<u32>(Age::Old), |
| 441 | .race = Race::Black, | 526 | .race = static_cast<u32>(Race::Black), |
| 442 | .values_count = 10, | 527 | .values_count = 10, |
| 443 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, | 528 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, |
| 444 | }, | 529 | }, |
| 445 | Service::Mii::RandomMiiData4{ | 530 | RandomMiiData4{ |
| 446 | .gender = Gender::Male, | 531 | .gender = static_cast<u32>(Gender::Male), |
| 447 | .age = Age::Young, | 532 | .age = static_cast<u32>(Age::Young), |
| 448 | .race = Race::White, | 533 | .race = static_cast<u32>(Race::White), |
| 449 | .values_count = 12, | 534 | .values_count = 12, |
| 450 | .values = {0, 0, 1, 2, 2, 3, 4, 5, 6, 7, 10, 11}, | 535 | .values = {0, 0, 1, 2, 2, 3, 4, 5, 6, 7, 10, 11}, |
| 451 | }, | 536 | }, |
| 452 | Service::Mii::RandomMiiData4{ | 537 | RandomMiiData4{ |
| 453 | .gender = Gender::Male, | 538 | .gender = static_cast<u32>(Gender::Male), |
| 454 | .age = Age::Normal, | 539 | .age = static_cast<u32>(Age::Normal), |
| 455 | .race = Race::White, | 540 | .race = static_cast<u32>(Race::White), |
| 456 | .values_count = 13, | 541 | .values_count = 13, |
| 457 | .values = {0, 1, 2, 2, 3, 4, 5, 6, 6, 7, 7, 10, 11}, | 542 | .values = {0, 1, 2, 2, 3, 4, 5, 6, 6, 7, 7, 10, 11}, |
| 458 | }, | 543 | }, |
| 459 | Service::Mii::RandomMiiData4{ | 544 | RandomMiiData4{ |
| 460 | .gender = Gender::Male, | 545 | .gender = static_cast<u32>(Gender::Male), |
| 461 | .age = Age::Old, | 546 | .age = static_cast<u32>(Age::Old), |
| 462 | .race = Race::White, | 547 | .race = static_cast<u32>(Race::White), |
| 463 | .values_count = 12, | 548 | .values_count = 12, |
| 464 | .values = {0, 0, 1, 2, 2, 3, 4, 5, 6, 7, 10, 11}, | 549 | .values = {0, 0, 1, 2, 2, 3, 4, 5, 6, 7, 10, 11}, |
| 465 | }, | 550 | }, |
| 466 | Service::Mii::RandomMiiData4{ | 551 | RandomMiiData4{ |
| 467 | .gender = Gender::Male, | 552 | .gender = static_cast<u32>(Gender::Male), |
| 468 | .age = Age::Young, | 553 | .age = static_cast<u32>(Age::Young), |
| 469 | .race = Race::Asian, | 554 | .race = static_cast<u32>(Race::Asian), |
| 470 | .values_count = 12, | 555 | .values_count = 12, |
| 471 | .values = {0, 0, 1, 2, 2, 3, 4, 5, 6, 7, 10, 11}, | 556 | .values = {0, 0, 1, 2, 2, 3, 4, 5, 6, 7, 10, 11}, |
| 472 | }, | 557 | }, |
| 473 | Service::Mii::RandomMiiData4{ | 558 | RandomMiiData4{ |
| 474 | .gender = Gender::Male, | 559 | .gender = static_cast<u32>(Gender::Male), |
| 475 | .age = Age::Normal, | 560 | .age = static_cast<u32>(Age::Normal), |
| 476 | .race = Race::Asian, | 561 | .race = static_cast<u32>(Race::Asian), |
| 477 | .values_count = 13, | 562 | .values_count = 13, |
| 478 | .values = {0, 1, 2, 2, 3, 4, 5, 6, 6, 7, 7, 10, 11}, | 563 | .values = {0, 1, 2, 2, 3, 4, 5, 6, 6, 7, 7, 10, 11}, |
| 479 | }, | 564 | }, |
| 480 | Service::Mii::RandomMiiData4{ | 565 | RandomMiiData4{ |
| 481 | .gender = Gender::Male, | 566 | .gender = static_cast<u32>(Gender::Male), |
| 482 | .age = Age::Old, | 567 | .age = static_cast<u32>(Age::Old), |
| 483 | .race = Race::Asian, | 568 | .race = static_cast<u32>(Race::Asian), |
| 484 | .values_count = 12, | 569 | .values_count = 12, |
| 485 | .values = {0, 0, 1, 2, 2, 3, 4, 5, 6, 7, 10, 11}, | 570 | .values = {0, 0, 1, 2, 2, 3, 4, 5, 6, 7, 10, 11}, |
| 486 | }, | 571 | }, |
| 487 | Service::Mii::RandomMiiData4{ | 572 | RandomMiiData4{ |
| 488 | .gender = Gender::Female, | 573 | .gender = static_cast<u32>(Gender::Female), |
| 489 | .age = Age::Young, | 574 | .age = static_cast<u32>(Age::Young), |
| 490 | .race = Race::Black, | 575 | .race = static_cast<u32>(Race::Black), |
| 491 | .values_count = 10, | 576 | .values_count = 10, |
| 492 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, | 577 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, |
| 493 | }, | 578 | }, |
| 494 | Service::Mii::RandomMiiData4{ | 579 | RandomMiiData4{ |
| 495 | .gender = Gender::Female, | 580 | .gender = static_cast<u32>(Gender::Female), |
| 496 | .age = Age::Normal, | 581 | .age = static_cast<u32>(Age::Normal), |
| 497 | .race = Race::Black, | 582 | .race = static_cast<u32>(Race::Black), |
| 498 | .values_count = 10, | 583 | .values_count = 10, |
| 499 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, | 584 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, |
| 500 | }, | 585 | }, |
| 501 | Service::Mii::RandomMiiData4{ | 586 | RandomMiiData4{ |
| 502 | .gender = Gender::Female, | 587 | .gender = static_cast<u32>(Gender::Female), |
| 503 | .age = Age::Old, | 588 | .age = static_cast<u32>(Age::Old), |
| 504 | .race = Race::Black, | 589 | .race = static_cast<u32>(Race::Black), |
| 505 | .values_count = 10, | 590 | .values_count = 10, |
| 506 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, | 591 | .values = {0, 0, 1, 1, 2, 3, 4, 5, 9, 9}, |
| 507 | }, | 592 | }, |
| 508 | Service::Mii::RandomMiiData4{ | 593 | RandomMiiData4{ |
| 509 | .gender = Gender::Female, | 594 | .gender = static_cast<u32>(Gender::Female), |
| 510 | .age = Age::Young, | 595 | .age = static_cast<u32>(Age::Young), |
| 511 | .race = Race::White, | 596 | .race = static_cast<u32>(Race::White), |
| 512 | .values_count = 12, | 597 | .values_count = 12, |
| 513 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, | 598 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, |
| 514 | }, | 599 | }, |
| 515 | Service::Mii::RandomMiiData4{ | 600 | RandomMiiData4{ |
| 516 | .gender = Gender::Female, | 601 | .gender = static_cast<u32>(Gender::Female), |
| 517 | .age = Age::Normal, | 602 | .age = static_cast<u32>(Age::Normal), |
| 518 | .race = Race::White, | 603 | .race = static_cast<u32>(Race::White), |
| 519 | .values_count = 12, | 604 | .values_count = 12, |
| 520 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, | 605 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, |
| 521 | }, | 606 | }, |
| 522 | Service::Mii::RandomMiiData4{ | 607 | RandomMiiData4{ |
| 523 | .gender = Gender::Female, | 608 | .gender = static_cast<u32>(Gender::Female), |
| 524 | .age = Age::Old, | 609 | .age = static_cast<u32>(Age::Old), |
| 525 | .race = Race::White, | 610 | .race = static_cast<u32>(Race::White), |
| 526 | .values_count = 12, | 611 | .values_count = 12, |
| 527 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, | 612 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, |
| 528 | }, | 613 | }, |
| 529 | Service::Mii::RandomMiiData4{ | 614 | RandomMiiData4{ |
| 530 | .gender = Gender::Female, | 615 | .gender = static_cast<u32>(Gender::Female), |
| 531 | .age = Age::Young, | 616 | .age = static_cast<u32>(Age::Young), |
| 532 | .race = Race::Asian, | 617 | .race = static_cast<u32>(Race::Asian), |
| 533 | .values_count = 12, | 618 | .values_count = 12, |
| 534 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, | 619 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, |
| 535 | }, | 620 | }, |
| 536 | Service::Mii::RandomMiiData4{ | 621 | RandomMiiData4{ |
| 537 | .gender = Gender::Female, | 622 | .gender = static_cast<u32>(Gender::Female), |
| 538 | .age = Age::Normal, | 623 | .age = static_cast<u32>(Age::Normal), |
| 539 | .race = Race::Asian, | 624 | .race = static_cast<u32>(Race::Asian), |
| 540 | .values_count = 12, | 625 | .values_count = 12, |
| 541 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, | 626 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, |
| 542 | }, | 627 | }, |
| 543 | Service::Mii::RandomMiiData4{ | 628 | RandomMiiData4{ |
| 544 | .gender = Gender::Female, | 629 | .gender = static_cast<u32>(Gender::Female), |
| 545 | .age = Age::Old, | 630 | .age = static_cast<u32>(Age::Old), |
| 546 | .race = Race::Asian, | 631 | .race = static_cast<u32>(Race::Asian), |
| 547 | .values_count = 12, | 632 | .values_count = 12, |
| 548 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, | 633 | .values = {0, 0, 0, 1, 1, 1, 2, 3, 4, 5, 8, 10}, |
| 549 | }, | 634 | }, |
| 550 | }; | 635 | }; |
| 551 | 636 | ||
| 552 | const std::array<Service::Mii::RandomMiiData3, 6> RandomMiiFacelineColor{ | 637 | const std::array<RandomMiiData3, 6> RandomMiiFacelineColor{ |
| 553 | Service::Mii::RandomMiiData3{ | 638 | RandomMiiData3{ |
| 554 | .arg_1 = 0, | 639 | .arg_1 = 0, |
| 555 | .arg_2 = 0, | 640 | .arg_2 = 0, |
| 556 | .values_count = 10, | 641 | .values_count = 10, |
| 557 | .values = {2, 2, 4, 4, 4, 4, 5, 5, 5, 5}, | 642 | .values = {2, 2, 4, 4, 4, 4, 5, 5, 5, 5}, |
| 558 | }, | 643 | }, |
| 559 | Service::Mii::RandomMiiData3{ | 644 | RandomMiiData3{ |
| 560 | .arg_1 = 0, | 645 | .arg_1 = 0, |
| 561 | .arg_2 = 1, | 646 | .arg_2 = 1, |
| 562 | .values_count = 10, | 647 | .values_count = 10, |
| 563 | .values = {0, 0, 0, 0, 1, 1, 2, 3, 3, 3}, | 648 | .values = {0, 0, 0, 0, 1, 1, 2, 3, 3, 3}, |
| 564 | }, | 649 | }, |
| 565 | Service::Mii::RandomMiiData3{ | 650 | RandomMiiData3{ |
| 566 | .arg_1 = 0, | 651 | .arg_1 = 0, |
| 567 | .arg_2 = 2, | 652 | .arg_2 = 2, |
| 568 | .values_count = 10, | 653 | .values_count = 10, |
| 569 | .values = {0, 0, 1, 1, 1, 1, 1, 1, 1, 2}, | 654 | .values = {0, 0, 1, 1, 1, 1, 1, 1, 1, 2}, |
| 570 | }, | 655 | }, |
| 571 | Service::Mii::RandomMiiData3{ | 656 | RandomMiiData3{ |
| 572 | .arg_1 = 1, | 657 | .arg_1 = 1, |
| 573 | .arg_2 = 0, | 658 | .arg_2 = 0, |
| 574 | .values_count = 10, | 659 | .values_count = 10, |
| 575 | .values = {2, 2, 4, 4, 4, 4, 5, 5, 5, 5}, | 660 | .values = {2, 2, 4, 4, 4, 4, 5, 5, 5, 5}, |
| 576 | }, | 661 | }, |
| 577 | Service::Mii::RandomMiiData3{ | 662 | RandomMiiData3{ |
| 578 | .arg_1 = 1, | 663 | .arg_1 = 1, |
| 579 | .arg_2 = 1, | 664 | .arg_2 = 1, |
| 580 | .values_count = 10, | 665 | .values_count = 10, |
| 581 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 1, 3}, | 666 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 1, 3}, |
| 582 | }, | 667 | }, |
| 583 | Service::Mii::RandomMiiData3{ | 668 | RandomMiiData3{ |
| 584 | .arg_1 = 1, | 669 | .arg_1 = 1, |
| 585 | .arg_2 = 2, | 670 | .arg_2 = 2, |
| 586 | .values_count = 10, | 671 | .values_count = 10, |
| @@ -588,407 +673,407 @@ const std::array<Service::Mii::RandomMiiData3, 6> RandomMiiFacelineColor{ | |||
| 588 | }, | 673 | }, |
| 589 | }; | 674 | }; |
| 590 | 675 | ||
| 591 | const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiFacelineWrinkle{ | 676 | const std::array<RandomMiiData4, 18> RandomMiiFacelineWrinkle{ |
| 592 | Service::Mii::RandomMiiData4{ | 677 | RandomMiiData4{ |
| 593 | .gender = Gender::Male, | 678 | .gender = static_cast<u32>(Gender::Male), |
| 594 | .age = Age::Young, | 679 | .age = static_cast<u32>(Age::Young), |
| 595 | .race = Race::Black, | 680 | .race = static_cast<u32>(Race::Black), |
| 596 | .values_count = 20, | 681 | .values_count = 20, |
| 597 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, | 682 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, |
| 598 | }, | 683 | }, |
| 599 | Service::Mii::RandomMiiData4{ | 684 | RandomMiiData4{ |
| 600 | .gender = Gender::Male, | 685 | .gender = static_cast<u32>(Gender::Male), |
| 601 | .age = Age::Normal, | 686 | .age = static_cast<u32>(Age::Normal), |
| 602 | .race = Race::Black, | 687 | .race = static_cast<u32>(Race::Black), |
| 603 | .values_count = 20, | 688 | .values_count = 20, |
| 604 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, | 689 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, |
| 605 | }, | 690 | }, |
| 606 | Service::Mii::RandomMiiData4{ | 691 | RandomMiiData4{ |
| 607 | .gender = Gender::Male, | 692 | .gender = static_cast<u32>(Gender::Male), |
| 608 | .age = Age::Old, | 693 | .age = static_cast<u32>(Age::Old), |
| 609 | .race = Race::Black, | 694 | .race = static_cast<u32>(Race::Black), |
| 610 | .values_count = 20, | 695 | .values_count = 20, |
| 611 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 8}, | 696 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 8}, |
| 612 | }, | 697 | }, |
| 613 | Service::Mii::RandomMiiData4{ | 698 | RandomMiiData4{ |
| 614 | .gender = Gender::Male, | 699 | .gender = static_cast<u32>(Gender::Male), |
| 615 | .age = Age::Young, | 700 | .age = static_cast<u32>(Age::Young), |
| 616 | .race = Race::White, | 701 | .race = static_cast<u32>(Race::White), |
| 617 | .values_count = 20, | 702 | .values_count = 20, |
| 618 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 3, 4, 5, 6, 7, 8, 8, 9}, | 703 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 3, 4, 5, 6, 7, 8, 8, 9}, |
| 619 | }, | 704 | }, |
| 620 | Service::Mii::RandomMiiData4{ | 705 | RandomMiiData4{ |
| 621 | .gender = Gender::Male, | 706 | .gender = static_cast<u32>(Gender::Male), |
| 622 | .age = Age::Normal, | 707 | .age = static_cast<u32>(Age::Normal), |
| 623 | .race = Race::White, | 708 | .race = static_cast<u32>(Race::White), |
| 624 | .values_count = 20, | 709 | .values_count = 20, |
| 625 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 3, 4, 5, 6, 7, 8, 8, 9}, | 710 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 3, 4, 5, 6, 7, 8, 8, 9}, |
| 626 | }, | 711 | }, |
| 627 | Service::Mii::RandomMiiData4{ | 712 | RandomMiiData4{ |
| 628 | .gender = Gender::Male, | 713 | .gender = static_cast<u32>(Gender::Male), |
| 629 | .age = Age::Old, | 714 | .age = static_cast<u32>(Age::Old), |
| 630 | .race = Race::White, | 715 | .race = static_cast<u32>(Race::White), |
| 631 | .values_count = 20, | 716 | .values_count = 20, |
| 632 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9}, | 717 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9}, |
| 633 | }, | 718 | }, |
| 634 | Service::Mii::RandomMiiData4{ | 719 | RandomMiiData4{ |
| 635 | .gender = Gender::Male, | 720 | .gender = static_cast<u32>(Gender::Male), |
| 636 | .age = Age::Young, | 721 | .age = static_cast<u32>(Age::Young), |
| 637 | .race = Race::Asian, | 722 | .race = static_cast<u32>(Race::Asian), |
| 638 | .values_count = 20, | 723 | .values_count = 20, |
| 639 | .values = {9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11}, | 724 | .values = {9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11}, |
| 640 | }, | 725 | }, |
| 641 | Service::Mii::RandomMiiData4{ | 726 | RandomMiiData4{ |
| 642 | .gender = Gender::Male, | 727 | .gender = static_cast<u32>(Gender::Male), |
| 643 | .age = Age::Normal, | 728 | .age = static_cast<u32>(Age::Normal), |
| 644 | .race = Race::Asian, | 729 | .race = static_cast<u32>(Race::Asian), |
| 645 | .values_count = 20, | 730 | .values_count = 20, |
| 646 | .values = {9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11}, | 731 | .values = {9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11}, |
| 647 | }, | 732 | }, |
| 648 | Service::Mii::RandomMiiData4{ | 733 | RandomMiiData4{ |
| 649 | .gender = Gender::Male, | 734 | .gender = static_cast<u32>(Gender::Male), |
| 650 | .age = Age::Old, | 735 | .age = static_cast<u32>(Age::Old), |
| 651 | .race = Race::Asian, | 736 | .race = static_cast<u32>(Race::Asian), |
| 652 | .values_count = 20, | 737 | .values_count = 20, |
| 653 | .values = {9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11}, | 738 | .values = {9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11}, |
| 654 | }, | 739 | }, |
| 655 | Service::Mii::RandomMiiData4{ | 740 | RandomMiiData4{ |
| 656 | .gender = Gender::Female, | 741 | .gender = static_cast<u32>(Gender::Female), |
| 657 | .age = Age::Young, | 742 | .age = static_cast<u32>(Age::Young), |
| 658 | .race = Race::Black, | 743 | .race = static_cast<u32>(Race::Black), |
| 659 | .values_count = 20, | 744 | .values_count = 20, |
| 660 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, | 745 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, |
| 661 | }, | 746 | }, |
| 662 | Service::Mii::RandomMiiData4{ | 747 | RandomMiiData4{ |
| 663 | .gender = Gender::Female, | 748 | .gender = static_cast<u32>(Gender::Female), |
| 664 | .age = Age::Normal, | 749 | .age = static_cast<u32>(Age::Normal), |
| 665 | .race = Race::Black, | 750 | .race = static_cast<u32>(Race::Black), |
| 666 | .values_count = 20, | 751 | .values_count = 20, |
| 667 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, | 752 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, |
| 668 | }, | 753 | }, |
| 669 | Service::Mii::RandomMiiData4{ | 754 | RandomMiiData4{ |
| 670 | .gender = Gender::Female, | 755 | .gender = static_cast<u32>(Gender::Female), |
| 671 | .age = Age::Old, | 756 | .age = static_cast<u32>(Age::Old), |
| 672 | .race = Race::Black, | 757 | .race = static_cast<u32>(Race::Black), |
| 673 | .values_count = 20, | 758 | .values_count = 20, |
| 674 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, | 759 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8}, |
| 675 | }, | 760 | }, |
| 676 | Service::Mii::RandomMiiData4{ | 761 | RandomMiiData4{ |
| 677 | .gender = Gender::Female, | 762 | .gender = static_cast<u32>(Gender::Female), |
| 678 | .age = Age::Young, | 763 | .age = static_cast<u32>(Age::Young), |
| 679 | .race = Race::White, | 764 | .race = static_cast<u32>(Race::White), |
| 680 | .values_count = 20, | 765 | .values_count = 20, |
| 681 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 4, 4, 8, 8}, | 766 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 4, 4, 8, 8}, |
| 682 | }, | 767 | }, |
| 683 | Service::Mii::RandomMiiData4{ | 768 | RandomMiiData4{ |
| 684 | .gender = Gender::Female, | 769 | .gender = static_cast<u32>(Gender::Female), |
| 685 | .age = Age::Normal, | 770 | .age = static_cast<u32>(Age::Normal), |
| 686 | .race = Race::White, | 771 | .race = static_cast<u32>(Race::White), |
| 687 | .values_count = 20, | 772 | .values_count = 20, |
| 688 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 4, 4, 8, 8}, | 773 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 4, 4, 8, 8}, |
| 689 | }, | 774 | }, |
| 690 | Service::Mii::RandomMiiData4{ | 775 | RandomMiiData4{ |
| 691 | .gender = Gender::Female, | 776 | .gender = static_cast<u32>(Gender::Female), |
| 692 | .age = Age::Old, | 777 | .age = static_cast<u32>(Age::Old), |
| 693 | .race = Race::White, | 778 | .race = static_cast<u32>(Race::White), |
| 694 | .values_count = 20, | 779 | .values_count = 20, |
| 695 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 4, 4}, | 780 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 4, 4}, |
| 696 | }, | 781 | }, |
| 697 | Service::Mii::RandomMiiData4{ | 782 | RandomMiiData4{ |
| 698 | .gender = Gender::Female, | 783 | .gender = static_cast<u32>(Gender::Female), |
| 699 | .age = Age::Young, | 784 | .age = static_cast<u32>(Age::Young), |
| 700 | .race = Race::Asian, | 785 | .race = static_cast<u32>(Race::Asian), |
| 701 | .values_count = 20, | 786 | .values_count = 20, |
| 702 | .values = {9, 9, 9, 9, 9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11}, | 787 | .values = {9, 9, 9, 9, 9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11}, |
| 703 | }, | 788 | }, |
| 704 | Service::Mii::RandomMiiData4{ | 789 | RandomMiiData4{ |
| 705 | .gender = Gender::Female, | 790 | .gender = static_cast<u32>(Gender::Female), |
| 706 | .age = Age::Normal, | 791 | .age = static_cast<u32>(Age::Normal), |
| 707 | .race = Race::Asian, | 792 | .race = static_cast<u32>(Race::Asian), |
| 708 | .values_count = 20, | 793 | .values_count = 20, |
| 709 | .values = {9, 9, 9, 9, 9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11}, | 794 | .values = {9, 9, 9, 9, 9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11}, |
| 710 | }, | 795 | }, |
| 711 | Service::Mii::RandomMiiData4{ | 796 | RandomMiiData4{ |
| 712 | .gender = Gender::Female, | 797 | .gender = static_cast<u32>(Gender::Female), |
| 713 | .age = Age::Old, | 798 | .age = static_cast<u32>(Age::Old), |
| 714 | .race = Race::Asian, | 799 | .race = static_cast<u32>(Race::Asian), |
| 715 | .values_count = 20, | 800 | .values_count = 20, |
| 716 | .values = {9, 9, 9, 9, 9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11}, | 801 | .values = {9, 9, 9, 9, 9, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11}, |
| 717 | }, | 802 | }, |
| 718 | }; | 803 | }; |
| 719 | 804 | ||
| 720 | const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiFacelineMakeup{ | 805 | const std::array<RandomMiiData4, 18> RandomMiiFacelineMakeup{ |
| 721 | Service::Mii::RandomMiiData4{ | 806 | RandomMiiData4{ |
| 722 | .gender = Gender::Male, | 807 | .gender = static_cast<u32>(Gender::Male), |
| 723 | .age = Age::Young, | 808 | .age = static_cast<u32>(Age::Young), |
| 724 | .race = Race::Black, | 809 | .race = static_cast<u32>(Race::Black), |
| 725 | .values_count = 20, | 810 | .values_count = 20, |
| 726 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, | 811 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, |
| 727 | }, | 812 | }, |
| 728 | Service::Mii::RandomMiiData4{ | 813 | RandomMiiData4{ |
| 729 | .gender = Gender::Male, | 814 | .gender = static_cast<u32>(Gender::Male), |
| 730 | .age = Age::Normal, | 815 | .age = static_cast<u32>(Age::Normal), |
| 731 | .race = Race::Black, | 816 | .race = static_cast<u32>(Race::Black), |
| 732 | .values_count = 20, | 817 | .values_count = 20, |
| 733 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9}, | 818 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9, 9}, |
| 734 | }, | 819 | }, |
| 735 | Service::Mii::RandomMiiData4{ | 820 | RandomMiiData4{ |
| 736 | .gender = Gender::Male, | 821 | .gender = static_cast<u32>(Gender::Male), |
| 737 | .age = Age::Old, | 822 | .age = static_cast<u32>(Age::Old), |
| 738 | .race = Race::Black, | 823 | .race = static_cast<u32>(Race::Black), |
| 739 | .values_count = 20, | 824 | .values_count = 20, |
| 740 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9}, | 825 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9}, |
| 741 | }, | 826 | }, |
| 742 | Service::Mii::RandomMiiData4{ | 827 | RandomMiiData4{ |
| 743 | .gender = Gender::Male, | 828 | .gender = static_cast<u32>(Gender::Male), |
| 744 | .age = Age::Young, | 829 | .age = static_cast<u32>(Age::Young), |
| 745 | .race = Race::White, | 830 | .race = static_cast<u32>(Race::White), |
| 746 | .values_count = 20, | 831 | .values_count = 20, |
| 747 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, | 832 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, |
| 748 | }, | 833 | }, |
| 749 | Service::Mii::RandomMiiData4{ | 834 | RandomMiiData4{ |
| 750 | .gender = Gender::Male, | 835 | .gender = static_cast<u32>(Gender::Male), |
| 751 | .age = Age::Normal, | 836 | .age = static_cast<u32>(Age::Normal), |
| 752 | .race = Race::White, | 837 | .race = static_cast<u32>(Race::White), |
| 753 | .values_count = 20, | 838 | .values_count = 20, |
| 754 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, | 839 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, |
| 755 | }, | 840 | }, |
| 756 | Service::Mii::RandomMiiData4{ | 841 | RandomMiiData4{ |
| 757 | .gender = Gender::Male, | 842 | .gender = static_cast<u32>(Gender::Male), |
| 758 | .age = Age::Old, | 843 | .age = static_cast<u32>(Age::Old), |
| 759 | .race = Race::White, | 844 | .race = static_cast<u32>(Race::White), |
| 760 | .values_count = 20, | 845 | .values_count = 20, |
| 761 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, | 846 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, |
| 762 | }, | 847 | }, |
| 763 | Service::Mii::RandomMiiData4{ | 848 | RandomMiiData4{ |
| 764 | .gender = Gender::Male, | 849 | .gender = static_cast<u32>(Gender::Male), |
| 765 | .age = Age::Young, | 850 | .age = static_cast<u32>(Age::Young), |
| 766 | .race = Race::Asian, | 851 | .race = static_cast<u32>(Race::Asian), |
| 767 | .values_count = 20, | 852 | .values_count = 20, |
| 768 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, | 853 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, |
| 769 | }, | 854 | }, |
| 770 | Service::Mii::RandomMiiData4{ | 855 | RandomMiiData4{ |
| 771 | .gender = Gender::Male, | 856 | .gender = static_cast<u32>(Gender::Male), |
| 772 | .age = Age::Normal, | 857 | .age = static_cast<u32>(Age::Normal), |
| 773 | .race = Race::Asian, | 858 | .race = static_cast<u32>(Race::Asian), |
| 774 | .values_count = 20, | 859 | .values_count = 20, |
| 775 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, | 860 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, |
| 776 | }, | 861 | }, |
| 777 | Service::Mii::RandomMiiData4{ | 862 | RandomMiiData4{ |
| 778 | .gender = Gender::Male, | 863 | .gender = static_cast<u32>(Gender::Male), |
| 779 | .age = Age::Old, | 864 | .age = static_cast<u32>(Age::Old), |
| 780 | .race = Race::Asian, | 865 | .race = static_cast<u32>(Race::Asian), |
| 781 | .values_count = 20, | 866 | .values_count = 20, |
| 782 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, | 867 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 9, 9}, |
| 783 | }, | 868 | }, |
| 784 | Service::Mii::RandomMiiData4{ | 869 | RandomMiiData4{ |
| 785 | .gender = Gender::Female, | 870 | .gender = static_cast<u32>(Gender::Female), |
| 786 | .age = Age::Young, | 871 | .age = static_cast<u32>(Age::Young), |
| 787 | .race = Race::Black, | 872 | .race = static_cast<u32>(Race::Black), |
| 788 | .values_count = 20, | 873 | .values_count = 20, |
| 789 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 2}, | 874 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 2}, |
| 790 | }, | 875 | }, |
| 791 | Service::Mii::RandomMiiData4{ | 876 | RandomMiiData4{ |
| 792 | .gender = Gender::Female, | 877 | .gender = static_cast<u32>(Gender::Female), |
| 793 | .age = Age::Normal, | 878 | .age = static_cast<u32>(Age::Normal), |
| 794 | .race = Race::Black, | 879 | .race = static_cast<u32>(Race::Black), |
| 795 | .values_count = 20, | 880 | .values_count = 20, |
| 796 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 9, 9}, | 881 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 9, 9}, |
| 797 | }, | 882 | }, |
| 798 | Service::Mii::RandomMiiData4{ | 883 | RandomMiiData4{ |
| 799 | .gender = Gender::Female, | 884 | .gender = static_cast<u32>(Gender::Female), |
| 800 | .age = Age::Old, | 885 | .age = static_cast<u32>(Age::Old), |
| 801 | .race = Race::Black, | 886 | .race = static_cast<u32>(Race::Black), |
| 802 | .values_count = 20, | 887 | .values_count = 20, |
| 803 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 9, 9}, | 888 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 9, 9}, |
| 804 | }, | 889 | }, |
| 805 | Service::Mii::RandomMiiData4{ | 890 | RandomMiiData4{ |
| 806 | .gender = Gender::Female, | 891 | .gender = static_cast<u32>(Gender::Female), |
| 807 | .age = Age::Young, | 892 | .age = static_cast<u32>(Age::Young), |
| 808 | .race = Race::White, | 893 | .race = static_cast<u32>(Race::White), |
| 809 | .values_count = 20, | 894 | .values_count = 20, |
| 810 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 3, 3, 4, 5, 5, 6, 7, 8, 9}, | 895 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 3, 3, 4, 5, 5, 6, 7, 8, 9}, |
| 811 | }, | 896 | }, |
| 812 | Service::Mii::RandomMiiData4{ | 897 | RandomMiiData4{ |
| 813 | .gender = Gender::Female, | 898 | .gender = static_cast<u32>(Gender::Female), |
| 814 | .age = Age::Normal, | 899 | .age = static_cast<u32>(Age::Normal), |
| 815 | .race = Race::White, | 900 | .race = static_cast<u32>(Race::White), |
| 816 | .values_count = 20, | 901 | .values_count = 20, |
| 817 | .values = {0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9}, | 902 | .values = {0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9}, |
| 818 | }, | 903 | }, |
| 819 | Service::Mii::RandomMiiData4{ | 904 | RandomMiiData4{ |
| 820 | .gender = Gender::Female, | 905 | .gender = static_cast<u32>(Gender::Female), |
| 821 | .age = Age::Old, | 906 | .age = static_cast<u32>(Age::Old), |
| 822 | .race = Race::White, | 907 | .race = static_cast<u32>(Race::White), |
| 823 | .values_count = 20, | 908 | .values_count = 20, |
| 824 | .values = {0, 0, 0, 0, 0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 6, 7, 8, 9, 9}, | 909 | .values = {0, 0, 0, 0, 0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 6, 7, 8, 9, 9}, |
| 825 | }, | 910 | }, |
| 826 | Service::Mii::RandomMiiData4{ | 911 | RandomMiiData4{ |
| 827 | .gender = Gender::Female, | 912 | .gender = static_cast<u32>(Gender::Female), |
| 828 | .age = Age::Young, | 913 | .age = static_cast<u32>(Age::Young), |
| 829 | .race = Race::Asian, | 914 | .race = static_cast<u32>(Race::Asian), |
| 830 | .values_count = 20, | 915 | .values_count = 20, |
| 831 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9}, | 916 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9}, |
| 832 | }, | 917 | }, |
| 833 | Service::Mii::RandomMiiData4{ | 918 | RandomMiiData4{ |
| 834 | .gender = Gender::Female, | 919 | .gender = static_cast<u32>(Gender::Female), |
| 835 | .age = Age::Normal, | 920 | .age = static_cast<u32>(Age::Normal), |
| 836 | .race = Race::Asian, | 921 | .race = static_cast<u32>(Race::Asian), |
| 837 | .values_count = 20, | 922 | .values_count = 20, |
| 838 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9}, | 923 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9}, |
| 839 | }, | 924 | }, |
| 840 | Service::Mii::RandomMiiData4{ | 925 | RandomMiiData4{ |
| 841 | .gender = Gender::Female, | 926 | .gender = static_cast<u32>(Gender::Female), |
| 842 | .age = Age::Old, | 927 | .age = static_cast<u32>(Age::Old), |
| 843 | .race = Race::Asian, | 928 | .race = static_cast<u32>(Race::Asian), |
| 844 | .values_count = 20, | 929 | .values_count = 20, |
| 845 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9}, | 930 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9}, |
| 846 | }, | 931 | }, |
| 847 | }; | 932 | }; |
| 848 | 933 | ||
| 849 | const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiHairType{ | 934 | const std::array<RandomMiiData4, 18> RandomMiiHairType{ |
| 850 | Service::Mii::RandomMiiData4{ | 935 | RandomMiiData4{ |
| 851 | .gender = Gender::Male, | 936 | .gender = static_cast<u32>(Gender::Male), |
| 852 | .age = Age::Young, | 937 | .age = static_cast<u32>(Age::Young), |
| 853 | .race = Race::Black, | 938 | .race = static_cast<u32>(Race::Black), |
| 854 | .values_count = 30, | 939 | .values_count = 30, |
| 855 | .values = {13, 23, 30, 31, 32, 33, 34, 35, 36, 37, 38, 40, 43, 44, 45, | 940 | .values = {13, 23, 30, 31, 32, 33, 34, 35, 36, 37, 38, 40, 43, 44, 45, |
| 856 | 47, 48, 49, 50, 51, 52, 54, 56, 57, 64, 66, 75, 76, 86, 89}, | 941 | 47, 48, 49, 50, 51, 52, 54, 56, 57, 64, 66, 75, 76, 86, 89}, |
| 857 | }, | 942 | }, |
| 858 | Service::Mii::RandomMiiData4{ | 943 | RandomMiiData4{ |
| 859 | .gender = Gender::Male, | 944 | .gender = static_cast<u32>(Gender::Male), |
| 860 | .age = Age::Normal, | 945 | .age = static_cast<u32>(Age::Normal), |
| 861 | .race = Race::Black, | 946 | .race = static_cast<u32>(Race::Black), |
| 862 | .values_count = 31, | 947 | .values_count = 31, |
| 863 | .values = {13, 23, 30, 31, 32, 33, 34, 35, 36, 37, 38, 40, 43, 44, 45, 47, | 948 | .values = {13, 23, 30, 31, 32, 33, 34, 35, 36, 37, 38, 40, 43, 44, 45, 47, |
| 864 | 48, 49, 50, 51, 52, 54, 56, 57, 64, 66, 73, 75, 81, 86, 87}, | 949 | 48, 49, 50, 51, 52, 54, 56, 57, 64, 66, 73, 75, 81, 86, 87}, |
| 865 | }, | 950 | }, |
| 866 | Service::Mii::RandomMiiData4{ | 951 | RandomMiiData4{ |
| 867 | .gender = Gender::Male, | 952 | .gender = static_cast<u32>(Gender::Male), |
| 868 | .age = Age::Old, | 953 | .age = static_cast<u32>(Age::Old), |
| 869 | .race = Race::Black, | 954 | .race = static_cast<u32>(Race::Black), |
| 870 | .values_count = 31, | 955 | .values_count = 31, |
| 871 | .values = {13, 23, 30, 31, 32, 33, 34, 35, 36, 37, 38, 40, 43, 44, 45, 47, | 956 | .values = {13, 23, 30, 31, 32, 33, 34, 35, 36, 37, 38, 40, 43, 44, 45, 47, |
| 872 | 48, 49, 50, 51, 52, 54, 56, 57, 64, 66, 73, 75, 81, 86, 87}, | 957 | 48, 49, 50, 51, 52, 54, 56, 57, 64, 66, 73, 75, 81, 86, 87}, |
| 873 | }, | 958 | }, |
| 874 | Service::Mii::RandomMiiData4{ | 959 | RandomMiiData4{ |
| 875 | .gender = Gender::Male, | 960 | .gender = static_cast<u32>(Gender::Male), |
| 876 | .age = Age::Young, | 961 | .age = static_cast<u32>(Age::Young), |
| 877 | .race = Race::White, | 962 | .race = static_cast<u32>(Race::White), |
| 878 | .values_count = 38, | 963 | .values_count = 38, |
| 879 | .values = {13, 23, 30, 31, 32, 33, 34, 36, 37, 38, 40, 42, 43, 44, 45, 47, 48, 49, 50, | 964 | .values = {13, 23, 30, 31, 32, 33, 34, 36, 37, 38, 40, 42, 43, 44, 45, 47, 48, 49, 50, |
| 880 | 51, 52, 53, 54, 55, 56, 58, 59, 60, 64, 65, 66, 67, 68, 70, 75, 76, 86, 89}, | 965 | 51, 52, 53, 54, 55, 56, 58, 59, 60, 64, 65, 66, 67, 68, 70, 75, 76, 86, 89}, |
| 881 | }, | 966 | }, |
| 882 | Service::Mii::RandomMiiData4{ | 967 | RandomMiiData4{ |
| 883 | .gender = Gender::Male, | 968 | .gender = static_cast<u32>(Gender::Male), |
| 884 | .age = Age::Normal, | 969 | .age = static_cast<u32>(Age::Normal), |
| 885 | .race = Race::White, | 970 | .race = static_cast<u32>(Race::White), |
| 886 | .values_count = 39, | 971 | .values_count = 39, |
| 887 | .values = {13, 23, 30, 31, 32, 33, 34, 36, 37, 38, 39, 40, 43, 44, 45, 47, 48, 49, 50, 51, | 972 | .values = {13, 23, 30, 31, 32, 33, 34, 36, 37, 38, 39, 40, 43, 44, 45, 47, 48, 49, 50, 51, |
| 888 | 52, 53, 54, 55, 56, 58, 59, 60, 64, 65, 66, 67, 68, 70, 73, 75, 81, 86, 87}, | 973 | 52, 53, 54, 55, 56, 58, 59, 60, 64, 65, 66, 67, 68, 70, 73, 75, 81, 86, 87}, |
| 889 | }, | 974 | }, |
| 890 | Service::Mii::RandomMiiData4{ | 975 | RandomMiiData4{ |
| 891 | .gender = Gender::Male, | 976 | .gender = static_cast<u32>(Gender::Male), |
| 892 | .age = Age::Old, | 977 | .age = static_cast<u32>(Age::Old), |
| 893 | .race = Race::White, | 978 | .race = static_cast<u32>(Race::White), |
| 894 | .values_count = 39, | 979 | .values_count = 39, |
| 895 | .values = {13, 23, 30, 31, 32, 33, 34, 36, 37, 38, 39, 40, 43, 44, 45, 47, 48, 49, 50, 51, | 980 | .values = {13, 23, 30, 31, 32, 33, 34, 36, 37, 38, 39, 40, 43, 44, 45, 47, 48, 49, 50, 51, |
| 896 | 52, 53, 54, 55, 56, 58, 59, 60, 64, 65, 66, 67, 68, 70, 73, 75, 81, 86, 87}, | 981 | 52, 53, 54, 55, 56, 58, 59, 60, 64, 65, 66, 67, 68, 70, 73, 75, 81, 86, 87}, |
| 897 | }, | 982 | }, |
| 898 | Service::Mii::RandomMiiData4{ | 983 | RandomMiiData4{ |
| 899 | .gender = Gender::Male, | 984 | .gender = static_cast<u32>(Gender::Male), |
| 900 | .age = Age::Young, | 985 | .age = static_cast<u32>(Age::Young), |
| 901 | .race = Race::Asian, | 986 | .race = static_cast<u32>(Race::Asian), |
| 902 | .values_count = 18, | 987 | .values_count = 18, |
| 903 | .values = {13, 23, 30, 36, 37, 41, 45, 47, 51, 53, 54, 55, 58, 59, 65, 67, 86, 88}, | 988 | .values = {13, 23, 30, 36, 37, 41, 45, 47, 51, 53, 54, 55, 58, 59, 65, 67, 86, 88}, |
| 904 | }, | 989 | }, |
| 905 | Service::Mii::RandomMiiData4{ | 990 | RandomMiiData4{ |
| 906 | .gender = Gender::Male, | 991 | .gender = static_cast<u32>(Gender::Male), |
| 907 | .age = Age::Normal, | 992 | .age = static_cast<u32>(Age::Normal), |
| 908 | .race = Race::Asian, | 993 | .race = static_cast<u32>(Race::Asian), |
| 909 | .values_count = 19, | 994 | .values_count = 19, |
| 910 | .values = {13, 23, 30, 36, 37, 39, 41, 45, 47, 51, 53, 54, 55, 58, 59, 65, 67, 86, 88}, | 995 | .values = {13, 23, 30, 36, 37, 39, 41, 45, 47, 51, 53, 54, 55, 58, 59, 65, 67, 86, 88}, |
| 911 | }, | 996 | }, |
| 912 | Service::Mii::RandomMiiData4{ | 997 | RandomMiiData4{ |
| 913 | .gender = Gender::Male, | 998 | .gender = static_cast<u32>(Gender::Male), |
| 914 | .age = Age::Old, | 999 | .age = static_cast<u32>(Age::Old), |
| 915 | .race = Race::Asian, | 1000 | .race = static_cast<u32>(Race::Asian), |
| 916 | .values_count = 19, | 1001 | .values_count = 19, |
| 917 | .values = {13, 23, 30, 36, 37, 39, 41, 45, 47, 51, 53, 54, 55, 58, 59, 65, 67, 86, 88}, | 1002 | .values = {13, 23, 30, 36, 37, 39, 41, 45, 47, 51, 53, 54, 55, 58, 59, 65, 67, 86, 88}, |
| 918 | }, | 1003 | }, |
| 919 | Service::Mii::RandomMiiData4{ | 1004 | RandomMiiData4{ |
| 920 | .gender = Gender::Female, | 1005 | .gender = static_cast<u32>(Gender::Female), |
| 921 | .age = Age::Young, | 1006 | .age = static_cast<u32>(Age::Young), |
| 922 | .race = Race::Black, | 1007 | .race = static_cast<u32>(Race::Black), |
| 923 | .values_count = 39, | 1008 | .values_count = 39, |
| 924 | .values = {0, 1, 2, 3, 4, 5, 6, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, | 1009 | .values = {0, 1, 2, 3, 4, 5, 6, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, |
| 925 | 21, 22, 24, 25, 26, 28, 46, 50, 61, 62, 63, 64, 69, 76, 77, 79, 80, 83, 85}, | 1010 | 21, 22, 24, 25, 26, 28, 46, 50, 61, 62, 63, 64, 69, 76, 77, 79, 80, 83, 85}, |
| 926 | }, | 1011 | }, |
| 927 | Service::Mii::RandomMiiData4{ | 1012 | RandomMiiData4{ |
| 928 | .gender = Gender::Female, | 1013 | .gender = static_cast<u32>(Gender::Female), |
| 929 | .age = Age::Normal, | 1014 | .age = static_cast<u32>(Age::Normal), |
| 930 | .race = Race::Black, | 1015 | .race = static_cast<u32>(Race::Black), |
| 931 | .values_count = 42, | 1016 | .values_count = 42, |
| 932 | .values = {0, 1, 2, 3, 4, 5, 6, 8, 9, 10, 11, 12, 13, 14, | 1017 | .values = {0, 1, 2, 3, 4, 5, 6, 8, 9, 10, 11, 12, 13, 14, |
| 933 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 28, 46, 50, | 1018 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 28, 46, 50, |
| 934 | 61, 62, 63, 64, 69, 72, 74, 77, 78, 82, 83, 84, 85, 87}, | 1019 | 61, 62, 63, 64, 69, 72, 74, 77, 78, 82, 83, 84, 85, 87}, |
| 935 | }, | 1020 | }, |
| 936 | Service::Mii::RandomMiiData4{ | 1021 | RandomMiiData4{ |
| 937 | .gender = Gender::Female, | 1022 | .gender = static_cast<u32>(Gender::Female), |
| 938 | .age = Age::Old, | 1023 | .age = static_cast<u32>(Age::Old), |
| 939 | .race = Race::Black, | 1024 | .race = static_cast<u32>(Race::Black), |
| 940 | .values_count = 42, | 1025 | .values_count = 42, |
| 941 | .values = {0, 1, 2, 3, 4, 5, 6, 8, 9, 10, 11, 12, 13, 14, | 1026 | .values = {0, 1, 2, 3, 4, 5, 6, 8, 9, 10, 11, 12, 13, 14, |
| 942 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 28, 46, 50, | 1027 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 28, 46, 50, |
| 943 | 61, 62, 63, 64, 69, 72, 74, 77, 78, 82, 83, 84, 85, 87}, | 1028 | 61, 62, 63, 64, 69, 72, 74, 77, 78, 82, 83, 84, 85, 87}, |
| 944 | }, | 1029 | }, |
| 945 | Service::Mii::RandomMiiData4{ | 1030 | RandomMiiData4{ |
| 946 | .gender = Gender::Female, | 1031 | .gender = static_cast<u32>(Gender::Female), |
| 947 | .age = Age::Young, | 1032 | .age = static_cast<u32>(Age::Young), |
| 948 | .race = Race::White, | 1033 | .race = static_cast<u32>(Race::White), |
| 949 | .values_count = 44, | 1034 | .values_count = 44, |
| 950 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, | 1035 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, |
| 951 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 27, 29, 42, 50, | 1036 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 27, 29, 42, 50, |
| 952 | 58, 60, 62, 63, 64, 69, 71, 76, 79, 80, 81, 82, 83, 86}, | 1037 | 58, 60, 62, 63, 64, 69, 71, 76, 79, 80, 81, 82, 83, 86}, |
| 953 | }, | 1038 | }, |
| 954 | Service::Mii::RandomMiiData4{ | 1039 | RandomMiiData4{ |
| 955 | .gender = Gender::Female, | 1040 | .gender = static_cast<u32>(Gender::Female), |
| 956 | .age = Age::Normal, | 1041 | .age = static_cast<u32>(Age::Normal), |
| 957 | .race = Race::White, | 1042 | .race = static_cast<u32>(Race::White), |
| 958 | .values_count = 44, | 1043 | .values_count = 44, |
| 959 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, | 1044 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, |
| 960 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 27, 29, 50, 58, | 1045 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 27, 29, 50, 58, |
| 961 | 60, 62, 63, 64, 69, 71, 72, 74, 79, 81, 82, 83, 84, 85}, | 1046 | 60, 62, 63, 64, 69, 71, 72, 74, 79, 81, 82, 83, 84, 85}, |
| 962 | }, | 1047 | }, |
| 963 | Service::Mii::RandomMiiData4{ | 1048 | RandomMiiData4{ |
| 964 | .gender = Gender::Female, | 1049 | .gender = static_cast<u32>(Gender::Female), |
| 965 | .age = Age::Old, | 1050 | .age = static_cast<u32>(Age::Old), |
| 966 | .race = Race::White, | 1051 | .race = static_cast<u32>(Race::White), |
| 967 | .values_count = 44, | 1052 | .values_count = 44, |
| 968 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, | 1053 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, |
| 969 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 27, 29, 50, 58, | 1054 | 15, 16, 17, 18, 19, 20, 21, 22, 24, 25, 26, 27, 29, 50, 58, |
| 970 | 60, 62, 63, 64, 69, 71, 72, 74, 79, 81, 82, 83, 84, 85}, | 1055 | 60, 62, 63, 64, 69, 71, 72, 74, 79, 81, 82, 83, 84, 85}, |
| 971 | }, | 1056 | }, |
| 972 | Service::Mii::RandomMiiData4{ | 1057 | RandomMiiData4{ |
| 973 | .gender = Gender::Female, | 1058 | .gender = static_cast<u32>(Gender::Female), |
| 974 | .age = Age::Young, | 1059 | .age = static_cast<u32>(Age::Young), |
| 975 | .race = Race::Asian, | 1060 | .race = static_cast<u32>(Race::Asian), |
| 976 | .values_count = 24, | 1061 | .values_count = 24, |
| 977 | .values = {0, 1, 2, 3, 4, 5, 6, 10, 11, 12, 13, 14, | 1062 | .values = {0, 1, 2, 3, 4, 5, 6, 10, 11, 12, 13, 14, |
| 978 | 16, 17, 18, 20, 21, 24, 25, 58, 62, 69, 76, 83}, | 1063 | 16, 17, 18, 20, 21, 24, 25, 58, 62, 69, 76, 83}, |
| 979 | }, | 1064 | }, |
| 980 | Service::Mii::RandomMiiData4{ | 1065 | RandomMiiData4{ |
| 981 | .gender = Gender::Female, | 1066 | .gender = static_cast<u32>(Gender::Female), |
| 982 | .age = Age::Normal, | 1067 | .age = static_cast<u32>(Age::Normal), |
| 983 | .race = Race::Asian, | 1068 | .race = static_cast<u32>(Race::Asian), |
| 984 | .values_count = 27, | 1069 | .values_count = 27, |
| 985 | .values = {0, 1, 2, 3, 4, 5, 6, 10, 11, 12, 13, 14, 16, 17, | 1070 | .values = {0, 1, 2, 3, 4, 5, 6, 10, 11, 12, 13, 14, 16, 17, |
| 986 | 18, 20, 21, 24, 25, 58, 62, 69, 74, 76, 81, 83, 85}, | 1071 | 18, 20, 21, 24, 25, 58, 62, 69, 74, 76, 81, 83, 85}, |
| 987 | }, | 1072 | }, |
| 988 | Service::Mii::RandomMiiData4{ | 1073 | RandomMiiData4{ |
| 989 | .gender = Gender::Female, | 1074 | .gender = static_cast<u32>(Gender::Female), |
| 990 | .age = Age::Old, | 1075 | .age = static_cast<u32>(Age::Old), |
| 991 | .race = Race::Asian, | 1076 | .race = static_cast<u32>(Race::Asian), |
| 992 | .values_count = 27, | 1077 | .values_count = 27, |
| 993 | .values = {0, 1, 2, 3, 4, 5, 6, 10, 11, 12, 13, 14, 16, 17, | 1078 | .values = {0, 1, 2, 3, 4, 5, 6, 10, 11, 12, 13, 14, 16, 17, |
| 994 | 18, 20, 21, 24, 25, 58, 62, 69, 74, 76, 81, 83, 85}, | 1079 | 18, 20, 21, 24, 25, 58, 62, 69, 74, 76, 81, 83, 85}, |
| @@ -996,55 +1081,55 @@ const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiHairType{ | |||
| 996 | }; | 1081 | }; |
| 997 | 1082 | ||
| 998 | const std::array<RandomMiiData3, 9> RandomMiiHairColor{ | 1083 | const std::array<RandomMiiData3, 9> RandomMiiHairColor{ |
| 999 | Service::Mii::RandomMiiData3{ | 1084 | RandomMiiData3{ |
| 1000 | .arg_1 = 0, | 1085 | .arg_1 = 0, |
| 1001 | .arg_2 = 0, | 1086 | .arg_2 = 0, |
| 1002 | .values_count = 20, | 1087 | .values_count = 20, |
| 1003 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, | 1088 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, |
| 1004 | }, | 1089 | }, |
| 1005 | Service::Mii::RandomMiiData3{ | 1090 | RandomMiiData3{ |
| 1006 | .arg_1 = 0, | 1091 | .arg_1 = 0, |
| 1007 | .arg_2 = 1, | 1092 | .arg_2 = 1, |
| 1008 | .values_count = 20, | 1093 | .values_count = 20, |
| 1009 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, | 1094 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, |
| 1010 | }, | 1095 | }, |
| 1011 | Service::Mii::RandomMiiData3{ | 1096 | RandomMiiData3{ |
| 1012 | .arg_1 = 0, | 1097 | .arg_1 = 0, |
| 1013 | .arg_2 = 2, | 1098 | .arg_2 = 2, |
| 1014 | .values_count = 20, | 1099 | .values_count = 20, |
| 1015 | .values = {0, 0, 0, 0, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4}, | 1100 | .values = {0, 0, 0, 0, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4}, |
| 1016 | }, | 1101 | }, |
| 1017 | Service::Mii::RandomMiiData3{ | 1102 | RandomMiiData3{ |
| 1018 | .arg_1 = 1, | 1103 | .arg_1 = 1, |
| 1019 | .arg_2 = 0, | 1104 | .arg_2 = 0, |
| 1020 | .values_count = 20, | 1105 | .values_count = 20, |
| 1021 | .values = {2, 3, 3, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7, 7}, | 1106 | .values = {2, 3, 3, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7, 7}, |
| 1022 | }, | 1107 | }, |
| 1023 | Service::Mii::RandomMiiData3{ | 1108 | RandomMiiData3{ |
| 1024 | .arg_1 = 1, | 1109 | .arg_1 = 1, |
| 1025 | .arg_2 = 1, | 1110 | .arg_2 = 1, |
| 1026 | .values_count = 20, | 1111 | .values_count = 20, |
| 1027 | .values = {2, 3, 3, 3, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7}, | 1112 | .values = {2, 3, 3, 3, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7}, |
| 1028 | }, | 1113 | }, |
| 1029 | Service::Mii::RandomMiiData3{ | 1114 | RandomMiiData3{ |
| 1030 | .arg_1 = 1, | 1115 | .arg_1 = 1, |
| 1031 | .arg_2 = 2, | 1116 | .arg_2 = 2, |
| 1032 | .values_count = 20, | 1117 | .values_count = 20, |
| 1033 | .values = {2, 3, 3, 4, 4, 4, 4, 4, 4, 5, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7}, | 1118 | .values = {2, 3, 3, 4, 4, 4, 4, 4, 4, 5, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7}, |
| 1034 | }, | 1119 | }, |
| 1035 | Service::Mii::RandomMiiData3{ | 1120 | RandomMiiData3{ |
| 1036 | .arg_1 = 2, | 1121 | .arg_1 = 2, |
| 1037 | .arg_2 = 0, | 1122 | .arg_2 = 0, |
| 1038 | .values_count = 20, | 1123 | .values_count = 20, |
| 1039 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1}, | 1124 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1}, |
| 1040 | }, | 1125 | }, |
| 1041 | Service::Mii::RandomMiiData3{ | 1126 | RandomMiiData3{ |
| 1042 | .arg_1 = 2, | 1127 | .arg_1 = 2, |
| 1043 | .arg_2 = 1, | 1128 | .arg_2 = 1, |
| 1044 | .values_count = 20, | 1129 | .values_count = 20, |
| 1045 | .values = {0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 3, 3, 3, 3, 3}, | 1130 | .values = {0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 3, 3, 3, 3, 3}, |
| 1046 | }, | 1131 | }, |
| 1047 | Service::Mii::RandomMiiData3{ | 1132 | RandomMiiData3{ |
| 1048 | .arg_1 = 2, | 1133 | .arg_1 = 2, |
| 1049 | .arg_2 = 2, | 1134 | .arg_2 = 2, |
| 1050 | .values_count = 20, | 1135 | .values_count = 20, |
| @@ -1052,598 +1137,642 @@ const std::array<RandomMiiData3, 9> RandomMiiHairColor{ | |||
| 1052 | }, | 1137 | }, |
| 1053 | }; | 1138 | }; |
| 1054 | 1139 | ||
| 1055 | const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiEyeType{ | 1140 | const std::array<RandomMiiData4, 18> RandomMiiEyeType{ |
| 1056 | Service::Mii::RandomMiiData4{ | 1141 | RandomMiiData4{ |
| 1057 | .gender = Gender::Male, | 1142 | .gender = static_cast<u32>(Gender::Male), |
| 1058 | .age = Age::Young, | 1143 | .age = static_cast<u32>(Age::Young), |
| 1059 | .race = Race::Black, | 1144 | .race = static_cast<u32>(Race::Black), |
| 1060 | .values_count = 26, | 1145 | .values_count = 26, |
| 1061 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 15, 16, 18, 27, | 1146 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 15, 16, 18, 27, |
| 1062 | 29, 32, 34, 36, 38, 39, 41, 43, 47, 49, 51, 53, 57}, | 1147 | 29, 32, 34, 36, 38, 39, 41, 43, 47, 49, 51, 53, 57}, |
| 1063 | }, | 1148 | }, |
| 1064 | Service::Mii::RandomMiiData4{ | 1149 | RandomMiiData4{ |
| 1065 | .gender = Gender::Male, | 1150 | .gender = static_cast<u32>(Gender::Male), |
| 1066 | .age = Age::Normal, | 1151 | .age = static_cast<u32>(Age::Normal), |
| 1067 | .race = Race::Black, | 1152 | .race = static_cast<u32>(Race::Black), |
| 1068 | .values_count = 26, | 1153 | .values_count = 26, |
| 1069 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 15, 16, 18, 27, | 1154 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 15, 16, 18, 27, |
| 1070 | 29, 32, 34, 36, 38, 39, 41, 43, 47, 49, 51, 53, 57}, | 1155 | 29, 32, 34, 36, 38, 39, 41, 43, 47, 49, 51, 53, 57}, |
| 1071 | }, | 1156 | }, |
| 1072 | Service::Mii::RandomMiiData4{ | 1157 | RandomMiiData4{ |
| 1073 | .gender = Gender::Male, | 1158 | .gender = static_cast<u32>(Gender::Male), |
| 1074 | .age = Age::Old, | 1159 | .age = static_cast<u32>(Age::Old), |
| 1075 | .race = Race::Black, | 1160 | .race = static_cast<u32>(Race::Black), |
| 1076 | .values_count = 27, | 1161 | .values_count = 27, |
| 1077 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 15, 16, 18, 26, 27, | 1162 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 15, 16, 18, 26, 27, |
| 1078 | 29, 32, 34, 36, 38, 39, 41, 43, 47, 48, 49, 53, 57}, | 1163 | 29, 32, 34, 36, 38, 39, 41, 43, 47, 48, 49, 53, 57}, |
| 1079 | }, | 1164 | }, |
| 1080 | Service::Mii::RandomMiiData4{ | 1165 | RandomMiiData4{ |
| 1081 | .gender = Gender::Male, | 1166 | .gender = static_cast<u32>(Gender::Male), |
| 1082 | .age = Age::Young, | 1167 | .age = static_cast<u32>(Age::Young), |
| 1083 | .race = Race::White, | 1168 | .race = static_cast<u32>(Race::White), |
| 1084 | .values_count = 35, | 1169 | .values_count = 35, |
| 1085 | .values = {2, 3, 5, 6, 7, 8, 9, 11, 12, 13, 15, 16, 17, 18, 21, 22, 27, 29, | 1170 | .values = {2, 3, 5, 6, 7, 8, 9, 11, 12, 13, 15, 16, 17, 18, 21, 22, 27, 29, |
| 1086 | 31, 32, 34, 36, 37, 38, 39, 41, 43, 44, 47, 49, 51, 53, 55, 56, 57}, | 1171 | 31, 32, 34, 36, 37, 38, 39, 41, 43, 44, 47, 49, 51, 53, 55, 56, 57}, |
| 1087 | }, | 1172 | }, |
| 1088 | Service::Mii::RandomMiiData4{ | 1173 | RandomMiiData4{ |
| 1089 | .gender = Gender::Male, | 1174 | .gender = static_cast<u32>(Gender::Male), |
| 1090 | .age = Age::Normal, | 1175 | .age = static_cast<u32>(Age::Normal), |
| 1091 | .race = Race::White, | 1176 | .race = static_cast<u32>(Race::White), |
| 1092 | .values_count = 35, | 1177 | .values_count = 35, |
| 1093 | .values = {2, 3, 5, 6, 7, 8, 9, 11, 12, 13, 15, 16, 17, 18, 21, 22, 27, 29, | 1178 | .values = {2, 3, 5, 6, 7, 8, 9, 11, 12, 13, 15, 16, 17, 18, 21, 22, 27, 29, |
| 1094 | 31, 32, 34, 36, 37, 38, 39, 41, 43, 44, 47, 49, 51, 53, 55, 56, 57}, | 1179 | 31, 32, 34, 36, 37, 38, 39, 41, 43, 44, 47, 49, 51, 53, 55, 56, 57}, |
| 1095 | }, | 1180 | }, |
| 1096 | Service::Mii::RandomMiiData4{ | 1181 | RandomMiiData4{ |
| 1097 | .gender = Gender::Male, | 1182 | .gender = static_cast<u32>(Gender::Male), |
| 1098 | .age = Age::Old, | 1183 | .age = static_cast<u32>(Age::Old), |
| 1099 | .race = Race::White, | 1184 | .race = static_cast<u32>(Race::White), |
| 1100 | .values_count = 35, | 1185 | .values_count = 35, |
| 1101 | .values = {2, 3, 5, 6, 7, 8, 9, 11, 12, 13, 15, 16, 18, 21, 22, 26, 27, 29, | 1186 | .values = {2, 3, 5, 6, 7, 8, 9, 11, 12, 13, 15, 16, 18, 21, 22, 26, 27, 29, |
| 1102 | 31, 32, 34, 36, 37, 38, 39, 41, 43, 44, 47, 48, 49, 50, 53, 56, 57}, | 1187 | 31, 32, 34, 36, 37, 38, 39, 41, 43, 44, 47, 48, 49, 50, 53, 56, 57}, |
| 1103 | }, | 1188 | }, |
| 1104 | Service::Mii::RandomMiiData4{ | 1189 | RandomMiiData4{ |
| 1105 | .gender = Gender::Male, | 1190 | .gender = static_cast<u32>(Gender::Male), |
| 1106 | .age = Age::Young, | 1191 | .age = static_cast<u32>(Age::Young), |
| 1107 | .race = Race::Asian, | 1192 | .race = static_cast<u32>(Race::Asian), |
| 1108 | .values_count = 30, | 1193 | .values_count = 30, |
| 1109 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 14, 15, 16, 17, 18, 21, | 1194 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 14, 15, 16, 17, 18, 21, |
| 1110 | 22, 31, 32, 34, 36, 37, 39, 41, 44, 49, 51, 53, 55, 56, 57}, | 1195 | 22, 31, 32, 34, 36, 37, 39, 41, 44, 49, 51, 53, 55, 56, 57}, |
| 1111 | }, | 1196 | }, |
| 1112 | Service::Mii::RandomMiiData4{ | 1197 | RandomMiiData4{ |
| 1113 | .gender = Gender::Male, | 1198 | .gender = static_cast<u32>(Gender::Male), |
| 1114 | .age = Age::Normal, | 1199 | .age = static_cast<u32>(Age::Normal), |
| 1115 | .race = Race::Asian, | 1200 | .race = static_cast<u32>(Race::Asian), |
| 1116 | .values_count = 30, | 1201 | .values_count = 30, |
| 1117 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 14, 15, 16, 17, 18, 21, | 1202 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 14, 15, 16, 17, 18, 21, |
| 1118 | 22, 31, 32, 34, 36, 37, 39, 41, 44, 49, 51, 53, 55, 56, 57}, | 1203 | 22, 31, 32, 34, 36, 37, 39, 41, 44, 49, 51, 53, 55, 56, 57}, |
| 1119 | }, | 1204 | }, |
| 1120 | Service::Mii::RandomMiiData4{ | 1205 | RandomMiiData4{ |
| 1121 | .gender = Gender::Male, | 1206 | .gender = static_cast<u32>(Gender::Male), |
| 1122 | .age = Age::Old, | 1207 | .age = static_cast<u32>(Age::Old), |
| 1123 | .race = Race::Asian, | 1208 | .race = static_cast<u32>(Race::Asian), |
| 1124 | .values_count = 30, | 1209 | .values_count = 30, |
| 1125 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 14, 15, 16, 18, 21, 22, | 1210 | .values = {2, 3, 5, 7, 8, 9, 11, 12, 13, 14, 15, 16, 18, 21, 22, |
| 1126 | 26, 31, 32, 34, 36, 37, 39, 41, 44, 48, 49, 50, 51, 53, 57}, | 1211 | 26, 31, 32, 34, 36, 37, 39, 41, 44, 48, 49, 50, 51, 53, 57}, |
| 1127 | }, | 1212 | }, |
| 1128 | Service::Mii::RandomMiiData4{ | 1213 | RandomMiiData4{ |
| 1129 | .gender = Gender::Female, | 1214 | .gender = static_cast<u32>(Gender::Female), |
| 1130 | .age = Age::Young, | 1215 | .age = static_cast<u32>(Age::Young), |
| 1131 | .race = Race::Black, | 1216 | .race = static_cast<u32>(Race::Black), |
| 1132 | .values_count = 39, | 1217 | .values_count = 39, |
| 1133 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, 24, 25, 27, | 1218 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, 24, 25, 27, |
| 1134 | 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 59}, | 1219 | 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 59}, |
| 1135 | }, | 1220 | }, |
| 1136 | Service::Mii::RandomMiiData4{ | 1221 | RandomMiiData4{ |
| 1137 | .gender = Gender::Female, | 1222 | .gender = static_cast<u32>(Gender::Female), |
| 1138 | .age = Age::Normal, | 1223 | .age = static_cast<u32>(Age::Normal), |
| 1139 | .race = Race::Black, | 1224 | .race = static_cast<u32>(Race::Black), |
| 1140 | .values_count = 39, | 1225 | .values_count = 39, |
| 1141 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, 24, 25, 27, | 1226 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, 24, 25, 27, |
| 1142 | 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 59}, | 1227 | 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 59}, |
| 1143 | }, | 1228 | }, |
| 1144 | Service::Mii::RandomMiiData4{ | 1229 | RandomMiiData4{ |
| 1145 | .gender = Gender::Female, | 1230 | .gender = static_cast<u32>(Gender::Female), |
| 1146 | .age = Age::Old, | 1231 | .age = static_cast<u32>(Age::Old), |
| 1147 | .race = Race::Black, | 1232 | .race = static_cast<u32>(Race::Black), |
| 1148 | .values_count = 40, | 1233 | .values_count = 40, |
| 1149 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, 24, 25, 26, | 1234 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, 24, 25, 26, |
| 1150 | 27, 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 59}, | 1235 | 27, 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 59}, |
| 1151 | }, | 1236 | }, |
| 1152 | Service::Mii::RandomMiiData4{ | 1237 | RandomMiiData4{ |
| 1153 | .gender = Gender::Female, | 1238 | .gender = static_cast<u32>(Gender::Female), |
| 1154 | .age = Age::Young, | 1239 | .age = static_cast<u32>(Age::Young), |
| 1155 | .race = Race::White, | 1240 | .race = static_cast<u32>(Race::White), |
| 1156 | .values_count = 46, | 1241 | .values_count = 46, |
| 1157 | .values = {0, 1, 2, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 15, 16, 17, | 1242 | .values = {0, 1, 2, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 15, 16, 17, |
| 1158 | 18, 19, 20, 21, 23, 24, 25, 27, 28, 29, 30, 32, 33, 34, 35, 37, | 1243 | 18, 19, 20, 21, 23, 24, 25, 27, 28, 29, 30, 32, 33, 34, 35, 37, |
| 1159 | 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 58, 59}, | 1244 | 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 58, 59}, |
| 1160 | }, | 1245 | }, |
| 1161 | Service::Mii::RandomMiiData4{ | 1246 | RandomMiiData4{ |
| 1162 | .gender = Gender::Female, | 1247 | .gender = static_cast<u32>(Gender::Female), |
| 1163 | .age = Age::Normal, | 1248 | .age = static_cast<u32>(Age::Normal), |
| 1164 | .race = Race::White, | 1249 | .race = static_cast<u32>(Race::White), |
| 1165 | .values_count = 46, | 1250 | .values_count = 46, |
| 1166 | .values = {0, 1, 2, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 15, 16, 17, | 1251 | .values = {0, 1, 2, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 15, 16, 17, |
| 1167 | 18, 19, 20, 21, 23, 24, 25, 27, 28, 29, 30, 32, 33, 34, 35, 37, | 1252 | 18, 19, 20, 21, 23, 24, 25, 27, 28, 29, 30, 32, 33, 34, 35, 37, |
| 1168 | 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 58, 59}, | 1253 | 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 58, 59}, |
| 1169 | }, | 1254 | }, |
| 1170 | Service::Mii::RandomMiiData4{ | 1255 | RandomMiiData4{ |
| 1171 | .gender = Gender::Female, | 1256 | .gender = static_cast<u32>(Gender::Female), |
| 1172 | .age = Age::Old, | 1257 | .age = static_cast<u32>(Age::Old), |
| 1173 | .race = Race::White, | 1258 | .race = static_cast<u32>(Race::White), |
| 1174 | .values_count = 46, | 1259 | .values_count = 46, |
| 1175 | .values = {0, 1, 2, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, | 1260 | .values = {0, 1, 2, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, |
| 1176 | 19, 20, 21, 23, 24, 25, 26, 27, 28, 29, 30, 32, 33, 34, 35, 37, | 1261 | 19, 20, 21, 23, 24, 25, 26, 27, 28, 29, 30, 32, 33, 34, 35, 37, |
| 1177 | 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 58, 59}, | 1262 | 38, 39, 40, 41, 42, 45, 46, 47, 48, 53, 54, 57, 58, 59}, |
| 1178 | }, | 1263 | }, |
| 1179 | Service::Mii::RandomMiiData4{ | 1264 | RandomMiiData4{ |
| 1180 | .gender = Gender::Female, | 1265 | .gender = static_cast<u32>(Gender::Female), |
| 1181 | .age = Age::Young, | 1266 | .age = static_cast<u32>(Age::Young), |
| 1182 | .race = Race::Asian, | 1267 | .race = static_cast<u32>(Race::Asian), |
| 1183 | .values_count = 34, | 1268 | .values_count = 34, |
| 1184 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, | 1269 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, |
| 1185 | 24, 25, 27, 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47}, | 1270 | 24, 25, 27, 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47}, |
| 1186 | }, | 1271 | }, |
| 1187 | Service::Mii::RandomMiiData4{ | 1272 | RandomMiiData4{ |
| 1188 | .gender = Gender::Female, | 1273 | .gender = static_cast<u32>(Gender::Female), |
| 1189 | .age = Age::Normal, | 1274 | .age = static_cast<u32>(Age::Normal), |
| 1190 | .race = Race::Asian, | 1275 | .race = static_cast<u32>(Race::Asian), |
| 1191 | .values_count = 34, | 1276 | .values_count = 34, |
| 1192 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, | 1277 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, |
| 1193 | 24, 25, 27, 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47}, | 1278 | 24, 25, 27, 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47}, |
| 1194 | }, | 1279 | }, |
| 1195 | Service::Mii::RandomMiiData4{ | 1280 | RandomMiiData4{ |
| 1196 | .gender = Gender::Female, | 1281 | .gender = static_cast<u32>(Gender::Female), |
| 1197 | .age = Age::Old, | 1282 | .age = static_cast<u32>(Age::Old), |
| 1198 | .race = Race::Asian, | 1283 | .race = static_cast<u32>(Race::Asian), |
| 1199 | .values_count = 35, | 1284 | .values_count = 35, |
| 1200 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, 24, | 1285 | .values = {0, 1, 2, 4, 5, 7, 8, 9, 10, 11, 12, 13, 15, 16, 18, 19, 23, 24, |
| 1201 | 25, 26, 27, 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47}, | 1286 | 25, 26, 27, 28, 29, 32, 33, 34, 35, 38, 39, 40, 41, 42, 45, 46, 47}, |
| 1202 | }, | 1287 | }, |
| 1203 | }; | 1288 | }; |
| 1204 | 1289 | ||
| 1205 | const std::array<Service::Mii::RandomMiiData2, 3> RandomMiiEyeColor{ | 1290 | const std::array<RandomMiiData2, 3> RandomMiiEyeColor{ |
| 1206 | Service::Mii::RandomMiiData2{ | 1291 | RandomMiiData2{ |
| 1207 | .arg_1 = 0, | 1292 | .arg_1 = 0, |
| 1208 | .values_count = 10, | 1293 | .values_count = 10, |
| 1209 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 1}, | 1294 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 1}, |
| 1210 | }, | 1295 | }, |
| 1211 | Service::Mii::RandomMiiData2{ | 1296 | RandomMiiData2{ |
| 1212 | .arg_1 = 1, | 1297 | .arg_1 = 1, |
| 1213 | .values_count = 10, | 1298 | .values_count = 10, |
| 1214 | .values = {0, 1, 1, 2, 3, 3, 4, 4, 4, 5}, | 1299 | .values = {0, 1, 1, 2, 3, 3, 4, 4, 4, 5}, |
| 1215 | }, | 1300 | }, |
| 1216 | Service::Mii::RandomMiiData2{ | 1301 | RandomMiiData2{ |
| 1217 | .arg_1 = 2, | 1302 | .arg_1 = 2, |
| 1218 | .values_count = 10, | 1303 | .values_count = 10, |
| 1219 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 1}, | 1304 | .values = {0, 0, 0, 0, 0, 0, 0, 0, 0, 1}, |
| 1220 | }, | 1305 | }, |
| 1221 | }; | 1306 | }; |
| 1222 | 1307 | ||
| 1223 | const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiEyebrowType{ | 1308 | const std::array<RandomMiiData4, 18> RandomMiiEyebrowType{ |
| 1224 | Service::Mii::RandomMiiData4{ | 1309 | RandomMiiData4{ |
| 1225 | .gender = Gender::Male, | 1310 | .gender = static_cast<u32>(Gender::Male), |
| 1226 | .age = Age::Young, | 1311 | .age = static_cast<u32>(Age::Young), |
| 1227 | .race = Race::Black, | 1312 | .race = static_cast<u32>(Race::Black), |
| 1228 | .values_count = 18, | 1313 | .values_count = 18, |
| 1229 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 17, 18, 20}, | 1314 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 17, 18, 20}, |
| 1230 | }, | 1315 | }, |
| 1231 | Service::Mii::RandomMiiData4{ | 1316 | RandomMiiData4{ |
| 1232 | .gender = Gender::Male, | 1317 | .gender = static_cast<u32>(Gender::Male), |
| 1233 | .age = Age::Normal, | 1318 | .age = static_cast<u32>(Age::Normal), |
| 1234 | .race = Race::Black, | 1319 | .race = static_cast<u32>(Race::Black), |
| 1235 | .values_count = 18, | 1320 | .values_count = 18, |
| 1236 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 17, 18, 20}, | 1321 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 17, 18, 20}, |
| 1237 | }, | 1322 | }, |
| 1238 | Service::Mii::RandomMiiData4{ | 1323 | RandomMiiData4{ |
| 1239 | .gender = Gender::Male, | 1324 | .gender = static_cast<u32>(Gender::Male), |
| 1240 | .age = Age::Old, | 1325 | .age = static_cast<u32>(Age::Old), |
| 1241 | .race = Race::Black, | 1326 | .race = static_cast<u32>(Race::Black), |
| 1242 | .values_count = 18, | 1327 | .values_count = 18, |
| 1243 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 17, 18, 20}, | 1328 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 17, 18, 20}, |
| 1244 | }, | 1329 | }, |
| 1245 | Service::Mii::RandomMiiData4{ | 1330 | RandomMiiData4{ |
| 1246 | .gender = Gender::Male, | 1331 | .gender = static_cast<u32>(Gender::Male), |
| 1247 | .age = Age::Young, | 1332 | .age = static_cast<u32>(Age::Young), |
| 1248 | .race = Race::White, | 1333 | .race = static_cast<u32>(Race::White), |
| 1249 | .values_count = 23, | 1334 | .values_count = 23, |
| 1250 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, | 1335 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, |
| 1251 | 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22}, | 1336 | 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22}, |
| 1252 | }, | 1337 | }, |
| 1253 | Service::Mii::RandomMiiData4{ | 1338 | RandomMiiData4{ |
| 1254 | .gender = Gender::Male, | 1339 | .gender = static_cast<u32>(Gender::Male), |
| 1255 | .age = Age::Normal, | 1340 | .age = static_cast<u32>(Age::Normal), |
| 1256 | .race = Race::White, | 1341 | .race = static_cast<u32>(Race::White), |
| 1257 | .values_count = 23, | 1342 | .values_count = 23, |
| 1258 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, | 1343 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, |
| 1259 | 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22}, | 1344 | 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22}, |
| 1260 | }, | 1345 | }, |
| 1261 | Service::Mii::RandomMiiData4{ | 1346 | RandomMiiData4{ |
| 1262 | .gender = Gender::Male, | 1347 | .gender = static_cast<u32>(Gender::Male), |
| 1263 | .age = Age::Old, | 1348 | .age = static_cast<u32>(Age::Old), |
| 1264 | .race = Race::White, | 1349 | .race = static_cast<u32>(Race::White), |
| 1265 | .values_count = 23, | 1350 | .values_count = 23, |
| 1266 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, | 1351 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, |
| 1267 | 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22}, | 1352 | 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22}, |
| 1268 | }, | 1353 | }, |
| 1269 | Service::Mii::RandomMiiData4{ | 1354 | RandomMiiData4{ |
| 1270 | .gender = Gender::Male, | 1355 | .gender = static_cast<u32>(Gender::Male), |
| 1271 | .age = Age::Young, | 1356 | .age = static_cast<u32>(Age::Young), |
| 1272 | .race = Race::Asian, | 1357 | .race = static_cast<u32>(Race::Asian), |
| 1273 | .values_count = 21, | 1358 | .values_count = 21, |
| 1274 | .values = {0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 20, 21, 22}, | 1359 | .values = {0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 20, 21, 22}, |
| 1275 | }, | 1360 | }, |
| 1276 | Service::Mii::RandomMiiData4{ | 1361 | RandomMiiData4{ |
| 1277 | .gender = Gender::Male, | 1362 | .gender = static_cast<u32>(Gender::Male), |
| 1278 | .age = Age::Normal, | 1363 | .age = static_cast<u32>(Age::Normal), |
| 1279 | .race = Race::Asian, | 1364 | .race = static_cast<u32>(Race::Asian), |
| 1280 | .values_count = 21, | 1365 | .values_count = 21, |
| 1281 | .values = {0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 20, 21, 22}, | 1366 | .values = {0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 20, 21, 22}, |
| 1282 | }, | 1367 | }, |
| 1283 | Service::Mii::RandomMiiData4{ | 1368 | RandomMiiData4{ |
| 1284 | .gender = Gender::Male, | 1369 | .gender = static_cast<u32>(Gender::Male), |
| 1285 | .age = Age::Old, | 1370 | .age = static_cast<u32>(Age::Old), |
| 1286 | .race = Race::Asian, | 1371 | .race = static_cast<u32>(Race::Asian), |
| 1287 | .values_count = 21, | 1372 | .values_count = 21, |
| 1288 | .values = {0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 20, 21, 22}, | 1373 | .values = {0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 20, 21, 22}, |
| 1289 | }, | 1374 | }, |
| 1290 | Service::Mii::RandomMiiData4{ | 1375 | RandomMiiData4{ |
| 1291 | .gender = Gender::Female, | 1376 | .gender = static_cast<u32>(Gender::Female), |
| 1292 | .age = Age::Young, | 1377 | .age = static_cast<u32>(Age::Young), |
| 1293 | .race = Race::Black, | 1378 | .race = static_cast<u32>(Race::Black), |
| 1294 | .values_count = 9, | 1379 | .values_count = 9, |
| 1295 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13}, | 1380 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13}, |
| 1296 | }, | 1381 | }, |
| 1297 | Service::Mii::RandomMiiData4{ | 1382 | RandomMiiData4{ |
| 1298 | .gender = Gender::Female, | 1383 | .gender = static_cast<u32>(Gender::Female), |
| 1299 | .age = Age::Normal, | 1384 | .age = static_cast<u32>(Age::Normal), |
| 1300 | .race = Race::Black, | 1385 | .race = static_cast<u32>(Race::Black), |
| 1301 | .values_count = 9, | 1386 | .values_count = 9, |
| 1302 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13}, | 1387 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13}, |
| 1303 | }, | 1388 | }, |
| 1304 | Service::Mii::RandomMiiData4{ | 1389 | RandomMiiData4{ |
| 1305 | .gender = Gender::Female, | 1390 | .gender = static_cast<u32>(Gender::Female), |
| 1306 | .age = Age::Old, | 1391 | .age = static_cast<u32>(Age::Old), |
| 1307 | .race = Race::Black, | 1392 | .race = static_cast<u32>(Race::Black), |
| 1308 | .values_count = 9, | 1393 | .values_count = 9, |
| 1309 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13}, | 1394 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13}, |
| 1310 | }, | 1395 | }, |
| 1311 | Service::Mii::RandomMiiData4{ | 1396 | RandomMiiData4{ |
| 1312 | .gender = Gender::Female, | 1397 | .gender = static_cast<u32>(Gender::Female), |
| 1313 | .age = Age::Young, | 1398 | .age = static_cast<u32>(Age::Young), |
| 1314 | .race = Race::White, | 1399 | .race = static_cast<u32>(Race::White), |
| 1315 | .values_count = 11, | 1400 | .values_count = 11, |
| 1316 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13, 15, 19}, | 1401 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13, 15, 19}, |
| 1317 | }, | 1402 | }, |
| 1318 | Service::Mii::RandomMiiData4{ | 1403 | RandomMiiData4{ |
| 1319 | .gender = Gender::Female, | 1404 | .gender = static_cast<u32>(Gender::Female), |
| 1320 | .age = Age::Normal, | 1405 | .age = static_cast<u32>(Age::Normal), |
| 1321 | .race = Race::White, | 1406 | .race = static_cast<u32>(Race::White), |
| 1322 | .values_count = 11, | 1407 | .values_count = 11, |
| 1323 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13, 15, 19}, | 1408 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13, 15, 19}, |
| 1324 | }, | 1409 | }, |
| 1325 | Service::Mii::RandomMiiData4{ | 1410 | RandomMiiData4{ |
| 1326 | .gender = Gender::Female, | 1411 | .gender = static_cast<u32>(Gender::Female), |
| 1327 | .age = Age::Old, | 1412 | .age = static_cast<u32>(Age::Old), |
| 1328 | .race = Race::White, | 1413 | .race = static_cast<u32>(Race::White), |
| 1329 | .values_count = 11, | 1414 | .values_count = 11, |
| 1330 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13, 15, 19}, | 1415 | .values = {0, 1, 3, 7, 8, 9, 10, 11, 13, 15, 19}, |
| 1331 | }, | 1416 | }, |
| 1332 | Service::Mii::RandomMiiData4{ | 1417 | RandomMiiData4{ |
| 1333 | .gender = Gender::Female, | 1418 | .gender = static_cast<u32>(Gender::Female), |
| 1334 | .age = Age::Young, | 1419 | .age = static_cast<u32>(Age::Young), |
| 1335 | .race = Race::Asian, | 1420 | .race = static_cast<u32>(Race::Asian), |
| 1336 | .values_count = 9, | 1421 | .values_count = 9, |
| 1337 | .values = {0, 3, 7, 8, 9, 10, 11, 13, 15}, | 1422 | .values = {0, 3, 7, 8, 9, 10, 11, 13, 15}, |
| 1338 | }, | 1423 | }, |
| 1339 | Service::Mii::RandomMiiData4{ | 1424 | RandomMiiData4{ |
| 1340 | .gender = Gender::Female, | 1425 | .gender = static_cast<u32>(Gender::Female), |
| 1341 | .age = Age::Normal, | 1426 | .age = static_cast<u32>(Age::Normal), |
| 1342 | .race = Race::Asian, | 1427 | .race = static_cast<u32>(Race::Asian), |
| 1343 | .values_count = 9, | 1428 | .values_count = 9, |
| 1344 | .values = {0, 3, 7, 8, 9, 10, 11, 13, 15}, | 1429 | .values = {0, 3, 7, 8, 9, 10, 11, 13, 15}, |
| 1345 | }, | 1430 | }, |
| 1346 | Service::Mii::RandomMiiData4{ | 1431 | RandomMiiData4{ |
| 1347 | .gender = Gender::Female, | 1432 | .gender = static_cast<u32>(Gender::Female), |
| 1348 | .age = Age::Old, | 1433 | .age = static_cast<u32>(Age::Old), |
| 1349 | .race = Race::Asian, | 1434 | .race = static_cast<u32>(Race::Asian), |
| 1350 | .values_count = 9, | 1435 | .values_count = 9, |
| 1351 | .values = {0, 3, 7, 8, 9, 10, 11, 13, 15}, | 1436 | .values = {0, 3, 7, 8, 9, 10, 11, 13, 15}, |
| 1352 | }, | 1437 | }, |
| 1353 | }; | 1438 | }; |
| 1354 | 1439 | ||
| 1355 | const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiNoseType{ | 1440 | const std::array<RandomMiiData4, 18> RandomMiiNoseType{ |
| 1356 | Service::Mii::RandomMiiData4{ | 1441 | RandomMiiData4{ |
| 1357 | .gender = Gender::Male, | 1442 | .gender = static_cast<u32>(Gender::Male), |
| 1358 | .age = Age::Young, | 1443 | .age = static_cast<u32>(Age::Young), |
| 1359 | .race = Race::Black, | 1444 | .race = static_cast<u32>(Race::Black), |
| 1360 | .values_count = 11, | 1445 | .values_count = 11, |
| 1361 | .values = {0, 1, 2, 3, 4, 5, 7, 8, 10, 13, 14}, | 1446 | .values = {0, 1, 2, 3, 4, 5, 7, 8, 10, 13, 14}, |
| 1362 | }, | 1447 | }, |
| 1363 | Service::Mii::RandomMiiData4{ | 1448 | RandomMiiData4{ |
| 1364 | .gender = Gender::Male, | 1449 | .gender = static_cast<u32>(Gender::Male), |
| 1365 | .age = Age::Normal, | 1450 | .age = static_cast<u32>(Age::Normal), |
| 1366 | .race = Race::Black, | 1451 | .race = static_cast<u32>(Race::Black), |
| 1367 | .values_count = 11, | 1452 | .values_count = 11, |
| 1368 | .values = {0, 1, 2, 3, 4, 5, 7, 8, 10, 13, 14}, | 1453 | .values = {0, 1, 2, 3, 4, 5, 7, 8, 10, 13, 14}, |
| 1369 | }, | 1454 | }, |
| 1370 | Service::Mii::RandomMiiData4{ | 1455 | RandomMiiData4{ |
| 1371 | .gender = Gender::Male, | 1456 | .gender = static_cast<u32>(Gender::Male), |
| 1372 | .age = Age::Old, | 1457 | .age = static_cast<u32>(Age::Old), |
| 1373 | .race = Race::Black, | 1458 | .race = static_cast<u32>(Race::Black), |
| 1374 | .values_count = 11, | 1459 | .values_count = 11, |
| 1375 | .values = {0, 1, 2, 3, 4, 5, 7, 8, 10, 13, 14}, | 1460 | .values = {0, 1, 2, 3, 4, 5, 7, 8, 10, 13, 14}, |
| 1376 | }, | 1461 | }, |
| 1377 | Service::Mii::RandomMiiData4{ | 1462 | RandomMiiData4{ |
| 1378 | .gender = Gender::Male, | 1463 | .gender = static_cast<u32>(Gender::Male), |
| 1379 | .age = Age::Young, | 1464 | .age = static_cast<u32>(Age::Young), |
| 1380 | .race = Race::White, | 1465 | .race = static_cast<u32>(Race::White), |
| 1381 | .values_count = 18, | 1466 | .values_count = 18, |
| 1382 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17}, | 1467 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17}, |
| 1383 | }, | 1468 | }, |
| 1384 | Service::Mii::RandomMiiData4{ | 1469 | RandomMiiData4{ |
| 1385 | .gender = Gender::Male, | 1470 | .gender = static_cast<u32>(Gender::Male), |
| 1386 | .age = Age::Normal, | 1471 | .age = static_cast<u32>(Age::Normal), |
| 1387 | .race = Race::White, | 1472 | .race = static_cast<u32>(Race::White), |
| 1388 | .values_count = 18, | 1473 | .values_count = 18, |
| 1389 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17}, | 1474 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17}, |
| 1390 | }, | 1475 | }, |
| 1391 | Service::Mii::RandomMiiData4{ | 1476 | RandomMiiData4{ |
| 1392 | .gender = Gender::Male, | 1477 | .gender = static_cast<u32>(Gender::Male), |
| 1393 | .age = Age::Old, | 1478 | .age = static_cast<u32>(Age::Old), |
| 1394 | .race = Race::White, | 1479 | .race = static_cast<u32>(Race::White), |
| 1395 | .values_count = 15, | 1480 | .values_count = 15, |
| 1396 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 10, 11, 12, 13, 14, 16}, | 1481 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 10, 11, 12, 13, 14, 16}, |
| 1397 | }, | 1482 | }, |
| 1398 | Service::Mii::RandomMiiData4{ | 1483 | RandomMiiData4{ |
| 1399 | .gender = Gender::Male, | 1484 | .gender = static_cast<u32>(Gender::Male), |
| 1400 | .age = Age::Young, | 1485 | .age = static_cast<u32>(Age::Young), |
| 1401 | .race = Race::Asian, | 1486 | .race = static_cast<u32>(Race::Asian), |
| 1402 | .values_count = 18, | 1487 | .values_count = 18, |
| 1403 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17}, | 1488 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17}, |
| 1404 | }, | 1489 | }, |
| 1405 | Service::Mii::RandomMiiData4{ | 1490 | RandomMiiData4{ |
| 1406 | .gender = Gender::Male, | 1491 | .gender = static_cast<u32>(Gender::Male), |
| 1407 | .age = Age::Normal, | 1492 | .age = static_cast<u32>(Age::Normal), |
| 1408 | .race = Race::Asian, | 1493 | .race = static_cast<u32>(Race::Asian), |
| 1409 | .values_count = 18, | 1494 | .values_count = 18, |
| 1410 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17}, | 1495 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17}, |
| 1411 | }, | 1496 | }, |
| 1412 | Service::Mii::RandomMiiData4{ | 1497 | RandomMiiData4{ |
| 1413 | .gender = Gender::Male, | 1498 | .gender = static_cast<u32>(Gender::Male), |
| 1414 | .age = Age::Old, | 1499 | .age = static_cast<u32>(Age::Old), |
| 1415 | .race = Race::Asian, | 1500 | .race = static_cast<u32>(Race::Asian), |
| 1416 | .values_count = 15, | 1501 | .values_count = 15, |
| 1417 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 10, 11, 12, 13, 14, 16}, | 1502 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 10, 11, 12, 13, 14, 16}, |
| 1418 | }, | 1503 | }, |
| 1419 | Service::Mii::RandomMiiData4{ | 1504 | RandomMiiData4{ |
| 1420 | .gender = Gender::Female, | 1505 | .gender = static_cast<u32>(Gender::Female), |
| 1421 | .age = Age::Young, | 1506 | .age = static_cast<u32>(Age::Young), |
| 1422 | .race = Race::Black, | 1507 | .race = static_cast<u32>(Race::Black), |
| 1423 | .values_count = 8, | 1508 | .values_count = 8, |
| 1424 | .values = {0, 1, 3, 4, 8, 10, 13, 14}, | 1509 | .values = {0, 1, 3, 4, 8, 10, 13, 14}, |
| 1425 | }, | 1510 | }, |
| 1426 | Service::Mii::RandomMiiData4{ | 1511 | RandomMiiData4{ |
| 1427 | .gender = Gender::Female, | 1512 | .gender = static_cast<u32>(Gender::Female), |
| 1428 | .age = Age::Normal, | 1513 | .age = static_cast<u32>(Age::Normal), |
| 1429 | .race = Race::Black, | 1514 | .race = static_cast<u32>(Race::Black), |
| 1430 | .values_count = 8, | 1515 | .values_count = 8, |
| 1431 | .values = {0, 1, 3, 4, 8, 10, 13, 14}, | 1516 | .values = {0, 1, 3, 4, 8, 10, 13, 14}, |
| 1432 | }, | 1517 | }, |
| 1433 | Service::Mii::RandomMiiData4{ | 1518 | RandomMiiData4{ |
| 1434 | .gender = Gender::Female, | 1519 | .gender = static_cast<u32>(Gender::Female), |
| 1435 | .age = Age::Old, | 1520 | .age = static_cast<u32>(Age::Old), |
| 1436 | .race = Race::Black, | 1521 | .race = static_cast<u32>(Race::Black), |
| 1437 | .values_count = 8, | 1522 | .values_count = 8, |
| 1438 | .values = {0, 1, 3, 4, 8, 10, 13, 14}, | 1523 | .values = {0, 1, 3, 4, 8, 10, 13, 14}, |
| 1439 | }, | 1524 | }, |
| 1440 | Service::Mii::RandomMiiData4{ | 1525 | RandomMiiData4{ |
| 1441 | .gender = Gender::Female, | 1526 | .gender = static_cast<u32>(Gender::Female), |
| 1442 | .age = Age::Young, | 1527 | .age = static_cast<u32>(Age::Young), |
| 1443 | .race = Race::White, | 1528 | .race = static_cast<u32>(Race::White), |
| 1444 | .values_count = 12, | 1529 | .values_count = 12, |
| 1445 | .values = {0, 1, 3, 4, 6, 8, 9, 10, 11, 13, 14, 15}, | 1530 | .values = {0, 1, 3, 4, 6, 8, 9, 10, 11, 13, 14, 15}, |
| 1446 | }, | 1531 | }, |
| 1447 | Service::Mii::RandomMiiData4{ | 1532 | RandomMiiData4{ |
| 1448 | .gender = Gender::Female, | 1533 | .gender = static_cast<u32>(Gender::Female), |
| 1449 | .age = Age::Normal, | 1534 | .age = static_cast<u32>(Age::Normal), |
| 1450 | .race = Race::White, | 1535 | .race = static_cast<u32>(Race::White), |
| 1451 | .values_count = 11, | 1536 | .values_count = 11, |
| 1452 | .values = {0, 1, 3, 4, 6, 8, 9, 10, 11, 13, 15}, | 1537 | .values = {0, 1, 3, 4, 6, 8, 9, 10, 11, 13, 15}, |
| 1453 | }, | 1538 | }, |
| 1454 | Service::Mii::RandomMiiData4{ | 1539 | RandomMiiData4{ |
| 1455 | .gender = Gender::Female, | 1540 | .gender = static_cast<u32>(Gender::Female), |
| 1456 | .age = Age::Old, | 1541 | .age = static_cast<u32>(Age::Old), |
| 1457 | .race = Race::White, | 1542 | .race = static_cast<u32>(Race::White), |
| 1458 | .values_count = 10, | 1543 | .values_count = 10, |
| 1459 | .values = {0, 1, 3, 4, 6, 8, 10, 11, 13, 14}, | 1544 | .values = {0, 1, 3, 4, 6, 8, 10, 11, 13, 14}, |
| 1460 | }, | 1545 | }, |
| 1461 | Service::Mii::RandomMiiData4{ | 1546 | RandomMiiData4{ |
| 1462 | .gender = Gender::Female, | 1547 | .gender = static_cast<u32>(Gender::Female), |
| 1463 | .age = Age::Young, | 1548 | .age = static_cast<u32>(Age::Young), |
| 1464 | .race = Race::Asian, | 1549 | .race = static_cast<u32>(Race::Asian), |
| 1465 | .values_count = 12, | 1550 | .values_count = 12, |
| 1466 | .values = {0, 1, 3, 4, 6, 8, 9, 10, 11, 13, 14, 15}, | 1551 | .values = {0, 1, 3, 4, 6, 8, 9, 10, 11, 13, 14, 15}, |
| 1467 | }, | 1552 | }, |
| 1468 | Service::Mii::RandomMiiData4{ | 1553 | RandomMiiData4{ |
| 1469 | .gender = Gender::Female, | 1554 | .gender = static_cast<u32>(Gender::Female), |
| 1470 | .age = Age::Normal, | 1555 | .age = static_cast<u32>(Age::Normal), |
| 1471 | .race = Race::Asian, | 1556 | .race = static_cast<u32>(Race::Asian), |
| 1472 | .values_count = 11, | 1557 | .values_count = 11, |
| 1473 | .values = {0, 1, 3, 4, 6, 8, 9, 10, 11, 13, 15}, | 1558 | .values = {0, 1, 3, 4, 6, 8, 9, 10, 11, 13, 15}, |
| 1474 | }, | 1559 | }, |
| 1475 | Service::Mii::RandomMiiData4{ | 1560 | RandomMiiData4{ |
| 1476 | .gender = Gender::Female, | 1561 | .gender = static_cast<u32>(Gender::Female), |
| 1477 | .age = Age::Old, | 1562 | .age = static_cast<u32>(Age::Old), |
| 1478 | .race = Race::Asian, | 1563 | .race = static_cast<u32>(Race::Asian), |
| 1479 | .values_count = 10, | 1564 | .values_count = 10, |
| 1480 | .values = {0, 1, 3, 4, 6, 8, 10, 11, 13, 14}, | 1565 | .values = {0, 1, 3, 4, 6, 8, 10, 11, 13, 14}, |
| 1481 | }, | 1566 | }, |
| 1482 | }; | 1567 | }; |
| 1483 | 1568 | ||
| 1484 | const std::array<Service::Mii::RandomMiiData4, 18> RandomMiiMouthType{ | 1569 | const std::array<RandomMiiData4, 18> RandomMiiMouthType{ |
| 1485 | Service::Mii::RandomMiiData4{ | 1570 | RandomMiiData4{ |
| 1486 | .gender = Gender::Male, | 1571 | .gender = static_cast<u32>(Gender::Male), |
| 1487 | .age = Age::Young, | 1572 | .age = static_cast<u32>(Age::Young), |
| 1488 | .race = Race::Black, | 1573 | .race = static_cast<u32>(Race::Black), |
| 1489 | .values_count = 25, | 1574 | .values_count = 25, |
| 1490 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 12, 14, 15, 17, 18, | 1575 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 12, 14, 15, 17, 18, |
| 1491 | 19, 21, 22, 23, 25, 26, 28, 30, 32, 33, 34, 35}, | 1576 | 19, 21, 22, 23, 25, 26, 28, 30, 32, 33, 34, 35}, |
| 1492 | }, | 1577 | }, |
| 1493 | Service::Mii::RandomMiiData4{ | 1578 | RandomMiiData4{ |
| 1494 | .gender = Gender::Male, | 1579 | .gender = static_cast<u32>(Gender::Male), |
| 1495 | .age = Age::Normal, | 1580 | .age = static_cast<u32>(Age::Normal), |
| 1496 | .race = Race::Black, | 1581 | .race = static_cast<u32>(Race::Black), |
| 1497 | .values_count = 27, | 1582 | .values_count = 27, |
| 1498 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 17, | 1583 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 17, |
| 1499 | 18, 19, 21, 22, 23, 25, 26, 28, 30, 32, 33, 34, 35}, | 1584 | 18, 19, 21, 22, 23, 25, 26, 28, 30, 32, 33, 34, 35}, |
| 1500 | }, | 1585 | }, |
| 1501 | Service::Mii::RandomMiiData4{ | 1586 | RandomMiiData4{ |
| 1502 | .gender = Gender::Male, | 1587 | .gender = static_cast<u32>(Gender::Male), |
| 1503 | .age = Age::Old, | 1588 | .age = static_cast<u32>(Age::Old), |
| 1504 | .race = Race::Black, | 1589 | .race = static_cast<u32>(Race::Black), |
| 1505 | .values_count = 28, | 1590 | .values_count = 28, |
| 1506 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 17, | 1591 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 17, |
| 1507 | 18, 19, 21, 22, 23, 25, 26, 28, 30, 31, 32, 33, 34, 35}, | 1592 | 18, 19, 21, 22, 23, 25, 26, 28, 30, 31, 32, 33, 34, 35}, |
| 1508 | }, | 1593 | }, |
| 1509 | Service::Mii::RandomMiiData4{ | 1594 | RandomMiiData4{ |
| 1510 | .gender = Gender::Male, | 1595 | .gender = static_cast<u32>(Gender::Male), |
| 1511 | .age = Age::Young, | 1596 | .age = static_cast<u32>(Age::Young), |
| 1512 | .race = Race::White, | 1597 | .race = static_cast<u32>(Race::White), |
| 1513 | .values_count = 24, | 1598 | .values_count = 24, |
| 1514 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 12, 14, 15, 16, | 1599 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 12, 14, 15, 16, |
| 1515 | 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, | 1600 | 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, |
| 1516 | }, | 1601 | }, |
| 1517 | Service::Mii::RandomMiiData4{ | 1602 | RandomMiiData4{ |
| 1518 | .gender = Gender::Male, | 1603 | .gender = static_cast<u32>(Gender::Male), |
| 1519 | .age = Age::Normal, | 1604 | .age = static_cast<u32>(Age::Normal), |
| 1520 | .race = Race::White, | 1605 | .race = static_cast<u32>(Race::White), |
| 1521 | .values_count = 26, | 1606 | .values_count = 26, |
| 1522 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, | 1607 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, |
| 1523 | 16, 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, | 1608 | 16, 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, |
| 1524 | }, | 1609 | }, |
| 1525 | Service::Mii::RandomMiiData4{ | 1610 | RandomMiiData4{ |
| 1526 | .gender = Gender::Male, | 1611 | .gender = static_cast<u32>(Gender::Male), |
| 1527 | .age = Age::Old, | 1612 | .age = static_cast<u32>(Age::Old), |
| 1528 | .race = Race::White, | 1613 | .race = static_cast<u32>(Race::White), |
| 1529 | .values_count = 26, | 1614 | .values_count = 26, |
| 1530 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, | 1615 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, |
| 1531 | 16, 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, | 1616 | 16, 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, |
| 1532 | }, | 1617 | }, |
| 1533 | Service::Mii::RandomMiiData4{ | 1618 | RandomMiiData4{ |
| 1534 | .gender = Gender::Male, | 1619 | .gender = static_cast<u32>(Gender::Male), |
| 1535 | .age = Age::Young, | 1620 | .age = static_cast<u32>(Age::Young), |
| 1536 | .race = Race::Asian, | 1621 | .race = static_cast<u32>(Race::Asian), |
| 1537 | .values_count = 24, | 1622 | .values_count = 24, |
| 1538 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 12, 14, 15, 16, | 1623 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 12, 14, 15, 16, |
| 1539 | 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, | 1624 | 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, |
| 1540 | }, | 1625 | }, |
| 1541 | Service::Mii::RandomMiiData4{ | 1626 | RandomMiiData4{ |
| 1542 | .gender = Gender::Male, | 1627 | .gender = static_cast<u32>(Gender::Male), |
| 1543 | .age = Age::Normal, | 1628 | .age = static_cast<u32>(Age::Normal), |
| 1544 | .race = Race::Asian, | 1629 | .race = static_cast<u32>(Race::Asian), |
| 1545 | .values_count = 26, | 1630 | .values_count = 26, |
| 1546 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, | 1631 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, |
| 1547 | 16, 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, | 1632 | 16, 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, |
| 1548 | }, | 1633 | }, |
| 1549 | Service::Mii::RandomMiiData4{ | 1634 | RandomMiiData4{ |
| 1550 | .gender = Gender::Male, | 1635 | .gender = static_cast<u32>(Gender::Male), |
| 1551 | .age = Age::Old, | 1636 | .age = static_cast<u32>(Age::Old), |
| 1552 | .race = Race::Asian, | 1637 | .race = static_cast<u32>(Race::Asian), |
| 1553 | .values_count = 26, | 1638 | .values_count = 26, |
| 1554 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, | 1639 | .values = {0, 2, 3, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, |
| 1555 | 16, 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, | 1640 | 16, 17, 18, 19, 20, 21, 22, 23, 30, 31, 33, 34, 35}, |
| 1556 | }, | 1641 | }, |
| 1557 | Service::Mii::RandomMiiData4{ | 1642 | RandomMiiData4{ |
| 1558 | .gender = Gender::Female, | 1643 | .gender = static_cast<u32>(Gender::Female), |
| 1559 | .age = Age::Young, | 1644 | .age = static_cast<u32>(Age::Young), |
| 1560 | .race = Race::Black, | 1645 | .race = static_cast<u32>(Race::Black), |
| 1561 | .values_count = 25, | 1646 | .values_count = 25, |
| 1562 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 14, 15, | 1647 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 14, 15, |
| 1563 | 17, 18, 19, 21, 22, 23, 25, 26, 30, 33, 34, 35}, | 1648 | 17, 18, 19, 21, 22, 23, 25, 26, 30, 33, 34, 35}, |
| 1564 | }, | 1649 | }, |
| 1565 | Service::Mii::RandomMiiData4{ | 1650 | RandomMiiData4{ |
| 1566 | .gender = Gender::Female, | 1651 | .gender = static_cast<u32>(Gender::Female), |
| 1567 | .age = Age::Normal, | 1652 | .age = static_cast<u32>(Age::Normal), |
| 1568 | .race = Race::Black, | 1653 | .race = static_cast<u32>(Race::Black), |
| 1569 | .values_count = 26, | 1654 | .values_count = 26, |
| 1570 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, | 1655 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, |
| 1571 | 15, 17, 18, 19, 21, 22, 23, 25, 26, 30, 33, 34, 35}, | 1656 | 15, 17, 18, 19, 21, 22, 23, 25, 26, 30, 33, 34, 35}, |
| 1572 | }, | 1657 | }, |
| 1573 | Service::Mii::RandomMiiData4{ | 1658 | RandomMiiData4{ |
| 1574 | .gender = Gender::Female, | 1659 | .gender = static_cast<u32>(Gender::Female), |
| 1575 | .age = Age::Old, | 1660 | .age = static_cast<u32>(Age::Old), |
| 1576 | .race = Race::Black, | 1661 | .race = static_cast<u32>(Race::Black), |
| 1577 | .values_count = 26, | 1662 | .values_count = 26, |
| 1578 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, | 1663 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, |
| 1579 | 15, 17, 18, 19, 21, 22, 23, 25, 26, 30, 33, 34, 35}, | 1664 | 15, 17, 18, 19, 21, 22, 23, 25, 26, 30, 33, 34, 35}, |
| 1580 | }, | 1665 | }, |
| 1581 | Service::Mii::RandomMiiData4{ | 1666 | RandomMiiData4{ |
| 1582 | .gender = Gender::Female, | 1667 | .gender = static_cast<u32>(Gender::Female), |
| 1583 | .age = Age::Young, | 1668 | .age = static_cast<u32>(Age::Young), |
| 1584 | .race = Race::White, | 1669 | .race = static_cast<u32>(Race::White), |
| 1585 | .values_count = 25, | 1670 | .values_count = 25, |
| 1586 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 14, 15, | 1671 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 14, 15, |
| 1587 | 17, 18, 19, 21, 22, 23, 24, 26, 27, 29, 33, 35}, | 1672 | 17, 18, 19, 21, 22, 23, 24, 26, 27, 29, 33, 35}, |
| 1588 | }, | 1673 | }, |
| 1589 | Service::Mii::RandomMiiData4{ | 1674 | RandomMiiData4{ |
| 1590 | .gender = Gender::Female, | 1675 | .gender = static_cast<u32>(Gender::Female), |
| 1591 | .age = Age::Normal, | 1676 | .age = static_cast<u32>(Age::Normal), |
| 1592 | .race = Race::White, | 1677 | .race = static_cast<u32>(Race::White), |
| 1593 | .values_count = 26, | 1678 | .values_count = 26, |
| 1594 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, | 1679 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, |
| 1595 | 15, 17, 18, 19, 21, 22, 23, 24, 26, 27, 29, 33, 35}, | 1680 | 15, 17, 18, 19, 21, 22, 23, 24, 26, 27, 29, 33, 35}, |
| 1596 | }, | 1681 | }, |
| 1597 | Service::Mii::RandomMiiData4{ | 1682 | RandomMiiData4{ |
| 1598 | .gender = Gender::Female, | 1683 | .gender = static_cast<u32>(Gender::Female), |
| 1599 | .age = Age::Old, | 1684 | .age = static_cast<u32>(Age::Old), |
| 1600 | .race = Race::White, | 1685 | .race = static_cast<u32>(Race::White), |
| 1601 | .values_count = 25, | 1686 | .values_count = 25, |
| 1602 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, | 1687 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, |
| 1603 | 15, 17, 18, 19, 21, 22, 23, 24, 25, 29, 33, 35}, | 1688 | 15, 17, 18, 19, 21, 22, 23, 24, 25, 29, 33, 35}, |
| 1604 | }, | 1689 | }, |
| 1605 | Service::Mii::RandomMiiData4{ | 1690 | RandomMiiData4{ |
| 1606 | .gender = Gender::Female, | 1691 | .gender = static_cast<u32>(Gender::Female), |
| 1607 | .age = Age::Young, | 1692 | .age = static_cast<u32>(Age::Young), |
| 1608 | .race = Race::Asian, | 1693 | .race = static_cast<u32>(Race::Asian), |
| 1609 | .values_count = 24, | 1694 | .values_count = 24, |
| 1610 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 14, | 1695 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 14, |
| 1611 | 15, 16, 17, 18, 19, 21, 22, 23, 25, 26, 29, 33}, | 1696 | 15, 16, 17, 18, 19, 21, 22, 23, 25, 26, 29, 33}, |
| 1612 | }, | 1697 | }, |
| 1613 | Service::Mii::RandomMiiData4{ | 1698 | RandomMiiData4{ |
| 1614 | .gender = Gender::Female, | 1699 | .gender = static_cast<u32>(Gender::Female), |
| 1615 | .age = Age::Normal, | 1700 | .age = static_cast<u32>(Age::Normal), |
| 1616 | .race = Race::Asian, | 1701 | .race = static_cast<u32>(Race::Asian), |
| 1617 | .values_count = 25, | 1702 | .values_count = 25, |
| 1618 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, | 1703 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, |
| 1619 | 15, 16, 17, 18, 19, 21, 22, 23, 25, 26, 29, 33}, | 1704 | 15, 16, 17, 18, 19, 21, 22, 23, 25, 26, 29, 33}, |
| 1620 | }, | 1705 | }, |
| 1621 | Service::Mii::RandomMiiData4{ | 1706 | RandomMiiData4{ |
| 1622 | .gender = Gender::Female, | 1707 | .gender = static_cast<u32>(Gender::Female), |
| 1623 | .age = Age::Old, | 1708 | .age = static_cast<u32>(Age::Old), |
| 1624 | .race = Race::Asian, | 1709 | .race = static_cast<u32>(Race::Asian), |
| 1625 | .values_count = 25, | 1710 | .values_count = 25, |
| 1626 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, | 1711 | .values = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 12, 13, 14, |
| 1627 | 15, 16, 17, 18, 19, 21, 22, 23, 25, 26, 29, 33}, | 1712 | 15, 16, 17, 18, 19, 21, 22, 23, 25, 26, 29, 33}, |
| 1628 | }, | 1713 | }, |
| 1629 | }; | 1714 | }; |
| 1630 | 1715 | ||
| 1631 | const std::array<Service::Mii::RandomMiiData2, 3> RandomMiiGlassType{ | 1716 | const std::array<RandomMiiData2, 3> RandomMiiGlassType{ |
| 1632 | Service::Mii::RandomMiiData2{ | 1717 | RandomMiiData2{ |
| 1633 | .arg_1 = 0, | 1718 | .arg_1 = 0, |
| 1634 | .values_count = 9, | 1719 | .values_count = 9, |
| 1635 | .values = {90, 94, 96, 100, 0, 0, 0, 0, 0}, | 1720 | .values = {90, 94, 96, 100, 0, 0, 0, 0, 0}, |
| 1636 | }, | 1721 | }, |
| 1637 | Service::Mii::RandomMiiData2{ | 1722 | RandomMiiData2{ |
| 1638 | .arg_1 = 1, | 1723 | .arg_1 = 1, |
| 1639 | .values_count = 9, | 1724 | .values_count = 9, |
| 1640 | .values = {83, 86, 90, 93, 94, 96, 98, 100, 0}, | 1725 | .values = {83, 86, 90, 93, 94, 96, 98, 100, 0}, |
| 1641 | }, | 1726 | }, |
| 1642 | Service::Mii::RandomMiiData2{ | 1727 | RandomMiiData2{ |
| 1643 | .arg_1 = 2, | 1728 | .arg_1 = 2, |
| 1644 | .values_count = 9, | 1729 | .values_count = 9, |
| 1645 | .values = {78, 83, 0, 93, 0, 0, 98, 100, 0}, | 1730 | .values = {78, 83, 0, 93, 0, 0, 98, 100, 0}, |
| 1646 | }, | 1731 | }, |
| 1647 | }; | 1732 | }; |
| 1648 | 1733 | ||
| 1734 | u8 FromVer3GetFacelineColor(u8 color) { | ||
| 1735 | return FromVer3FacelineColorTable[color]; | ||
| 1736 | } | ||
| 1737 | |||
| 1738 | u8 FromVer3GetHairColor(u8 color) { | ||
| 1739 | return FromVer3HairColorTable[color]; | ||
| 1740 | } | ||
| 1741 | |||
| 1742 | u8 FromVer3GetEyeColor(u8 color) { | ||
| 1743 | return FromVer3EyeColorTable[color]; | ||
| 1744 | } | ||
| 1745 | |||
| 1746 | u8 FromVer3GetMouthlineColor(u8 color) { | ||
| 1747 | return FromVer3MouthlineColorTable[color]; | ||
| 1748 | } | ||
| 1749 | |||
| 1750 | u8 FromVer3GetGlassColor(u8 color) { | ||
| 1751 | return FromVer3GlassColorTable[color]; | ||
| 1752 | } | ||
| 1753 | |||
| 1754 | u8 FromVer3GetGlassType(u8 type) { | ||
| 1755 | return FromVer3GlassTypeTable[type]; | ||
| 1756 | } | ||
| 1757 | |||
| 1758 | FacelineColor GetFacelineColorFromVer3(u32 color) { | ||
| 1759 | return static_cast<FacelineColor>(Ver3FacelineColorTable[color]); | ||
| 1760 | } | ||
| 1761 | |||
| 1762 | CommonColor GetHairColorFromVer3(u32 color) { | ||
| 1763 | return static_cast<CommonColor>(Ver3HairColorTable[color]); | ||
| 1764 | } | ||
| 1765 | |||
| 1766 | CommonColor GetEyeColorFromVer3(u32 color) { | ||
| 1767 | return static_cast<CommonColor>(Ver3EyeColorTable[color]); | ||
| 1768 | } | ||
| 1769 | |||
| 1770 | CommonColor GetMouthColorFromVer3(u32 color) { | ||
| 1771 | return static_cast<CommonColor>(Ver3MouthColorTable[color]); | ||
| 1772 | } | ||
| 1773 | |||
| 1774 | CommonColor GetGlassColorFromVer3(u32 color) { | ||
| 1775 | return static_cast<CommonColor>(Ver3GlassColorTable[color]); | ||
| 1776 | } | ||
| 1777 | |||
| 1649 | } // namespace Service::Mii::RawData | 1778 | } // namespace Service::Mii::RawData |
diff --git a/src/core/hle/service/mii/types/raw_data.h b/src/core/hle/service/mii/types/raw_data.h new file mode 100644 index 000000000..9a4cfa738 --- /dev/null +++ b/src/core/hle/service/mii/types/raw_data.h | |||
| @@ -0,0 +1,73 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include <array> | ||
| 7 | |||
| 8 | #include "core/hle/service/mii/mii_types.h" | ||
| 9 | |||
| 10 | namespace Service::Mii::RawData { | ||
| 11 | |||
| 12 | struct RandomMiiValues { | ||
| 13 | std::array<u8, 188> values{}; | ||
| 14 | }; | ||
| 15 | static_assert(sizeof(RandomMiiValues) == 0xbc, "RandomMiiValues has incorrect size."); | ||
| 16 | |||
| 17 | struct RandomMiiData4 { | ||
| 18 | u32 gender{}; | ||
| 19 | u32 age{}; | ||
| 20 | u32 race{}; | ||
| 21 | u32 values_count{}; | ||
| 22 | std::array<u32, 47> values{}; | ||
| 23 | }; | ||
| 24 | static_assert(sizeof(RandomMiiData4) == 0xcc, "RandomMiiData4 has incorrect size."); | ||
| 25 | |||
| 26 | struct RandomMiiData3 { | ||
| 27 | u32 arg_1; | ||
| 28 | u32 arg_2; | ||
| 29 | u32 values_count; | ||
| 30 | std::array<u32, 47> values{}; | ||
| 31 | }; | ||
| 32 | static_assert(sizeof(RandomMiiData3) == 0xc8, "RandomMiiData3 has incorrect size."); | ||
| 33 | |||
| 34 | struct RandomMiiData2 { | ||
| 35 | u32 arg_1; | ||
| 36 | u32 values_count; | ||
| 37 | std::array<u32, 47> values{}; | ||
| 38 | }; | ||
| 39 | static_assert(sizeof(RandomMiiData2) == 0xc4, "RandomMiiData2 has incorrect size."); | ||
| 40 | |||
| 41 | extern const std::array<Service::Mii::DefaultMii, 2> BaseMii; | ||
| 42 | extern const std::array<Service::Mii::DefaultMii, 6> DefaultMii; | ||
| 43 | |||
| 44 | extern const std::array<u8, 62> EyeRotateLookup; | ||
| 45 | extern const std::array<u8, 24> EyebrowRotateLookup; | ||
| 46 | |||
| 47 | extern const std::array<RandomMiiData4, 18> RandomMiiFaceline; | ||
| 48 | extern const std::array<RandomMiiData3, 6> RandomMiiFacelineColor; | ||
| 49 | extern const std::array<RandomMiiData4, 18> RandomMiiFacelineWrinkle; | ||
| 50 | extern const std::array<RandomMiiData4, 18> RandomMiiFacelineMakeup; | ||
| 51 | extern const std::array<RandomMiiData4, 18> RandomMiiHairType; | ||
| 52 | extern const std::array<RandomMiiData3, 9> RandomMiiHairColor; | ||
| 53 | extern const std::array<RandomMiiData4, 18> RandomMiiEyeType; | ||
| 54 | extern const std::array<RandomMiiData2, 3> RandomMiiEyeColor; | ||
| 55 | extern const std::array<RandomMiiData4, 18> RandomMiiEyebrowType; | ||
| 56 | extern const std::array<RandomMiiData4, 18> RandomMiiNoseType; | ||
| 57 | extern const std::array<RandomMiiData4, 18> RandomMiiMouthType; | ||
| 58 | extern const std::array<RandomMiiData2, 3> RandomMiiGlassType; | ||
| 59 | |||
| 60 | u8 FromVer3GetFacelineColor(u8 color); | ||
| 61 | u8 FromVer3GetHairColor(u8 color); | ||
| 62 | u8 FromVer3GetEyeColor(u8 color); | ||
| 63 | u8 FromVer3GetMouthlineColor(u8 color); | ||
| 64 | u8 FromVer3GetGlassColor(u8 color); | ||
| 65 | u8 FromVer3GetGlassType(u8 type); | ||
| 66 | |||
| 67 | FacelineColor GetFacelineColorFromVer3(u32 color); | ||
| 68 | CommonColor GetHairColorFromVer3(u32 color); | ||
| 69 | CommonColor GetEyeColorFromVer3(u32 color); | ||
| 70 | CommonColor GetMouthColorFromVer3(u32 color); | ||
| 71 | CommonColor GetGlassColorFromVer3(u32 color); | ||
| 72 | |||
| 73 | } // namespace Service::Mii::RawData | ||
diff --git a/src/core/hle/service/mii/types/store_data.cpp b/src/core/hle/service/mii/types/store_data.cpp new file mode 100644 index 000000000..8fce636c7 --- /dev/null +++ b/src/core/hle/service/mii/types/store_data.cpp | |||
| @@ -0,0 +1,643 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #include "core/hle/service/mii/mii_util.h" | ||
| 5 | #include "core/hle/service/mii/types/raw_data.h" | ||
| 6 | #include "core/hle/service/mii/types/store_data.h" | ||
| 7 | |||
| 8 | namespace Service::Mii { | ||
| 9 | |||
| 10 | void StoreData::BuildDefault(u32 mii_index) { | ||
| 11 | const auto& default_mii = RawData::DefaultMii[mii_index]; | ||
| 12 | core_data.SetDefault(); | ||
| 13 | |||
| 14 | core_data.SetFacelineType(static_cast<FacelineType>(default_mii.face_type)); | ||
| 15 | core_data.SetFacelineColor( | ||
| 16 | RawData::GetFacelineColorFromVer3(static_cast<u8>(default_mii.face_color))); | ||
| 17 | core_data.SetFacelineWrinkle(static_cast<FacelineWrinkle>(default_mii.face_wrinkle)); | ||
| 18 | core_data.SetFacelineMake(static_cast<FacelineMake>(default_mii.face_makeup)); | ||
| 19 | |||
| 20 | core_data.SetHairType(static_cast<HairType>(default_mii.hair_type)); | ||
| 21 | core_data.SetHairColor(RawData::GetHairColorFromVer3(static_cast<u8>(default_mii.hair_color))); | ||
| 22 | core_data.SetHairFlip(static_cast<HairFlip>(default_mii.hair_flip)); | ||
| 23 | core_data.SetEyeType(static_cast<EyeType>(default_mii.eye_type)); | ||
| 24 | core_data.SetEyeColor(RawData::GetEyeColorFromVer3(static_cast<u8>(default_mii.eye_color))); | ||
| 25 | core_data.SetEyeScale(static_cast<u8>(default_mii.eye_scale)); | ||
| 26 | core_data.SetEyeAspect(static_cast<u8>(default_mii.eye_aspect)); | ||
| 27 | core_data.SetEyeRotate(static_cast<u8>(default_mii.eye_rotate)); | ||
| 28 | core_data.SetEyeX(static_cast<u8>(default_mii.eye_x)); | ||
| 29 | core_data.SetEyeY(static_cast<u8>(default_mii.eye_y)); | ||
| 30 | |||
| 31 | core_data.SetEyebrowType(static_cast<EyebrowType>(default_mii.eyebrow_type)); | ||
| 32 | core_data.SetEyebrowColor( | ||
| 33 | RawData::GetHairColorFromVer3(static_cast<u8>(default_mii.eyebrow_color))); | ||
| 34 | core_data.SetEyebrowScale(static_cast<u8>(default_mii.eyebrow_scale)); | ||
| 35 | core_data.SetEyebrowAspect(static_cast<u8>(default_mii.eyebrow_aspect)); | ||
| 36 | core_data.SetEyebrowRotate(static_cast<u8>(default_mii.eyebrow_rotate)); | ||
| 37 | core_data.SetEyebrowX(static_cast<u8>(default_mii.eyebrow_x)); | ||
| 38 | core_data.SetEyebrowY(static_cast<u8>(default_mii.eyebrow_y)); | ||
| 39 | |||
| 40 | core_data.SetNoseType(static_cast<NoseType>(default_mii.nose_type)); | ||
| 41 | core_data.SetNoseScale(static_cast<u8>(default_mii.nose_scale)); | ||
| 42 | core_data.SetNoseY(static_cast<u8>(default_mii.nose_y)); | ||
| 43 | |||
| 44 | core_data.SetMouthType(static_cast<u8>(default_mii.mouth_type)); | ||
| 45 | core_data.SetMouthColor( | ||
| 46 | RawData::GetMouthColorFromVer3(static_cast<u8>(default_mii.mouth_color))); | ||
| 47 | core_data.SetMouthScale(static_cast<u8>(default_mii.mouth_scale)); | ||
| 48 | core_data.SetMouthAspect(static_cast<u8>(default_mii.mouth_aspect)); | ||
| 49 | core_data.SetMouthY(static_cast<u8>(default_mii.mouth_y)); | ||
| 50 | |||
| 51 | core_data.SetMustacheType(static_cast<MustacheType>(default_mii.mustache_type)); | ||
| 52 | core_data.SetBeardType(static_cast<BeardType>(default_mii.beard_type)); | ||
| 53 | core_data.SetBeardColor( | ||
| 54 | RawData::GetHairColorFromVer3(static_cast<u8>(default_mii.beard_color))); | ||
| 55 | core_data.SetMustacheScale(static_cast<u8>(default_mii.mustache_scale)); | ||
| 56 | core_data.SetMustacheY(static_cast<u8>(default_mii.mustache_y)); | ||
| 57 | |||
| 58 | core_data.SetGlassType(static_cast<GlassType>(default_mii.glasses_type)); | ||
| 59 | core_data.SetGlassColor( | ||
| 60 | RawData::GetGlassColorFromVer3(static_cast<u8>(default_mii.glasses_color))); | ||
| 61 | core_data.SetGlassScale(static_cast<u8>(default_mii.glasses_scale)); | ||
| 62 | core_data.SetGlassY(static_cast<u8>(default_mii.glasses_y)); | ||
| 63 | |||
| 64 | core_data.SetMoleType(static_cast<MoleType>(default_mii.mole_type)); | ||
| 65 | core_data.SetMoleScale(static_cast<u8>(default_mii.mole_scale)); | ||
| 66 | core_data.SetMoleX(static_cast<u8>(default_mii.mole_x)); | ||
| 67 | core_data.SetMoleY(static_cast<u8>(default_mii.mole_y)); | ||
| 68 | |||
| 69 | core_data.SetHeight(static_cast<u8>(default_mii.height)); | ||
| 70 | core_data.SetBuild(static_cast<u8>(default_mii.weight)); | ||
| 71 | core_data.SetGender(static_cast<Gender>(default_mii.gender)); | ||
| 72 | core_data.SetFavoriteColor(static_cast<FavoriteColor>(default_mii.favorite_color)); | ||
| 73 | core_data.SetRegionMove(static_cast<u8>(default_mii.region_move)); | ||
| 74 | core_data.SetFontRegion(static_cast<FontRegion>(default_mii.font_region)); | ||
| 75 | core_data.SetType(static_cast<u8>(default_mii.type)); | ||
| 76 | core_data.SetNickname(default_mii.nickname); | ||
| 77 | |||
| 78 | const auto device_id = MiiUtil::GetDeviceId(); | ||
| 79 | create_id = MiiUtil::MakeCreateId(); | ||
| 80 | device_crc = MiiUtil::CalculateCrc16(&device_id, sizeof(Common::UUID)); | ||
| 81 | data_crc = MiiUtil::CalculateCrc16(&core_data, sizeof(CoreData)); | ||
| 82 | } | ||
| 83 | |||
| 84 | void StoreData::BuildBase(Gender gender) { | ||
| 85 | const auto& default_mii = RawData::BaseMii[gender == Gender::Female ? 1 : 0]; | ||
| 86 | core_data.SetDefault(); | ||
| 87 | |||
| 88 | core_data.SetFacelineType(static_cast<FacelineType>(default_mii.face_type)); | ||
| 89 | core_data.SetFacelineColor( | ||
| 90 | RawData::GetFacelineColorFromVer3(static_cast<u8>(default_mii.face_color))); | ||
| 91 | core_data.SetFacelineWrinkle(static_cast<FacelineWrinkle>(default_mii.face_wrinkle)); | ||
| 92 | core_data.SetFacelineMake(static_cast<FacelineMake>(default_mii.face_makeup)); | ||
| 93 | |||
| 94 | core_data.SetHairType(static_cast<HairType>(default_mii.hair_type)); | ||
| 95 | core_data.SetHairColor(RawData::GetHairColorFromVer3(static_cast<u8>(default_mii.hair_color))); | ||
| 96 | core_data.SetHairFlip(static_cast<HairFlip>(default_mii.hair_flip)); | ||
| 97 | core_data.SetEyeType(static_cast<EyeType>(default_mii.eye_type)); | ||
| 98 | core_data.SetEyeColor(RawData::GetEyeColorFromVer3(static_cast<u8>(default_mii.eye_color))); | ||
| 99 | core_data.SetEyeScale(static_cast<u8>(default_mii.eye_scale)); | ||
| 100 | core_data.SetEyeAspect(static_cast<u8>(default_mii.eye_aspect)); | ||
| 101 | core_data.SetEyeRotate(static_cast<u8>(default_mii.eye_rotate)); | ||
| 102 | core_data.SetEyeX(static_cast<u8>(default_mii.eye_x)); | ||
| 103 | core_data.SetEyeY(static_cast<u8>(default_mii.eye_y)); | ||
| 104 | |||
| 105 | core_data.SetEyebrowType(static_cast<EyebrowType>(default_mii.eyebrow_type)); | ||
| 106 | core_data.SetEyebrowColor( | ||
| 107 | RawData::GetHairColorFromVer3(static_cast<u8>(default_mii.eyebrow_color))); | ||
| 108 | core_data.SetEyebrowScale(static_cast<u8>(default_mii.eyebrow_scale)); | ||
| 109 | core_data.SetEyebrowAspect(static_cast<u8>(default_mii.eyebrow_aspect)); | ||
| 110 | core_data.SetEyebrowRotate(static_cast<u8>(default_mii.eyebrow_rotate)); | ||
| 111 | core_data.SetEyebrowX(static_cast<u8>(default_mii.eyebrow_x)); | ||
| 112 | core_data.SetEyebrowY(static_cast<u8>(default_mii.eyebrow_y)); | ||
| 113 | |||
| 114 | core_data.SetNoseType(static_cast<NoseType>(default_mii.nose_type)); | ||
| 115 | core_data.SetNoseScale(static_cast<u8>(default_mii.nose_scale)); | ||
| 116 | core_data.SetNoseY(static_cast<u8>(default_mii.nose_y)); | ||
| 117 | |||
| 118 | core_data.SetMouthType(static_cast<u8>(default_mii.mouth_type)); | ||
| 119 | core_data.SetMouthColor( | ||
| 120 | RawData::GetMouthColorFromVer3(static_cast<u8>(default_mii.mouth_color))); | ||
| 121 | core_data.SetMouthScale(static_cast<u8>(default_mii.mouth_scale)); | ||
| 122 | core_data.SetMouthAspect(static_cast<u8>(default_mii.mouth_aspect)); | ||
| 123 | core_data.SetMouthY(static_cast<u8>(default_mii.mouth_y)); | ||
| 124 | |||
| 125 | core_data.SetMustacheType(static_cast<MustacheType>(default_mii.mustache_type)); | ||
| 126 | core_data.SetBeardType(static_cast<BeardType>(default_mii.beard_type)); | ||
| 127 | core_data.SetBeardColor( | ||
| 128 | RawData::GetHairColorFromVer3(static_cast<u8>(default_mii.beard_color))); | ||
| 129 | core_data.SetMustacheScale(static_cast<u8>(default_mii.mustache_scale)); | ||
| 130 | core_data.SetMustacheY(static_cast<u8>(default_mii.mustache_y)); | ||
| 131 | |||
| 132 | core_data.SetGlassType(static_cast<GlassType>(default_mii.glasses_type)); | ||
| 133 | core_data.SetGlassColor( | ||
| 134 | RawData::GetGlassColorFromVer3(static_cast<u8>(default_mii.glasses_color))); | ||
| 135 | core_data.SetGlassScale(static_cast<u8>(default_mii.glasses_scale)); | ||
| 136 | core_data.SetGlassY(static_cast<u8>(default_mii.glasses_y)); | ||
| 137 | |||
| 138 | core_data.SetMoleType(static_cast<MoleType>(default_mii.mole_type)); | ||
| 139 | core_data.SetMoleScale(static_cast<u8>(default_mii.mole_scale)); | ||
| 140 | core_data.SetMoleX(static_cast<u8>(default_mii.mole_x)); | ||
| 141 | core_data.SetMoleY(static_cast<u8>(default_mii.mole_y)); | ||
| 142 | |||
| 143 | core_data.SetHeight(static_cast<u8>(default_mii.height)); | ||
| 144 | core_data.SetBuild(static_cast<u8>(default_mii.weight)); | ||
| 145 | core_data.SetGender(static_cast<Gender>(default_mii.gender)); | ||
| 146 | core_data.SetFavoriteColor(static_cast<FavoriteColor>(default_mii.favorite_color)); | ||
| 147 | core_data.SetRegionMove(static_cast<u8>(default_mii.region_move)); | ||
| 148 | core_data.SetFontRegion(static_cast<FontRegion>(default_mii.font_region)); | ||
| 149 | core_data.SetType(static_cast<u8>(default_mii.type)); | ||
| 150 | core_data.SetNickname(default_mii.nickname); | ||
| 151 | |||
| 152 | const auto device_id = MiiUtil::GetDeviceId(); | ||
| 153 | create_id = MiiUtil::MakeCreateId(); | ||
| 154 | device_crc = MiiUtil::CalculateCrc16(&device_id, sizeof(Common::UUID)); | ||
| 155 | data_crc = MiiUtil::CalculateCrc16(&core_data, sizeof(CoreData)); | ||
| 156 | } | ||
| 157 | |||
| 158 | void StoreData::BuildRandom(Age age, Gender gender, Race race) { | ||
| 159 | core_data.BuildRandom(age, gender, race); | ||
| 160 | const auto device_id = MiiUtil::GetDeviceId(); | ||
| 161 | create_id = MiiUtil::MakeCreateId(); | ||
| 162 | device_crc = MiiUtil::CalculateCrc16(&device_id, sizeof(Common::UUID)); | ||
| 163 | data_crc = MiiUtil::CalculateCrc16(&core_data, sizeof(CoreData)); | ||
| 164 | } | ||
| 165 | |||
| 166 | void StoreData::SetInvalidName() { | ||
| 167 | const auto& invalid_name = core_data.GetInvalidNickname(); | ||
| 168 | const auto device_id = MiiUtil::GetDeviceId(); | ||
| 169 | core_data.SetNickname(invalid_name); | ||
| 170 | device_crc = MiiUtil::CalculateCrc16(&device_id, sizeof(Common::UUID)); | ||
| 171 | data_crc = MiiUtil::CalculateCrc16(&core_data, sizeof(CoreData)); | ||
| 172 | } | ||
| 173 | |||
| 174 | bool StoreData::IsSpecial() const { | ||
| 175 | return GetType() == 1; | ||
| 176 | } | ||
| 177 | |||
| 178 | u32 StoreData::IsValid() const { | ||
| 179 | // TODO: complete this | ||
| 180 | return 0; | ||
| 181 | } | ||
| 182 | |||
| 183 | void StoreData::SetFontRegion(FontRegion value) { | ||
| 184 | core_data.SetFontRegion(value); | ||
| 185 | } | ||
| 186 | |||
| 187 | void StoreData::SetFavoriteColor(FavoriteColor value) { | ||
| 188 | core_data.SetFavoriteColor(value); | ||
| 189 | } | ||
| 190 | |||
| 191 | void StoreData::SetGender(Gender value) { | ||
| 192 | core_data.SetGender(value); | ||
| 193 | } | ||
| 194 | |||
| 195 | void StoreData::SetHeight(u8 value) { | ||
| 196 | core_data.SetHeight(value); | ||
| 197 | } | ||
| 198 | |||
| 199 | void StoreData::SetBuild(u8 value) { | ||
| 200 | core_data.SetBuild(value); | ||
| 201 | } | ||
| 202 | |||
| 203 | void StoreData::SetType(u8 value) { | ||
| 204 | core_data.SetType(value); | ||
| 205 | } | ||
| 206 | |||
| 207 | void StoreData::SetRegionMove(u8 value) { | ||
| 208 | core_data.SetRegionMove(value); | ||
| 209 | } | ||
| 210 | |||
| 211 | void StoreData::SetFacelineType(FacelineType value) { | ||
| 212 | core_data.SetFacelineType(value); | ||
| 213 | } | ||
| 214 | |||
| 215 | void StoreData::SetFacelineColor(FacelineColor value) { | ||
| 216 | core_data.SetFacelineColor(value); | ||
| 217 | } | ||
| 218 | |||
| 219 | void StoreData::SetFacelineWrinkle(FacelineWrinkle value) { | ||
| 220 | core_data.SetFacelineWrinkle(value); | ||
| 221 | } | ||
| 222 | |||
| 223 | void StoreData::SetFacelineMake(FacelineMake value) { | ||
| 224 | core_data.SetFacelineMake(value); | ||
| 225 | } | ||
| 226 | |||
| 227 | void StoreData::SetHairType(HairType value) { | ||
| 228 | core_data.SetHairType(value); | ||
| 229 | } | ||
| 230 | |||
| 231 | void StoreData::SetHairColor(CommonColor value) { | ||
| 232 | core_data.SetHairColor(value); | ||
| 233 | } | ||
| 234 | |||
| 235 | void StoreData::SetHairFlip(HairFlip value) { | ||
| 236 | core_data.SetHairFlip(value); | ||
| 237 | } | ||
| 238 | |||
| 239 | void StoreData::SetEyeType(EyeType value) { | ||
| 240 | core_data.SetEyeType(value); | ||
| 241 | } | ||
| 242 | |||
| 243 | void StoreData::SetEyeColor(CommonColor value) { | ||
| 244 | core_data.SetEyeColor(value); | ||
| 245 | } | ||
| 246 | |||
| 247 | void StoreData::SetEyeScale(u8 value) { | ||
| 248 | core_data.SetEyeScale(value); | ||
| 249 | } | ||
| 250 | |||
| 251 | void StoreData::SetEyeAspect(u8 value) { | ||
| 252 | core_data.SetEyeAspect(value); | ||
| 253 | } | ||
| 254 | |||
| 255 | void StoreData::SetEyeRotate(u8 value) { | ||
| 256 | core_data.SetEyeRotate(value); | ||
| 257 | } | ||
| 258 | |||
| 259 | void StoreData::SetEyeX(u8 value) { | ||
| 260 | core_data.SetEyeX(value); | ||
| 261 | } | ||
| 262 | |||
| 263 | void StoreData::SetEyeY(u8 value) { | ||
| 264 | core_data.SetEyeY(value); | ||
| 265 | } | ||
| 266 | |||
| 267 | void StoreData::SetEyebrowType(EyebrowType value) { | ||
| 268 | core_data.SetEyebrowType(value); | ||
| 269 | } | ||
| 270 | |||
| 271 | void StoreData::SetEyebrowColor(CommonColor value) { | ||
| 272 | core_data.SetEyebrowColor(value); | ||
| 273 | } | ||
| 274 | |||
| 275 | void StoreData::SetEyebrowScale(u8 value) { | ||
| 276 | core_data.SetEyebrowScale(value); | ||
| 277 | } | ||
| 278 | |||
| 279 | void StoreData::SetEyebrowAspect(u8 value) { | ||
| 280 | core_data.SetEyebrowAspect(value); | ||
| 281 | } | ||
| 282 | |||
| 283 | void StoreData::SetEyebrowRotate(u8 value) { | ||
| 284 | core_data.SetEyebrowRotate(value); | ||
| 285 | } | ||
| 286 | |||
| 287 | void StoreData::SetEyebrowX(u8 value) { | ||
| 288 | core_data.SetEyebrowX(value); | ||
| 289 | } | ||
| 290 | |||
| 291 | void StoreData::SetEyebrowY(u8 value) { | ||
| 292 | core_data.SetEyebrowY(value); | ||
| 293 | } | ||
| 294 | |||
| 295 | void StoreData::SetNoseType(NoseType value) { | ||
| 296 | core_data.SetNoseType(value); | ||
| 297 | } | ||
| 298 | |||
| 299 | void StoreData::SetNoseScale(u8 value) { | ||
| 300 | core_data.SetNoseScale(value); | ||
| 301 | } | ||
| 302 | |||
| 303 | void StoreData::SetNoseY(u8 value) { | ||
| 304 | core_data.SetNoseY(value); | ||
| 305 | } | ||
| 306 | |||
| 307 | void StoreData::SetMouthType(u8 value) { | ||
| 308 | core_data.SetMouthType(value); | ||
| 309 | } | ||
| 310 | |||
| 311 | void StoreData::SetMouthColor(CommonColor value) { | ||
| 312 | core_data.SetMouthColor(value); | ||
| 313 | } | ||
| 314 | |||
| 315 | void StoreData::SetMouthScale(u8 value) { | ||
| 316 | core_data.SetMouthScale(value); | ||
| 317 | } | ||
| 318 | |||
| 319 | void StoreData::SetMouthAspect(u8 value) { | ||
| 320 | core_data.SetMouthAspect(value); | ||
| 321 | } | ||
| 322 | |||
| 323 | void StoreData::SetMouthY(u8 value) { | ||
| 324 | core_data.SetMouthY(value); | ||
| 325 | } | ||
| 326 | |||
| 327 | void StoreData::SetBeardColor(CommonColor value) { | ||
| 328 | core_data.SetBeardColor(value); | ||
| 329 | } | ||
| 330 | |||
| 331 | void StoreData::SetBeardType(BeardType value) { | ||
| 332 | core_data.SetBeardType(value); | ||
| 333 | } | ||
| 334 | |||
| 335 | void StoreData::SetMustacheType(MustacheType value) { | ||
| 336 | core_data.SetMustacheType(value); | ||
| 337 | } | ||
| 338 | |||
| 339 | void StoreData::SetMustacheScale(u8 value) { | ||
| 340 | core_data.SetMustacheScale(value); | ||
| 341 | } | ||
| 342 | |||
| 343 | void StoreData::SetMustacheY(u8 value) { | ||
| 344 | core_data.SetMustacheY(value); | ||
| 345 | } | ||
| 346 | |||
| 347 | void StoreData::SetGlassType(GlassType value) { | ||
| 348 | core_data.SetGlassType(value); | ||
| 349 | } | ||
| 350 | |||
| 351 | void StoreData::SetGlassColor(CommonColor value) { | ||
| 352 | core_data.SetGlassColor(value); | ||
| 353 | } | ||
| 354 | |||
| 355 | void StoreData::SetGlassScale(u8 value) { | ||
| 356 | core_data.SetGlassScale(value); | ||
| 357 | } | ||
| 358 | |||
| 359 | void StoreData::SetGlassY(u8 value) { | ||
| 360 | core_data.SetGlassY(value); | ||
| 361 | } | ||
| 362 | |||
| 363 | void StoreData::SetMoleType(MoleType value) { | ||
| 364 | core_data.SetMoleType(value); | ||
| 365 | } | ||
| 366 | |||
| 367 | void StoreData::SetMoleScale(u8 value) { | ||
| 368 | core_data.SetMoleScale(value); | ||
| 369 | } | ||
| 370 | |||
| 371 | void StoreData::SetMoleX(u8 value) { | ||
| 372 | core_data.SetMoleX(value); | ||
| 373 | } | ||
| 374 | |||
| 375 | void StoreData::SetMoleY(u8 value) { | ||
| 376 | core_data.SetMoleY(value); | ||
| 377 | } | ||
| 378 | |||
| 379 | void StoreData::SetNickname(Nickname value) { | ||
| 380 | core_data.SetNickname(value); | ||
| 381 | } | ||
| 382 | |||
| 383 | Common::UUID StoreData::GetCreateId() const { | ||
| 384 | return create_id; | ||
| 385 | } | ||
| 386 | |||
| 387 | FontRegion StoreData::GetFontRegion() const { | ||
| 388 | return static_cast<FontRegion>(core_data.GetFontRegion()); | ||
| 389 | } | ||
| 390 | |||
| 391 | FavoriteColor StoreData::GetFavoriteColor() const { | ||
| 392 | return core_data.GetFavoriteColor(); | ||
| 393 | } | ||
| 394 | |||
| 395 | Gender StoreData::GetGender() const { | ||
| 396 | return core_data.GetGender(); | ||
| 397 | } | ||
| 398 | |||
| 399 | u8 StoreData::GetHeight() const { | ||
| 400 | return core_data.GetHeight(); | ||
| 401 | } | ||
| 402 | |||
| 403 | u8 StoreData::GetBuild() const { | ||
| 404 | return core_data.GetBuild(); | ||
| 405 | } | ||
| 406 | |||
| 407 | u8 StoreData::GetType() const { | ||
| 408 | return core_data.GetType(); | ||
| 409 | } | ||
| 410 | |||
| 411 | u8 StoreData::GetRegionMove() const { | ||
| 412 | return core_data.GetRegionMove(); | ||
| 413 | } | ||
| 414 | |||
| 415 | FacelineType StoreData::GetFacelineType() const { | ||
| 416 | return core_data.GetFacelineType(); | ||
| 417 | } | ||
| 418 | |||
| 419 | FacelineColor StoreData::GetFacelineColor() const { | ||
| 420 | return core_data.GetFacelineColor(); | ||
| 421 | } | ||
| 422 | |||
| 423 | FacelineWrinkle StoreData::GetFacelineWrinkle() const { | ||
| 424 | return core_data.GetFacelineWrinkle(); | ||
| 425 | } | ||
| 426 | |||
| 427 | FacelineMake StoreData::GetFacelineMake() const { | ||
| 428 | return core_data.GetFacelineMake(); | ||
| 429 | } | ||
| 430 | |||
| 431 | HairType StoreData::GetHairType() const { | ||
| 432 | return core_data.GetHairType(); | ||
| 433 | } | ||
| 434 | |||
| 435 | CommonColor StoreData::GetHairColor() const { | ||
| 436 | return core_data.GetHairColor(); | ||
| 437 | } | ||
| 438 | |||
| 439 | HairFlip StoreData::GetHairFlip() const { | ||
| 440 | return core_data.GetHairFlip(); | ||
| 441 | } | ||
| 442 | |||
| 443 | EyeType StoreData::GetEyeType() const { | ||
| 444 | return core_data.GetEyeType(); | ||
| 445 | } | ||
| 446 | |||
| 447 | CommonColor StoreData::GetEyeColor() const { | ||
| 448 | return core_data.GetEyeColor(); | ||
| 449 | } | ||
| 450 | |||
| 451 | u8 StoreData::GetEyeScale() const { | ||
| 452 | return core_data.GetEyeScale(); | ||
| 453 | } | ||
| 454 | |||
| 455 | u8 StoreData::GetEyeAspect() const { | ||
| 456 | return core_data.GetEyeAspect(); | ||
| 457 | } | ||
| 458 | |||
| 459 | u8 StoreData::GetEyeRotate() const { | ||
| 460 | return core_data.GetEyeRotate(); | ||
| 461 | } | ||
| 462 | |||
| 463 | u8 StoreData::GetEyeX() const { | ||
| 464 | return core_data.GetEyeX(); | ||
| 465 | } | ||
| 466 | |||
| 467 | u8 StoreData::GetEyeY() const { | ||
| 468 | return core_data.GetEyeY(); | ||
| 469 | } | ||
| 470 | |||
| 471 | EyebrowType StoreData::GetEyebrowType() const { | ||
| 472 | return core_data.GetEyebrowType(); | ||
| 473 | } | ||
| 474 | |||
| 475 | CommonColor StoreData::GetEyebrowColor() const { | ||
| 476 | return core_data.GetEyebrowColor(); | ||
| 477 | } | ||
| 478 | |||
| 479 | u8 StoreData::GetEyebrowScale() const { | ||
| 480 | return core_data.GetEyebrowScale(); | ||
| 481 | } | ||
| 482 | |||
| 483 | u8 StoreData::GetEyebrowAspect() const { | ||
| 484 | return core_data.GetEyebrowAspect(); | ||
| 485 | } | ||
| 486 | |||
| 487 | u8 StoreData::GetEyebrowRotate() const { | ||
| 488 | return core_data.GetEyebrowRotate(); | ||
| 489 | } | ||
| 490 | |||
| 491 | u8 StoreData::GetEyebrowX() const { | ||
| 492 | return core_data.GetEyebrowX(); | ||
| 493 | } | ||
| 494 | |||
| 495 | u8 StoreData::GetEyebrowY() const { | ||
| 496 | return core_data.GetEyebrowY(); | ||
| 497 | } | ||
| 498 | |||
| 499 | NoseType StoreData::GetNoseType() const { | ||
| 500 | return core_data.GetNoseType(); | ||
| 501 | } | ||
| 502 | |||
| 503 | u8 StoreData::GetNoseScale() const { | ||
| 504 | return core_data.GetNoseScale(); | ||
| 505 | } | ||
| 506 | |||
| 507 | u8 StoreData::GetNoseY() const { | ||
| 508 | return core_data.GetNoseY(); | ||
| 509 | } | ||
| 510 | |||
| 511 | MouthType StoreData::GetMouthType() const { | ||
| 512 | return core_data.GetMouthType(); | ||
| 513 | } | ||
| 514 | |||
| 515 | CommonColor StoreData::GetMouthColor() const { | ||
| 516 | return core_data.GetMouthColor(); | ||
| 517 | } | ||
| 518 | |||
| 519 | u8 StoreData::GetMouthScale() const { | ||
| 520 | return core_data.GetMouthScale(); | ||
| 521 | } | ||
| 522 | |||
| 523 | u8 StoreData::GetMouthAspect() const { | ||
| 524 | return core_data.GetMouthAspect(); | ||
| 525 | } | ||
| 526 | |||
| 527 | u8 StoreData::GetMouthY() const { | ||
| 528 | return core_data.GetMouthY(); | ||
| 529 | } | ||
| 530 | |||
| 531 | CommonColor StoreData::GetBeardColor() const { | ||
| 532 | return core_data.GetBeardColor(); | ||
| 533 | } | ||
| 534 | |||
| 535 | BeardType StoreData::GetBeardType() const { | ||
| 536 | return core_data.GetBeardType(); | ||
| 537 | } | ||
| 538 | |||
| 539 | MustacheType StoreData::GetMustacheType() const { | ||
| 540 | return core_data.GetMustacheType(); | ||
| 541 | } | ||
| 542 | |||
| 543 | u8 StoreData::GetMustacheScale() const { | ||
| 544 | return core_data.GetMustacheScale(); | ||
| 545 | } | ||
| 546 | |||
| 547 | u8 StoreData::GetMustacheY() const { | ||
| 548 | return core_data.GetMustacheY(); | ||
| 549 | } | ||
| 550 | |||
| 551 | GlassType StoreData::GetGlassType() const { | ||
| 552 | return core_data.GetGlassType(); | ||
| 553 | } | ||
| 554 | |||
| 555 | CommonColor StoreData::GetGlassColor() const { | ||
| 556 | return core_data.GetGlassColor(); | ||
| 557 | } | ||
| 558 | |||
| 559 | u8 StoreData::GetGlassScale() const { | ||
| 560 | return core_data.GetGlassScale(); | ||
| 561 | } | ||
| 562 | |||
| 563 | u8 StoreData::GetGlassY() const { | ||
| 564 | return core_data.GetGlassY(); | ||
| 565 | } | ||
| 566 | |||
| 567 | MoleType StoreData::GetMoleType() const { | ||
| 568 | return core_data.GetMoleType(); | ||
| 569 | } | ||
| 570 | |||
| 571 | u8 StoreData::GetMoleScale() const { | ||
| 572 | return core_data.GetMoleScale(); | ||
| 573 | } | ||
| 574 | |||
| 575 | u8 StoreData::GetMoleX() const { | ||
| 576 | return core_data.GetMoleX(); | ||
| 577 | } | ||
| 578 | |||
| 579 | u8 StoreData::GetMoleY() const { | ||
| 580 | return core_data.GetMoleY(); | ||
| 581 | } | ||
| 582 | |||
| 583 | Nickname StoreData::GetNickname() const { | ||
| 584 | return core_data.GetNickname(); | ||
| 585 | } | ||
| 586 | |||
| 587 | bool StoreData::operator==(const StoreData& data) { | ||
| 588 | bool is_identical = data.core_data.IsValid() == 0; | ||
| 589 | is_identical &= core_data.GetNickname().data == data.core_data.GetNickname().data; | ||
| 590 | is_identical &= GetCreateId() == data.GetCreateId(); | ||
| 591 | is_identical &= GetFontRegion() == data.GetFontRegion(); | ||
| 592 | is_identical &= GetFavoriteColor() == data.GetFavoriteColor(); | ||
| 593 | is_identical &= GetGender() == data.GetGender(); | ||
| 594 | is_identical &= GetHeight() == data.GetHeight(); | ||
| 595 | is_identical &= GetBuild() == data.GetBuild(); | ||
| 596 | is_identical &= GetType() == data.GetType(); | ||
| 597 | is_identical &= GetRegionMove() == data.GetRegionMove(); | ||
| 598 | is_identical &= GetFacelineType() == data.GetFacelineType(); | ||
| 599 | is_identical &= GetFacelineColor() == data.GetFacelineColor(); | ||
| 600 | is_identical &= GetFacelineWrinkle() == data.GetFacelineWrinkle(); | ||
| 601 | is_identical &= GetFacelineMake() == data.GetFacelineMake(); | ||
| 602 | is_identical &= GetHairType() == data.GetHairType(); | ||
| 603 | is_identical &= GetHairColor() == data.GetHairColor(); | ||
| 604 | is_identical &= GetHairFlip() == data.GetHairFlip(); | ||
| 605 | is_identical &= GetEyeType() == data.GetEyeType(); | ||
| 606 | is_identical &= GetEyeColor() == data.GetEyeColor(); | ||
| 607 | is_identical &= GetEyeScale() == data.GetEyeScale(); | ||
| 608 | is_identical &= GetEyeAspect() == data.GetEyeAspect(); | ||
| 609 | is_identical &= GetEyeRotate() == data.GetEyeRotate(); | ||
| 610 | is_identical &= GetEyeX() == data.GetEyeX(); | ||
| 611 | is_identical &= GetEyeY() == data.GetEyeY(); | ||
| 612 | is_identical &= GetEyebrowType() == data.GetEyebrowType(); | ||
| 613 | is_identical &= GetEyebrowColor() == data.GetEyebrowColor(); | ||
| 614 | is_identical &= GetEyebrowScale() == data.GetEyebrowScale(); | ||
| 615 | is_identical &= GetEyebrowAspect() == data.GetEyebrowAspect(); | ||
| 616 | is_identical &= GetEyebrowRotate() == data.GetEyebrowRotate(); | ||
| 617 | is_identical &= GetEyebrowX() == data.GetEyebrowX(); | ||
| 618 | is_identical &= GetEyebrowY() == data.GetEyebrowY(); | ||
| 619 | is_identical &= GetNoseType() == data.GetNoseType(); | ||
| 620 | is_identical &= GetNoseScale() == data.GetNoseScale(); | ||
| 621 | is_identical &= GetNoseY() == data.GetNoseY(); | ||
| 622 | is_identical &= GetMouthType() == data.GetMouthType(); | ||
| 623 | is_identical &= GetMouthColor() == data.GetMouthColor(); | ||
| 624 | is_identical &= GetMouthScale() == data.GetMouthScale(); | ||
| 625 | is_identical &= GetMouthAspect() == data.GetMouthAspect(); | ||
| 626 | is_identical &= GetMouthY() == data.GetMouthY(); | ||
| 627 | is_identical &= GetBeardColor() == data.GetBeardColor(); | ||
| 628 | is_identical &= GetBeardType() == data.GetBeardType(); | ||
| 629 | is_identical &= GetMustacheType() == data.GetMustacheType(); | ||
| 630 | is_identical &= GetMustacheScale() == data.GetMustacheScale(); | ||
| 631 | is_identical &= GetMustacheY() == data.GetMustacheY(); | ||
| 632 | is_identical &= GetGlassType() == data.GetGlassType(); | ||
| 633 | is_identical &= GetGlassColor() == data.GetGlassColor(); | ||
| 634 | is_identical &= GetGlassScale() == data.GetGlassScale(); | ||
| 635 | is_identical &= GetGlassY() == data.GetGlassY(); | ||
| 636 | is_identical &= GetMoleType() == data.GetMoleType(); | ||
| 637 | is_identical &= GetMoleScale() == data.GetMoleScale(); | ||
| 638 | is_identical &= GetMoleX() == data.GetMoleX(); | ||
| 639 | is_identical &= data.GetMoleY() == data.GetMoleY(); | ||
| 640 | return is_identical; | ||
| 641 | } | ||
| 642 | |||
| 643 | } // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/types/store_data.h b/src/core/hle/service/mii/types/store_data.h new file mode 100644 index 000000000..224c32cf8 --- /dev/null +++ b/src/core/hle/service/mii/types/store_data.h | |||
| @@ -0,0 +1,145 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include "core/hle/service/mii/mii_types.h" | ||
| 7 | #include "core/hle/service/mii/types/core_data.h" | ||
| 8 | |||
| 9 | namespace Service::Mii { | ||
| 10 | |||
| 11 | class StoreData { | ||
| 12 | public: | ||
| 13 | // nn::mii::detail::StoreDataRaw::BuildDefault | ||
| 14 | void BuildDefault(u32 mii_index); | ||
| 15 | // nn::mii::detail::StoreDataRaw::BuildDefault | ||
| 16 | |||
| 17 | void BuildBase(Gender gender); | ||
| 18 | // nn::mii::detail::StoreDataRaw::BuildRandom | ||
| 19 | void BuildRandom(Age age, Gender gender, Race race); | ||
| 20 | |||
| 21 | bool IsSpecial() const; | ||
| 22 | |||
| 23 | u32 IsValid() const; | ||
| 24 | |||
| 25 | void SetFontRegion(FontRegion value); | ||
| 26 | void SetFavoriteColor(FavoriteColor value); | ||
| 27 | void SetGender(Gender value); | ||
| 28 | void SetHeight(u8 value); | ||
| 29 | void SetBuild(u8 value); | ||
| 30 | void SetType(u8 value); | ||
| 31 | void SetRegionMove(u8 value); | ||
| 32 | void SetFacelineType(FacelineType value); | ||
| 33 | void SetFacelineColor(FacelineColor value); | ||
| 34 | void SetFacelineWrinkle(FacelineWrinkle value); | ||
| 35 | void SetFacelineMake(FacelineMake value); | ||
| 36 | void SetHairType(HairType value); | ||
| 37 | void SetHairColor(CommonColor value); | ||
| 38 | void SetHairFlip(HairFlip value); | ||
| 39 | void SetEyeType(EyeType value); | ||
| 40 | void SetEyeColor(CommonColor value); | ||
| 41 | void SetEyeScale(u8 value); | ||
| 42 | void SetEyeAspect(u8 value); | ||
| 43 | void SetEyeRotate(u8 value); | ||
| 44 | void SetEyeX(u8 value); | ||
| 45 | void SetEyeY(u8 value); | ||
| 46 | void SetEyebrowType(EyebrowType value); | ||
| 47 | void SetEyebrowColor(CommonColor value); | ||
| 48 | void SetEyebrowScale(u8 value); | ||
| 49 | void SetEyebrowAspect(u8 value); | ||
| 50 | void SetEyebrowRotate(u8 value); | ||
| 51 | void SetEyebrowX(u8 value); | ||
| 52 | void SetEyebrowY(u8 value); | ||
| 53 | void SetNoseType(NoseType value); | ||
| 54 | void SetNoseScale(u8 value); | ||
| 55 | void SetNoseY(u8 value); | ||
| 56 | void SetMouthType(u8 value); | ||
| 57 | void SetMouthColor(CommonColor value); | ||
| 58 | void SetMouthScale(u8 value); | ||
| 59 | void SetMouthAspect(u8 value); | ||
| 60 | void SetMouthY(u8 value); | ||
| 61 | void SetBeardColor(CommonColor value); | ||
| 62 | void SetBeardType(BeardType value); | ||
| 63 | void SetMustacheType(MustacheType value); | ||
| 64 | void SetMustacheScale(u8 value); | ||
| 65 | void SetMustacheY(u8 value); | ||
| 66 | void SetGlassType(GlassType value); | ||
| 67 | void SetGlassColor(CommonColor value); | ||
| 68 | void SetGlassScale(u8 value); | ||
| 69 | void SetGlassY(u8 value); | ||
| 70 | void SetMoleType(MoleType value); | ||
| 71 | void SetMoleScale(u8 value); | ||
| 72 | void SetMoleX(u8 value); | ||
| 73 | void SetMoleY(u8 value); | ||
| 74 | void SetNickname(Nickname nickname); | ||
| 75 | void SetInvalidName(); | ||
| 76 | |||
| 77 | Common::UUID GetCreateId() const; | ||
| 78 | FontRegion GetFontRegion() const; | ||
| 79 | FavoriteColor GetFavoriteColor() const; | ||
| 80 | Gender GetGender() const; | ||
| 81 | u8 GetHeight() const; | ||
| 82 | u8 GetBuild() const; | ||
| 83 | u8 GetType() const; | ||
| 84 | u8 GetRegionMove() const; | ||
| 85 | FacelineType GetFacelineType() const; | ||
| 86 | FacelineColor GetFacelineColor() const; | ||
| 87 | FacelineWrinkle GetFacelineWrinkle() const; | ||
| 88 | FacelineMake GetFacelineMake() const; | ||
| 89 | HairType GetHairType() const; | ||
| 90 | CommonColor GetHairColor() const; | ||
| 91 | HairFlip GetHairFlip() const; | ||
| 92 | EyeType GetEyeType() const; | ||
| 93 | CommonColor GetEyeColor() const; | ||
| 94 | u8 GetEyeScale() const; | ||
| 95 | u8 GetEyeAspect() const; | ||
| 96 | u8 GetEyeRotate() const; | ||
| 97 | u8 GetEyeX() const; | ||
| 98 | u8 GetEyeY() const; | ||
| 99 | EyebrowType GetEyebrowType() const; | ||
| 100 | CommonColor GetEyebrowColor() const; | ||
| 101 | u8 GetEyebrowScale() const; | ||
| 102 | u8 GetEyebrowAspect() const; | ||
| 103 | u8 GetEyebrowRotate() const; | ||
| 104 | u8 GetEyebrowX() const; | ||
| 105 | u8 GetEyebrowY() const; | ||
| 106 | NoseType GetNoseType() const; | ||
| 107 | u8 GetNoseScale() const; | ||
| 108 | u8 GetNoseY() const; | ||
| 109 | MouthType GetMouthType() const; | ||
| 110 | CommonColor GetMouthColor() const; | ||
| 111 | u8 GetMouthScale() const; | ||
| 112 | u8 GetMouthAspect() const; | ||
| 113 | u8 GetMouthY() const; | ||
| 114 | CommonColor GetBeardColor() const; | ||
| 115 | BeardType GetBeardType() const; | ||
| 116 | MustacheType GetMustacheType() const; | ||
| 117 | u8 GetMustacheScale() const; | ||
| 118 | u8 GetMustacheY() const; | ||
| 119 | GlassType GetGlassType() const; | ||
| 120 | CommonColor GetGlassColor() const; | ||
| 121 | u8 GetGlassScale() const; | ||
| 122 | u8 GetGlassY() const; | ||
| 123 | MoleType GetMoleType() const; | ||
| 124 | u8 GetMoleScale() const; | ||
| 125 | u8 GetMoleX() const; | ||
| 126 | u8 GetMoleY() const; | ||
| 127 | Nickname GetNickname() const; | ||
| 128 | |||
| 129 | bool operator==(const StoreData& data); | ||
| 130 | |||
| 131 | private: | ||
| 132 | CoreData core_data{}; | ||
| 133 | Common::UUID create_id{}; | ||
| 134 | u16 data_crc{}; | ||
| 135 | u16 device_crc{}; | ||
| 136 | }; | ||
| 137 | static_assert(sizeof(StoreData) == 0x44, "StoreData has incorrect size."); | ||
| 138 | |||
| 139 | struct StoreDataElement { | ||
| 140 | StoreData store_data{}; | ||
| 141 | Source source{}; | ||
| 142 | }; | ||
| 143 | static_assert(sizeof(StoreDataElement) == 0x48, "StoreDataElement has incorrect size."); | ||
| 144 | |||
| 145 | }; // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/types/ver3_store_data.cpp b/src/core/hle/service/mii/types/ver3_store_data.cpp new file mode 100644 index 000000000..1c28e0b1b --- /dev/null +++ b/src/core/hle/service/mii/types/ver3_store_data.cpp | |||
| @@ -0,0 +1,241 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #include "core/hle/service/mii/mii_util.h" | ||
| 5 | #include "core/hle/service/mii/types/raw_data.h" | ||
| 6 | #include "core/hle/service/mii/types/store_data.h" | ||
| 7 | #include "core/hle/service/mii/types/ver3_store_data.h" | ||
| 8 | |||
| 9 | namespace Service::Mii { | ||
| 10 | |||
| 11 | void NfpStoreDataExtension::SetFromStoreData(const StoreData& store_data) { | ||
| 12 | faceline_color = static_cast<u8>(store_data.GetFacelineColor()) & 0xf; | ||
| 13 | hair_color = static_cast<u8>(store_data.GetHairColor()) & 0x7f; | ||
| 14 | eye_color = static_cast<u8>(store_data.GetEyeColor()) & 0x7f; | ||
| 15 | eyebrow_color = static_cast<u8>(store_data.GetEyebrowColor()) & 0x7f; | ||
| 16 | mouth_color = static_cast<u8>(store_data.GetMouthColor()) & 0x7f; | ||
| 17 | beard_color = static_cast<u8>(store_data.GetBeardColor()) & 0x7f; | ||
| 18 | glass_color = static_cast<u8>(store_data.GetGlassColor()) & 0x7f; | ||
| 19 | glass_type = static_cast<u8>(store_data.GetGlassType()) & 0x1f; | ||
| 20 | } | ||
| 21 | |||
| 22 | void Ver3StoreData::BuildToStoreData(StoreData& out_store_data) const { | ||
| 23 | out_store_data.BuildBase(Gender::Male); | ||
| 24 | |||
| 25 | if (!IsValid()) { | ||
| 26 | return; | ||
| 27 | } | ||
| 28 | |||
| 29 | // TODO: We are ignoring a bunch of data from the mii_v3 | ||
| 30 | |||
| 31 | out_store_data.SetGender(static_cast<Gender>(mii_information.gender.Value())); | ||
| 32 | out_store_data.SetFavoriteColor( | ||
| 33 | static_cast<FavoriteColor>(mii_information.favorite_color.Value())); | ||
| 34 | out_store_data.SetHeight(height); | ||
| 35 | out_store_data.SetBuild(build); | ||
| 36 | |||
| 37 | out_store_data.SetNickname(mii_name); | ||
| 38 | out_store_data.SetFontRegion( | ||
| 39 | static_cast<FontRegion>(static_cast<u8>(region_information.font_region))); | ||
| 40 | |||
| 41 | out_store_data.SetFacelineType( | ||
| 42 | static_cast<FacelineType>(appearance_bits1.faceline_type.Value())); | ||
| 43 | out_store_data.SetFacelineColor( | ||
| 44 | static_cast<FacelineColor>(appearance_bits1.faceline_color.Value())); | ||
| 45 | out_store_data.SetFacelineWrinkle( | ||
| 46 | static_cast<FacelineWrinkle>(appearance_bits2.faceline_wrinkle.Value())); | ||
| 47 | out_store_data.SetFacelineMake( | ||
| 48 | static_cast<FacelineMake>(appearance_bits2.faceline_make.Value())); | ||
| 49 | |||
| 50 | out_store_data.SetHairType(static_cast<HairType>(hair_type)); | ||
| 51 | out_store_data.SetHairColor(static_cast<CommonColor>(appearance_bits3.hair_color.Value())); | ||
| 52 | out_store_data.SetHairFlip(static_cast<HairFlip>(appearance_bits3.hair_flip.Value())); | ||
| 53 | |||
| 54 | out_store_data.SetEyeType(static_cast<EyeType>(appearance_bits4.eye_type.Value())); | ||
| 55 | out_store_data.SetEyeColor(static_cast<CommonColor>(appearance_bits4.eye_color.Value())); | ||
| 56 | out_store_data.SetEyeScale(static_cast<u8>(appearance_bits4.eye_scale)); | ||
| 57 | out_store_data.SetEyeAspect(static_cast<u8>(appearance_bits4.eye_aspect)); | ||
| 58 | out_store_data.SetEyeRotate(static_cast<u8>(appearance_bits4.eye_rotate)); | ||
| 59 | out_store_data.SetEyeX(static_cast<u8>(appearance_bits4.eye_x)); | ||
| 60 | out_store_data.SetEyeY(static_cast<u8>(appearance_bits4.eye_y)); | ||
| 61 | |||
| 62 | out_store_data.SetEyebrowType(static_cast<EyebrowType>(appearance_bits5.eyebrow_type.Value())); | ||
| 63 | out_store_data.SetEyebrowColor( | ||
| 64 | static_cast<CommonColor>(appearance_bits5.eyebrow_color.Value())); | ||
| 65 | out_store_data.SetEyebrowScale(static_cast<u8>(appearance_bits5.eyebrow_scale)); | ||
| 66 | out_store_data.SetEyebrowAspect(static_cast<u8>(appearance_bits5.eyebrow_aspect)); | ||
| 67 | out_store_data.SetEyebrowRotate(static_cast<u8>(appearance_bits5.eyebrow_rotate)); | ||
| 68 | out_store_data.SetEyebrowX(static_cast<u8>(appearance_bits5.eyebrow_x)); | ||
| 69 | out_store_data.SetEyebrowY(static_cast<u8>(appearance_bits5.eyebrow_y)); | ||
| 70 | |||
| 71 | out_store_data.SetNoseType(static_cast<NoseType>(appearance_bits6.nose_type.Value())); | ||
| 72 | out_store_data.SetNoseScale(static_cast<u8>(appearance_bits6.nose_scale)); | ||
| 73 | out_store_data.SetNoseY(static_cast<u8>(appearance_bits6.nose_y)); | ||
| 74 | |||
| 75 | out_store_data.SetMouthType(static_cast<u8>(appearance_bits7.mouth_type)); | ||
| 76 | out_store_data.SetMouthColor(static_cast<CommonColor>(appearance_bits7.mouth_color.Value())); | ||
| 77 | out_store_data.SetMouthScale(static_cast<u8>(appearance_bits7.mouth_scale)); | ||
| 78 | out_store_data.SetMouthAspect(static_cast<u8>(appearance_bits7.mouth_aspect)); | ||
| 79 | out_store_data.SetMouthY(static_cast<u8>(appearance_bits8.mouth_y)); | ||
| 80 | |||
| 81 | out_store_data.SetMustacheType( | ||
| 82 | static_cast<MustacheType>(appearance_bits8.mustache_type.Value())); | ||
| 83 | out_store_data.SetMustacheScale(static_cast<u8>(appearance_bits9.mustache_scale)); | ||
| 84 | out_store_data.SetMustacheY(static_cast<u8>(appearance_bits9.mustache_y)); | ||
| 85 | |||
| 86 | out_store_data.SetBeardType(static_cast<BeardType>(appearance_bits9.beard_type.Value())); | ||
| 87 | out_store_data.SetBeardColor(static_cast<CommonColor>(appearance_bits9.beard_color.Value())); | ||
| 88 | |||
| 89 | out_store_data.SetGlassType(static_cast<GlassType>(appearance_bits10.glass_type.Value())); | ||
| 90 | out_store_data.SetGlassColor(static_cast<CommonColor>(appearance_bits10.glass_color.Value())); | ||
| 91 | out_store_data.SetGlassScale(static_cast<u8>(appearance_bits10.glass_scale)); | ||
| 92 | out_store_data.SetGlassY(static_cast<u8>(appearance_bits10.glass_y)); | ||
| 93 | |||
| 94 | out_store_data.SetMoleType(static_cast<MoleType>(appearance_bits11.mole_type.Value())); | ||
| 95 | out_store_data.SetMoleScale(static_cast<u8>(appearance_bits11.mole_scale)); | ||
| 96 | out_store_data.SetMoleX(static_cast<u8>(appearance_bits11.mole_x)); | ||
| 97 | out_store_data.SetMoleY(static_cast<u8>(appearance_bits11.mole_y)); | ||
| 98 | } | ||
| 99 | |||
| 100 | void Ver3StoreData::BuildFromStoreData(const StoreData& store_data) { | ||
| 101 | version = 1; | ||
| 102 | mii_information.gender.Assign(static_cast<u8>(store_data.GetGender())); | ||
| 103 | mii_information.favorite_color.Assign(static_cast<u8>(store_data.GetFavoriteColor())); | ||
| 104 | height = store_data.GetHeight(); | ||
| 105 | build = store_data.GetBuild(); | ||
| 106 | |||
| 107 | mii_name = store_data.GetNickname(); | ||
| 108 | region_information.font_region.Assign(static_cast<u8>(store_data.GetFontRegion())); | ||
| 109 | |||
| 110 | appearance_bits1.faceline_type.Assign(static_cast<u8>(store_data.GetFacelineType())); | ||
| 111 | appearance_bits2.faceline_wrinkle.Assign(static_cast<u8>(store_data.GetFacelineWrinkle())); | ||
| 112 | appearance_bits2.faceline_make.Assign(static_cast<u8>(store_data.GetFacelineMake())); | ||
| 113 | |||
| 114 | hair_type = static_cast<u8>(store_data.GetHairType()); | ||
| 115 | appearance_bits3.hair_flip.Assign(static_cast<u8>(store_data.GetHairFlip())); | ||
| 116 | |||
| 117 | appearance_bits4.eye_type.Assign(static_cast<u8>(store_data.GetEyeType())); | ||
| 118 | appearance_bits4.eye_scale.Assign(store_data.GetEyeScale()); | ||
| 119 | appearance_bits4.eye_aspect.Assign(store_data.GetEyebrowAspect()); | ||
| 120 | appearance_bits4.eye_rotate.Assign(store_data.GetEyeRotate()); | ||
| 121 | appearance_bits4.eye_x.Assign(store_data.GetEyeX()); | ||
| 122 | appearance_bits4.eye_y.Assign(store_data.GetEyeY()); | ||
| 123 | |||
| 124 | appearance_bits5.eyebrow_type.Assign(static_cast<u8>(store_data.GetEyebrowType())); | ||
| 125 | appearance_bits5.eyebrow_scale.Assign(store_data.GetEyebrowScale()); | ||
| 126 | appearance_bits5.eyebrow_aspect.Assign(store_data.GetEyebrowAspect()); | ||
| 127 | appearance_bits5.eyebrow_rotate.Assign(store_data.GetEyebrowRotate()); | ||
| 128 | appearance_bits5.eyebrow_x.Assign(store_data.GetEyebrowX()); | ||
| 129 | appearance_bits5.eyebrow_y.Assign(store_data.GetEyebrowY()); | ||
| 130 | |||
| 131 | appearance_bits6.nose_type.Assign(static_cast<u8>(store_data.GetNoseType())); | ||
| 132 | appearance_bits6.nose_scale.Assign(store_data.GetNoseScale()); | ||
| 133 | appearance_bits6.nose_y.Assign(store_data.GetNoseY()); | ||
| 134 | |||
| 135 | appearance_bits7.mouth_type.Assign(static_cast<u8>(store_data.GetMouthType())); | ||
| 136 | appearance_bits7.mouth_scale.Assign(store_data.GetMouthScale()); | ||
| 137 | appearance_bits7.mouth_aspect.Assign(store_data.GetMouthAspect()); | ||
| 138 | appearance_bits8.mouth_y.Assign(store_data.GetMouthY()); | ||
| 139 | |||
| 140 | appearance_bits8.mustache_type.Assign(static_cast<u8>(store_data.GetMustacheType())); | ||
| 141 | appearance_bits9.mustache_scale.Assign(store_data.GetMustacheScale()); | ||
| 142 | appearance_bits9.mustache_y.Assign(store_data.GetMustacheY()); | ||
| 143 | |||
| 144 | appearance_bits9.beard_type.Assign(static_cast<u8>(store_data.GetBeardType())); | ||
| 145 | |||
| 146 | appearance_bits10.glass_scale.Assign(store_data.GetGlassScale()); | ||
| 147 | appearance_bits10.glass_y.Assign(store_data.GetGlassY()); | ||
| 148 | |||
| 149 | appearance_bits11.mole_type.Assign(static_cast<u8>(store_data.GetMoleType())); | ||
| 150 | appearance_bits11.mole_scale.Assign(store_data.GetMoleScale()); | ||
| 151 | appearance_bits11.mole_x.Assign(store_data.GetMoleX()); | ||
| 152 | appearance_bits11.mole_y.Assign(store_data.GetMoleY()); | ||
| 153 | |||
| 154 | // These types are converted to V3 from a table | ||
| 155 | appearance_bits1.faceline_color.Assign( | ||
| 156 | RawData::FromVer3GetFacelineColor(static_cast<u8>(store_data.GetFacelineColor()))); | ||
| 157 | appearance_bits3.hair_color.Assign( | ||
| 158 | RawData::FromVer3GetHairColor(static_cast<u8>(store_data.GetHairColor()))); | ||
| 159 | appearance_bits4.eye_color.Assign( | ||
| 160 | RawData::FromVer3GetEyeColor(static_cast<u8>(store_data.GetEyeColor()))); | ||
| 161 | appearance_bits5.eyebrow_color.Assign( | ||
| 162 | RawData::FromVer3GetHairColor(static_cast<u8>(store_data.GetEyebrowColor()))); | ||
| 163 | appearance_bits7.mouth_color.Assign( | ||
| 164 | RawData::FromVer3GetMouthlineColor(static_cast<u8>(store_data.GetMouthColor()))); | ||
| 165 | appearance_bits9.beard_color.Assign( | ||
| 166 | RawData::FromVer3GetHairColor(static_cast<u8>(store_data.GetBeardColor()))); | ||
| 167 | appearance_bits10.glass_color.Assign( | ||
| 168 | RawData::FromVer3GetGlassColor(static_cast<u8>(store_data.GetGlassColor()))); | ||
| 169 | appearance_bits10.glass_type.Assign( | ||
| 170 | RawData::FromVer3GetGlassType(static_cast<u8>(store_data.GetGlassType()))); | ||
| 171 | |||
| 172 | crc = MiiUtil::CalculateCrc16(&version, sizeof(Ver3StoreData) - sizeof(u16)); | ||
| 173 | } | ||
| 174 | |||
| 175 | u32 Ver3StoreData::IsValid() const { | ||
| 176 | bool is_valid = version == 0 || version == 3; | ||
| 177 | |||
| 178 | is_valid = is_valid && (mii_name.data[0] != '\0'); | ||
| 179 | |||
| 180 | is_valid = is_valid && (mii_information.birth_month < 13); | ||
| 181 | is_valid = is_valid && (mii_information.birth_day < 32); | ||
| 182 | is_valid = is_valid && (mii_information.favorite_color <= static_cast<u8>(FavoriteColor::Max)); | ||
| 183 | is_valid = is_valid && (height <= MaxHeight); | ||
| 184 | is_valid = is_valid && (build <= MaxBuild); | ||
| 185 | |||
| 186 | is_valid = is_valid && (appearance_bits1.faceline_type <= static_cast<u8>(FacelineType::Max)); | ||
| 187 | is_valid = is_valid && (appearance_bits1.faceline_color <= MaxVer3CommonColor - 2); | ||
| 188 | is_valid = | ||
| 189 | is_valid && (appearance_bits2.faceline_wrinkle <= static_cast<u8>(FacelineWrinkle::Max)); | ||
| 190 | is_valid = is_valid && (appearance_bits2.faceline_make <= static_cast<u8>(FacelineMake::Max)); | ||
| 191 | |||
| 192 | is_valid = is_valid && (hair_type <= static_cast<u8>(HairType::Max)); | ||
| 193 | is_valid = is_valid && (appearance_bits3.hair_color <= MaxVer3CommonColor); | ||
| 194 | |||
| 195 | is_valid = is_valid && (appearance_bits4.eye_type <= static_cast<u8>(EyeType::Max)); | ||
| 196 | is_valid = is_valid && (appearance_bits4.eye_color <= MaxVer3CommonColor - 2); | ||
| 197 | is_valid = is_valid && (appearance_bits4.eye_scale <= MaxEyeScale); | ||
| 198 | is_valid = is_valid && (appearance_bits4.eye_aspect <= MaxEyeAspect); | ||
| 199 | is_valid = is_valid && (appearance_bits4.eye_rotate <= MaxEyeRotate); | ||
| 200 | is_valid = is_valid && (appearance_bits4.eye_x <= MaxEyeX); | ||
| 201 | is_valid = is_valid && (appearance_bits4.eye_y <= MaxEyeY); | ||
| 202 | |||
| 203 | is_valid = is_valid && (appearance_bits5.eyebrow_type <= static_cast<u8>(EyebrowType::Max)); | ||
| 204 | is_valid = is_valid && (appearance_bits5.eyebrow_color <= MaxVer3CommonColor); | ||
| 205 | is_valid = is_valid && (appearance_bits5.eyebrow_scale <= MaxEyebrowScale); | ||
| 206 | is_valid = is_valid && (appearance_bits5.eyebrow_aspect <= MaxEyebrowAspect); | ||
| 207 | is_valid = is_valid && (appearance_bits5.eyebrow_rotate <= MaxEyebrowRotate); | ||
| 208 | is_valid = is_valid && (appearance_bits5.eyebrow_x <= MaxEyebrowX); | ||
| 209 | is_valid = is_valid && (appearance_bits5.eyebrow_y <= MaxEyebrowY); | ||
| 210 | |||
| 211 | is_valid = is_valid && (appearance_bits6.nose_type <= static_cast<u8>(NoseType::Max)); | ||
| 212 | is_valid = is_valid && (appearance_bits6.nose_scale <= MaxNoseScale); | ||
| 213 | is_valid = is_valid && (appearance_bits6.nose_y <= MaxNoseY); | ||
| 214 | |||
| 215 | is_valid = is_valid && (appearance_bits7.mouth_type <= static_cast<u8>(MouthType::Max)); | ||
| 216 | is_valid = is_valid && (appearance_bits7.mouth_color <= MaxVer3CommonColor - 3); | ||
| 217 | is_valid = is_valid && (appearance_bits7.mouth_scale <= MaxMouthScale); | ||
| 218 | is_valid = is_valid && (appearance_bits7.mouth_aspect <= MaxMoutAspect); | ||
| 219 | is_valid = is_valid && (appearance_bits8.mouth_y <= MaxMouthY); | ||
| 220 | |||
| 221 | is_valid = is_valid && (appearance_bits8.mustache_type <= static_cast<u8>(MustacheType::Max)); | ||
| 222 | is_valid = is_valid && (appearance_bits9.mustache_scale < MaxMustacheScale); | ||
| 223 | is_valid = is_valid && (appearance_bits9.mustache_y <= MasMustacheY); | ||
| 224 | |||
| 225 | is_valid = is_valid && (appearance_bits9.beard_type <= static_cast<u8>(BeardType::Max)); | ||
| 226 | is_valid = is_valid && (appearance_bits9.beard_color <= MaxVer3CommonColor); | ||
| 227 | |||
| 228 | is_valid = is_valid && (appearance_bits10.glass_type <= MaxVer3GlassType); | ||
| 229 | is_valid = is_valid && (appearance_bits10.glass_color <= MaxVer3CommonColor - 2); | ||
| 230 | is_valid = is_valid && (appearance_bits10.glass_scale <= MaxGlassScale); | ||
| 231 | is_valid = is_valid && (appearance_bits10.glass_y <= MaxGlassScale); | ||
| 232 | |||
| 233 | is_valid = is_valid && (appearance_bits11.mole_type <= static_cast<u8>(MoleType::Max)); | ||
| 234 | is_valid = is_valid && (appearance_bits11.mole_scale <= MaxMoleScale); | ||
| 235 | is_valid = is_valid && (appearance_bits11.mole_x <= MaxMoleX); | ||
| 236 | is_valid = is_valid && (appearance_bits11.mole_y <= MaxMoleY); | ||
| 237 | |||
| 238 | return is_valid; | ||
| 239 | } | ||
| 240 | |||
| 241 | } // namespace Service::Mii | ||
diff --git a/src/core/hle/service/mii/types/ver3_store_data.h b/src/core/hle/service/mii/types/ver3_store_data.h new file mode 100644 index 000000000..47907bf7d --- /dev/null +++ b/src/core/hle/service/mii/types/ver3_store_data.h | |||
| @@ -0,0 +1,160 @@ | |||
| 1 | // SPDX-FileCopyrightText: Copyright 2020 yuzu Emulator Project | ||
| 2 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 3 | |||
| 4 | #pragma once | ||
| 5 | |||
| 6 | #include "core/hle/service/mii/mii_types.h" | ||
| 7 | |||
| 8 | namespace Service::Mii { | ||
| 9 | class StoreData; | ||
| 10 | |||
| 11 | // This is nn::mii::Ver3StoreData | ||
| 12 | // Based on citra HLE::Applets::MiiData and PretendoNetwork. | ||
| 13 | // https://github.com/citra-emu/citra/blob/master/src/core/hle/applets/mii_selector.h#L48 | ||
| 14 | // https://github.com/PretendoNetwork/mii-js/blob/master/mii.js#L299 | ||
| 15 | |||
| 16 | struct NfpStoreDataExtension { | ||
| 17 | void SetFromStoreData(const StoreData& store_data); | ||
| 18 | |||
| 19 | u8 faceline_color; | ||
| 20 | u8 hair_color; | ||
| 21 | u8 eye_color; | ||
| 22 | u8 eyebrow_color; | ||
| 23 | u8 mouth_color; | ||
| 24 | u8 beard_color; | ||
| 25 | u8 glass_color; | ||
| 26 | u8 glass_type; | ||
| 27 | }; | ||
| 28 | static_assert(sizeof(NfpStoreDataExtension) == 0x8, "NfpStoreDataExtension is an invalid size"); | ||
| 29 | |||
| 30 | #pragma pack(push, 4) | ||
| 31 | class Ver3StoreData { | ||
| 32 | public: | ||
| 33 | void BuildToStoreData(StoreData& out_store_data) const; | ||
| 34 | void BuildFromStoreData(const StoreData& store_data); | ||
| 35 | |||
| 36 | u32 IsValid() const; | ||
| 37 | |||
| 38 | u8 version; | ||
| 39 | union { | ||
| 40 | u8 raw; | ||
| 41 | |||
| 42 | BitField<0, 1, u8> allow_copying; | ||
| 43 | BitField<1, 1, u8> profanity_flag; | ||
| 44 | BitField<2, 2, u8> region_lock; | ||
| 45 | BitField<4, 2, u8> font_region; | ||
| 46 | } region_information; | ||
| 47 | u16_be mii_id; | ||
| 48 | u64_be system_id; | ||
| 49 | u32_be specialness_and_creation_date; | ||
| 50 | std::array<u8, 6> creator_mac; | ||
| 51 | u16_be padding; | ||
| 52 | union { | ||
| 53 | u16 raw; | ||
| 54 | |||
| 55 | BitField<0, 1, u16> gender; | ||
| 56 | BitField<1, 4, u16> birth_month; | ||
| 57 | BitField<5, 5, u16> birth_day; | ||
| 58 | BitField<10, 4, u16> favorite_color; | ||
| 59 | BitField<14, 1, u16> favorite; | ||
| 60 | } mii_information; | ||
| 61 | Nickname mii_name; | ||
| 62 | u8 height; | ||
| 63 | u8 build; | ||
| 64 | union { | ||
| 65 | u8 raw; | ||
| 66 | |||
| 67 | BitField<0, 1, u8> disable_sharing; | ||
| 68 | BitField<1, 4, u8> faceline_type; | ||
| 69 | BitField<5, 3, u8> faceline_color; | ||
| 70 | } appearance_bits1; | ||
| 71 | union { | ||
| 72 | u8 raw; | ||
| 73 | |||
| 74 | BitField<0, 4, u8> faceline_wrinkle; | ||
| 75 | BitField<4, 4, u8> faceline_make; | ||
| 76 | } appearance_bits2; | ||
| 77 | u8 hair_type; | ||
| 78 | union { | ||
| 79 | u8 raw; | ||
| 80 | |||
| 81 | BitField<0, 3, u8> hair_color; | ||
| 82 | BitField<3, 1, u8> hair_flip; | ||
| 83 | } appearance_bits3; | ||
| 84 | union { | ||
| 85 | u32 raw; | ||
| 86 | |||
| 87 | BitField<0, 6, u32> eye_type; | ||
| 88 | BitField<6, 3, u32> eye_color; | ||
| 89 | BitField<9, 4, u32> eye_scale; | ||
| 90 | BitField<13, 3, u32> eye_aspect; | ||
| 91 | BitField<16, 5, u32> eye_rotate; | ||
| 92 | BitField<21, 4, u32> eye_x; | ||
| 93 | BitField<25, 5, u32> eye_y; | ||
| 94 | } appearance_bits4; | ||
| 95 | union { | ||
| 96 | u32 raw; | ||
| 97 | |||
| 98 | BitField<0, 5, u32> eyebrow_type; | ||
| 99 | BitField<5, 3, u32> eyebrow_color; | ||
| 100 | BitField<8, 4, u32> eyebrow_scale; | ||
| 101 | BitField<12, 3, u32> eyebrow_aspect; | ||
| 102 | BitField<16, 4, u32> eyebrow_rotate; | ||
| 103 | BitField<21, 4, u32> eyebrow_x; | ||
| 104 | BitField<25, 5, u32> eyebrow_y; | ||
| 105 | } appearance_bits5; | ||
| 106 | union { | ||
| 107 | u16 raw; | ||
| 108 | |||
| 109 | BitField<0, 5, u16> nose_type; | ||
| 110 | BitField<5, 4, u16> nose_scale; | ||
| 111 | BitField<9, 5, u16> nose_y; | ||
| 112 | } appearance_bits6; | ||
| 113 | union { | ||
| 114 | u16 raw; | ||
| 115 | |||
| 116 | BitField<0, 6, u16> mouth_type; | ||
| 117 | BitField<6, 3, u16> mouth_color; | ||
| 118 | BitField<9, 4, u16> mouth_scale; | ||
| 119 | BitField<13, 3, u16> mouth_aspect; | ||
| 120 | } appearance_bits7; | ||
| 121 | union { | ||
| 122 | u8 raw; | ||
| 123 | |||
| 124 | BitField<0, 5, u8> mouth_y; | ||
| 125 | BitField<5, 3, u8> mustache_type; | ||
| 126 | } appearance_bits8; | ||
| 127 | u8 allow_copying; | ||
| 128 | union { | ||
| 129 | u16 raw; | ||
| 130 | |||
| 131 | BitField<0, 3, u16> beard_type; | ||
| 132 | BitField<3, 3, u16> beard_color; | ||
| 133 | BitField<6, 4, u16> mustache_scale; | ||
| 134 | BitField<10, 5, u16> mustache_y; | ||
| 135 | } appearance_bits9; | ||
| 136 | union { | ||
| 137 | u16 raw; | ||
| 138 | |||
| 139 | BitField<0, 4, u16> glass_type; | ||
| 140 | BitField<4, 3, u16> glass_color; | ||
| 141 | BitField<7, 4, u16> glass_scale; | ||
| 142 | BitField<11, 5, u16> glass_y; | ||
| 143 | } appearance_bits10; | ||
| 144 | union { | ||
| 145 | u16 raw; | ||
| 146 | |||
| 147 | BitField<0, 1, u16> mole_type; | ||
| 148 | BitField<1, 4, u16> mole_scale; | ||
| 149 | BitField<5, 5, u16> mole_x; | ||
| 150 | BitField<10, 5, u16> mole_y; | ||
| 151 | } appearance_bits11; | ||
| 152 | |||
| 153 | Nickname author_name; | ||
| 154 | INSERT_PADDING_BYTES(0x2); | ||
| 155 | u16_be crc; | ||
| 156 | }; | ||
| 157 | static_assert(sizeof(Ver3StoreData) == 0x60, "Ver3StoreData is an invalid size"); | ||
| 158 | #pragma pack(pop) | ||
| 159 | |||
| 160 | }; // namespace Service::Mii | ||
diff --git a/src/core/hle/service/nfc/common/device.cpp b/src/core/hle/service/nfc/common/device.cpp index 5df40f9a0..5dda12343 100644 --- a/src/core/hle/service/nfc/common/device.cpp +++ b/src/core/hle/service/nfc/common/device.cpp | |||
| @@ -28,7 +28,6 @@ | |||
| 28 | #include "core/hle/kernel/k_event.h" | 28 | #include "core/hle/kernel/k_event.h" |
| 29 | #include "core/hle/service/ipc_helpers.h" | 29 | #include "core/hle/service/ipc_helpers.h" |
| 30 | #include "core/hle/service/mii/mii_manager.h" | 30 | #include "core/hle/service/mii/mii_manager.h" |
| 31 | #include "core/hle/service/mii/types.h" | ||
| 32 | #include "core/hle/service/nfc/common/amiibo_crypto.h" | 31 | #include "core/hle/service/nfc/common/amiibo_crypto.h" |
| 33 | #include "core/hle/service/nfc/common/device.h" | 32 | #include "core/hle/service/nfc/common/device.h" |
| 34 | #include "core/hle/service/nfc/mifare_result.h" | 33 | #include "core/hle/service/nfc/mifare_result.h" |
| @@ -681,12 +680,16 @@ Result NfcDevice::GetRegisterInfo(NFP::RegisterInfo& register_info) const { | |||
| 681 | return ResultRegistrationIsNotInitialized; | 680 | return ResultRegistrationIsNotInitialized; |
| 682 | } | 681 | } |
| 683 | 682 | ||
| 684 | Service::Mii::MiiManager manager; | 683 | Mii::CharInfo char_info{}; |
| 684 | Mii::StoreData store_data{}; | ||
| 685 | tag_data.owner_mii.BuildToStoreData(store_data); | ||
| 686 | char_info.SetFromStoreData(store_data); | ||
| 687 | |||
| 685 | const auto& settings = tag_data.settings; | 688 | const auto& settings = tag_data.settings; |
| 686 | 689 | ||
| 687 | // TODO: Validate this data | 690 | // TODO: Validate this data |
| 688 | register_info = { | 691 | register_info = { |
| 689 | .mii_char_info = manager.ConvertV3ToCharInfo(tag_data.owner_mii), | 692 | .mii_char_info = char_info, |
| 690 | .creation_date = settings.init_date.GetWriteDate(), | 693 | .creation_date = settings.init_date.GetWriteDate(), |
| 691 | .amiibo_name = GetAmiiboName(settings), | 694 | .amiibo_name = GetAmiiboName(settings), |
| 692 | .font_region = settings.settings.font_region, | 695 | .font_region = settings.settings.font_region, |
| @@ -825,8 +828,11 @@ Result NfcDevice::SetRegisterInfoPrivate(const NFP::RegisterInfoPrivate& registe | |||
| 825 | return ResultWrongDeviceState; | 828 | return ResultWrongDeviceState; |
| 826 | } | 829 | } |
| 827 | 830 | ||
| 828 | Service::Mii::MiiManager manager; | 831 | Service::Mii::StoreData store_data{}; |
| 829 | const auto mii = manager.BuildBase(Mii::Gender::Male); | 832 | Service::Mii::NfpStoreDataExtension extension{}; |
| 833 | store_data.BuildBase(Mii::Gender::Male); | ||
| 834 | extension.SetFromStoreData(store_data); | ||
| 835 | |||
| 830 | auto& settings = tag_data.settings; | 836 | auto& settings = tag_data.settings; |
| 831 | 837 | ||
| 832 | if (tag_data.settings.settings.amiibo_initialized == 0) { | 838 | if (tag_data.settings.settings.amiibo_initialized == 0) { |
| @@ -835,8 +841,8 @@ Result NfcDevice::SetRegisterInfoPrivate(const NFP::RegisterInfoPrivate& registe | |||
| 835 | } | 841 | } |
| 836 | 842 | ||
| 837 | SetAmiiboName(settings, register_info.amiibo_name); | 843 | SetAmiiboName(settings, register_info.amiibo_name); |
| 838 | tag_data.owner_mii = manager.BuildFromStoreData(mii); | 844 | tag_data.owner_mii.BuildFromStoreData(store_data); |
| 839 | tag_data.mii_extension = manager.SetFromStoreData(mii); | 845 | tag_data.mii_extension = extension; |
| 840 | tag_data.unknown = 0; | 846 | tag_data.unknown = 0; |
| 841 | tag_data.unknown2 = {}; | 847 | tag_data.unknown2 = {}; |
| 842 | settings.country_code_id = 0; | 848 | settings.country_code_id = 0; |
| @@ -1453,7 +1459,7 @@ void NfcDevice::UpdateRegisterInfoCrc() { | |||
| 1453 | 1459 | ||
| 1454 | void NfcDevice::BuildAmiiboWithoutKeys(NFP::NTAG215File& stubbed_tag_data, | 1460 | void NfcDevice::BuildAmiiboWithoutKeys(NFP::NTAG215File& stubbed_tag_data, |
| 1455 | const NFP::EncryptedNTAG215File& encrypted_file) const { | 1461 | const NFP::EncryptedNTAG215File& encrypted_file) const { |
| 1456 | Service::Mii::MiiManager manager; | 1462 | Service::Mii::StoreData store_data{}; |
| 1457 | auto& settings = stubbed_tag_data.settings; | 1463 | auto& settings = stubbed_tag_data.settings; |
| 1458 | 1464 | ||
| 1459 | stubbed_tag_data = NFP::AmiiboCrypto::NfcDataToEncodedData(encrypted_file); | 1465 | stubbed_tag_data = NFP::AmiiboCrypto::NfcDataToEncodedData(encrypted_file); |
| @@ -1467,7 +1473,8 @@ void NfcDevice::BuildAmiiboWithoutKeys(NFP::NTAG215File& stubbed_tag_data, | |||
| 1467 | SetAmiiboName(settings, {'y', 'u', 'z', 'u', 'A', 'm', 'i', 'i', 'b', 'o'}); | 1473 | SetAmiiboName(settings, {'y', 'u', 'z', 'u', 'A', 'm', 'i', 'i', 'b', 'o'}); |
| 1468 | settings.settings.font_region.Assign(0); | 1474 | settings.settings.font_region.Assign(0); |
| 1469 | settings.init_date = GetAmiiboDate(GetCurrentPosixTime()); | 1475 | settings.init_date = GetAmiiboDate(GetCurrentPosixTime()); |
| 1470 | stubbed_tag_data.owner_mii = manager.BuildFromStoreData(manager.BuildBase(Mii::Gender::Male)); | 1476 | store_data.BuildBase(Mii::Gender::Male); |
| 1477 | stubbed_tag_data.owner_mii.BuildFromStoreData(store_data); | ||
| 1471 | 1478 | ||
| 1472 | // Admin info | 1479 | // Admin info |
| 1473 | settings.settings.amiibo_initialized.Assign(1); | 1480 | settings.settings.amiibo_initialized.Assign(1); |
diff --git a/src/core/hle/service/nfp/nfp_types.h b/src/core/hle/service/nfp/nfp_types.h index aed12a7f8..f96d21220 100644 --- a/src/core/hle/service/nfp/nfp_types.h +++ b/src/core/hle/service/nfp/nfp_types.h | |||
| @@ -6,7 +6,9 @@ | |||
| 6 | #include <array> | 6 | #include <array> |
| 7 | 7 | ||
| 8 | #include "common/swap.h" | 8 | #include "common/swap.h" |
| 9 | #include "core/hle/service/mii/types.h" | 9 | #include "core/hle/service/mii/types/char_info.h" |
| 10 | #include "core/hle/service/mii/types/store_data.h" | ||
| 11 | #include "core/hle/service/mii/types/ver3_store_data.h" | ||
| 10 | #include "core/hle/service/nfc/nfc_types.h" | 12 | #include "core/hle/service/nfc/nfc_types.h" |
| 11 | 13 | ||
| 12 | namespace Service::NFP { | 14 | namespace Service::NFP { |
| @@ -322,7 +324,7 @@ static_assert(sizeof(RegisterInfo) == 0x100, "RegisterInfo is an invalid size"); | |||
| 322 | 324 | ||
| 323 | // This is nn::nfp::RegisterInfoPrivate | 325 | // This is nn::nfp::RegisterInfoPrivate |
| 324 | struct RegisterInfoPrivate { | 326 | struct RegisterInfoPrivate { |
| 325 | Service::Mii::MiiStoreData mii_store_data; | 327 | Service::Mii::StoreData mii_store_data; |
| 326 | WriteDate creation_date; | 328 | WriteDate creation_date; |
| 327 | AmiiboName amiibo_name; | 329 | AmiiboName amiibo_name; |
| 328 | u8 font_region; | 330 | u8 font_region; |
diff --git a/src/yuzu/applets/qt_amiibo_settings.cpp b/src/yuzu/applets/qt_amiibo_settings.cpp index 4988fcc83..b457a736a 100644 --- a/src/yuzu/applets/qt_amiibo_settings.cpp +++ b/src/yuzu/applets/qt_amiibo_settings.cpp | |||
| @@ -160,7 +160,8 @@ void QtAmiiboSettingsDialog::LoadAmiiboData() { | |||
| 160 | } | 160 | } |
| 161 | 161 | ||
| 162 | const auto amiibo_name = std::string(register_info.amiibo_name.data()); | 162 | const auto amiibo_name = std::string(register_info.amiibo_name.data()); |
| 163 | const auto owner_name = Common::UTF16ToUTF8(register_info.mii_char_info.name.data()); | 163 | const auto owner_name = |
| 164 | Common::UTF16ToUTF8(register_info.mii_char_info.GetNickname().data.data()); | ||
| 164 | const auto creation_date = | 165 | const auto creation_date = |
| 165 | QDate(register_info.creation_date.year, register_info.creation_date.month, | 166 | QDate(register_info.creation_date.year, register_info.creation_date.month, |
| 166 | register_info.creation_date.day); | 167 | register_info.creation_date.day); |