/*===========================================================================*
* *
* sflcvdp.c - *
* *
* Copyright (c) 1991-2003 iMatix Corporation *
* *
* ------------------ GPL Licensed Source Code ------------------ *
* iMatix makes this software available under the GNU General *
* Public License (GPL) license for open source projects. For *
* details of the GPL license please see www.gnu.org or read the *
* file license.gpl provided in this package. *
* *
* This program is free software; you can redistribute it and/or *
* modify it under the terms of the GNU General Public License as *
* published by the Free Software Foundation; either version 2 of *
* the License, or (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public *
* License along with this program in the file 'license.gpl'; if *
* not, write to the Free Software Foundation, Inc., 59 Temple *
* Place - Suite 330, Boston, MA 02111-1307, USA. *
* *
* You can also license this software under iMatix's General Terms *
* of Business (GTB) for commercial projects. If you have not *
* explicitly licensed this software under the iMatix GTB you may *
* only use it under the terms of the GNU General Public License. *
* *
* For more information, send an email to info@imatix.com. *
* -------------------------------------------------------------- *
*===========================================================================*/
#include "prelude.h" /* Universal header file */
#include "sflconv.h" /* Prototypes for functions */
#include "sfldate.h" /* Date/time library functions */
#include "sflstr.h" /* String-handling functions */
/* ---------------------------------------------------------------------[<]-
Function: conv_date_pict
Synopsis: Converts a date to a string using a picture. The picture is
composed of any combination of these formats:
cc century 2 digits, 01-99
y day of year, 1-366
yy year 2 digits, 00-99
yyyy year 4 digits, 100-9999
m month, 1-12
mm month, 01-12
mmm month, 3 letters
mmmm month, full name
MMM month, 3 letters, ucase
MMMM month, full name, ucase
d day, 1-31
dd day, 01-31
ddd day of week, Sun-Sat
dddd day of week, Sunday-Saturday
DDD day of week, SUN-SAT
DDDD day of week, SUNDAY-SATURDAY
w day of week, 1-7 (1=Sunday)
ww week of year, 1-53
q year quarter, 1-4
\x literal character x
other literal character
Returns the formatted result. This is a static string, of at most 80
characters, that is overwritten by each call. If date is zero, returns
an empty string. The 'm' and 'd' formats output a leading space when
used at the start of the picture. This is to improve alignment of
columns of dates. The 'm' and 'd' formats also output a space when the
previous character was a digit; otherwise the date components stick
together and are illegible.
Examples:
puts (conv_date_pict (19951202, "mm d, yy"));
Dec 2, 95
puts (conv_date_pict (19951202, "d mmm, yy"));
2 Dec, 95
---------------------------------------------------------------------[>]-*/
char *
conv_date_pict (
long date,
const char *picture)
{
static char
*month_name [] =
{
"January", "February", "March", "April", "May", "June", "July",
"August", "September", "October", "November", "December"
},
*day_name [] =
{
"Sunday", "Monday", "Tuesday", "Wednesday",
"Thursday", "Friday", "Saturday"
},
formatted [FORMAT_MAX + 1]; /* Formatted return string */
int
century, /* Century component of date */
year, /* Year component of date */
month, /* Month component of date */
day, /* Day component of date */
cursize; /* Size of current component */
char
*dest, /* Store formatted data here */
ch, /* Next character in picture */
lastch = '0'; /* Last character we output */
long
full_date = date;
conv_reason = 0; /* No conversion errors so far */
/* Zero date is returned as empty string */
if (date == 0)
{
strclr (formatted);
return (formatted);
}
default_century (&full_date);
century = GET_CENTURY (full_date);
year = GET_YEAR (full_date);
month = GET_MONTH (full_date);
day = GET_DAY (full_date);
ASSERT (month > 0 && month <= 12);
ASSERT (day > 0 && day <= 31);
/* Scan through picture, converting each component */
dest = formatted;
*dest = 0; /* string is empty */
while (*picture)
{
/* Get character and count number of occurences */
ch = *picture++;
for (cursize = 1; *picture == ch; cursize++)
picture++;
switch (ch)
{
/* cc century 2 digits, 01-99 */
case 'c':
if (cursize == 2)
sprintf (dest, "%02d", century);
break;
/* y day of year, 1-366 */
/* yy year 2 digits, 00-99 */
/* yyyy year 4 digits, 0100-9999 */
case 'y': /* y = day of year */
if (cursize == 1)
sprintf (dest, "%d", julian_date (full_date));
else
if (cursize == 2)
sprintf (dest, "%02d", year);
else
if (cursize == 4)
sprintf (dest, "%02d%02d", century, year);
break;
/* m month, 1-12 */
/* mm month, 01-12 */
/* mmm month, 3 letters */
/* mmmm month, full name */
case 'm':
if (cursize == 1)
sprintf (dest, (isdigit (lastch)? "%2d": "%d"), month);
else
if (cursize == 2)
sprintf (dest, "%02d", month);
else
if (cursize == 3)
{
memcpy (dest, month_name [month - 1], 3);
dest [3] = 0;
}
else
if (cursize == 4)
strcpy (dest, month_name [month - 1]);
break;
/* MMM month, 3-letters, ucase */
/* MMMM month, full name, ucase */
case 'M':
if (cursize == 3)
{
memcpy (dest, month_name [month - 1], 3);
dest [3] = 0;
strupc (dest);
}
else
if (cursize == 4)
{
strcpy (dest, month_name [month - 1]);
strupc (dest);
}
break;
/* d day, 1-31 */
/* dd day, 01-31 */
/* ddd day of week, Sun-Sat */
/* dddd day of week, Sunday-Saturday */
case 'd':
if (cursize == 1)
sprintf (dest, (isdigit (lastch)? "%2d": "%d"), day);
else
if (cursize == 2)
sprintf (dest, "%02d", day);
else
if (cursize == 3)
{
memcpy (dest, day_name [day_of_week (full_date)], 3);
dest [3] = 0;
}
else
if (cursize == 4)
strcpy (dest, day_name [day_of_week (full_date)]);
break;
/* DDD day of week, SUN-SAT */
/* DDDD day of week, SUNDAY-SATURDAY */
case 'D':
if (cursize == 3)
{
memcpy (dest, day_name [day_of_week (full_date)], 3);
dest [3] = 0;
strupc (dest);
}
else
if (cursize == 4)
{
strcpy (dest, day_name [day_of_week (full_date)]);
strupc (dest);
}
break;
/* w day of week, 1-7 (1=Sunday) */
/* ww week of year, 1-53 */
case 'w':
if (cursize == 1)
sprintf (dest, "%d", day_of_week (full_date) + 1);
else
if (cursize == 2)
sprintf (dest, "%d", week_of_year (full_date));
break;
/* q year quarter, 1-4 */
case 'q':
if (cursize == 1)
sprintf (dest, "%d", year_quarter (full_date));
break;
/* \x literal character x */
case '\\':
ch = *picture++;
}
if (*dest) /* If something was output, */
while (*dest) /* skip to end of string */
dest++;
else
while (cursize--) /* Else output ch once or more */
*dest++ = ch; /* and bump dest pointer */
lastch = *(dest - 1); /* Get previous character */
*dest = 0; /* Terminate the string nicely */
}
return (formatted);
}