Convert DateCalculatorViewModel to runtime class (#769)

This commit is contained in:
Rudy Huyn
2019-11-06 06:58:34 -08:00
committed by Matt Cooley
parent 577aafb3f4
commit caa1c6bb9d
5 changed files with 104 additions and 107 deletions

View File

@@ -9,6 +9,11 @@ using namespace Windows::Foundation;
using namespace Windows::Globalization;
using namespace CalculatorApp::Common::DateCalculation;
bool operator==(const DateDifference& l, const DateDifference& r)
{
return l.year == r.year && l.month == r.month && l.week == r.week && l.day == r.day;
}
DateCalculationEngine::DateCalculationEngine(_In_ String ^ calendarIdentifier)
{
m_calendar = ref new Calendar();
@@ -18,10 +23,9 @@ DateCalculationEngine::DateCalculationEngine(_In_ String ^ calendarIdentifier)
// Adding Duration to a Date
// Returns: True if function succeeds to calculate the date else returns False
bool DateCalculationEngine::AddDuration(_In_ DateTime startDate, _In_ const DateDifference& duration, _Out_ DateTime* endDate)
IBox<DateTime> ^ DateCalculationEngine::AddDuration(DateTime startDate, DateDifference duration)
{
auto currentCalendarSystem = m_calendar->GetCalendarSystem();
try
{
m_calendar->SetDateTime(startDate);
@@ -50,7 +54,8 @@ bool DateCalculationEngine::AddDuration(_In_ DateTime startDate, _In_ const Date
m_calendar->AddDays(duration.day);
}
*endDate = m_calendar->GetDateTime();
m_calendar->ChangeCalendarSystem(currentCalendarSystem);
return m_calendar->GetDateTime();
}
catch (Platform::InvalidArgumentException ^ ex)
{
@@ -58,17 +63,13 @@ bool DateCalculationEngine::AddDuration(_In_ DateTime startDate, _In_ const Date
m_calendar->ChangeCalendarSystem(currentCalendarSystem);
// Do nothing
return false;
return nullptr;
}
m_calendar->ChangeCalendarSystem(currentCalendarSystem);
return true;
}
// Subtracting Duration from a Date
// Returns: True if function succeeds to calculate the date else returns False
bool DateCalculationEngine::SubtractDuration(_In_ DateTime startDate, _In_ const DateDifference& duration, _Out_ DateTime* endDate)
IBox<DateTime> ^ DateCalculationEngine::SubtractDuration(_In_ DateTime startDate, _In_ DateDifference duration)
{
auto currentCalendarSystem = m_calendar->GetCalendarSystem();
@@ -101,7 +102,18 @@ bool DateCalculationEngine::SubtractDuration(_In_ DateTime startDate, _In_ const
{
m_calendar->AddYears(-duration.year);
}
*endDate = m_calendar->GetDateTime();
m_calendar->ChangeCalendarSystem(currentCalendarSystem);
auto dateTime = m_calendar->GetDateTime();
// Check that the UniversalTime value is not negative
if (dateTime.UniversalTime >= 0)
{
return dateTime;
}
else
{
return nullptr;
}
}
catch (Platform::InvalidArgumentException ^ ex)
{
@@ -109,17 +121,12 @@ bool DateCalculationEngine::SubtractDuration(_In_ DateTime startDate, _In_ const
m_calendar->ChangeCalendarSystem(currentCalendarSystem);
// Do nothing
return false;
return nullptr;
}
m_calendar->ChangeCalendarSystem(currentCalendarSystem);
// Check that the UniversalTime value is not negative
return (endDate->UniversalTime >= 0);
}
// Calculate the difference between two dates
bool DateCalculationEngine::TryGetDateDifference(_In_ DateTime date1, _In_ DateTime date2, _In_ DateUnit outputFormat, _Out_ DateDifference* difference)
IBox<DateDifference> ^ DateCalculationEngine::TryGetDateDifference(_In_ DateTime date1, _In_ DateTime date2, _In_ DateUnit outputFormat)
{
DateTime startDate;
DateTime endDate;
@@ -177,8 +184,7 @@ bool DateCalculationEngine::TryGetDateDifference(_In_ DateTime date1, _In_ DateT
{
// Operation failed due to out of bound result
// For example: 31st Dec, 9999 - last valid date
*difference = DateDifferenceUnknown;
return false;
return nullptr;
}
}
@@ -194,8 +200,7 @@ bool DateCalculationEngine::TryGetDateDifference(_In_ DateTime date1, _In_ DateT
if (differenceInDates[unitIndex] == 0)
{
// differenceInDates[unitIndex] is unsigned, the value can't be negative
*difference = DateDifferenceUnknown;
return false;
return nullptr;
}
differenceInDates[unitIndex] -= 1;
pivotDate = tempPivotDate;
@@ -220,8 +225,7 @@ bool DateCalculationEngine::TryGetDateDifference(_In_ DateTime date1, _In_ DateT
{
// Operation failed due to out of bound result
// For example: 31st Dec, 9999 - last valid date
*difference = DateDifferenceUnknown;
return false;
return nullptr;
}
}
} while (tempDaysDiff != 0); // dates are the same - exit the loop
@@ -232,8 +236,7 @@ bool DateCalculationEngine::TryGetDateDifference(_In_ DateTime date1, _In_ DateT
if (signedDaysDiff < 0)
{
// daysDiff is unsigned, the value can't be negative
*difference = DateDifferenceUnknown;
return false;
return nullptr;
}
daysDiff = signedDaysDiff;
@@ -244,11 +247,12 @@ bool DateCalculationEngine::TryGetDateDifference(_In_ DateTime date1, _In_ DateT
differenceInDates[3] = daysDiff;
difference->year = differenceInDates[0];
difference->month = differenceInDates[1];
difference->week = differenceInDates[2];
difference->day = differenceInDates[3];
return true;
DateDifference result;
result.year = differenceInDates[0];
result.month = differenceInDates[1];
result.week = differenceInDates[2];
result.day = differenceInDates[3];
return result;
}
// Private Methods

View File

@@ -29,39 +29,30 @@ namespace CalculatorApp
};
// Struct to store the difference between two Dates in the form of Years, Months , Weeks
struct DateDifference
public
value struct DateDifference
{
int year = 0;
int month = 0;
int week = 0;
int day = 0;
bool operator==(const DateDifference& dd) const
{
return year == dd.year && month == dd.month && week == dd.week && day == dd.day;
}
int year;
int month;
int week;
int day;
};
const DateDifference DateDifferenceUnknown{ INT_MIN, INT_MIN, INT_MIN, INT_MIN };
class DateCalculationEngine
public
ref class DateCalculationEngine sealed
{
public:
// Constructor
DateCalculationEngine(_In_ Platform::String ^ calendarIdentifier);
// Public Methods
bool __nothrow
AddDuration(_In_ Windows::Foundation::DateTime startDate, _In_ const DateDifference& duration, _Out_ Windows::Foundation::DateTime* endDate);
bool __nothrow SubtractDuration(
_In_ Windows::Foundation::DateTime startDate,
_In_ const DateDifference& duration,
_Out_ Windows::Foundation::DateTime* endDate);
bool __nothrow TryGetDateDifference(
_In_ Windows::Foundation::DateTime date1,
_In_ Windows::Foundation::DateTime date2,
_In_ DateUnit outputFormat,
_Out_ DateDifference* difference);
Platform::IBox<Windows::Foundation::DateTime> ^ AddDuration(_In_ Windows::Foundation::DateTime startDate, _In_ DateDifference duration);
Platform::IBox<Windows::Foundation::DateTime> ^ SubtractDuration(_In_ Windows::Foundation::DateTime startDate, _In_ DateDifference duration);
Platform::IBox<
DateDifference> ^ TryGetDateDifference(_In_ Windows::Foundation::DateTime date1, _In_ Windows::Foundation::DateTime date2, _In_ DateUnit outputFormat);
private:
// Private Variables
@@ -76,3 +67,5 @@ namespace CalculatorApp
}
}
}
bool operator==(const CalculatorApp::Common::DateCalculation::DateDifference& l, const CalculatorApp::Common::DateCalculation::DateDifference& r);

View File

@@ -45,13 +45,13 @@ DateCalculatorViewModel::DateCalculatorViewModel()
, m_StrDateResult(L"")
, m_StrDateResultAutomationName(L"")
{
const auto& localizationSettings = LocalizationSettings::GetInstance();
const auto & localizationSettings = LocalizationSettings::GetInstance();
// Initialize Date Output format instances
InitializeDateOutputFormats(localizationSettings.GetCalendarIdentifier());
// Initialize Date Calc engine
m_dateCalcEngine = make_shared<DateCalculationEngine>(localizationSettings.GetCalendarIdentifier());
m_dateCalcEngine = ref new DateCalculationEngine(localizationSettings.GetCalendarIdentifier());
// Initialize dates of DatePicker controls to today's date
auto calendar = ref new Calendar();
// We force the timezone to UTC, in order to avoid being affected by Daylight Saving Time
@@ -111,20 +111,20 @@ void DateCalculatorViewModel::OnPropertyChanged(_In_ String ^ prop)
void DateCalculatorViewModel::OnInputsChanged()
{
DateDifference dateDiff;
if (m_IsDateDiffMode)
{
DateTime clippedFromDate = ClipTime(FromDate, true);
DateTime clippedToDate = ClipTime(ToDate, true);
// Calculate difference between two dates
if (m_dateCalcEngine->TryGetDateDifference(clippedFromDate, clippedToDate, m_daysOutputFormat, &dateDiff))
auto dateDiff = m_dateCalcEngine->TryGetDateDifference(clippedFromDate, clippedToDate, m_daysOutputFormat);
if (dateDiff != nullptr)
{
DateDiffResultInDays = dateDiff;
if (m_dateCalcEngine->TryGetDateDifference(clippedFromDate, clippedToDate, m_allDateUnitsOutputFormat, &dateDiff))
DateDiffResultInDays = dateDiff->Value;
dateDiff = m_dateCalcEngine->TryGetDateDifference(clippedFromDate, clippedToDate, m_allDateUnitsOutputFormat);
if (dateDiff != nullptr)
{
DateDiffResult = dateDiff;
DateDiffResult = dateDiff->Value;
}
else
{
@@ -140,26 +140,28 @@ void DateCalculatorViewModel::OnInputsChanged()
}
else
{
DateDifference dateDiff;
dateDiff.day = DaysOffset;
dateDiff.month = MonthsOffset;
dateDiff.year = YearsOffset;
DateTime dateTimeResult;
IBox<DateTime> ^ dateTimeResult;
if (m_IsAddMode)
{
// Add number of Days, Months and Years to a Date
IsOutOfBound = !m_dateCalcEngine->AddDuration(StartDate, dateDiff, &dateTimeResult);
dateTimeResult = m_dateCalcEngine->AddDuration(StartDate, dateDiff);
}
else
{
// Subtract number of Days, Months and Years from a Date
IsOutOfBound = !m_dateCalcEngine->SubtractDuration(StartDate, dateDiff, &dateTimeResult);
dateTimeResult = m_dateCalcEngine->SubtractDuration(StartDate, dateDiff);
}
IsOutOfBound = dateTimeResult == nullptr;
if (!m_isOutOfBound)
{
DateResult = dateTimeResult;
DateResult = dateTimeResult->Value;
}
}
}
@@ -181,8 +183,7 @@ void DateCalculatorViewModel::UpdateDisplayResult()
StrDateDiffResultInDays = L"";
StrDateDiffResult = AppResourceProvider::GetInstance()->GetResourceString(L"Date_SameDates");
}
else if (m_dateDiffResult == DateDifferenceUnknown ||
(m_dateDiffResult.year == 0 && m_dateDiffResult.month == 0 && m_dateDiffResult.week == 0))
else if (m_dateDiffResult == DateDifferenceUnknown || (m_dateDiffResult.year == 0 && m_dateDiffResult.month == 0 && m_dateDiffResult.week == 0))
{
IsDiffInDays = true;
StrDateDiffResultInDays = L"";

View File

@@ -176,7 +176,7 @@ namespace CalculatorApp
CalculatorApp::Common::DateCalculation::DateDifference m_dateDiffResultInDays;
// Private members
std::shared_ptr<CalculatorApp::Common::DateCalculation::DateCalculationEngine> m_dateCalcEngine;
CalculatorApp::Common::DateCalculation::DateCalculationEngine ^ m_dateCalcEngine;
CalculatorApp::Common::DateCalculation::DateUnit m_daysOutputFormat;
CalculatorApp::Common::DateCalculation::DateUnit m_allDateUnitsOutputFormat;
Windows::Globalization::DateTimeFormatting::DateTimeFormatter ^ m_dateTimeFormatter;