From 5d166ab6b8a69aac663156e1d159ed22883ed65f Mon Sep 17 00:00:00 2001 From: Eskimue Date: Sat, 11 Apr 2026 14:05:54 +0200 Subject: [PATCH] Zeiten nochmal verbessert --- public/astronomical_conversions.php | 21 +++++++++++------- .../astronomical_conversions.cpython-314.pyc | Bin 23706 -> 24007 bytes public/py/astronomical_conversions.py | 11 +++++---- 3 files changed, 20 insertions(+), 12 deletions(-) diff --git a/public/astronomical_conversions.php b/public/astronomical_conversions.php index a904527..ccd0846 100644 --- a/public/astronomical_conversions.php +++ b/public/astronomical_conversions.php @@ -1021,7 +1021,7 @@ $timeLocationLongitude = isset($currentLocation['longitude']) && is_numeric($cur }); const parseUtcDateTime = function (value) { - const match = String(value).trim().match(/^(\d{4})-(\d{2})-(\d{2})(?:[ T](\d{2}):(\d{2})(?::(\d{2}))?)?$/); + const match = String(value).trim().match(/^(\d{4})-(\d{2})-(\d{2})(?:[ T](\d{2}):(\d{2})(?::(\d{2})(?:[.,](\d{1,3}))?)?)?$/); if (!match) { return null; } @@ -1032,7 +1032,8 @@ $timeLocationLongitude = isset($currentLocation['longitude']) && is_numeric($cur const hour = Number(match[4] || '0'); const minute = Number(match[5] || '0'); const second = Number(match[6] || '0'); - const date = new Date(Date.UTC(year, month - 1, day, hour, minute, second)); + const millisecond = Number((match[7] || '0').padEnd(3, '0')); + const date = new Date(Date.UTC(year, month - 1, day, hour, minute, second, millisecond)); return Number.isNaN(date.getTime()) ? null : date; }; @@ -1054,7 +1055,7 @@ $timeLocationLongitude = isset($currentLocation['longitude']) && is_numeric($cur date.getUTCSeconds().toString().padStart(2, '0') ]; - return parts.join('-') + ' ' + timeParts.join(':'); + return parts.join('-') + ' ' + timeParts.join(':') + '.' + date.getUTCMilliseconds().toString().padStart(3, '0'); }; const formatUtcDateTimeGerman = function (date) { @@ -1074,11 +1075,11 @@ $timeLocationLongitude = isset($currentLocation['longitude']) && is_numeric($cur date.getUTCSeconds().toString().padStart(2, '0') ]; - return parts.join('.') + ' ' + timeParts.join(':'); + return parts.join('.') + ' ' + timeParts.join(':') + ',' + date.getUTCMilliseconds().toString().padStart(3, '0'); }; const parseUtcDateTimeGerman = function (value) { - const match = String(value).trim().match(/^(\d{2})\.(\d{2})\.(\d{4})(?:[ ](\d{2}):(\d{2})(?::(\d{2}))?)?$/); + const match = String(value).trim().match(/^(\d{2})\.(\d{2})\.(\d{4})(?:[ ](\d{2}):(\d{2})(?::(\d{2})(?:[.,](\d{1,3}))?)?)?$/); if (!match) { return null; } @@ -1089,7 +1090,8 @@ $timeLocationLongitude = isset($currentLocation['longitude']) && is_numeric($cur const hour = Number(match[4] || '0'); const minute = Number(match[5] || '0'); const second = Number(match[6] || '0'); - const date = new Date(Date.UTC(year, month - 1, day, hour, minute, second)); + const millisecond = Number((match[7] || '0').padEnd(3, '0')); + const date = new Date(Date.UTC(year, month - 1, day, hour, minute, second, millisecond)); return Number.isNaN(date.getTime()) ? null : date; }; @@ -1101,6 +1103,9 @@ $timeLocationLongitude = isset($currentLocation['longitude']) && is_numeric($cur isSyncingTimePicker = true; timeUtcPicker.setDate(date, false); + if (timeUtcPicker.altInput) { + timeUtcPicker.altInput.value = formatUtcDateTimeGerman(date); + } isSyncingTimePicker = false; }; @@ -1138,14 +1143,14 @@ $timeLocationLongitude = isset($currentLocation['longitude']) && is_numeric($cur updateTimeFrom('utc'); if (instance.altInput) { - instance.altInput.setAttribute('placeholder', 'TT.MM.JJJJ HH:MM:SS'); + instance.altInput.setAttribute('placeholder', 'TT.MM.JJJJ HH:MM:SS,mmm'); } } }); if (timeUtcPicker.altInput) { timeUtcPicker.altInput.classList.add('astro-conv-input'); - timeUtcPicker.altInput.setAttribute('placeholder', 'TT.MM.JJJJ HH:MM:SS'); + timeUtcPicker.altInput.setAttribute('placeholder', 'TT.MM.JJJJ HH:MM:SS,mmm'); } } diff --git a/public/py/__pycache__/astronomical_conversions.cpython-314.pyc b/public/py/__pycache__/astronomical_conversions.cpython-314.pyc index a6e945a7d5d555f0dd3cb6a25180ee0139bd04e8..9c37d7bdbdde2c1039ab4732f3ffbdb6db8bc7b1 100644 GIT binary patch delta 2480 zcmbW3eQZp)vqZ5oheNYgg$oad0B z?Vo8+dcSwxIrqGK&pG!V`@}oq=NE*je6cB0N7ok{)bQ=|ru|FmB(YW8)iF<{-_f3D zHmBZU1q~b!Jbdml&{I$M%n96OY0}4ZJ!r16;!iA@dY|aQ&)KbQKB+=_FkGke=}o#? zsbWE)E7mE7zgt|rm99voE9i8!d0d?y*Jg0jm_L3(A6NC&tAb-PddyCfniUBTKr|j2 zhzCgBNrBXtWeUoSw-aBH>`KclS~X=U9qpKrbmlhcu>Ou@ z$gqB3bxd2`*R1Z7BU9G;ujJdMHVGa1`L=9we^*|!UP$92YrR<>Um}QTSz*JFqXhqv zvj{uvIrv7tSDa7Y%0DQ~e)3pYH0;AY1$Ak#m9aWg8_hAb_p@GWX$J5$$&$w-Om_h9AG@h;4=cx6V%Mq>FEy-CtxeS zT&T!jCiTVSj|=reT*h(d)ofP4J_h#&MS`Pvx~N({MlY99EqYT-;E@$?7r(?t1MsrJ z$lyZ+FSAyHPL>bh_Tmcpt0Yb!7GDrk*j@6eIF24yfqas*Q~0!NMocHW-8M;l4PVdA z$I-GfaRbN7erX+}0q|YM_ZVjwXYq)#mh6|5>Dqa_st?8Ds{HKE=uqh4vE-o2!B8x* z6CCXP22Eg>-z4#7^6n#5Qpx-m;D>B~oAJM}#5jIb=@vK9SaqxG zRWhpS;rNd5a5xcC^}~T-Wf8o~F5hN+hjEH=nxTF5EKBb&v{s<20*3#1q~t;`g}gu>-W?KRwnUXVDaC zNoDON>ERXECv%%NWfc6HeYh{E8AH+G!Ej=CFw~`;W|+YJ9l1-j?xzSS`?N_BFo-Q1AAf`cf-(k2p=S8^#!}4!o@FIB z0;psh!|!i=x-`{N{Oz4BbFuUO)i$`AkqAdZ@kAgJgI=uJq-Ed${|h4%|^(+*y_?$Rv6@Tg4$f*m+p4Cy)B1x$EnOhfDEda>Dl; zQNEC#Yy5TIXu!1t_R>A#k!+AwkV* zkHn&o(AquBuYm_Bz6Lhe| ze=D?70%t!}KW(3A%}(o&$Jn54jgu_#>HW{#ai-wBZW(a}o1FwT-5ZGpcMpZu!eH`) mZH>atf3;>aQ#6XY+3a*-nYGc+@T?Q7`x>Q|MflmimH!4SVssz? delta 2267 zcmai$du)?c6u^7iexr{K+HGa;QP}g_a1YiYFgG^XCKEPfgAHM0l(k6By4KSo&Y*xu zgb+nI5SW61;se2feuxob1VexXg*_1P3&wY1Fh(XU#^@iO^L66lKQ`H~=bp#C=bZcK zE}RxGe#_28g&PM>iO+KOl48AmLxwNK1`o?=4jTHxAbkjM)`3t?pW80?*B!jib@Vyohhs}Z6V zmH7G6qvWv_$2jhYoywn%X+kuiD`C0xIH`AHPr^?*`$@W&aI~-u=?Hr}Zu8fnRmbDs z2xuBi8=oTd__WlP*l4inYG>$lL4As@)kxvm=iw-{-yd&liFN5CilCv{@UR&-Bo$Mf zl2kU<2$^JQfX9fk5vL^2oXtA|eum7D7)=D#((LYB?X3X_fNX?R*5|X{u+kq^qk?V- zc|9RsI~z|Wr&-pJq!kjvZGELG&^oO(ylwQ2OQZ4!h??D&9yh;l6F^Y zuQ-}`EcI~eOBI80QwO4_4vo>-77JXEk{oZRiImc+LjBo7YgL7Gwp>(I;QEx^qE|^w z-6(90WdAo!=*A;yQwvqA-`4?wkhdey<$*=y5)y=La1vFEC)^$mw1<6uFYvMIMN|4O zQQahg1=|uc#VN%(p-QxBZHZD%v)!HEE{_{v3cIXeXl=UJ9N7$;Si6?-G~*e@I>vg& z27+pdq|@%}3d6Jbu~U||kouJJv(q5NdHi)^e=I8?k_bt%9=77Zq#|h>4bJ13j9zgG zPiCCVc!7;ZEq93G5I)}UB5Usz;#(15f&3}ZY4;flj+QMgecpN=NlcjScUR8D#(LUW(dWzfi;sX9rQYVdb}k6s&&Wit`Fd>e$Ab>ZUn$wF}$lH&)j)LNWVr(eNpjlvjy!xVk)_ z5S9kfI1Q+RiKhgP@g{luf1^*OyZEoAlm1N`RP5X=p1(mRj#v`NL$`PTV z652=9>%#-Ls$>Bkgn5;DTqEQ%xG>ecusaxebs)^jHH`Zh+wkVRr8$weX<=P`%}6`= z%xjlIHS+}zh28!jG~=>*d9IzxR;_gNJ?^kqyZ!uZtLB;~JLpjQ0$mVG9>6a#@Jlw* zRhIZps;2oXLSA^n3$PIf>T_|2Gd`BfkrUtoI}I|T(b~)D8dz-bt zG5Q$;j9(ckZ0%%8+uw&+;$ME?T>@@&WNWk|!0$F_&*e6jv|Z;H4EV18w|CqrIHtp) rr3u2Tm|Lfd6#lPd*c4%um^vJ5687Qo^b0$jj%{tz_3Ny-r>*dB8s<>Y diff --git a/public/py/astronomical_conversions.py b/public/py/astronomical_conversions.py index c36d797..4c7e661 100644 --- a/public/py/astronomical_conversions.py +++ b/public/py/astronomical_conversions.py @@ -129,11 +129,13 @@ def format_decimal_german(value: Decimal | float | int | None, *, max_fraction_d def format_utc_datetime(dt_utc: datetime) -> str: - return dt_utc.astimezone(timezone.utc).strftime("%Y-%m-%d %H:%M:%S") + dt_utc = dt_utc.astimezone(timezone.utc) + return dt_utc.strftime("%Y-%m-%d %H:%M:%S") + f".{dt_utc.microsecond // 1000:03d}" def format_german_datetime(dt_utc: datetime) -> str: - return dt_utc.astimezone(timezone.utc).strftime("%d.%m.%Y %H:%M:%S") + dt_utc = dt_utc.astimezone(timezone.utc) + return dt_utc.strftime("%d.%m.%Y %H:%M:%S") + f",{dt_utc.microsecond // 1000:03d}" def format_clock(hours_value: float) -> str: @@ -161,9 +163,10 @@ def parse_utc_datetime(value: str) -> datetime | None: if text == "": return None - for fmt in ("%Y-%m-%d %H:%M:%S", "%Y-%m-%dT%H:%M:%S", "%Y-%m-%d %H:%M", "%Y-%m-%d"): + normalized = text.replace(",", ".") + for fmt in ("%Y-%m-%d %H:%M:%S.%f", "%Y-%m-%dT%H:%M:%S.%f", "%Y-%m-%d %H:%M:%S", "%Y-%m-%dT%H:%M:%S", "%Y-%m-%d %H:%M", "%Y-%m-%d"): try: - parsed = datetime.strptime(text, fmt) + parsed = datetime.strptime(normalized, fmt) return parsed.replace(tzinfo=timezone.utc) except ValueError: continue