Designer or ViSi: Routine for Parsing a Time String
Introduction
This codebase example shows how to parse a time string to find the hour, minute, and second information. The program expects the input string to be of the format hh:mm:ss xx
, where,
- hh = hour
- mm = minute
- ss = second
- xx = "am/pm/nn/mn" indicator
When the hour is 0 or greater than twelve, the input is assumed to be of the 24-hour format, hence, the indicator is ignored.
Note
That the indicator "xx" may be excluded from the input string.
Example 1: input: "12:0:0 am" , output: globalHour = 0 , globalMinute = 0, globalSecond = 0;
Example 2: input: "12:00:0" , output: globalHour = 0 , globalMinute = 0, globalSecond = 0;
Example 3: input: "12:34:45 PM", output: globalHour = 12, globalMinute = 34, globalSecond = 45;
Example 4: input: "15:6:9 Am" , output: globalHour = 15, globalMinute = 6, globalSecond = 9, indicator is ignored
Example 1: input: "99:99:99" , output: globalHour = 99 , globalMinute = 99, globalSecond = 99;
If the program does not understand the input time string, it prints out an error message.
Prerequisites
This codebase example assumes the reader can program the 4D Systems display module using Workshop4 IDE ViSi or Designer environment. Beginners are advised to read the following aplication notes.
How the Program Works
In summary, the program does the following:
-
Find the locations of the first and second colon characters and the first space character. The program prints out an error message if both colon characters are not found.
-
Use the data in step 1 to locate the hour, minute, second, and indicator (if it exists) substrings and copy them to separate arrays.
-
Extract any decimal number from the minute substring and convert it to its equivalent integer value, which is then stored in the global variable "globalMinute". The minute substring must be one- or two-characters wide. If the program cannot find a decimal number in the minute substring, it prints the message "No minute extracted.".
-
Extract any decimal number from the second substring and convert it to its equivalent integer value, which is then stored in the global variable "globalSecond". The second substring must be one- or two-characters wide. If the program cannot find a decimal number in the second substring, it prints the message "No second extracted.".
-
Extract any decimal number from the hour substring and convert it to its equivalent integer value, which is then stored in the global variable "globalHour". The hour substring must be one- or two-characters wide. If the program cannot find a decimal number in the hour substring, it prints the message "No hour extracted.".
-
Compare the indicator substring (if it exists) to a list of stored strings of correct and expected indicators. Note that the indicator substring must be one- or two- characters long and that the matching process is case insensitive. If the program finds a match for the input indicator substring, it may modify the value stored in "globalHour". Otherwise it prints out an error message.
Note
This program will only parse a string for the hour, minute, and second information; it will not check if the information is valid. For example, "99:99:99" is a valid input since it has an hour, minute, and second information. Further testing of the values of the extracted variables can be easily implemented by the user using the code snippet in 4D-CD-00023 Designer or ViSi Time and Date Validation.
To see an actual example of a more complete time string check, see the codebase example 4D-CD-00044 Designer or ViSi Parse and Check a Time String. 4D-CD-00044 combines this example (4D-CD-00042) and 4D-CD-00023 Designer or ViSi Time and Date Validation to perform both parsing and checking the validity of a time string. Furthermore, 4D-CD-00044 shows how the source code in this example(4D-CD-00042) is converted to an include file that can be used in a larger project.
All variables and arrays used in the program are located inside the array PTClass[]
.
This array contains PTi + 1 words, some of which are used for storing strings, and some are used as variables. A list of constants is then used for indexing into the array. The list is partially shown below.
#CONST
PTssHour // 2 words for hour substring array
PTssMinute 2 // 2 words for minute substring array
PTssSecond 4 // 2 words for second substring array
PTssIndic 6 // 2 words for "am/pm/nn/mn" indicator substring array
PTptrBGTime 8 // 1 word for byte-aligned pointer to input time string array
PTptrSSHour // 1 word for byte-aligned pointer to hour substring array
PTptrSSMinute // 1 word for byte-aligned pointer to minute substring array
PTptrSSSecond // 1 word for byte-aligned pointer to second substring array
PTptrSSIndic // 1 word for byte-aligned pointer to "am/pm/nn/mn" indicator substring array
PTptrWGTime // 1 word for word-aligned pointer to global time string array
PTptrGHour // 1 word for word-aligned pointer to global hour
...
PTindicFlag // 1 word for indicator existence flag
PTi // 1 word as a general-purpose variable
#END
The constants have the implicit values shown below:
#CONST
PTssHour 0 // implicit value
PTssMinute 2 // explicit value
PTssSecond 4 // explicit value
PTssIndic 6 // explicit value
PTptrBGTime 8 // explicit value
PTptrSSHour 9 // implicit value
PTptrSSMinute 10 // implicit value
PTptrSSSecond 11 // implicit value
PTptrSSIndic 12 // implicit value
PTptrWGTime 13 // implicit value
PTptrGHour 14 // implicit value
...
PTindicFlag 25 // implicit value
PTi 26 // implicit value
#END
Thus, we can use the 27th element of the array as a general-purpose counter variable:
Also, we can use the fifteenth element of the array as a pointer to another variable:
To access the content of the global variable "globalHour", we can dereference its pointer:
To assign a value to the global variable "globalHour" thru its pointer we write,
Also, we can input a sequence of bytes (e.g. the input hour substring) starting at the address of PTClass[PTssHour]:
We arbitrarily limit the length of the input byte sequence to 4 including the null terminator, so it will not overlap with the bytes located starting at &PTClass[PTssMinute].
We can use an element of the big array "PTClass[]" as a byte-aligned pointer to another section of the array:
Putting all variables and "sub-arrays" inside a large array and using constants in an organized list as indices into the array allow for the writing of the definitions (as comments) of all the variables and arrays in one place in the source code.
Instructions
-
In the attached Designer code, modify the input time string on line 96. Compile the project and upload it to a uLCD-32PTU (or your target display).
-
The program should now run on the display module. See the video for more information.