diff --git a/100_core/src/gplx/DateAdp.java b/100_core/src/gplx/DateAdp.java
index fa12a01d3..be7f7c0fb 100644
--- a/100_core/src/gplx/DateAdp.java
+++ b/100_core/src/gplx/DateAdp.java
@@ -85,6 +85,9 @@ public class DateAdp implements CompareAble, Gfo_invk {
: Timezone_offset_test
;
}
+ public String Timezone_id() {
+ return "UTC"; // under.getTimeZone().getID(); // NOTE: timezone is always UTC, unless over-ridden by tests
+ }
public DateAdp XtoUtc() {
java.util.Date date = under.getTime();
java.util.TimeZone tz = under.getTimeZone();
@@ -109,6 +112,7 @@ public class DateAdp implements CompareAble, Gfo_invk {
long dst_adj = dst ? 3600000 : 0;
return (under.getTimeInMillis() + offsetFromUTC + dst_adj) / 1000;
}
+
public int WeekOfYear() {return under.get(Calendar.WEEK_OF_YEAR);}
public int Frac() {return under.get(Calendar.MILLISECOND);}
public DateAdp Add_frac(int val) {return CloneAndAdd(Calendar.MILLISECOND, val);}
diff --git a/100_core/src/gplx/DateAdp__tst.java b/100_core/src/gplx/DateAdp__tst.java
index 02d99a22f..0bc081a95 100644
--- a/100_core/src/gplx/DateAdp__tst.java
+++ b/100_core/src/gplx/DateAdp__tst.java
@@ -60,6 +60,9 @@ public class DateAdp__tst {
@Test public void XtoUtc() {
fxt.Test__to_utc("2012-01-01 00:00", "2012-01-01 05:00"); //4=Wed
}
+ @Test public void Timezone_id() {
+ fxt.Test__timezone_id("2015-12-26T10:03:53Z", "UTC");
+ }
}
class DateAdp__fxt {
public void Test__parse_gplx(String raw, String expd) {
@@ -83,4 +86,7 @@ class DateAdp__fxt {
public void Test__to_utc(String raw, String expd) {
Tfds.Eq(expd, DateAdp_.parse_gplx(raw).XtoUtc().XtoStr_fmt_yyyy_MM_dd_HH_mm());
}
+ public void Test__timezone_id(String raw, String expd) {
+ Gftest.Eq__str(expd, DateAdp_.parse_gplx(raw).XtoUtc().Timezone_id());
+ }
}
diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_.java
index dd2abd9f3..6a4556f52 100644
--- a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_.java
+++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_.java
@@ -52,6 +52,10 @@ public class Pft_fmt_itm_ {
, Tid_hijiri_month_idx = 31
, Tid_hijiri_day_idx = 32
, Tid_hijiri_month_name = 33
+ , Tid_timezone_id_full = 35
+ , Tid_timezone_id_abrv = 36
+ , Tid_timezone_offset_4 = 37
+ , Tid_timezone_offset_4_colon = 38
;
public static final Pft_fmt_itm
@@ -107,6 +111,10 @@ public class Pft_fmt_itm_ {
, Hijiri_month_idx = new Pft_fmt_itm_hijiri_month_idx()
, Hijiri_day_idx = new Pft_fmt_itm_hijiri_day_idx()
, Hijiri_month_name = new Pft_fmt_itm_hijiri_month_name()
+ , Timezone_id_full = new Pft_fmt_itm_timezone_id(Bool_.N)
+ , Timezone_id_abrv = new Pft_fmt_itm_timezone_id(Bool_.Y)
+ , Timezone_offset_4 = new Pft_fmt_itm_timezone_offset_4(Bool_.N)
+ , Timezone_offset_4_colon = new Pft_fmt_itm_timezone_offset_4(Bool_.Y)
;
public static final Btrie_fast_mgr Regy = Btrie_fast_mgr.cs()
.Add(Byte_ascii.Ltr_Y , Pft_fmt_itm_.Year_len4) // 2012
@@ -139,6 +147,10 @@ public class Pft_fmt_itm_ {
.Add(Byte_ascii.Ltr_Z , Pft_fmt_itm_.Timezone_offset) // timezone offset in seconds
.Add(Byte_ascii.Ltr_c , Pft_fmt_itm_.Iso_fmt) // 2012-01-02T03:04:05+00:00
.Add(Byte_ascii.Ltr_r , Pft_fmt_itm_.Rfc_5322) // Mon 02 Jan 2012 08:04:05 +0000
+ .Add(Byte_ascii.Ltr_e , Pft_fmt_itm_.Timezone_id_full) // UTC
+ .Add(Byte_ascii.Ltr_T , Pft_fmt_itm_.Timezone_id_abrv) // UTC
+ .Add(Byte_ascii.Ltr_O , Pft_fmt_itm_.Timezone_offset_4) // timezone offset in seconds +0000
+ .Add(Byte_ascii.Ltr_P , Pft_fmt_itm_.Timezone_offset_4_colon) // timezone offset in seconds with colon +00:00
.Add("xr" , Pft_fmt_itm_.Roman) // MCXI
.Add("xkY" , Pft_fmt_itm_.Thai) // Year += 543
.Add("xoY" , Pft_fmt_itm_.Minguo) // Year -= 1911
diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_seg_int.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_seg_int.java
index 0b51540af..e470205d1 100644
--- a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_seg_int.java
+++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_seg_int.java
@@ -81,12 +81,14 @@ class Pft_fmt_itm_dayOfYear implements Pft_fmt_itm {
class Pft_fmt_itm_am_pm implements Pft_fmt_itm {
public int TypeId() {return Pft_fmt_itm_.Tid_AmPm;}
public void Fmt(Bry_bfr bfr, Xowe_wiki wiki, Xol_lang_itm lang, DateAdp date, Pft_func_formatdate_bldr bldr) {
- boolean am = date.Hour() < 13;
+ boolean am = date.Hour() < 12;
byte[] val = null;
- if ( am && lower) val = Ary_am_lower;
- else if ( am && !lower) val = Ary_am_upper;
- else if (!am && lower) val = Ary_pm_lower;
- else if (!am && !lower) val = Ary_pm_upper;
+ if (am) {
+ val = lower ? Ary_am_lower : Ary_am_upper;
+ }
+ else {
+ val = lower ? Ary_pm_lower : Ary_pm_upper;
+ }
bfr.Add(val);
} private static final byte[] Ary_am_upper = Bry_.new_a7("AM"), Ary_pm_upper = Bry_.new_a7("PM"), Ary_am_lower = Bry_.new_a7("am"), Ary_pm_lower = Bry_.new_a7("pm");
public Pft_fmt_itm_am_pm(boolean lower) {this.lower = lower;} private boolean lower;
diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_timezone.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_timezone.java
new file mode 100644
index 000000000..cf21d9d95
--- /dev/null
+++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_fmt_itm_timezone.java
@@ -0,0 +1,51 @@
+/*
+XOWA: the XOWA Offline Wiki Application
+Copyright (C) 2012-2017 gnosygnu@gmail.com
+
+XOWA is licensed under the terms of the General Public License (GPL) Version 3,
+or alternatively under the terms of the Apache License Version 2.0.
+
+You may use XOWA according to either of these licenses as is most appropriate
+for your project on a case-by-case basis.
+
+The terms of each license can be found in the source code repository:
+
+GPLv3 License: https://github.com/gnosygnu/xowa/blob/master/LICENSE-GPLv3.txt
+Apache License: https://github.com/gnosygnu/xowa/blob/master/LICENSE-APACHE2.txt
+*/
+package gplx.xowa.xtns.pfuncs.times; import gplx.*; import gplx.xowa.*; import gplx.xowa.xtns.*; import gplx.xowa.xtns.pfuncs.*;
+import gplx.xowa.langs.*;
+class Pft_fmt_itm_timezone_offset_4 implements Pft_fmt_itm {
+ private final boolean colon;
+ public Pft_fmt_itm_timezone_offset_4(boolean colon) {this.colon = colon;}
+ public int TypeId() {return Pft_fmt_itm_.Tid_timezone_offset_4;}
+ public void Fmt(Bry_bfr bfr, Xowe_wiki wiki, Xol_lang_itm lang, DateAdp date, Pft_func_formatdate_bldr bldr) {
+ // get tz_secs
+ int tz_secs = date.Timezone_offset();
+
+ // add "+" or "-"
+ if (tz_secs < 0) {
+ bfr.Add_byte(Byte_ascii.Dash);
+ tz_secs *= -1;
+ }
+ else {
+ bfr.Add_byte(Byte_ascii.Plus);
+ }
+
+ // calc mins / hours
+ int tz_mins = tz_secs / 60;
+
+ // add bfr
+ bfr.Add_int_fixed((tz_mins / 60), 2);
+ if (colon)
+ bfr.Add_byte(Byte_ascii.Colon);
+ bfr.Add_int_fixed((tz_mins % 60), 2);
+ }
+}
+class Pft_fmt_itm_timezone_id implements Pft_fmt_itm {
+ public Pft_fmt_itm_timezone_id(boolean abrv) {}
+ public int TypeId() {return Pft_fmt_itm_.Tid_timezone_id_full;}
+ public void Fmt(Bry_bfr bfr, Xowe_wiki wiki, Xol_lang_itm lang, DateAdp date, Pft_func_formatdate_bldr bldr) {
+ bfr.Add_str_a7(date.Timezone_id());
+ }
+}
diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_func_time__basic__tst.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_func_time__basic__tst.java
index 62742a4d6..d93849934 100644
--- a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_func_time__basic__tst.java
+++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pft_func_time__basic__tst.java
@@ -107,4 +107,65 @@ public class Pft_func_time__basic__tst {
@Test public void Iso8601_T() {fxt.Test_parse_tmpl_str("{{#time:Y-m-d h:i:s A|T1:23}}" , "2012-01-02 01:23:00 AM");} // handle "T" flag; PAGE:pl.w:StarCraft_II:_Wings_of_Liberty
@Test public void Iso8601_T_ws() {fxt.Test_parse_tmpl_str("{{#time:Y-m-d h:i:s A|T 1:23}}" , "2012-01-02 01:23:00 AM");} // handle "T" flag and ws
@Test public void Iso8601_T_fail() {fxt.Test_parse_tmpl_str("{{#time:Y-m-d h:i:s A|T2012-01-02}}" , "Invalid hour: T");} // handle "T" flag and ws
+
+ @Test public void Timezone_id() {// hard-coded to return "UTC"; DATE:2020-01-18
+ fxt.Test_parse_tmpl_str("{{#time:e|2012-01-02 03:04:05}}", "UTC");
+ }
+ @Test public void Timezone_abrv() { // hard-coded to return "UTC"; DATE:2020-01-18
+ fxt.Test_parse_tmpl_str("{{#time:T|2012-01-02 03:04:05}}", "UTC");
+ }
+ @Test public void Timezone_offset_4() { // hard-coded to return "+0000"; DATE:2020-01-18
+ fxt.Test_parse_tmpl_str("{{#time:O|2012-01-02 03:04:05}}", "+0000");
+ }
+ @Test public void Timezone_offset_4_colon() { // hard-coded to return "+00:00"; DATE:2020-01-18
+ fxt.Test_parse_tmpl_str("{{#time:O|2012-01-02 03:04:05}}", "+0000");
+ }
+ @Test public void Timezone_offset_4__vals() {
+ Pft_func_time__fxt func_fxt = new Pft_func_time__fxt(fxt);
+ func_fxt.Test__parse_w_offset_mins( 60, "{{#time:O|2012-01-02 03:04:05}}", "+0100");
+ func_fxt.Test__parse_w_offset_mins(-300, "{{#time:O|2012-01-02 03:04:05}}", "-0500");
+ func_fxt.Test__parse_w_offset_mins( 330, "{{#time:O|2012-01-02 03:04:05}}", "+0530");
+ }
+ @Test public void Meridian__AM__bugfix() {
+ fxt.Test_parse_tmpl_str("{{#time:A|2012-01-02 12:00:00}}", "PM");
+ }
+ @Test public void Meridian__AM() {
+ fxt.Test_parse_tmpl_str("{{#time:A|12:00 AM}}", "AM");
+ fxt.Test_parse_tmpl_str("{{#time:A|12:00 a.m}}", "AM");
+ fxt.Test_parse_tmpl_str("{{#time:A|12:00 am.}}", "AM");
+ fxt.Test_parse_tmpl_str("{{#time:A|12:00 a.m.}}", "AM");
+ }
+ @Test public void Meridian__PM() {
+ fxt.Test_parse_tmpl_str("{{#time:A|2:00 PM}}", "PM");
+ fxt.Test_parse_tmpl_str("{{#time:A|2:00 p.m}}", "PM");
+ fxt.Test_parse_tmpl_str("{{#time:A|2:00 pm.}}", "PM");
+ fxt.Test_parse_tmpl_str("{{#time:A|2:00 p.m.}}", "PM");
+ }
+ @Test public void Meridian__basic() {
+ fxt.Test_parse_tmpl_str("{{#time:h:i:s A|1PM}}" , "01:00:00 PM");
+ fxt.Test_parse_tmpl_str("{{#time:h:i:s A|1 PM}}" , "01:00:00 PM");
+ fxt.Test_parse_tmpl_str("{{#time:h:i:s A|1:02 PM}}" , "01:02:00 PM");
+ fxt.Test_parse_tmpl_str("{{#time:h:i:s A|1:02:03 PM}}" , "01:02:03 PM");
+ }
+ @Test public void Meridian__errors() {
+ fxt.Test_parse_tmpl_str("{{#time:h|PM}}" , "Invalid time. Nothing found before meridian");
+ fxt.Test_parse_tmpl_str("{{#time:h|monday PM}}" , "Invalid time. Text found before meridian");
+ fxt.Test_parse_tmpl_str("{{#time:h|0 AM}}" , "Invalid time. Invalid digit for meridian: 0");
+ fxt.Test_parse_tmpl_str("{{#time:h|13 AM}}" , "Invalid time. Invalid digit for meridian: 13");
+ fxt.Test_parse_tmpl_str("{{#time:h|1 :00 AM}}" , "Invalid time. Text found before 1st colon");
+ fxt.Test_parse_tmpl_str("{{#time:h|1 :00:00 AM}}" , "Invalid time. Text found before 2nd colon");
+ }
+}
+class Pft_func_time__fxt {
+ private final Xop_fxt fxt;
+ public Pft_func_time__fxt(Xop_fxt fxt) {this.fxt = fxt;}
+ public void Test__parse_w_offset_mins(int offset, String raw, String expd) {
+ try {
+ DateAdp.Timezone_offset_test = offset * 60;
+ fxt.Test_parse_tmpl_str(raw, expd);
+ }
+ finally {
+ DateAdp.Timezone_offset_test = Int_.Min_value;
+ }
+ }
}
diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_.java
index 4f8415fe8..ad2957890 100644
--- a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_.java
+++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_.java
@@ -40,6 +40,7 @@ class Pxd_itm_ {
, Tid_unit_relative = 11 // next, previous
, Tid_unixtime = 12 // @123
, Tid_iso8601_t = 13 // T
+ , Tid_meridian = 14 // PM
, Tid_dash = Byte_ascii.Dash
, Tid_dot = Byte_ascii.Dot
, Tid_slash = Byte_ascii.Slash
@@ -101,5 +102,6 @@ class Pft_func_time_log {
, Invalid_second = Gfo_msg_itm_.new_warn_(owner, "Invalid second: ~{0}")
, Invalid_date = Gfo_msg_itm_.new_warn_(owner, "Invalid date: ~{0}")
, Invalid_timezone = Gfo_msg_itm_.new_warn_(owner, "Invalid timezone: ~{0}")
+ , Invalid_time = Gfo_msg_itm_.new_warn_(owner, "Invalid time. ~{0}")
;
}
diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_int.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_int.java
index 0f3e6ebd9..9c2e100dd 100644
--- a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_int.java
+++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_int.java
@@ -40,7 +40,7 @@ class Pxd_itm_int extends Pxd_itm_base implements Pxd_itm_int_interface {
public int Val() {return val;} public Pxd_itm_int Val_(int v) {val = v; return this;} private int val;
public boolean Val_is_adj() {return val_is_adj;} public void Val_is_adj_(boolean v) {val_is_adj = v;} private boolean val_is_adj;
public int Xto_int_or(int or) {return val;}
- public int Digits() {return digits;} private int digits;
+ public int Digits() {return digits;} private int digits; // NOTE: digits exists primarily for year evaluation; EX: 11 vs 2011
@Override public boolean Time_ini(Pxd_date_bldr bldr) {
int seg_idx = this.Seg_idx();
if (seg_idx == Pxd_itm_base.Seg_idx_skip) return true;
diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_meridian.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_meridian.java
new file mode 100644
index 000000000..3b636aef3
--- /dev/null
+++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_itm_meridian.java
@@ -0,0 +1,113 @@
+/*
+XOWA: the XOWA Offline Wiki Application
+Copyright (C) 2012-2017 gnosygnu@gmail.com
+
+XOWA is licensed under the terms of the General Public License (GPL) Version 3,
+or alternatively under the terms of the Apache License Version 2.0.
+
+You may use XOWA according to either of these licenses as is most appropriate
+for your project on a case-by-case basis.
+
+The terms of each license can be found in the source code repository:
+
+GPLv3 License: https://github.com/gnosygnu/xowa/blob/master/LICENSE-GPLv3.txt
+Apache License: https://github.com/gnosygnu/xowa/blob/master/LICENSE-APACHE2.txt
+*/
+package gplx.xowa.xtns.pfuncs.times; import gplx.*; import gplx.xowa.*; import gplx.xowa.xtns.*; import gplx.xowa.xtns.pfuncs.*;
+import gplx.core.brys.*;
+class Pxd_itm_meridian extends Pxd_itm_base implements Pxd_itm_prototype {
+ private final boolean pm;
+ public Pxd_itm_meridian(int ary_idx, boolean pm) {this.Ctor(ary_idx); this.pm = pm;}
+ @Override public byte Tkn_tid() {return Pxd_itm_.Tid_meridian;}
+ @Override public int Eval_idx() {return 19;}
+ @Override public boolean Time_ini(Pxd_date_bldr bldr) {return true;}
+ public Pxd_itm MakeNew(int ary_idx) {return new Pxd_itm_meridian(ary_idx, pm);}
+ @Override public boolean Eval(Pxd_parser state) {
+ Pxd_itm[] tkns = state.Tkns();
+
+ // init some vars
+ Pxd_itm itm = null;
+ boolean colon_found = false;
+
+ // get previous item before meridian, skipping ws
+ int itm_idx;
+ for (itm_idx = this.Ary_idx() - 1; itm_idx > -1; --itm_idx) {
+ itm = tkns[itm_idx];
+ if (itm.Tkn_tid() != Pxd_itm_.Tid_ws)
+ break;
+ }
+
+ // null-check to handle error cases like "AM"
+ if (itm == null) {
+ return Fail(state, "Nothing found before meridian");
+ }
+ else {
+ // itm is not int, then err; EX: "monday AM"
+ if (itm.Tkn_tid() != Pxd_itm_.Tid_int) {
+ return Fail(state, "Text found before meridian");
+ }
+ // itm is an int
+ else {
+ // int_itm may be minute / seconds if there are colons; EX "12AM" vs "12:00AM" or "12:00:00AM"
+ if (itm_idx > 0 && tkns[itm_idx - 1].Tkn_tid() == Pxd_itm_.Tid_colon) {
+ colon_found = true;
+ itm_idx--;
+ // make sure int exists before ":"
+ if (itm_idx > 0 && tkns[itm_idx - 1].Tkn_tid() == Pxd_itm_.Tid_int) {
+ itm = tkns[itm_idx - 1];
+ itm_idx--;
+ // check again for ":"
+ if (itm_idx > 0 && tkns[itm_idx - 1].Tkn_tid() == Pxd_itm_.Tid_colon) {
+ itm_idx--;
+ // make sure int exists before ":"
+ if (itm_idx > 0 && tkns[itm_idx - 1].Tkn_tid() == Pxd_itm_.Tid_int) {
+ itm = tkns[itm_idx - 1];
+ }
+ else {
+ return Fail(state, "Text found before 2nd colon");
+ }
+ }
+ }
+ else {
+ return Fail(state, "Text found before 1st colon");
+ }
+ }
+
+ // hour found
+ Pxd_itm_int hour_itm = (Pxd_itm_int)itm;
+ int hour = hour_itm.Val();
+
+ // invalid digit; fail
+ if (hour == 0 || hour > 12) {
+ return Fail(state, "Invalid digit for meridian: " + Int_.To_str(hour));
+ }
+ else {
+ // update hour
+ if (pm) {
+ // convert "1 PM" -> hour=13
+ hour_itm.Val_(hour + 12);
+ }
+ else { // convert "12 AM" -> 00:00
+ if (hour == 12) {
+ hour_itm.Val_(0);
+ }
+ }
+
+ // if no colon, eval int now else int will get eval'd as year; EX: "12 AM"
+ if (!colon_found)
+ return Pxd_eval_seg.Eval_as_h(state, hour_itm);
+ else {
+ // colon exists; don't need to do anything else b/c parser will handle normally; i.e.: "12:00 PM" is just like "12:00"
+ }
+ }
+ }
+ }
+
+ return true;
+ }
+ private boolean Fail(Pxd_parser state, String err) {
+ // MW just throws "Invalid time."; add extra description message for debugging purposes
+ state.Err_set(Pft_func_time_log.Invalid_time, Bfr_arg_.New_bry(err));
+ return false;
+ }
+}
diff --git a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_parser.java b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_parser.java
index b0cc9745d..39b89eee1 100644
--- a/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_parser.java
+++ b/400_xowa/src/gplx/xowa/xtns/pfuncs/times/Pxd_parser.java
@@ -222,6 +222,8 @@ class Pxd_parser_ {
Init_relative();
trie.Add_obj(Pxd_itm_unixtime.Name_const, new Pxd_itm_unixtime(-1, -1));
trie.Add_obj(Pxd_itm_iso8601_t.Name_const, new Pxd_itm_iso8601_t(-1, -1));
+ Init_meridian(Bool_.N, "am", "a.m", "am.", "a.m.");
+ Init_meridian(Bool_.Y, "pm", "p.m", "pm.", "p.m.");
}
private static void Init_reg_months(String[] names) {
for (int i = 0; i < names.length; i++)
@@ -255,6 +257,11 @@ class Pxd_parser_ {
trie.Add_obj("previous", Pxd_itm_unit_relative.Prev);
trie.Add_obj("this", Pxd_itm_unit_relative.This);
}
+ private static void Init_meridian(boolean is_pm, String... ary) {
+ Pxd_itm_meridian meridian = new Pxd_itm_meridian(-1, is_pm);
+ for (String itm : ary)
+ trie.Add_obj(itm, meridian);
+ }
}
/*
NOTE_1:parsing works by completing previous items and then setting current;