Report Designer Rule Functions - Date/Time and Other String Conversion Functions

Report Designer Rule Functions - Date/Time and Other String Conversion Functions

When building Report Designer rules there a re a bunch of date/time functions (and others) available in the string conversion functions. Here are some MEDITECH articles that are a great reference when using these functions. I have also included the M-AT source code for these functions. This is helpful in figuring out what arguments need to be setup for these Report Designer functions.

 
Some additional related articles: 
MEDITECH KB article #41937 - Selecting By A Date Range of the Previous Month
MEDITECH KB article #40054 - Reformat Date and Time Elapsed Calculation in a Rule



MisUtilities.DateTimeGen.C

//:Doc Purpose
//  This ExternalSubRoutineSet contains many of the adjustment, formatting,
//  and conversion utilities for date, time, and datetime data.
//
//:Doc Additional Notes
//  All of the utilities in this ExternalSubRoutineSet are documented in the
//  M-AT Wiki.  Adding any new utilities or functions need to be added to that
//  documentation.
//
#Translation
  :Options
    Result                        MSFile
    Result                        FSFile
  :Product
    Type                          ExternalSubroutineSet

#Preamble

#Magic

:EntryPoint                       AdjustDate
:EntryPoint                       ElapsedDates
:EntryPoint                       ElapsedDatesAsAge
:EntryPoint                       AgeToBdate
:EntryPoint                       FormatTime
:EntryPoint                       FormatDate
:EntryPoint                       DayOfWeek
:EntryPoint                       Month
:EntryPoint                       CreateDateTime
:EntryPoint                       GetLocalDate
:EntryPoint                       GetLocalTime
:EntryPoint                       GetZoneLabel
:EntryPoint                       AdjustDateTime
:EntryPoint                       ElapsedDateTimes
:EntryPoint                       ElapsedDateTimesAsAge
:EntryPoint                       SecondsToDateTime
:EntryPoint                       DateTimeToSeconds
:EntryPoint                       FormatDateTime
:EntryPoint                       FormatLocalDate
:EntryPoint                       FormatLocalTime
:EntryPoint                       CreateDateTimeOt
:EntryPoint                       DateTimeOtDateOnly
:EntryPoint                       ExtToIntDateTime
:EntryPoint                       ExtToIntDateTime5
:EntryPoint                       ExtToIntDateTimeOt
:EntryPoint                       CompareAges
:EntryPoint                       DateLimit
:EntryPoint                       GmtFromDateTime

:Code AdjustDate
// arg - {YYYYMMDD,value to add,override unit}
@IF{|1@IF{|0="-" ~|0}?"N"@NV "";
    |0@CallSub(ValidDate)@NV "";
    1 ^{X,A,U}
      U|0@UA^U
      {X,A}@IF{U="Y" @CallSub(DateAddYears);
               U="M" @CallSub(DateAddMonths);
               U@{="D",@NV}@! @CallSub(DateAddDays);
               1 ""}};

:Code ElapsedDates
// arg - {YYYYMMDD,YYYYMMDD,override unit,override precision}
^{F,T,U,P}
U|0@UA^U
IF{{F,T}@[@CallSub(ValidDate)]@&@NV "";
   U@{="D",@NV}@! {T,F}@CallSub(DaysElapsed);
   P@CallSub(ValidPrecision)^P@NV "";
   U@IF{="Y" 12;="M" 1;1 ""}^U@NV "";
   {{F,T},{U,P}}@CallSub(Age)};

:Code ElapsedDatesAsAge
// arg - {YYYYMMDD,YYYYMMDD}
@IF{@CV=1 @{,"T"@ToInternal(DATE)}@JV}
@IF{@[@CallSub(ValidDate)]@&@NV "";
    1 @{}@CallSub(Age)};

:Code AgeToBdate
// arg - {YY.MM.DD,YYYYMMDD}
@IF{@CV=1 @{,"T"@ToInternal(DATE)}@JV}
@IF{|0@CallSub(ValidAge)@NV "";
    |1@CallSub(ValidDate)@NV "";
    1 @{}@CallSub(DateFromAge)};

:Code FormatTime
// arg - {HHMM(SS),override parameter(12, "12C", or 24),display seconds("S" or "SZ"),allow 2400}
^{T,D,S,A},
IF{T@CallSub(ValidTime)@NV "";
   D@{@NV,=12,="12C",=24}@!@NV "";
   S@{@NV,="S",="SZ"}@!@NV "";
   IF{D;@GetStateVariable(ClockFormat)}^D,
   {T=2359,A}@& D@IF{=12 "12:00 ed";="12C" "12:00e";1 "24:00"};
   (T$2@IF{D$2=12 @IF{=00 12;>12 -12;+0}},
    ":",T$4%2,
    S@IF{="S" T~$4;="SZ" IF{T~$4;00}}@IF{ @(":",)},
    IF{D=12 (" ",IF{T$2<12 "a";"p"},"m");
       D="12C" IF{T+0=0 "m";IF{T$2=12 T~$2+0=0} "n";T$2<12 "a";"p"}})};

:Code FormatDate
// arg - {YYYYMMDD,format name}
@IF{|0@CallSub(ValidDate)@NV "";
    IF{|1;"NUMERIC"}@CallSub(ValidDateFormat)^F@NV "";
    F="SPECIAL1" |0@CallSub(FormatDateSpecial1);
    F="DAYDATEMONTHYEAR" |0@CallSub(FormatDateDayDateMonthYear);
    1 @{|0,F,|1@{#" ",@SV}@<}@CallSub(FormatDateInt)};

:Code DayOfWeek
// arg - {YYYYMMDD,"S" or "L"}
@IF{|0@CallSub(ValidDate)@NV "";
    IF{|1|0@UA;"S"}^F~="L"~="S" "";
    1 @{@CallList(Days),|0@{$4,$6%2,%2}@DT}@|
      @IF{F="S" $3}};

:Code Month
// arg - {YYYYMMDD,"S" or "L"}
@IF{|0@CallSub(ValidDate)@NV "";
    IF{|1|0@UA;"S"}^F~="L"~="S" "";
    1 @{@CallList(Months),|0$6%2}@|
      @IF{F="S" $3}};

:Code CreateDateTime
// arg - {YYYYMMDD,HHMMSS,override time zone,optional "D" or "S" for ambiguous hour,1}
@IF{|0@CallSub(ValidDate)@NV "";
    |1@CallSub(ValidTime)@NV "";
    |3@UA~="D"~="S" "";
    1 @{@(|0,".",|1),|2,|3,|4}@GetDateTimeFromLocal()};

:Code GetLocalDate
// arg - {DateTime,no-op,override zone}
^{D,,Z},
IF{Z {D|0,Z}@GetDateTimeFromGMT()^D},
IF{D@CallSub(ValidDateTime)@NV "";
   D|1;
   D|0$8};

:Code GetLocalTime
// arg - {DateTime,return seconds("S" or "SZ"),override zone}
^{T,S,Z},
IF{Z {T|0,Z}@GetDateTimeFromGMT()^T},
IF{T@CallSub(ValidDateTime)@NV "";
   T|2@NV "";
   S@{@NV,="S",="SZ"}@!@NV "";
   (T|2,IF{S="S" T|0~$13;S="SZ" IF{T|0~$13;00}})};

:Code GetZoneLabel
// arg - {DateTime}
|0@IF{|3@NV "";
      |4 |3@GetTimeZoneDltLabel();
      1 |3@GetTimeZoneStdLabel()};

:Code AdjustDateTime
//:Doc Purpose
//  Adjust a DateTime by the defined value.
//
//:Doc Arguments
//  |0 - X - DateTime
//  |1 - A - Value to Add
//  |2 - U - Override Unit
//
//:Doc Local Variables
//  A - Value to Add
//  U - Override Unit
//  S - Sign. Either "-" for negative values or "" for positive values
//  X - DateTime
//
//:Doc Returns
//  Returns an adjusted DateTime. Nil is returned if the Value to Add is not in the correct format.
//
^{X,A,U},
U@UA^U,
IF{A@IF{|0="-" ~|0}
   @IF{U="DUR" @ToExternal(DURATION)@Valid(DURATION);
       @{,"N"}@?;
       1 ""}@NV "";
   X|3@GetTimeZoneName()@NV "";
   X@CallSub(ValidDateTime)@NV "";
   IF{{X}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,DateTimeOtDateOnly) X@{|0,|1,0000,|3,|4}^X},
   IF{U="DUR"@NV {{A,U}};
      A@CallSub(GetDurAdjList)}
   @[^{A,U},
     IF{X@NV "";
        U|0="Y" X@IF{|1;1 |0$8}@{,A}@CallSub(DateAddYears)
                @{@(,".",X@(|2,|0~$13)),X|3,IF{X|4 "D";"S"}}@GetDateTimeFromLocal();
        U$2="MO" X@IF{|1;1 |0$8}@{,A}@CallSub(DateAddMonths)
                 @{@(,".",X@(|2,|0~$13)),X|3,IF{X|4 "D";"S"}}@GetDateTimeFromLocal();
        U|0="D" X@IF{|1;1 |0$8}@{,A}@CallSub(DateAddDays)
                @{@(,".",X@(|2,|0~$13)),X|3,IF{X|4 "D";"S"}}@GetDateTimeFromLocal();
        U|0="H" IF{A|0="-"^S A~|0^A}
                X|0$8@IF{A/24>0^D @{,(S,D)}@CallSub(DateAddDays)}
                @{@(,".",X|0~$9),(S,A\24+100%2,00)}@CallSub(OffsetTime)
                @{,X|3}@CallSub(ComposeFromGmt);
        U$2="MI" IF{A|0="-"^S A~|0^A}
                 X|0$8@IF{A/1440>0^D @{,(S,D)}@CallSub(DateAddDays)}
                 @{@(,".",X|0~$9),(S,A\1440/60+100%2,A\60+100%2)}@CallSub(OffsetTime)
                 @{,X|3}@CallSub(ComposeFromGmt);
        U@{|0="S",@NV}@! IF{A|0="-"^S A~|0^A}
                         X|0$8@IF{A/86400>0^D @{,(S,D)}@CallSub(DateAddDays)}
                         @{@(,".",X|0~$9),(S,A\86400/3600+100%2,A\3600/60+100%2,A\60+100%2)}
                         @CallSub(OffsetTime)
                         @{,X|3}@CallSub(ComposeFromGmt);
        U="LH" IF{A|0="-"^S A~|0^A}
               X@IF{|1;1 |0$8}@IF{A/24>0^D @{,(S,D)}@CallSub(DateAddDays)}
               @{@(,".",X@(|2,|0~$13)),(S,A\24+100%2,00)}@CallSub(OffsetTime)
               @{,X|3,IF{X|4 "D";"S"},1}@GetDateTimeFromLocal()
               @IF{|1="X" |0@{,@{@{X,,"H"}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,ElapsedDateTimes)~=(S,A),"X"}};
                   1 |0@{,@{@{X,,"H"}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,ElapsedDateTimes)~=(S,A)}@PV}};
        1 ""}^X],
   X};

:Code GetDurAdjList
//:Doc Purpose
//  Get the list adjustment values for a DURATION DataType.
//
//:Doc Arguments
//  DURATION value in internal form
//
//:Doc Local Variables
//  S - Sign. Either "-" for negative values or "" for positive values
//
//:Doc Returns
//  Returns a list of {{NNN,"D"},{NNN,"H"},{NNN,"MI"}} for all entries with an adjustment number
//  greater than 0.
//
//:Doc Additional Notes
//  Each adjustment value is summed with 0 in order to remove unnecessary zeros from the value.
//
@IF{|0="-"^S ~|0}@AV
@{|0+0@IF{=0 "";@{@(S,),"D"}},
  |2+0@IF{=0 "";@{@(S,),"H"}},
  |4+0@IF{=0 "";@{@(S,),"MI"}}}@OV;

:Code ElapsedDateTimes
// arg - {DateTime,DateTime,override unit,override precision}
^{F,T,U,P}
U@UA^U
IF{U@{|0="Y",$2="MO",|0="D"}@! {F,T}@[|0$8]@{,{U,P}}@MV@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,ElapsedDates);
   {F,T}@[@CallSub(ValidDateTime)]@&@NV "";
   {F,T}@[@IF{@{}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,DateTimeOtDateOnly) @{|0,|1,0000,|3,|4}}]^{F,T}
   {F,T}@[|0$8]@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,ElapsedDates)^D
   {T,F}@[|0~$9@IF{@SV=4 @(,00)}@{$2*3600,$4%2*60,%2}@+]@~-@{,D~*86400}@~+^S
   U@{|0="S",@NV}@! S;
   P@CallSub(ValidPrecision)^P@NV "";
   U@IF{|0="H" 3600;$2="MI" 60;1 ""}^U@NV "";
   ("S:",P~%1+1,"D")@EV~/U
   @IF{P%1="R" ^X("X:",P~%1,"D")@EV;
       1 ~%1@IF{%1="." ~%1}}
   [P~%1^P]@IF{~+0~=0;P=0;("0.",0:P)}};

:Code ElapsedDateTimesAsAge
// arg - {DateTime,DateTime}
@[|0$8]@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,ElapsedDatesAsAge);

:Code SecondsToDateTime
// arg - {Seconds,override zone}
^{S,Z}
IF{S?"N"@NV "";
   {{19800301.000000,Z}@GetDateTimeFromLocal()^A,
    {A,S}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,AdjustDateTime)^B}
   @[|4]
   @IF{@=="+" B;
       @PV=@NL B;
       ={"","+"} {B,0~-3600}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,AdjustDateTime);
       ={"+",""} {B,3600}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,AdjustDateTime);
       1 ""}};

:Code DateTimeToSeconds
// arg - {DateTime,override zone}
^{B,Z}
IF{B@CallSub(ValidDateTime)@NV "";
   {19800301.000000,IF{Z;B|3}}@GetDateTimeFromLocal()^A,
   {A,B}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,ElapsedDateTimes)^S,
   {A,B}@[|4]
   @IF{@=="+" S;
       @PV=@NL S;
       ={"","+"} S~+3600;
       ={"+",""} S~-3600;
       1 ""}?"N"};

:Code FormatDateTime
// arg - {DateTime,date format name,zone label flag,
//        override parameter(12, "12C", or 24),display seconds("S" or "SZ"),allow 2400}
^{T,F,Z,D,S,A}
IF{{T}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,DateTimeOtDateOnly) @{,F}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,FormatDate);
   Z@UA^Z~="Y"~="N" "";
   {T}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,GetLocalDate)^X@NV "";
   {T,S}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,GetLocalTime)^Y@NV "";
   {X,F}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,FormatDate)^X@NV "";
   {Y,D,S,A}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,FormatTime)^Y@NV "";
   (X," ",Y,{T,Z}@CallSub(TimeZoneDisplay))};

:Code FormatLocalDate
// age - {DateTime,date format name}
^{T,F}
IF{{T}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,GetLocalDate)^X@NV "";
   {X,F}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,FormatDate)};

:Code FormatLocalTime
// arg - {DateTime,zone label flag,
//        override parameter(12, "12C", or 24),display seconds("S" or "SZ"),allow 2400}
^{T,Z,D,S,A}
IF{Z@UA^Z~="Y"~="N" "";
   {T,S}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,GetLocalTime)^Y@NV "";
   {Y,D,S,A}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,FormatTime)^Y@NV "";
   (Y,{T,Z}@CallSub(TimeZoneDisplay))};

:Code CreateDateTimeOt
// arg - {YYYYMMDD,HHMMSS,override zone,optional "D" or "S" for ambiguous hour,1}
@IF{|1@NV [|4^E]
          @{|0,0000,|2}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,CreateDateTime)
          @IF{@NV "";
              1 @{|0,|1,"",|3,|4}^A,
                IF{E {A,""};A}};
    1 @CallExternalSub(Mis,MisUtilities.DateTimeGen.C,CreateDateTime)};

:Code DateTimeOtDateOnly
// arg - {DateTime}
|0@IF{@CallSub(ValidDateTime) @IF{|2@NV @IF{|1;1 |0$8};1 ""};
      1 ""};

:Code ExtToIntDateTime
// Arguments: {External DateTime,Override Zone}
//
// Variables: E - External DateTime
//            Z - Override Zone
//
// Returns: {DateTime,Error} on success, else nil
^{E,Z},
E@SA@UA^E,
IF{E="N" {Z@GetCurrentDateTimeForZone(),""};
   {E,Z,"DT"}@CallSub(DateTimeIntConvert)};

:Code ExtToIntDateTime5
// Arguments: {External DateTime,Override Zone}
//
// Variables: E - External DateTime
//            Z - Override Zone
//
// Returns: {DateTime,Error} on success, else nil
^{E,Z},
E@SA@UA^E,
{E,Z,"DT5"}@CallSub(DateTimeIntConvert);

:Code ExtToIntDateTimeOt
// Arguments: {External DateTime,Override Zone}
//
// Variables: E - External DateTime
//            Z - Override Zone
//
// Returns: {DateTime,Error} on success, else nil
^{E,Z},
E@SA@UA^E,
IF{E="N" {Z@GetCurrentDateTimeForZone(),""};
   {E,Z,"DTO"}@CallSub(DateTimeIntConvert)};

:Code CompareAges
// Arguments: {Age1,Age2,Granularity,CompareType}
//
// Variables: A - Age1
//            B - Age2
//            G - Granularity ("Y" = Years, "MO" = Months, "D" = Days)
//                 Default is based on youngest age.  A<1 = "D", 1<=A<5 = "MO", A>=5 = "Y"
//            C - Compare ("E" = equal to, "G" = greater than, "L" = less than,
//                         "LE" = less than or equal to, "GE" = greater than or equal to)
//
// Returns:  Age1 if compare is TRUE, else nil
^{A,B,G,C},
//
//  If either age is not a valid internal form, return nil
IF{A@CallSub(ValidAge)@NV "";
   B@CallSub(ValidAge)@NV "";
   //
   // Pad value as necessary for the granularity passed in or default of "D" for days
   IF{G@UA;
      A&B@AV|0~+0
      @IF{<1 "D";
          <5 "MO";
          1 "Y"}}
   @IF{="D" {A,B}@[@AV@(|0:3Z,".",|2:2Z,".",|4:2Z)];
       ="MO" {A,B}@[@AV@(|0:3Z,".",|2:2Z)];
       ="Y" {A,B}@[@AV|0:3Z];
       1 ""}
   //
   // Compare Age1 (A) to Age2 (B) using the compare argument or default value of "E"
   @IF{@NV "";
       C="L" @<;
       C="G" @>;
       C="LE" @~>;
       C="GE" @~<;
       C@{="E",@NV}@! @=;
       1 ""}
   //
   // Return A if valued, else nil
   IF{ A}};

//-------------------------------------------------------------------

:Code DateLimit
^{M,Y}
M+0^M
IF{M=2 IF{Y\4=0&(Y\100~=0!(Y\400=0)) 29;28};
   M~=4~=6~=9~=11 31;30};

:Code DateAddDays
^{X,A}
X$4^Y,
IF{A|0="-" IF{A~|0/146097>0 @{Y,*400}@~-^Y,A~|0\146097@("-",)^A};
   IF{A/146097>0 *400+Y^Y,A\146097^A}}
X$6%2^M,
IF{A|0="-" X%2~-(A~|0);
   X%2+A}^D
IF{D>28 DO{{M,Y}@CallSub(DateLimit)^L,
           D>L M+1^M,D~-L^D,IF{M>12 M~-12^M,Y+1^Y}};
   DO{D<1 M~-1^M,IF{M<1 Y~-1^Y,M+12^M},{M,Y}@CallSub(DateLimit)^L,D~+L^D}}
(Y,M+100%2,D+100%2);

:Code DateAddMonths
^{X,A}
X$4^Y,X%2^D,
IF{A|0="-" X$6%2~-(A~|0);
   X$6%2+A}^M,
IF{M>12 IF{M\12=0 M/12+Y-1^Y,12^M;
           M/12+Y^Y,M\12^M};
   M>0;
   0~-M^M,
   Y~-1~-(M/12)^Y,
   12-(M\12)^M}
{Y,M,D}@CallSub(AdjustForEndOfMonth);

:Code DateAddYears
^{X,A}
X$6%2^M,X%2^D,
IF{A|0="-" X$4~-(A~|0);
   X$4+A}^Y
{Y,M,D}@CallSub(AdjustForEndOfMonth);

:Code AdjustForEndOfMonth
^{Y,M,D}
{{M,Y}@CallSub(DateLimit),D}@&^D
(Y,M+100%2,D+100%2);

:Code DaysElapsed
[@[$6]@&@IF{%2<03 $4-1;1 $4}/400*400+10000%4^B]
@[@{$4,$6%2,%2}^{Y,M,D}
  {Y-B@IF{M<03 -1}@{/4*1461,\4*365}@+,
   M+9\12@{/5*153,\5/2*61,\5\2*31}@+,
   D}@+
  @{,/36525@{/4*3,\4}@+}@-]@~-;

:Code ValidDate
@{?8N,$4+0>0,$6%2+0>0<13,%2+0>0,@{@{$6%2,$4}@CallSub(DateLimit),%2}@~<}@&;

:Code ValidTime
@IF{?6N @{$2<24,$4$2<60,%2<60}@&;?4N @{$2<24,%2<60}@&;1 ""};

:Code ValidAge
@IF{?"N"<151;
    @AV@{@QV,@CV=5,@{|1=".",|3="."}@&,@{|0?"N",|2"N",|4"N"}@&}@&;
    1 ""};

:Code ValidDateTime
@IF{@QV@NV "";
    |0$8@CallSub(ValidDate)@NV "";
    |0~$9@CallSub(ValidTime)@NV "";
    IF{|2 @CallSub(ValidTime)@NV} "";
    |1@NV;
    |1@CallSub(ValidDate)@NV "";
    1};

:Code ValidPrecision
@UA@IF{@NV "0T";?1N @(,"T");@{="T",="R"}@! @(0,);@{@SV=2,|0?1N,|1@{="T",="R"}@!}@& ;1 ""};

:Code Age
[|0[@IF{|`1,0'@< "-"^S}][@&^F$4^B][@!^T]
IF{{F,T}@[%2]@~> T$6@{%2,$4}@CallSub(DateLimit)^N;
    T$6@IF{%2=01 31;1 @{%2-1,$4}@CallSub(DateLimit)}^N
    {F%2,T%2,N}@> (F$6,N)^F}
{T,F}@[@{$4-B*12*N,$6%2*N,%2}@+]@-^D]
IF{|1^{U,P} ("D:",P~%1+1,"D")@EV~/(U*N)
            @IF{P%1="R" ^X("X:",P~%1,"D")@EV;
                1 ~%1@IF{%1="." ~%1}}
            [P~%1^P]@IF{~+0~=0;P=0;("0.",0:P)}
            @IF{~+0~=0 @(S,)};
   1 (S,D/(12*N),".",D\(12*N)/N+100%2,".",D\N+100%2)};

:Code DateFromAge
|0^{A,T},
A@AV@{|0+0^Y,|2+0^M,|4+0^D},
IF{Y>0 {T,("-",Y)}@CallSub(DateAddYears)^T},
IF{D>0 {T,("-",D)}@CallSub(DateAddDays)^T},
IF{M>0 {T,("-",M)}@CallSub(DateAddMonths)^T},
T;

:Code ValidDateFormat
@UA@IF{@NV "";
       ="DAYDATEMONTHYEAR";
       ="SPECIAL1";
       ="LONG" IF{@CallSub(LongFormatOK);
                  @GetStateVariable(Country)~="US" "D441";
                  "M441"};
       ="SHORT" IF{@CallSub(ShortFormatOK);
                   @GetStateVariable(Country)~="US" "D432";
                   "M432"};
       ~="NUMERIC"~="NUMERIC10"~="NUMERIC8" @CallSub(ConvertDateFormat);
       [IF{@CallSub(NumericFormatOK);
           @GetStateVariable(Country)~="US" "D222";
           "M222"}^F]
       %2=10 F@(|0,4,%2);
       %1=8 F@(|0,2,%2);
       1 F};

:Code LongFormatOK
IF{@GetStateVariable(DateFormatLong) @CallSub(ConvertDateFormat)@{="M441",="D441"}@!};

:Code ShortFormatOK
IF{@GetStateVariable(DateFormatShort) @CallSub(ConvertDateFormat)@IF{~|0~=432 ""}};

:Code NumericFormatOK
IF{@GetStateVariable(DateFormatNumeric) @CallSub(ConvertDateFormat)@IF{="M422";
                                                                       ="D422";
                                                                       ="M222";
                                                                       ="D222";
                                                                       1 ""}};

:Code ConvertDateFormat
@UA@AV@[@IF{?1P "";@QA@WV@NV ""}]@PV
@IF{=@NL "";
    @[|0]@CA^O~="YMD"~="DMY"~="MDY" "";
    @{,O@{#"Y",#"M",#"D"}}@|@[@SV]@CA^L
    ~=442~=441~=432~=431~=232~=231~=422~=222 "";
    1 (O|0,L)@IF{$2="Y2" ""}};

:Code FormatDateInt
[|0[$4^Y][$6%2^M]%2^D]
[IF{IF{|1|1=2 Y@CallSub(InCentury)} Y%2^Y}]
[@IF{|1|2~=2^A [" "^S]
               [@CallList(Months)|M^M]
               |1[IF{|2=3 M$3^M}]IF{|3=1 D+0^D};
     1 [IF{|2 " ";@GetStateVariable(DateNumericPunctuation)=".";"/"}^S]}]
|1|0@IF{="Y" IF{@GetStateVariable(DateFormatShort)$1="D" (Y,S,D,S,M);
                (Y,S,M,S,D)};
        ="M" (M,S,D,IF{A ","},S,Y);
        ="D" (D,S,M,S,Y);
        1 ""};

:Code InCentury
^Y$3^D,
""@GetCurrentDateTime()@IF{|1;1 |0}$3[-5^L]+4^U,
IF{D&U!L=D Y};

:Code FormatDateSpecial1
@{^D,"Y431"}@CallSub(FormatDateInt)
@IF{{D,"T"@ToInternal(DATE)}@[$4]@= @({D}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,DayOfWeek),~$4)};


:Code FormatDateDayDateMonthYear
@{^D,"D431"}@CallSub(FormatDateInt)
@({D}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,DayOfWeek)," ",);


:Code OffsetTime
//:Doc Purpose
//  This code member offsets a time for a give GMT datetime by a number of
//  hours, minutes, and/or seconds.
//
//:Doc Arguments
//  {T,O}
//
//:Doc Local Variables
//  D:  Number of days to decrement, specified as a negative number
//  H:  Hours
//  M:  Minutes
//  O:  Amount to offset time in HHMMSS
//  S:  Seconds
//  T:  GMT datetime in YYYYMMDD.HHMMSS
//
//:Doc Returns
//  Offset GMT datetime in the form YYYYMMDD.HHMMSS.
//
//:Doc Additional Notes
//  Real number addition and subtraction are performed in areas where a
//  negative number could occur.  If the time offset should result in a
//  time on the prior day, the current day is decremented by invoking
//  DateAddDays with a "-1".
//
^{T,O}
T$11%2^H,T$13%2^M,T~$13^S,
IF{O|0="-" O~|0^O
           IF{O@SV=6 S+60-(O%2)
                     @IF{<60 [M~-1^M];
                         1 -60}+100%2^S
                     O$4^O}
           M~+60-(O%2)
           @IF{<60 [H~-1^H];
               1 -60}^M
           H~+24-(O$2)
           @IF{<24 ["-1"^D];
               1 -24}^H;
   IF{O@SV=6 S+(O%2)
             @IF{<60;
                 1 [M+1^M]-60}+100%2^S
             O$4^O}
   M+(O%2)
   @IF{<60;
       1 [H+1^H]-60}^M
   H+(O$2)
   @IF{<24;
       1 [1^D]-24}^H}
IF{D {T$8,D}@CallSub(DateAddDays);
   T$8}
@(,".",H+100%2,M+100%2,S);

:Code ComposeFromGmt
^{G,Z}
IF{{G,Z}@GetTimeOffsetForGmt() [@{G,|0}@CallSub(OffsetTime)^L]
                               @{G,{L$8,G$8}@~=,L$13%4,Z,|1}};

:Code TimeZoneDisplay
@IF{@IF{|1="N" "";
        |1="Y";
        @GetStateVariable(TimeZoneDisplay);
        |0@{@(@IF{|1;1 |0$8},".",|2),|3}@GetTimeOffsetForLocal()="?";
        1 |0@{|3,@GetCurrentTimeZone()}@~=} |0,IF{@{}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,GetZoneLabel) @(" ",)};
    1 ""};

:Code GmtFromDateTime
//:Doc Purpose
//     Extract GMT date information from a DATETIME object.
//
//:Doc Arguments
//     |0: DATETIME
//     |1: Granularity Choice:
//         "Y":  year
//         "MO": month
//         "D":  days
//         "H":  hours
//         "MI": minutes
//         "S":  seconds
//         You can pass granularity text as well such as "YEAR" since only the
//         first letter or two is examined.
//
//:Doc Local Variables
//     D: DATETIME argument
//     G: Granularity (as passed to subroutine)
//
//:Doc Returns
//     GMT date time information depending on granularity argument:
//         "Y":  year   - YYYY
//         "MO": month  - YYYYMM
//         "D":  day    - YYYYMMDD
//         "H":  hour   - YYYYMMDDHH
//         "MI": minute - YYYYMMDDHHMM
//         "S":  second - YYYYMMDDHHMMSS
//     Nil is returned if the date is invalid or the granularity is unrecognized.
//
^{D,G},
G@UA
@IF{D@CallSub(ValidDateTime)@NV "";
    |0="Y" D|0$4;
    $2="MO" D|0$6;
    |0="D" D|0$8;
    |0="H" D|0@AV@(|0,|2$2);
    $2="MI" D|0@AV@(|0,|2$4);
    |0="S" D|0@AV@(|0,|2);
    1 ""};

:List Days
{Sunday|Monday|Tuesday|Wednesday|Thursday|Friday|Saturday}

:List Months
{|January|February|March|April|May|June|July|August|September|October|November|December}

:Code DateTimeIntConvert
// Arguments: {External DateTime,Override Zone,Type}
//
// Variables: E - External DateTime
//            Z - Override Zone
//            O - Type ("DT", "DT5", or "DTO")
//            P - Space Delimiter Location
//            D - Date
//            T - Time
//
// Returns: {DateTime,Error} on success, else nil
^{E,Z,O},
E#" "^P,
E$P^D,
E~$P@SA@IF{@{%2="AM",%2="PM",%1="A",%1="P"}@! ;
           @{@{%2="ED",%1="E"}@!,O="DT5"}@& ;
           @{~#" ",@SV}@<^P ~%P}^T,
IF{D@Valid(DATE)@NV "";
   IF{O="DT5" T@Valid(HHMM5)@NV;
      T @Valid(HHMM)@NV;
      O="DTO"@NV} "";
   D@ToInternal(DATE)^D,
   IF{O="DT5" T@ToInternal(HHMM5);T@ToInternal(HHMM)}^T,
   O="DTO" {D,T,Z,"",1}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,CreateDateTimeOt);
   {D,T,Z,"",1}@CallExternalSub(Mis,MisUtilities.DateTimeGen.C,CreateDateTime)};


    • Related Articles

    • Report Designer Rule Functions

      https://customer.meditech.com/en/d/prwrd/pages/rd6basmatrulefunctions.htm
    • Report Designer Export Report Records

      When creating a MEDITECH Report Designer "Export" format type of report, you must define record names for each data row in the report download file. Each record name will force a new row to be created on the report. Typically you don't want this. ...
    • Patient Lookup On Report Designer

      To get the patient name, number, lookup on a report designer report use the RegAcct.AccountNumber with override data type value of object identifier, pointer RegAcct and pointed to field AcctNumber. This give user the ability to use name, medical ...
    • List of MEDITECH Reports that we have Archived for Customers

      This is a list of some of the more popular reports that we have run out of MEDITECH and archived to PaperStore or another archive solution, like MEDITECH Scanning and Archiving. Whenever we start working on MEDITECH archiving projects, customers ...
    • BarAcct Transaction Types for 6.1 MEDITECH Patient Accounting (B/AR)

      Transaction Type Mnemonic Name ADJ ATE BCS BDX BFW BPR CCX CEA CED CHG CLM CLT CPX CQD CRM CSQ CSR CSX DEL DIS GED IBX IED INT LTR MRK NTC NTE PAY PST REF REV RMC RPR SED SGC STM TSK Adjustment Account Type Edit Biller/Collector/Coll Stream Edit Bad ...