⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 amsedit.cpp

📁 用户管理系统
💻 CPP
📖 第 1 页 / 共 5 页
字号:
					else
						Behavior::_OnChar(uChar, nRepCnt, nFlags);
				}
			}
			else
			{
				if (IsValidDayDigit(c, 1) && _ShouldEnter(c))
				{
					if (nLen > nStart)
					{
						m_pEdit->SetSel(nStart, nStart + 1);
						m_pEdit->ReplaceSel(CString(c), TRUE);
					}
					else
						Behavior::_OnChar(uChar, nRepCnt, nFlags);
				}
			}
			break;
		}

		case 5:		// SECOND SLASH	(year's first digit)
		{
			int nSlash = 0;
			if (c == m_cSep)
				nSlash = 1;
			else
				nSlash = (IsValidYearDigit(c, 0) ? 2 : 0);

			// If we need the slash, enter it
			if (nSlash && _ShouldEnter(c))
			{
				m_pEdit->SetSel(nStart, nStart + 1, FALSE);
				m_pEdit->ReplaceSel(CString(m_cSep), TRUE);
			}

			// If the slash is to be preceded by a valid digit, "type" it in.
			if (nSlash == 2)
				keybd_event((BYTE)c, 0, 0, 0);
			break;			
		}

		case 6:		// YEAR (all 4 digits)
		case 7:
		case 8:
		case 9:
		{
			if (IsValidYearDigit(c, nStart - GetYearStartPosition()) && _ShouldEnter(c))
			{
				if (nLen > nStart)
				{
					m_pEdit->SetSel(nStart, nStart + 1, FALSE);
					m_pEdit->ReplaceSel(CString(c), TRUE);

					if (nLen > nStart + 1)
					{
						if (!IsValidYearDigit(strText[nStart + 1], nStart - (GetYearStartPosition() - 1)))
						{
							m_pEdit->SetSel(nStart + 1, 10, FALSE);
							CString strPortion;
							for (int iPos = nStart + 1; iPos < 10; iPos++)
								strPortion += GetMinYearDigit(iPos - GetYearStartPosition(), true);
							
							m_pEdit->ReplaceSel(strPortion, TRUE);
							m_pEdit->SetSel(nStart + 1, 10, FALSE);
						}
					}
				}
				else
					Behavior::_OnChar(uChar, nRepCnt, nFlags);

				if (IsValidYear(GetYear()))
				{
					AdjustMaxDay();			// adjust the day first
					AdjustMaxMonthAndDay();	// then adjust the month and the day, if necessary
				}
			}
			break;
		}
	}
}

void CAMSEdit::DateBehavior::_OnKeyDown(UINT uChar, UINT nRepCnt, UINT nFlags) 
{
	switch (uChar)
	{
		case VK_DELETE:
		{
			// If deleting make sure it's the last character or that
			// the selection goes all the way to the end of the text

			int nStart, nEnd;
			m_pEdit->GetSel(nStart, nEnd);

			CString strText = m_pEdit->GetText();
			int nLen = strText.GetLength();

			if (nEnd != nLen)
			{
				if (!(nEnd == nStart && nEnd == nLen - 1))
					return;
			}
			break;
		}

		case VK_UP:
		{
			// If pressing the UP arrow, increment the corresponding value.

			int nStart, nEnd;
			m_pEdit->GetSel(nStart, nEnd);

			if (nStart >= GetYearStartPosition() && nStart <= GetYearStartPosition() + 4)
			{
				int nYear = GetYear();
				if (nYear >= m_dateMin.GetYear() && nYear < m_dateMax.GetYear())
					SetYear(++nYear);
			}

			else if (nStart >= GetMonthStartPosition() && nStart <= GetMonthStartPosition() + 2)
			{
				int nMonth = GetMonth();
				if (nMonth >= GetMinMonth() && nMonth < GetMaxMonth())
					SetMonth(++nMonth);
			}

			else if (nStart >= GetDayStartPosition() && nStart <= GetDayStartPosition() + 2)
			{
				int nDay = GetDay();
				if (nDay >= GetMinDay() && nDay < GetMaxDay())
					SetDay(++nDay);
			}
			
			return;
		}

		case VK_DOWN:
		{
			// If pressing the DOWN arrow, decrement the corresponding value.

			int nStart, nEnd;
			m_pEdit->GetSel(nStart, nEnd);

			if (nStart >= GetYearStartPosition() && nStart <= GetYearStartPosition() + 4)
			{
				int nYear = GetYear();
				if (nYear > m_dateMin.GetYear())
					SetYear(--nYear);
			}

			else if (nStart >= GetMonthStartPosition() && nStart <= GetMonthStartPosition() + 2)
			{
				int nMonth = GetMonth();
				if (nMonth > GetMinMonth())
					SetMonth(--nMonth);
			}

			else if (nStart >= GetDayStartPosition() && nStart <= GetDayStartPosition() + 2)
			{
				int nDay = GetDay();
				if (nDay > GetMinDay())
					SetDay(--nDay);
			}
			
			return;
		}
	}

	Behavior::_OnKeyDown(uChar, nRepCnt, nFlags);
}

CString CAMSEdit::DateBehavior::GetString(int nValue, bool bTwoDigitWithLeadingZero /*= true*/)
{
	CString strValue;
	if (bTwoDigitWithLeadingZero)
		strValue.Format(_T("%02d"), nValue);
	else
		strValue.Format(_T("%d"), nValue);
	return strValue;
}

int CAMSEdit::DateBehavior::GetMonthStartPosition() const
{
	return ((m_uFlags & DayBeforeMonth) ? 3 : 0);
}

int CAMSEdit::DateBehavior::GetDayStartPosition() const
{
	return ((m_uFlags & DayBeforeMonth) ? 0 : 3);
}

int CAMSEdit::DateBehavior::GetYearStartPosition() const
{
	return 6;
}

int CAMSEdit::DateBehavior::GetMaxMonth() const
{
	if (GetValidYear() == m_dateMax.GetYear())
		return m_dateMax.GetMonth();
	return 12;
}

int CAMSEdit::DateBehavior::GetMinMonth() const
{
	if (GetValidYear() == m_dateMin.GetYear())
		return m_dateMin.GetMonth();
	return 1;
}

int CAMSEdit::DateBehavior::GetMaxDay() const
{
	int nYear = GetValidYear();
	int nMonth = GetValidMonth();

	if (nYear == m_dateMax.GetYear() && nMonth == m_dateMax.GetMonth())
		return m_dateMax.GetDay();

	return GetMaxDayOfMonth(nMonth, nYear);
}

int CAMSEdit::DateBehavior::GetMinDay() const
{
	int nYear = GetValidYear();
	int nMonth = GetValidMonth();

	if (nYear == m_dateMin.GetYear() && nMonth == m_dateMin.GetMonth())
		return m_dateMin.GetDay();

	return 1;
}

int CAMSEdit::DateBehavior::GetMaxDayOfMonth(int nMonth, int nYear)
{
	ASSERT(nMonth >= 1 && nMonth <= 12);

	switch (nMonth)
	{
		case 4:
		case 6:
		case 9:
		case 11:
			return 30;

		case 2:
			return IsLeapYear(nYear) ? 29 : 28;
	}
	return 31;
}

TCHAR CAMSEdit::DateBehavior::GetMaxMonthDigit(int nPos) const
{
	ASSERT(nPos >= 0 && nPos <= 1);

	int nYear = GetValidYear();
	int nMaxMonth = m_dateMax.GetMonth();
	int nMaxYear = m_dateMax.GetYear();

	// First digit
	if (nPos == 0)
	{
		// If the year is at the max, then use the first digit of the max month
		if (nYear == nMaxYear)
			return GetString(nMaxMonth)[0];

		// Otherwise, it's always '1'
		return '1';
	}

	// Second digit
	CString strWindowText = m_pEdit->GetText();
	TCHAR cFirstDigit = (strWindowText.GetLength() > GetMonthStartPosition()) ? strWindowText[GetMonthStartPosition()] : 0;
	ASSERT(cFirstDigit);  // must have a valid first digit at this point

	// If the year is at the max, then check if the first digits match
	if (nYear == nMaxYear && IsValidYear(GetYear()))
	{
		// If the first digits match, then use the second digit of the max month
		if (GetString(nMaxMonth)[0] == cFirstDigit)
			return GetString(nMaxMonth)[1];

		// Assuming the logic for the first digit is correct, then it must be '0'
		ASSERT(cFirstDigit == '0');
		return '9';  
	}

	// Use the first digit to determine the second digit's max
	return (cFirstDigit == '1' ? '2' : '9');
}

TCHAR CAMSEdit::DateBehavior::GetMinMonthDigit(int nPos) const
{
	ASSERT(nPos >= 0 && nPos <= 1);

	int nYear = GetValidYear();
	int nMinMonth = m_dateMin.GetMonth();
	int nMinYear = m_dateMin.GetYear();

	// First digit
	if (nPos == 0)
	{
		// If the year is at the min, then use the first digit of the min month
		if (nYear == nMinYear)
			return GetString(nMinMonth)[0];

		// Otherwise, it's always '0'
		return '0';
	}

	// Second digit
	CString strWindowText = m_pEdit->GetText();
	TCHAR cFirstDigit = (strWindowText.GetLength() > GetMonthStartPosition()) ? strWindowText[GetMonthStartPosition()] : 0;
	if (!cFirstDigit)
		return '1';

	// If the year is at the max, then check if the first digits match
	if (nYear == nMinYear && IsValidYear(GetYear()))
	{
		// If the first digits match, then use the second digit of the max month
		if (GetString(nMinMonth)[0] == cFirstDigit)
			return GetString(nMinMonth)[1];

		return '0';  
	}

	// Use the first digit to determine the second digit's min
	return (cFirstDigit == '1' ? '0' : '1');
}

bool CAMSEdit::DateBehavior::IsValidMonthDigit(TCHAR c, int nPos) const
{
	return (c >= GetMinMonthDigit(nPos) && c <= GetMaxMonthDigit(nPos));
}

bool CAMSEdit::DateBehavior::IsValid(const COleDateTime& date) const
{
	return (date.GetStatus() == COleDateTime::valid && date >= m_dateMin && date <= m_dateMax);
}

bool CAMSEdit::DateBehavior::IsValidMonth(int nMonth) const
{
	int nYear = GetValidYear();
	return IsValid(COleDateTime(nYear, nMonth, 1, 0, 0, 0));
}

TCHAR CAMSEdit::DateBehavior::GetMaxDayDigit(int nPos) const
{
	ASSERT(nPos >= 0 && nPos <= 1);

	int nMonth = GetValidMonth();
	int nYear = GetValidYear();
	int nMaxDay = m_dateMax.GetDay();
	int nMaxMonth = m_dateMax.GetMonth();
	int nMaxYear = m_dateMax.GetYear();

	// First digit
	if (nPos == 0)
	{
		// If the year and month are at the max, then use the first digit of the max day
		if (nYear == nMaxYear && nMonth == nMaxMonth)
			return GetString(nMaxDay)[0];
		return GetString(GetMaxDayOfMonth(nMonth, nYear))[0];
	}

	// Second digit
	CString strWindowText = m_pEdit->GetText();
	TCHAR cFirstDigit = (strWindowText.GetLength() > GetDayStartPosition()) ? strWindowText[GetDayStartPosition()] : 0;
	ASSERT(cFirstDigit);  // must have a valid first digit at this point

	// If the year and month are at the max, then use the second digit of the max day
	if (nYear == nMaxYear && nMonth == nMaxMonth && GetString(nMaxDay)[0] == cFirstDigit)
		return GetString(nMaxDay)[1];

	if (cFirstDigit == '0' || 
		cFirstDigit == '1' || 
		(cFirstDigit == '2' && nMonth != 2) || 
		(nMonth == 2 && !IsValidYear(GetYear())))
		return '9';
	return GetString(GetMaxDayOfMonth(nMonth, nYear))[1];
}

TCHAR CAMSEdit::DateBehavior::GetMinDayDigit(int nPos) const
{
	ASSERT(nPos >= 0 && nPos <= 1);

	int nMonth = GetValidMonth();
	int nYear = GetValidYear();
	int nMinDay = m_dateMin.GetDay();
	int nMinMonth = m_dateMin.GetMonth();
	int nMinYear = m_dateMin.GetYear();

	// First digit
	if (nPos == 0)
	{
		// If the year and month are at the min, then use the first digit of the min day
		if (nYear == nMinYear && nMonth == nMinMonth)
			return GetString(nMinDay)[0];
		return '0';
	}

	// Second digit
	CString strWindowText = m_pEdit->GetText();
	TCHAR cFirstDigit = (strWindowText.GetLength() > GetDayStartPosition()) ? strWindowText[GetDayStartPosition()] : 0;
	if (!cFirstDigit)  // must have a valid first digit at this point
		return '1';

	// If the year and month are at the max, then use the first second of the max day
	if (nYear == nMinYear && nMonth == nMinMonth && GetString(nMinDay)[0] == cFirstDigit)
		return GetString(nMinDay)[1];

	// Use the first digit to determine the second digit's min
	return (cFirstDigit == '0' ? '1' : '0');
}

bool CAMSEdit::DateBehavior::IsValidDayDigit(TCHAR c, int nPos) const
{
	return (c >= GetMinDayDigit(nPos) && c <= GetMaxDayDigit(nPos));
}

bool CAMSEdit::DateBehavior::IsValidDay(int nDay) const
{
	return IsValid(COleDateTime(GetValidYear(), GetValidMonth(), nDay, 0, 0, 0));
}

bool CAMSEdit::DateBehavior::IsValidYear(int nYear) const
{
	return (nYear >= m_dateMin.GetYear() && nYear <= m_dateMax.GetYear());
}

bool CAMSEdit::DateBehavior::AdjustMaxMonthAndDay()
{
	int nMonth = GetMonth();	
	if (nMonth && !IsValidMonth(nMonth))
	{
		SetMonth(GetMinMonth());  // this adjusts the day automatically
		return true;
	}

	return AdjustMaxDay();
}

bool CAMSEdit::DateBehavior::AdjustMaxDay()
{
	int nDay = GetDay();
	if (nDay && !IsValidDay(nDay))
	{
		SetDay(GetMaxDay());
		return true;
	}
	
	return false;	// nothing had to be adjusted
}

TCHAR CAMSEdit::DateBehavior::GetMaxYearDigit(int nPos) const
{
	ASSERT(nPos >= 0 && nPos <= 3);

	CString strYear = GetString(GetYear(), false);
	CString strMaxYear = GetString(m_dateMax.GetYear(), false);

	if (nPos == 0 || strMaxYear.Left(nPos) == strYear.Left(nPos))
		return strMaxYear[nPos];
	return '9';
}

TCHAR CAMSEdit::DateBehavior::GetMinYearDigit(int nPos, bool bValidYear /*= false*/) const
{
	ASSERT(nPos >= 0 && nPos <= 3);

	int nYear = GetYear();
	if (!IsValidYear(nYear) && bValidYear)
		nYear = GetValidYear();

	CString strYear = GetString(nYear, false);
	CString strMinYear = GetString(m_dateMin.GetYear(), false);

	if (nPos == 0 || strMinYear.Left(nPos) == strYear.Left(nPos))
		return strMinYear[nPos];
	return '0';
}

bool CAMSEdit::DateBehavior::IsValidYearDigit(TCHAR c, int nPos) const
{
	return (c >= GetMinYearDigit(nPos) && c <= GetMaxYearDigit(nPos));
}

int CAMSEdit::DateBehavior::GetValidMonth() const
{
	int nMonth = GetMonth();
	
	// It it's outside the range, fix it
	if (nMonth < GetMinMonth())
		nMonth = GetMinMonth();
	else if (nMonth > GetMaxMonth())
		nMonth = GetMaxMonth();

	return nMonth;
}

int CAMSEdit::DateBehavior::GetMonth() const
{
	CString strText = m_pEdit->GetText();
	if (strText.GetLength() >= 2)
		return _ttoi(strText.Mid(0, 2));
	return 0;
}

int CAMSEdit::DateBehavior::GetValidYear() const
{
	int nYear = GetYear();
	if (nYear < m_dateMin.GetYear())
		nYear = m_dateMin.GetYear();

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -