From bce6ec10e476da96a69a4722bad61ea5b073b8d2 Mon Sep 17 00:00:00 2001 From: Tian Liao Date: Mon, 28 Oct 2024 16:55:52 +0800 Subject: [PATCH] connect ui --- src/CalcViewModel/ApplicationViewModel.cpp | 494 +----------------- src/CalcViewModel/ApplicationViewModel.h | 5 +- src/CalcViewModel/Snapshots.cpp | 19 +- .../StandardCalculatorViewModel.cpp | 122 ++--- .../StandardCalculatorViewModel.h | 39 +- src/Calculator/Utils/JsonUtils.cs | 8 +- src/Calculator/Views/MainPage.xaml.cs | 50 +- 7 files changed, 78 insertions(+), 659 deletions(-) diff --git a/src/CalcViewModel/ApplicationViewModel.cpp b/src/CalcViewModel/ApplicationViewModel.cpp index c8b2153e..f2835fb4 100644 --- a/src/CalcViewModel/ApplicationViewModel.cpp +++ b/src/CalcViewModel/ApplicationViewModel.cpp @@ -37,446 +37,6 @@ namespace { StringReference CategoriesPropertyName(L"Categories"); StringReference ClearMemoryVisibilityPropertyName(L"ClearMemoryVisibility"); - - // struct SnapshotHelper - //{ - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const ApplicationSnapshot& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // jsonObject->SetNamedValue(L"SnapshotVersion", Windows::Data::Json::JsonValue::CreateNumberValue(value.SnapshotVersion)); - // jsonObject->SetNamedValue(L"Mode", Windows::Data::Json::JsonValue::CreateNumberValue(value.Mode)); - // if (value.StandardCalc.has_value()) - // { - // jsonObject->SetNamedValue(L"StandardCalculatorSnapshot", SaveSnapshotToJson(*value.StandardCalc)); - // } - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const StandardCalculatorSnapshot& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // jsonObject->SetNamedValue(L"CalculatorManagerSnapshot", SaveSnapshotToJson(value.CalcManager)); - // jsonObject->SetNamedValue(L"PrimaryDisplay", SaveSnapshotToJson(value.PrimaryDisplay)); - // if (value.ExpressionDisplay.has_value()) - // { - // jsonObject->SetNamedValue(L"ExpressionDisplay", SaveSnapshotToJson(*value.ExpressionDisplay)); - // } - // auto commandsJsonArray = ref new Windows::Data::Json::JsonArray(); - // for (const auto& command : value.DisplayCommands) - // { - // commandsJsonArray->Append(SaveSnapshotToJson(command)); - // } - // jsonObject->SetNamedValue(L"DisplayCommands", commandsJsonArray); - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const PrimaryDisplaySnapshot& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // jsonObject->SetNamedValue(L"DisplayValue", Windows::Data::Json::JsonValue::CreateStringValue(value.DisplayValue)); - // jsonObject->SetNamedValue(L"IsError", Windows::Data::Json::JsonValue::CreateBooleanValue(value.IsError)); - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const ExpressionDisplaySnapshot& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // auto tokensJsonArray = ref new Windows::Data::Json::JsonArray(); - // for (const auto& token : value.Tokens) - // { - // auto tokenJsonArray = ref new Windows::Data::Json::JsonArray(); - // tokenJsonArray->Append(Windows::Data::Json::JsonValue::CreateStringValue(ref new Platform::String(token.first.c_str()))); - // tokenJsonArray->Append(Windows::Data::Json::JsonValue::CreateNumberValue(token.second)); - // tokensJsonArray->Append(tokenJsonArray); - // } - // jsonObject->SetNamedValue(L"Tokens", tokensJsonArray); - - // auto commandsJsonArray = ref new Windows::Data::Json::JsonArray(); - // for (const auto& command : value.Commands) - // { - // commandsJsonArray->Append(SaveSnapshotToJson(command)); - // } - // jsonObject->SetNamedValue(L"Commands", commandsJsonArray); - - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const CalculatorManagerSnapshot& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // if (value.HistoryItems.has_value()) - // { - // auto historyJsonArray = ref new Windows::Data::Json::JsonArray(); - // for (const auto& item : *value.HistoryItems) - // { - // historyJsonArray->Append(SaveSnapshotToJson(*item)); - // } - // jsonObject->SetNamedValue(L"HistoryItems", historyJsonArray); - // } - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const CalculationManager::HISTORYITEM& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // jsonObject->SetNamedValue(L"Expression", Windows::Data::Json::JsonValue::CreateStringValue(ref new - // Platform::String(value.historyItemVector.expression.c_str()))); jsonObject->SetNamedValue(L"Result", - // Windows::Data::Json::JsonValue::CreateStringValue(ref new Platform::String(value.historyItemVector.result.c_str()))); - - // auto tokensJsonArray = ref new Windows::Data::Json::JsonArray(); - // for (const auto& token : *value.historyItemVector.spTokens) - // { - // auto tokenJsonArray = ref new Windows::Data::Json::JsonArray(); - // tokenJsonArray->Append(Windows::Data::Json::JsonValue::CreateStringValue(ref new Platform::String(token.first.c_str()))); - // tokenJsonArray->Append(Windows::Data::Json::JsonValue::CreateNumberValue(token.second)); - // tokensJsonArray->Append(tokenJsonArray); - // } - // jsonObject->SetNamedValue(L"Tokens", tokensJsonArray); - - // auto commandsJsonArray = ref new Windows::Data::Json::JsonArray(); - // for (const auto& command : *value.historyItemVector.spCommands) - // { - // commandsJsonArray->Append(SaveSnapshotToJson(command)); - // } - // jsonObject->SetNamedValue(L"Commands", commandsJsonArray); - - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const std::shared_ptr& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // auto opndCommand = dynamic_cast(value.get()); - // if (opndCommand != nullptr) - // { - // jsonObject = SaveSnapshotToJson(*opndCommand); - // } - // auto unaryCommand = dynamic_cast(value.get()); - // if (unaryCommand != nullptr) - // { - // jsonObject = SaveSnapshotToJson(*unaryCommand); - // } - // auto binaryCommand = dynamic_cast(value.get()); - // if (binaryCommand != nullptr) - // { - // jsonObject = SaveSnapshotToJson(*binaryCommand); - // } - // auto parenthesesCommand = dynamic_cast(value.get()); - // if (parenthesesCommand != nullptr) - // { - // jsonObject = SaveSnapshotToJson(*parenthesesCommand); - // } - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const COpndCommand& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // jsonObject->SetNamedValue(L"CommandType", Windows::Data::Json::JsonValue::CreateNumberValue(static_cast(value.GetCommandType()))); - // jsonObject->SetNamedValue(L"IsNegative", Windows::Data::Json::JsonValue::CreateBooleanValue(value.IsNegative())); - // jsonObject->SetNamedValue(L"IsDecimalPresent", Windows::Data::Json::JsonValue::CreateBooleanValue(value.IsDecimalPresent())); - // jsonObject->SetNamedValue(L"IsSciFmt", Windows::Data::Json::JsonValue::CreateBooleanValue(value.IsSciFmt())); - // auto commandsJsonArray = ref new Windows::Data::Json::JsonArray(); - // for (const auto& command : *value.GetCommands()) - // { - // commandsJsonArray->Append(Windows::Data::Json::JsonValue::CreateNumberValue(command)); - // } - // jsonObject->SetNamedValue(L"Commands", commandsJsonArray); - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const CUnaryCommand& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // jsonObject->SetNamedValue(L"CommandType", Windows::Data::Json::JsonValue::CreateNumberValue(static_cast(value.GetCommandType()))); - // auto commandsJsonArray = ref new Windows::Data::Json::JsonArray(); - // for (const auto& command : *value.GetCommands()) - // { - // commandsJsonArray->Append(Windows::Data::Json::JsonValue::CreateNumberValue(command)); - // } - // jsonObject->SetNamedValue(L"Commands", commandsJsonArray); - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const CBinaryCommand& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // jsonObject->SetNamedValue(L"CommandType", Windows::Data::Json::JsonValue::CreateNumberValue(static_cast(value.GetCommandType()))); - // jsonObject->SetNamedValue(L"Command", Windows::Data::Json::JsonValue::CreateNumberValue(value.GetCommand())); - // return jsonObject; - // } - - // static Windows::Data::Json::JsonObject ^ SaveSnapshotToJson(const CParentheses& value) - // { - // auto jsonObject = ref new Windows::Data::Json::JsonObject(); - // jsonObject->SetNamedValue(L"CommandType", Windows::Data::Json::JsonValue::CreateNumberValue(static_cast(value.GetCommandType()))); - // jsonObject->SetNamedValue(L"Command", Windows::Data::Json::JsonValue::CreateNumberValue(value.GetCommand())); - // return jsonObject; - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // ApplicationSnapshot applicationSnapshot; - // applicationSnapshot.SnapshotVersion = static_cast(jsonObject->GetNamedNumber(L"SnapshotVersion")); - // if (applicationSnapshot.SnapshotVersion > SnapshotVersion) - // { - // return; - // } - // applicationSnapshot.Mode = static_cast(jsonObject->GetNamedNumber(L"Mode")); - // if (jsonObject->HasKey(L"StandardCalculatorSnapshot")) - // { - // std::optional standardCalculatorSnapshot; - // RestoreJsonToSnapshot(jsonObject->GetNamedObject(L"StandardCalculatorSnapshot"), standardCalculatorSnapshot); - // if (standardCalculatorSnapshot.has_value()) - // { - // applicationSnapshot.StandardCalc = std::move(*standardCalculatorSnapshot); - // } - // else - // { - // return; - // } - // } - // value = std::move(applicationSnapshot); - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // StandardCalculatorSnapshot standardCalculatorSnapshot; - // std::optional calcManagerSnapshot; - // RestoreJsonToSnapshot(jsonObject->GetNamedObject(L"CalculatorManagerSnapshot"), calcManagerSnapshot); - // if (calcManagerSnapshot.has_value()) - // { - // standardCalculatorSnapshot.CalcManager = std::move(*calcManagerSnapshot); - // } - // else - // { - // return; - // } - // std::optional primaryDisplaySnapshot; - // RestoreJsonToSnapshot(jsonObject->GetNamedObject(L"PrimaryDisplay"), primaryDisplaySnapshot); - // if (primaryDisplaySnapshot.has_value()) - // { - // standardCalculatorSnapshot.PrimaryDisplay = std::move(*primaryDisplaySnapshot); - // } - // else - // { - // return; - // } - // if (jsonObject->HasKey(L"ExpressionDisplay")) - // { - // std::optional expressionDisplaySnapshot; - // RestoreJsonToSnapshot(jsonObject->GetNamedObject(L"ExpressionDisplay"), expressionDisplaySnapshot); - // if (expressionDisplaySnapshot.has_value()) - // { - // standardCalculatorSnapshot.ExpressionDisplay = std::move(*expressionDisplaySnapshot); - // } - // else - // { - // return; - // } - // } - // standardCalculatorSnapshot.DisplayCommands = RestoreExpressionCommandsFromJsonArray(jsonObject->GetNamedArray(L"DisplayCommands")); - // value = std::move(standardCalculatorSnapshot); - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // value = PrimaryDisplaySnapshot{ jsonObject->GetNamedString(L"DisplayValue"), jsonObject->GetNamedBoolean(L"IsError") }; - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // ExpressionDisplaySnapshot expressionDisplaySnapshot; - // expressionDisplaySnapshot.Tokens = RestoreExpressionTokensFromJsonArray(jsonObject->GetNamedArray(L"Tokens")); - // if (expressionDisplaySnapshot.Tokens.empty()) - // { - // return; - // } - // expressionDisplaySnapshot.Commands = RestoreExpressionCommandsFromJsonArray(jsonObject->GetNamedArray(L"Commands")); - // if (expressionDisplaySnapshot.Commands.empty()) - // { - // return; - // } - // value = std::move(expressionDisplaySnapshot); - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // CalculatorManagerSnapshot calcManagerSnapshot; - // if (jsonObject->HasKey(L"HistoryItems")) - // { - // std::vector> historyItems; - // auto historyJsonArray = jsonObject->GetNamedArray(L"HistoryItems"); - // for (uint32_t i = 0; i < historyJsonArray->Size; ++i) - // { - // std::optional historyItem; - // RestoreJsonToSnapshot(historyJsonArray->GetObjectAt(i), historyItem); - // if (historyItem.has_value()) - // { - // historyItems.push_back(std::make_shared(*historyItem)); - // } - // else - // { - // return; - // } - // } - // calcManagerSnapshot.HistoryItems = std::move(historyItems); - // } - // value = std::move(calcManagerSnapshot); - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // CalculationManager::HISTORYITEM historyItem; - // historyItem.historyItemVector.expression = std::wstring(jsonObject->GetNamedString(L"Expression")->Data()); - // historyItem.historyItemVector.result = std::wstring(jsonObject->GetNamedString(L"Result")->Data()); - // historyItem.historyItemVector.spTokens = - // std::make_shared>>(RestoreExpressionTokensFromJsonArray(jsonObject->GetNamedArray(L"Tokens"))); - // if (historyItem.historyItemVector.spTokens->empty()) - // { - // return; - // } - // historyItem.historyItemVector.spCommands = std::make_shared>>( - // RestoreExpressionCommandsFromJsonArray(jsonObject->GetNamedArray(L"Commands"))); - // if (historyItem.historyItemVector.spCommands->empty()) - // { - // return; - // } - // value = std::move(historyItem); - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional>& value) - // { - // auto commandType = static_cast(jsonObject->GetNamedNumber(L"CommandType")); - // switch (commandType) - // { - // case CalculationManager::CommandType::OperandCommand: - // { - // std::optional opndCommand; - // RestoreJsonToSnapshot(jsonObject, opndCommand); - // if (opndCommand.has_value()) - // { - // value = std::make_shared(*opndCommand); - // } - // break; - // } - // case CalculationManager::CommandType::UnaryCommand: - // { - // std::optional unaryCommand; - // RestoreJsonToSnapshot(jsonObject, unaryCommand); - // if (unaryCommand.has_value()) - // { - // value = std::make_shared(*unaryCommand); - // } - // break; - // } - // case CalculationManager::CommandType::BinaryCommand: - // { - // std::optional binaryCommand; - // RestoreJsonToSnapshot(jsonObject, binaryCommand); - // if (binaryCommand.has_value()) - // { - // value = std::make_shared(*binaryCommand); - // } - // break; - // } - // case CalculationManager::CommandType::Parentheses: - // { - // std::optional parenthesesCommand; - // RestoreJsonToSnapshot(jsonObject, parenthesesCommand); - // if (parenthesesCommand.has_value()) - // { - // value = std::make_shared(*parenthesesCommand); - // } - // break; - // } - // default: - // throw std::logic_error{ "c8cba597-dfec-447a-bd1c-e78a9ffaad95" }; - // } - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // auto isNegative = jsonObject->GetNamedBoolean(L"IsNegative"); - // auto isDecimalPresent = jsonObject->GetNamedBoolean(L"IsDecimalPresent"); - // auto isSciFmt = jsonObject->GetNamedBoolean(L"IsSciFmt"); - // std::vector commands; - // auto commandsJsonArray = jsonObject->GetNamedArray(L"Commands"); - // for (uint32_t i = 0; i < commandsJsonArray->Size; ++i) - // { - // commands.push_back(static_cast(commandsJsonArray->GetNumberAt(i))); - // } - // value = COpndCommand(std::make_shared>(std::move(commands)), isNegative, isDecimalPresent, isSciFmt); - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // std::vector commands; - // auto commandsJsonArray = jsonObject->GetNamedArray(L"Commands"); - // if (commandsJsonArray->Size == 1) - // { - // value = CUnaryCommand(static_cast(commandsJsonArray->GetNumberAt(0))); - // } - // else if (commandsJsonArray->Size == 2) - // { - // value = CUnaryCommand(static_cast(commandsJsonArray->GetNumberAt(0)), static_cast(commandsJsonArray->GetNumberAt(1))); - // } - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // value = CBinaryCommand(static_cast(jsonObject->GetNamedNumber(L"Command"))); - // } - - // static void RestoreJsonToSnapshot(Windows::Data::Json::JsonObject ^ jsonObject, std::optional& value) - // { - // value = CParentheses(static_cast(jsonObject->GetNamedNumber(L"Command"))); - // } - - // static std::vector> RestoreExpressionTokensFromJsonArray(Windows::Data::Json::JsonArray ^ jsonArray) - // { - // std::vector> tokens; - // for (uint32_t i = 0; i < jsonArray->Size; ++i) - // { - // auto tokenJsonArray = jsonArray->GetArrayAt(i); - // if (tokenJsonArray->Size == 2 && tokenJsonArray->GetAt(0)->ValueType == Windows::Data::Json::JsonValueType::String - // && tokenJsonArray->GetAt(1)->ValueType == Windows::Data::Json::JsonValueType::Number) - // { - // tokens.emplace_back(std::wstring(tokenJsonArray->GetAt(0)->GetString()->Data()), static_cast(tokenJsonArray->GetAt(1)->GetNumber())); - // } - // else - // { - // return {}; - // } - // } - // return tokens; - // } - - // static std::vector> RestoreExpressionCommandsFromJsonArray(Windows::Data::Json::JsonArray ^ jsonArray) - // { - // std::vector> commands; - // for (uint32_t i = 0; i < jsonArray->Size; ++i) - // { - // std::optional> command; - // RestoreJsonToSnapshot(jsonArray->GetObjectAt(i), command); - // if (command.has_value()) - // { - // commands.push_back(*command); - // } - // else - // { - // return {}; - // } - // } - // return commands; - // } - - // static bool IsJsonParsingException(Platform::COMException ^ e) - // { - // return e->HResult == WEB_E_JSON_VALUE_NOT_FOUND || e->HResult == E_ILLEGAL_METHOD_CALL; - // } - //}; } ApplicationViewModel::ApplicationViewModel() @@ -556,10 +116,13 @@ void ApplicationViewModel::Initialize(ViewMode mode) } } -void ApplicationViewModel::Initialize(CalculatorApp::ViewModel::Snapshot::ApplicationSnapshot ^ snapshot) +void ApplicationViewModel::RestoreFromSnapshot(CalculatorApp::ViewModel::Snapshot::ApplicationSnapshot ^ snapshot) { - m_CalculatorViewModel = ref new StandardCalculatorViewModel(snapshot->StandardCalculator); - Initialize(static_cast(snapshot->Mode)); + Mode = static_cast(snapshot->Mode); + if (snapshot->StandardCalculator != nullptr) + { + m_CalculatorViewModel->Snapshot = snapshot->StandardCalculator; + } } bool ApplicationViewModel::TryRecoverFromNavigationModeFailure() @@ -728,48 +291,3 @@ void ApplicationViewModel::SetDisplayNormalAlwaysOnTopOption() DisplayNormalAlwaysOnTopOption = m_mode == ViewMode::Standard && ApplicationView::GetForCurrentView()->IsViewModeSupported(ApplicationViewMode::CompactOverlay) && !IsAlwaysOnTop; } - -// Windows::Data::Json::JsonObject ^ ApplicationViewModel::SaveApplicationSnapshot() -//{ -// ApplicationSnapshot applicationSnapshot; -// applicationSnapshot.SnapshotVersion = SnapshotHelper::SnapshotVersion; -// applicationSnapshot.Mode = static_cast(Mode); -// if (m_CalculatorViewModel != nullptr && m_mode == ViewMode::Standard) -// { -// // Standard calculator is the only supported mode so far. -// applicationSnapshot.StandardCalc = m_CalculatorViewModel->GetStandardCalculatorSnapshot(); -// } -// return SnapshotHelper::SaveSnapshotToJson(applicationSnapshot); -// } -// -// bool ApplicationViewModel::TryRestoreFromSnapshot(Windows::Data::Json::JsonObject ^ jsonObject) -//{ -// std::optional applicationSnapshot; -// try -// { -// SnapshotHelper::RestoreJsonToSnapshot(jsonObject, applicationSnapshot); -// } -// catch (Platform::COMException ^ e) -// { -// if (SnapshotHelper::IsJsonParsingException(e)) -// { -// return false; -// } -// throw; -// } -// -// if (applicationSnapshot.has_value()) -// { -// Mode = static_cast(applicationSnapshot->Mode); -// if (applicationSnapshot->StandardCalc.has_value()) -// { -// if (m_CalculatorViewModel == nullptr) -// { -// m_CalculatorViewModel = ref new StandardCalculatorViewModel(); -// } -// m_CalculatorViewModel->SetStandardCalculatorSnapshot(applicationSnapshot->StandardCalc.value()); -// } -// return true; -// } -// return false; -// } diff --git a/src/CalcViewModel/ApplicationViewModel.h b/src/CalcViewModel/ApplicationViewModel.h index 1cb2f2df..afb67eb6 100644 --- a/src/CalcViewModel/ApplicationViewModel.h +++ b/src/CalcViewModel/ApplicationViewModel.h @@ -18,9 +18,8 @@ namespace CalculatorApp public: ApplicationViewModel(); - [Windows::Foundation::Metadata::DefaultOverload] void Initialize(CalculatorApp::ViewModel::Common::ViewMode mode); // Use for first init, use deserialize for rehydration - void Initialize(CalculatorApp::ViewModel::Snapshot::ApplicationSnapshot^ snapshot); + void RestoreFromSnapshot(CalculatorApp::ViewModel::Snapshot::ApplicationSnapshot^ snapshot); OBSERVABLE_OBJECT(); OBSERVABLE_PROPERTY_RW(StandardCalculatorViewModel ^, CalculatorViewModel); @@ -104,8 +103,6 @@ namespace CalculatorApp void ToggleAlwaysOnTop(float width, float height); - //bool TryRestoreFromSnapshot(Windows::Data::Json::JsonObject ^ jsonObject); - private: bool TryRecoverFromNavigationModeFailure(); diff --git a/src/CalcViewModel/Snapshots.cpp b/src/CalcViewModel/Snapshots.cpp index 404cce36..69c082ad 100644 --- a/src/CalcViewModel/Snapshots.cpp +++ b/src/CalcViewModel/Snapshots.cpp @@ -123,7 +123,7 @@ namespace CalculatorApp::ViewModel::Snapshot CalcManagerHistoryToken::CalcManagerHistoryToken() { - OpCodeName = nullptr; + OpCodeName = ref new Platform::String(); CommandIndex = 0; } @@ -224,7 +224,22 @@ namespace CalculatorApp::ViewModel::Snapshot std::vector> ToUnderlying(Windows::Foundation::Collections::IVector ^ items) { - return {}; // TODO + std::vector> result; + for (CalcManagerHistoryItem ^ item : items) + { + CalculationManager::HISTORYITEMVECTOR nativeItem; + nativeItem.spTokens = std::make_shared>>(); + for (CalcManagerHistoryToken ^ token : item->Tokens) + { + nativeItem.spTokens->push_back(std::make_pair(token->OpCodeName->Data(), token->CommandIndex)); + } + nativeItem.spCommands = std::make_shared>>(ToUnderlying(item->Commands)); + nativeItem.expression = item->Expression->Data(); + nativeItem.result = item->Result->Data(); + auto spItem = std::make_shared(CalculationManager::HISTORYITEM{ std::move(nativeItem) }); + result.push_back(std::move(std::move(spItem))); + } + return result; } std::vector> ToUnderlying(Windows::Foundation::Collections::IVector ^ commands) diff --git a/src/CalcViewModel/StandardCalculatorViewModel.cpp b/src/CalcViewModel/StandardCalculatorViewModel.cpp index 9d773974..a1cee93b 100644 --- a/src/CalcViewModel/StandardCalculatorViewModel.cpp +++ b/src/CalcViewModel/StandardCalculatorViewModel.cpp @@ -115,7 +115,7 @@ namespace CalculatorResourceKeys StringReference DisplayCopied(L"Display_Copied"); } -StandardCalculatorViewModel::StandardCalculatorViewModel(CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ snapshot) +StandardCalculatorViewModel::StandardCalculatorViewModel() : m_DisplayValue(L"0") , m_DecimalDisplayValue(L"0") , m_HexDisplayValue(L"0") @@ -183,42 +183,6 @@ StandardCalculatorViewModel::StandardCalculatorViewModel(CalculatorApp::ViewMode IsNegateEnabled = true; IsDecimalEnabled = true; AreProgrammerRadixOperatorsVisible = false; - - if (snapshot != nullptr) - { - if (snapshot->CalcManager->HistoryItems != nullptr) - { - m_standardCalculatorManager.SetHistoryItems(ToUnderlying(snapshot->CalcManager->HistoryItems)); - } - - std::vector commands; - if (snapshot->ExpressionDisplay != nullptr && snapshot->ExpressionDisplay->Tokens->GetAt(snapshot->ExpressionDisplay->Tokens->Size)) - { - commands = GetCommandsFromExpressionCommands(ToUnderlying(snapshot->ExpressionDisplay->Commands)); - } - if (commands.empty() && snapshot->DisplayCommands->Size > 0) - { - commands = GetCommandsFromExpressionCommands(ToUnderlying(snapshot->DisplayCommands)); - } - for (auto cmd : commands) - { - m_standardCalculatorManager.SendCommand(static_cast(cmd)); - } - if (snapshot->ExpressionDisplay != nullptr) - { - using RawTokenCollection = std::vector>; - RawTokenCollection rawTokens; - for (CalculatorApp::ViewModel::Snapshot::CalcManagerHistoryToken ^ token : snapshot->ExpressionDisplay->Tokens) - { - rawTokens.push_back(std::pair{ token->OpCodeName->Data(), token->CommandIndex }); - } - snapshot->ExpressionDisplay->Tokens; - SetExpressionDisplay( - std::make_shared(rawTokens), - std::make_shared>>(ToUnderlying(snapshot->ExpressionDisplay->Commands))); - } - SetPrimaryDisplay(snapshot->PrimaryDisplay->DisplayValue, snapshot->PrimaryDisplay->IsError); - } } String ^ StandardCalculatorViewModel::LocalizeDisplayValue(_In_ wstring const& displayValue) @@ -1823,7 +1787,7 @@ void StandardCalculatorViewModel::SetBitshiftRadioButtonCheckedAnnouncement(Plat Announcement = CalculatorAnnouncement::GetBitShiftRadioButtonCheckedAnnouncement(announcement); } -CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ StandardCalculatorViewModel::GetSnapshot() const +CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ StandardCalculatorViewModel::Snapshot::get() { auto result = ref new CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot(); result->CalcManager = ref new CalculatorApp::ViewModel::Snapshot::CalcManagerSnapshot(m_standardCalculatorManager); @@ -1837,49 +1801,39 @@ CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ StandardCalcula return result; } -// StandardCalculatorSnapshot StandardCalculatorViewModel::GetStandardCalculatorSnapshot() const -//{ -// StandardCalculatorSnapshot snapshot; -// auto& historyItems = m_standardCalculatorManager.GetHistoryItems(); -// if (!historyItems.empty()) -// { -// snapshot.CalcManager.HistoryItems = std::move(historyItems); -// } -// snapshot.PrimaryDisplay = PrimaryDisplaySnapshot{ m_DisplayValue, m_IsInError }; -// if (!m_tokens->empty() && !m_commands->empty()) -// { -// snapshot.ExpressionDisplay = { *m_tokens, *m_commands }; -// } -// snapshot.DisplayCommands = m_standardCalculatorManager.GetDisplayCommandsSnapshot(); -// return snapshot; -// } -// -// void StandardCalculatorViewModel::SetStandardCalculatorSnapshot(const StandardCalculatorSnapshot& snapshot) -//{ -// if (snapshot.CalcManager.HistoryItems.has_value()) -// { -// m_standardCalculatorManager.SetHistoryItems(snapshot.CalcManager.HistoryItems.value()); -// } -// -// std::vector commands; -// if (snapshot.ExpressionDisplay.has_value() && snapshot.ExpressionDisplay->Tokens.back().first == L"=") -// { -// commands = GetCommandsFromExpressionCommands(snapshot.ExpressionDisplay->Commands); -// } -// if (commands.empty() && !snapshot.DisplayCommands.empty()) -// { -// commands = GetCommandsFromExpressionCommands(snapshot.DisplayCommands); -// } -// for (const auto& command : commands) -// { -// m_standardCalculatorManager.SendCommand(static_cast(command)); -// } -// -// if (snapshot.ExpressionDisplay.has_value()) -// { -// SetExpressionDisplay( -// std::make_shared>>(snapshot.ExpressionDisplay->Tokens), -// std::make_shared>>(snapshot.ExpressionDisplay->Commands)); -// } -// SetPrimaryDisplay(snapshot.PrimaryDisplay.DisplayValue, snapshot.PrimaryDisplay.IsError); -// } +void CalculatorApp::ViewModel::StandardCalculatorViewModel::Snapshot::set(CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ snapshot) +{ + assert(snapshot != nullptr); + m_standardCalculatorManager.Reset(); + if (snapshot->CalcManager->HistoryItems != nullptr) + { + m_standardCalculatorManager.SetHistoryItems(ToUnderlying(snapshot->CalcManager->HistoryItems)); + } + + std::vector commands; + if (snapshot->ExpressionDisplay != nullptr && snapshot->ExpressionDisplay->Tokens->GetAt(snapshot->ExpressionDisplay->Tokens->Size - 1)->OpCodeName == L"=") + { + commands = GetCommandsFromExpressionCommands(ToUnderlying(snapshot->ExpressionDisplay->Commands)); + } + if (commands.empty() && snapshot->DisplayCommands->Size > 0) + { + commands = GetCommandsFromExpressionCommands(ToUnderlying(snapshot->DisplayCommands)); + } + for (auto cmd : commands) + { + m_standardCalculatorManager.SendCommand(static_cast(cmd)); + } + if (snapshot->ExpressionDisplay != nullptr) + { + using RawTokenCollection = std::vector>; + RawTokenCollection rawTokens; + for (CalculatorApp::ViewModel::Snapshot::CalcManagerHistoryToken ^ token : snapshot->ExpressionDisplay->Tokens) + { + rawTokens.push_back(std::pair{ token->OpCodeName->Data(), token->CommandIndex }); + } + SetExpressionDisplay( + std::make_shared(rawTokens), + std::make_shared>>(ToUnderlying(snapshot->ExpressionDisplay->Commands))); + } + SetPrimaryDisplay(snapshot->PrimaryDisplay->DisplayValue, snapshot->PrimaryDisplay->IsError); +} diff --git a/src/CalcViewModel/StandardCalculatorViewModel.h b/src/CalcViewModel/StandardCalculatorViewModel.h index 8026e709..65cf7eb6 100644 --- a/src/CalcViewModel/StandardCalculatorViewModel.h +++ b/src/CalcViewModel/StandardCalculatorViewModel.h @@ -37,31 +37,6 @@ namespace CalculatorApp bool canSendNegate; }; - // struct CalculatorManagerSnapshot - //{ - // std::optional>> HistoryItems; - // }; - - // struct PrimaryDisplaySnapshot - //{ - // Platform::String ^ DisplayValue; - // bool IsError = false; - // }; - - // struct ExpressionDisplaySnapshot - //{ - // std::vector> Tokens; - // std::vector> Commands; - // }; - - // struct StandardCalculatorSnapshot - //{ - // CalculatorManagerSnapshot CalcManager; - // PrimaryDisplaySnapshot PrimaryDisplay; - // std::optional ExpressionDisplay; - // std::vector> DisplayCommands; - // }; - [Windows::UI::Xaml::Data::Bindable] public ref class StandardCalculatorViewModel sealed : public Windows::UI::Xaml::Data::INotifyPropertyChanged { public: @@ -268,12 +243,13 @@ namespace CalculatorApp } } - property CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot - ^ Snapshot { CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ get() { return GetSnapshot(); } } + property CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ Snapshot { + CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ get(); + void set(CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ snapshot); + }; - // Used by unit tests - void - ResetCalcManager(bool clearMemory); + // Used by unit tests + void ResetCalcManager(bool clearMemory); void SendCommandToCalcManager(int command); public: @@ -327,10 +303,9 @@ namespace CalculatorApp } internal :; - explicit StandardCalculatorViewModel(CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ snapshot = nullptr); + explicit StandardCalculatorViewModel(); private: - CalculatorApp::ViewModel::Snapshot::StandardCalculatorSnapshot ^ GetSnapshot() const; void SetMemorizedNumbers(const std::vector& memorizedNumbers); void UpdateProgrammerPanelDisplay(); void HandleUpdatedOperandData(CalculationManager::Command cmdenum); diff --git a/src/Calculator/Utils/JsonUtils.cs b/src/Calculator/Utils/JsonUtils.cs index e138b2eb..0a49b430 100644 --- a/src/Calculator/Utils/JsonUtils.cs +++ b/src/Calculator/Utils/JsonUtils.cs @@ -163,7 +163,13 @@ namespace CalculatorApp.JsonUtils public IEnumerable HistoryItems { get => Value.HistoryItems.Select(x => new CalcManagerHistoryItemAlias { Value = x }); - set => Value.HistoryItems = value.Select(x => new CalcManagerHistoryItem { Tokens = x.Tokens.Select(Helpers.MapHistoryToken).ToList() }).ToList(); + set => Value.HistoryItems = value.Select(x => new CalcManagerHistoryItem + { + Tokens = x.Tokens.Select(Helpers.MapHistoryToken).ToList(), + Commands = x.Commands.Select(Helpers.MapCommandAlias).ToList(), + Expression = x.Expression, + Result = x.Result + }).ToList(); } public CalcManagerSnapshotAlias() => Value = new CalcManagerSnapshot(); diff --git a/src/Calculator/Views/MainPage.xaml.cs b/src/Calculator/Views/MainPage.xaml.cs index 3d9cc9ea..7f3b10cf 100644 --- a/src/Calculator/Views/MainPage.xaml.cs +++ b/src/Calculator/Views/MainPage.xaml.cs @@ -179,22 +179,8 @@ namespace CalculatorApp } else if (e.Parameter is SnapshotLaunchArguments snapshotArgs) { - //_ = Window.Current.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, async () => - //{ - // var channel = UserActivityChannel.GetDefault(); - // var activity = await channel.GetOrCreateUserActivityAsync(snapshotArgs.ActivityId); - - // if (TryRestoreFromActivity(snapshotArgs, activity, out var errorMessage)) - // { - // TraceLogger.GetInstance().LogRecallRestore(Model.Mode); - // SelectNavigationItemByModel(); - // } - // else - // { - // TraceLogger.GetInstance().LogRecallError(Model.Mode, errorMessage); - // } - //}); - Model.Initialize(snapshotArgs.Snapshot); + Model.RestoreFromSnapshot(snapshotArgs.Snapshot); + Model.Initialize(initialMode); } else { @@ -202,38 +188,6 @@ namespace CalculatorApp } } - //private bool TryRestoreFromActivity(SnapshotLaunchArguments snapshotArgs, UserActivity activity, out string errorMessage) - //{ - // if (!snapshotArgs.VerifyIncomingActivity(activity)) - // { - // errorMessage = "IncomingActivityFailed"; - // return false; - // } - - // // Work around for bug https://microsoft.visualstudio.com/DefaultCollection/OS/_workitems/edit/48931227 - // // where ContentInfo can't be directly accessed. - // if (!JsonObject.TryParse(activity.ToJson(), out var activityJson)) - // { - // errorMessage = "ParseJsonError"; - // return false; - // } - - // if (!activityJson.ContainsKey("contentInfo")) - // { - // errorMessage = "ContentInfoNotExist"; - // return false; - // } - - // if (!Model.TryRestoreFromSnapshot(activityJson.GetNamedObject("contentInfo"))) - // { - // errorMessage = "RestoreFromSnapshotFailed"; - // return false; - // } - - // errorMessage = string.Empty; - // return true; - //} - private void InitializeNavViewCategoriesSource() { NavViewCategoriesSource = ExpandNavViewCategoryGroups(Model.Categories);