07469d2d0d55667942c3d64ebbc9d473eee97d53
tdreszer
  Thu Feb 10 14:56:58 2011 -0800
Moved date routines into common, and made expired restriction dates dimmer in hgTrackUi
diff --git src/lib/common.c src/lib/common.c
index ef7b762..ca004a6 100644
--- src/lib/common.c
+++ src/lib/common.c
@@ -3004,15 +3004,88 @@
     struct tm storage={0,0,0,0,0,0,0,0,0};
     if(strptime(date,format,&storage)==NULL)
         return 0;
     else
         return mktime(&storage);
 }
 
 boolean dateIsOld(const char *date,const char*format)
 // Is this string date older than now?
 {
 time_t test = dateToSeconds(date,format);
 time_t now = clock1();
 return (test < now);
 }
 
+static int daysOfMonth(struct tm *tp)
+/* Returns the days of the month given the year */
+{
+int days=0;
+switch(tp->tm_mon)
+    {
+    case 3:
+    case 5:
+    case 8:
+    case 10:    days = 30;   break;
+    case 1:     days = 28;
+                if( (tp->tm_year % 4) == 0
+                && ((tp->tm_year % 20) != 0 || (tp->tm_year % 100) == 0) )
+                    days = 29;
+                break;
+    default:    days = 31;   break;
+    }
+return days;
+}
+
+static void dateAdd(struct tm *tp,int addYears,int addMonths,int addDays)
+/* Add years,months,days to a date */
+{
+tp->tm_mday  += addDays;
+tp->tm_mon   += addMonths;
+tp->tm_year  += addYears;
+int dom=28;
+while( (tp->tm_mon >11  || tp->tm_mon <0)
+    || (tp->tm_mday>dom || tp->tm_mday<1) )
+    {
+    if(tp->tm_mon>11)   // First month: tm.tm_mon is 0-11 range
+        {
+        tp->tm_year += (tp->tm_mon / 12);
+        tp->tm_mon  = (tp->tm_mon % 12);
+        }
+    else if(tp->tm_mon<0)
+        {
+        tp->tm_year += (tp->tm_mon / 12) - 1;
+        tp->tm_mon  =  (tp->tm_mon % 12) + 12;
+        }
+    else
+        {
+        dom = daysOfMonth(tp);
+        if(tp->tm_mday>dom)
+            {
+            tp->tm_mday -= dom;
+            tp->tm_mon  += 1;
+            dom = daysOfMonth(tp);
+            }
+        else if(tp->tm_mday < 1)
+            {
+            tp->tm_mon  -= 1;
+            dom = daysOfMonth(tp);
+            tp->tm_mday += dom;
+            }
+        }
+    }
+}
+
+char *dateAddTo(char *date,char *format,int addYears,int addMonths,int addDays)
+/* Add years,months,days to a formatted date and returns the new date as a cloned string
+*  format is a strptime/strftime format: %F = yyyy-mm-dd */
+{
+char *newDate = needMem(12);
+struct tm tp;
+if(strptime (date,format, &tp))
+    {
+    dateAdd(&tp,addYears,addMonths,addDays); // tp.tm_year only contains years since 1900
+    strftime(newDate,12,format,&tp);
+    }
+return cloneString(newDate);  // newDate is never freed!
+}
+