source: trunk/EraserUI/Masked.cpp @ 27

Revision 27, 11.1 KB checked in by lowjoel, 7 years ago (diff)

In goes the 3rd party code.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
Line 
1// MaskEd.cpp
2//
3// Orginially written by : DunnoWho
4// Modified by : Jeremy Davis, 24/07/1998
5//     Added CTimeEdit::SetMins and CTimeEdit::SetHours
6// Modified by : sami@tolvanen.com
7//     Added handler to right mouse click to stop the popup menu from showing
8//     Miscellanious bug fixes
9
10#include "stdafx.h"
11#include "MaskEd.h"
12
13#ifdef _DEBUG
14#define new DEBUG_NEW
15#undef THIS_FILE
16static char THIS_FILE[] = __FILE__;
17#endif
18
19/////////////////////////////////////////////////////////////////////////////
20// COleDateTime read /write
21
22static COleDateTime ReadCOleDateTime(LPCSTR lpszData)
23{
24    COleDateTime DateTime;
25    DateTime.ParseDateTime(lpszData);
26
27    return DateTime;
28}
29
30static void FormatCOleDateTime(CString& strData, COleDateTime DateTime, int len)
31{
32    strData.Empty();
33
34    if (DateTime.m_dt == 0)
35    {
36        if(len == 5)
37            strData = "00:00";
38
39        return;
40    }
41
42    if (len == 8)
43        strData = DateTime.Format(TEXT("%d/%m/%y"));
44    else if (len == 5) // added these two
45        strData = DateTime.Format(TEXT("%H:%M"));
46    else
47        strData = DateTime.Format(TEXT("%d/%m/%Y"));
48}
49
50/////////////////////////////////////////////////////////////////////////////
51// CMaskEdit class
52
53IMPLEMENT_DYNAMIC(CMaskEdit, CEdit)
54
55BEGIN_MESSAGE_MAP(CMaskEdit, CEdit)
56//{{AFX_MSG_MAP(CMaskEdit)
57ON_WM_CHAR()
58ON_WM_KEYDOWN()
59//}}AFX_MSG_MAP
60END_MESSAGE_MAP()
61
62CMaskEdit::CMaskEdit()
63{
64    m_bUseMask              = FALSE;
65    m_strMask               = TEXT("");
66    m_strLiteral            = TEXT("");
67    m_strValid              = TEXT("");
68    m_strHours              = TEXT("23");
69    m_strMins               = TEXT("59");
70    m_strMinHours           = TEXT("00");
71    m_strMinMins            = TEXT("00");
72    m_bMaskKeyInProgress    = FALSE;
73    m_strMaskLiteral        = TEXT("");
74}
75
76void CMaskEdit::SetMask(LPCSTR lpMask, LPCSTR lpLiteral, LPCSTR lpValid)
77{
78    m_bUseMask = FALSE;
79
80    if (lpMask == NULL)
81        return;
82
83    m_strMask = lpMask;
84
85    if (m_strMask.IsEmpty())
86        return;
87
88    if (lpLiteral != NULL)
89    {
90        m_strLiteral = lpLiteral;
91
92        if (m_strLiteral.GetLength() != m_strMask.GetLength())
93            m_strLiteral.Empty();
94    }
95    else
96        m_strLiteral.Empty();
97
98    if (lpValid != NULL)
99        m_strValid = lpValid;
100    else
101        m_strValid.Empty();
102
103    m_bUseMask = TRUE;
104}
105
106void CMaskEdit::SendChar(UINT nChar)
107{
108    m_bMaskKeyInProgress = TRUE;
109
110    AfxCallWndProc(this, m_hWnd, WM_CHAR, nChar, 1);
111
112    m_bMaskKeyInProgress = FALSE;
113}
114
115void CMaskEdit::OnChar(UINT nChar, UINT nRepCnt, UINT nFlags)
116{
117    if (!m_bMaskKeyInProgress)
118    {
119        if (!CheckChar(nChar))
120            return;
121    }
122
123    if (m_bUseMask)
124    {
125        if (isprint(nChar))
126        {
127            // si un masque existe, on est en insert mode
128            int startPos, endPos;
129
130            GetSel(startPos, endPos);
131            SetSel(startPos, endPos + 1);
132            Clear();
133
134            m_str.SetAt(endPos, (TCHAR)nChar); // added this
135        }
136        else if (nChar == VK_BACK)
137        {
138            int startPos, endPos;
139            GetSel(startPos, endPos);
140
141            // sanity range check
142            if ((startPos == endPos) && (startPos >= 1) && (startPos <= m_str.GetLength()))
143            {
144                // get the masked literal representation
145                TRACE(TEXT("m_strMaskLiteral = [%s](%s)\n"), m_strMaskLiteral, m_str);
146
147                // back space the cursor
148                SendMessage(WM_KEYDOWN, VK_LEFT, 0);
149
150                if (!m_strMaskLiteral.IsEmpty())
151                {
152                    // update the char backspacing over
153                    SendChar(m_strMaskLiteral[startPos-1]);
154
155                    // back space the cursor again
156                    SendMessage(WM_KEYDOWN, VK_LEFT, 0);
157                }
158            }
159            else // out of range or have more than one char selected
160                MessageBeep(static_cast < UINT>(-1));
161
162            return;
163        }
164    }
165
166    CEdit::OnChar(nChar, nRepCnt, nFlags);
167
168    if (!m_bMaskKeyInProgress && m_bUseMask && !m_strLiteral.IsEmpty())
169    {
170        int startPos, endPos;
171        GetSel(startPos, endPos);
172
173        // make sure the string is not longer than the mask
174        if (endPos < m_strLiteral.GetLength())
175        {
176            UINT c = m_strLiteral.GetAt(endPos);
177
178            if (c != TEXT('_'))
179                SendChar(c);
180        }
181    }
182}
183
184BOOL CMaskEdit::CheckChar(UINT nChar)
185{
186    UINT c;
187
188    // do not use mask
189    if (!m_bUseMask)
190        return TRUE;
191
192    // control character, OK
193    if (!isprint(nChar))
194        return TRUE;
195
196    // unselect all selections, if any
197    int startPos, endPos;
198
199    GetSel(startPos, endPos);
200    SetSel(-1, 0);
201    SetSel(startPos, startPos);
202
203    // check the key against the mask
204    GetSel(startPos, endPos);
205
206    // make sure the string is not longer than the mask
207    if (endPos >= m_strMask.GetLength())
208    {
209        MessageBeep(static_cast < UINT>(-1));
210        return FALSE;
211    }
212
213    // check to see if a literal is in this position
214    c = TEXT('_');
215
216    if (!m_strLiteral.IsEmpty())
217        c = m_strLiteral.GetAt(endPos);
218
219    if (c != TEXT('_'))
220    {
221        SendChar(c);
222        GetSel(startPos, endPos);
223    }
224
225    // check the valid string character
226    if (m_strValid.Find((TCHAR)nChar) != -1)
227        return TRUE;
228
229    // check the key against the mask
230    c = m_strMask.GetAt(endPos);
231
232    switch (c)
233    {
234    case TEXT('0'):       // digit only // completely changed this
235        {
236            BOOL doit = TRUE;
237
238            if (isdigit(nChar))
239            {
240                if (m_isdate)
241                {
242                    if (endPos == 0)
243                    {
244                        if (nChar > TEXT('3'))
245                            doit = FALSE;
246                    }
247
248                    if (endPos == 1)
249                    {
250                        if (m_str.GetAt(0) == TEXT('3'))
251                        {
252                            if (nChar > TEXT('1'))
253                                doit = FALSE;
254                        }
255                    }
256
257                    if (endPos == 3)
258                    {
259                        if (nChar > TEXT('1'))
260                            doit = FALSE;
261                    }
262
263                    if (endPos == 4)
264                    {
265                        if (m_str.GetAt(3) == TEXT('1'))
266                        {
267                            if (nChar > TEXT('2'))
268                                doit = FALSE;
269                        }
270                    }
271                }
272                else if (m_bisTime)
273                {
274                    if (endPos == 0)
275                    {
276                        if (nChar > static_cast < UINT>(m_strHours[0]) ||
277                            nChar < static_cast < UINT>(m_strMinHours[0]))
278                            doit = FALSE;
279                    }
280
281                    if (endPos == 1)
282                    {
283                        if (m_str.GetAt(0) == m_strHours[0])
284                        {
285                            if (nChar > static_cast < UINT>(m_strHours[1]))
286                                doit = FALSE;
287                        }
288                        else if (m_str.GetAt(0) == m_strMinHours[0])
289                        {
290                            if (nChar < static_cast < UINT>(m_strMinHours[1]))
291                                doit = FALSE;
292                        }
293                    }
294
295                    if (endPos == 3)
296                    {
297                        if (nChar > static_cast < UINT>(m_strMins[0]) ||
298                            nChar < static_cast < UINT>(m_strMinMins[0]))
299                            doit = FALSE;
300                    }
301
302                    if (endPos == 4)
303                    {
304                        if (m_str.GetAt(3) == m_strMins[0])
305                        {
306                            if (nChar > static_cast < UINT>(m_strMins[1]))
307                                doit = FALSE;
308                        }
309                        else if (m_str.GetAt(3) == m_strMinMins[0])
310                        {
311                            if (nChar < static_cast < UINT>(m_strMinMins[1]))
312                                doit = FALSE;
313                        }
314                    }
315                }
316
317                return doit;
318            }
319            break;
320        }
321    case TEXT('9'):       // digit or space
322        {
323            if (isdigit(nChar) || nChar == VK_SPACE)
324                return TRUE;
325
326            break;
327        }
328    case TEXT('#'):       // digit or space or '+' or '-'
329        {
330            if (isdigit(nChar) || nChar == VK_SPACE ||
331                nChar == VK_ADD || nChar == VK_SUBTRACT)
332                return TRUE;
333
334            break;
335        }
336    case TEXT('L'):       // alpha only
337        {
338            if (isalpha(nChar))
339                return TRUE;
340
341            break;
342        }
343    case TEXT('?'):       // alpha or space
344        {
345            if (isalpha(nChar) || nChar == VK_SPACE)
346                return TRUE;
347
348            break;
349        }
350    case TEXT('A'):       // alpha numeric only
351        {
352            if (isalnum(nChar))
353                return TRUE;
354
355            break;
356        }
357    case TEXT('a'):       // alpha numeric or space
358        {
359            if (isalnum(nChar) || nChar == VK_SPACE)
360                return TRUE;
361
362            break;
363        }
364    case TEXT('&'):       // all print character only
365        {
366            if (isprint(nChar))
367                return TRUE;
368
369            break;
370        }
371    default:
372        break;
373    }
374
375    MessageBeep(static_cast < UINT>(-1));
376    return FALSE;
377}
378
379void CMaskEdit::OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags)
380{
381    // si un masque existe, tester les touches spéciales
382    if (m_bUseMask)
383    {
384        if (nChar == VK_DELETE || nChar == VK_INSERT)
385            return;
386    }
387
388    CEdit::OnKeyDown(nChar, nRepCnt, nFlags);
389}
390
391
392/////////////////////////////////////////////////////////////////////////////
393// CTimeEdit class completely new
394
395IMPLEMENT_DYNAMIC(CTimeEdit, CMaskEdit)
396
397BEGIN_MESSAGE_MAP(CTimeEdit, CMaskEdit)
398//{{AFX_MSG_MAP(CTimeEdit)
399    ON_WM_RBUTTONDOWN()
400    //}}AFX_MSG_MAP
401END_MESSAGE_MAP()
402
403CTimeEdit::CTimeEdit()
404{
405    m_bUseMask = TRUE;
406    m_isdate = FALSE;
407    m_strMask = TEXT("00:00");
408    m_strLiteral = TEXT("__:__");
409}
410
411void CTimeEdit::SetTime(COleDateTime& Date)
412{
413    CString strText;
414    FormatCOleDateTime(strText, Date, 5);
415    m_str = m_strMaskLiteral = strText;
416    SetWindowText(strText);
417}
418
419void CTimeEdit::SetTime(CString Date)
420{
421    m_str = m_strMaskLiteral = Date;
422    SetWindowText(Date);
423}
424
425COleDateTime CTimeEdit::GetTime()
426{
427    CString strText;
428    GetWindowText(strText);
429    return ReadCOleDateTime(strText);
430}
431
432CString CTimeEdit::GetTimeStr()
433{
434    CString strText;
435    GetWindowText(strText);
436    return strText;
437}
438
439void CTimeEdit::SetHours(int hrs)
440{
441    m_strHours.Format(TEXT("%.2u"), hrs);
442}
443
444void CTimeEdit::SetMins(int hrs)
445{
446    m_strMins.Format(TEXT("%.2u"), hrs);
447}
448
449void CTimeEdit::SetMinHours(int hrs)
450{
451    m_strMinHours.Format(TEXT("%.2u"), hrs);
452}
453
454void CTimeEdit::SetMinMins(int hrs)
455{
456    m_strMinMins.Format(TEXT("%.2u"), hrs);
457}
458
459void CTimeEdit::OnRButtonDown(UINT /*nFlags*/, CPoint /*point*/)
460{
461    return;
462}
Note: See TracBrowser for help on using the repository browser.