From 878410abbfe177aeea193100bca712fee117836c Mon Sep 17 00:00:00 2001 From: jsrobson10 Date: Sun, 21 Jun 2020 18:48:01 +1000 Subject: [PATCH] Started working on the worker for lighting --- src/projectzombie/Main.java | 4 +- .../display/lighting/TileLighting.java | 64 ++++++++++++ src/projectzombie/worker/Worker.java | 95 +++++++++++------- worker.jar | Bin 64125 -> 64154 bytes 4 files changed, 126 insertions(+), 37 deletions(-) diff --git a/src/projectzombie/Main.java b/src/projectzombie/Main.java index 5421139..b2bd1fa 100755 --- a/src/projectzombie/Main.java +++ b/src/projectzombie/Main.java @@ -42,6 +42,7 @@ public class Main public static AudioEngine audio; public static Random rand = new Random(); public static Menu menu; + public static Worker worker; public static boolean game_paused = false; public static int tickrate = 10; @@ -61,7 +62,8 @@ public class Main public static void main(String[] args) throws IOException { - Worker worker = new Worker(); + worker = new Worker(); + worker.start(); // Initialize cheats, settings, and environment Environment.init(args); diff --git a/src/projectzombie/display/lighting/TileLighting.java b/src/projectzombie/display/lighting/TileLighting.java index bd1f29f..45d1c00 100755 --- a/src/projectzombie/display/lighting/TileLighting.java +++ b/src/projectzombie/display/lighting/TileLighting.java @@ -2,12 +2,16 @@ package projectzombie.display.lighting; import static org.lwjgl.opengl.GL11.GL_RGBA; import static org.lwjgl.opengl.GL11.GL_UNSIGNED_BYTE; +import static org.lwjgl.opengl.GL12.GL_TEXTURE_3D; +import static org.lwjgl.opengl.GL12.glTexImage3D; import java.nio.ByteBuffer; import java.util.Arrays; import org.lwjgl.opengl.GL33; +import bdf.types.BdfNamedList; +import bdf.types.BdfObject; import gl_engine.MathHelpers; import gl_engine.range.Range4i; import gl_engine.vec.Vec2i; @@ -56,6 +60,66 @@ public class TileLighting return; } + int size = (Chunk.RENDER_DISTANCE * 2 + 1) * 16; + float[] lights = new float[size * size * 3]; + for(int cx=-Chunk.RENDER_DISTANCE;cx<=Chunk.RENDER_DISTANCE;cx++) { + for(int cy=-Chunk.RENDER_DISTANCE;cy<=Chunk.RENDER_DISTANCE;cy++) + { + Vec2i cpos = new Vec2i( + cx + MathHelpers.floor(player.pos.x / 16), + cy + MathHelpers.floor(player.pos.y / 16)); + + Chunk chunk = layer.chunks.get(cpos); + + for(int x=0;x<16;x++) { + for(int y=0;y<16;y++) + { + Vec2i tpos = new Vec2i(x, y); + int tid = tpos.getId(Chunk.CHUNK_SIZE); + + TileState ft = chunk.getFrontTile(tid); + TileState bt = chunk.getBackTile(tid); + + float transparency = (float)MathHelpers.biggest( + ft.tile.getLightDissipation(ft), + bt.tile.getLightDissipation(bt)); + + float lightSrc = (float)MathHelpers.biggest( + ft.tile.getLightLevel(ft, tpos), + bt.tile.getLightLevel(bt, tpos)); + + float lightSun = ft.tile.passNaturalLight && bt.tile.passNaturalLight ? 1 : 0; + + int id = ((cx * 16 + x + Chunk.RENDER_DISTANCE * 16) + + (cy * 16 + y + Chunk.RENDER_DISTANCE * 16) * size) * 3; + + lights[id+0] = lightSun; + lights[id+1] = lightSrc; + lights[id+2] = transparency; + } + } + } + } + + Main.worker.processLighting(lights, size, size); + } + + public static void updateLighting(BdfObject bdf) + { + BdfNamedList nl = bdf.getNamedList(); + float[] light = nl.get("light").getFloatArray(); + int width = nl.get("w").getInteger(); + int height = nl.get("h").getInteger(); + + float[] pixels = new float[width*height*3]; + + for(int i=0;iZ<(3#3koGk0QiHm3FH4MZAXoOw z6hl>oB&K^)GV24o{HOVzVt$#k>&HxoU=6$JbKXx~-g@QIP3+KRs#9jP%A|hf{+mOx*U;qSu%ybW3kqk=sW%yL_9(tc4$Z zwlFctT7_gt*(J@qw!}5Uoh6;MW=ltE_p_#%+lBf)-{#4Re#m^Ww9HFx&gDSP`3}A| zb4}aBjKA=6!dqR2jQMytbu9HS*BvlXM= zuLdqylpv%%InF%Q@pXz`cxg>r_L9W~9ewvM1jd~b4?4^%X(jDrwRh>`V$b$`-B_QS zEFK3|^ywG0dy1%do1fYcvhRE!m#fp=s~=S#Qm4g2-*7Va>I!UMeoVOQ=%KK~KCdpQK7M2<-?m89%PUUH z_349-P&=6eQdSb@rEebEG|_xBXIA)Tbs=rZ#Tiy+tG3LXmaJ;9JXt3GWNgrJle8y! zamUTSMS2}~K66UYJluC%llk5WXP@2-Nt$&rx}9HGyOQZ*{o3=>Ha|<|nl&-TMCjVi zY_(-d$4~GbKR7QW#okM%@Ameh8@0(hr`8$T+0Az4A=Z7ZQn9&G_075|*!qRM&F!tdjVDiNKicmUe`<2oYuTdskZl*P$_ChIe%I;0 z&D=G8_ddbb9-6Y6HdU)S8iI`O-}$}zbp74?f7r~o7gkT&S+?Kt%)K(NwdVB_Tb9bL zeD7ftxqa%JN;NK%ja_GXEIY*JJm|f4>WbeZzVE?Pe3tF+DXZz{`_tmLnnV1}5--<^ zXCjV=`~3u?JT|AC^Ysrma9StQ6SSFYUAe_tr4>m&Eh|pUD>)&(xNA+W!!zlei4T{j z?bY0;p7y&=SMbSFD*-zPw*?~Z4DpB4>udQ9%H(xpHeHo%uw>GxF`vTtLgHpVV`r6OA61!p&g1VNa9A$! z%T7Jv$htq5#r(pJO^v@6u>4@1DzqYB_|$2S4XNzMRQ(q(fBch8i|G{i?+wZ9oqVqs zTh`Z~j9$I>tMATcuc8XC%!#YjSDfMVuUxw~>+M#to!6>#mqvwpg@=51&E-BjG0k+r z*AuQY-)4T0yi0Vgp5zI7t1RMu zed5Cz=QY18j?A5Y@AgF3zTREu9-UUZx<+kn^K#DJ7RSP5i&jR6F|dJ&pQolS7SF1q*oftt)p&_*&;rjeE1_^^eV;<+i#V*v;L4(3tDTg)yu8eCFZfpKxD?ZN8!G4-CGZ)^6ZYhg^s_xie zlbWvZEj`egbM^N6-j{zDgqldsoxT4`X!!5B3Y#X1&8P}Zul)M8yH}WL^Y3?0>m4?) zj0<0VjB)nlHM#bCpSwq~YLyr?7Z%ScD!f&a;u_UCK{VetESr#V2m>sLAkCThv_{>~?BJ zj>wI|wHI|>++EkjwbZTHz>J++!d&rQ@yB|*bzD8JT@Bm+y0iRFxhDO{$)xvs`>}`0 z$y2)5N(Ff*mo#ruQw}Zpz}aOc#(L@Sz1Wz;%b6A*S+ZqyXv(dVq27FUhsDk8>P;6k z2phd$8n=0+lelWk^2s^dJ^5s>N1Us4*6CKe;48kpVD^*O-%QdqC!C!2|9A~gYEA0n zbBb5A>vzw2+sDnXtdh5Ux$gy0@zu+UyxSJuDJ|d^m5!HJxWf2ocf?_HlUj*i%ObR+ zbtS*NOFX=%Cc8@S_-lp3VuCZI4#k$;zPDIn;+KEkHiv6vH)lQa_1l=?ls~QLhRnEfi-SCv5Pr{_IX{{RUkZ~Sm)FeP_$%Vw<8?ciu@xP9nSA%kte$M$jY_GF0KA@qHx$qM=JA7!6v z)H#XX-~8P(>R*HW&Fp#qW?xa){5)ZW;?WH8K=O|DTXttaz! zJSel~erJs+VP;@B$%>p=mtxLbDenU_5ErJ?tWg+nE5xBC`dE{*oe%x3PGCO>P5 z)0FrmW{rieObbJ!yK*n?^30pP^rTvjnZrl+MRva)O*Xc%Y&L%JL#c0BkHJ2x$Mp~P zKkB(wY@V5U>(*ZTTM^EECPi^PN`vxY}jHa4V(itn6UDP?qW>Jo<+OWxkNm)ZC&Bd6=Y=BIm% zF7&1Qc(hn6T*y@Fm~dcQ&)XFnqcm6F@zjnE5t*R*e9faNPj6M-i{YtY-K}+D_RTeY z^Cxqkn*C+#7nkJOS2_A8ywXZ>FHv^#&MD9C3zIPXsB?&|tp1^8=UtcI$IIRnDQ$hS zG9xxmPk@EYaD_YIL*F@y+BLw;$aGR{8uZNtQT+!S1x_8gh$g0|w z)exq$#tg^e$Kg~y_`kq;+ZhVlWebeh4UZvGG+>@k(Unzy)F{g3<2+|l$sWB;zW z&0RXr_IQj>F@ez zx`*X-#ra?*u^B~oqmBmuH0@~!+?v07r_Ou#(zP$l??^P2JUsXGlxgf@rL(Oyo76pk!B(fEJ0`nRT-ogtg%?0IK8`_h^7FSnUZ*IpsByEP!&DVkSl z!{zT!C)J03oIQnQ{h8Rtb=TfG?dvQ$dv;~wq;7!kU+;cDdF#3OVy@7nuwKhGw-G4lq1=TjPZ7WPOyYS*zSzq&ugMDh3E8Vtc zy8IEJAvr(m#d6-5+bb5%zIeNK-9NT{Cq-xuBraQkxUwAIG>$cgBBk?hp=h%N(!~99GEUoSsw{z*92=_l%-c@th$Yia5JXQUn z;X3&zk3{<#)f4}IlW<=y|M6V_qN2G{e&zKiSX3)qLQPw~Np`s$3-b zlU@5KPw83vC0`kN9@vQqJ`C>ftz2oTe=#igIL{aNvZC?{?svSEzYCW)tdIzQRKxd> zrH#PbUo=LoW#Ii3*u%uj-vNue1}t1l>LVG1whb zPx*O8-$n8V`(B~lN4Okig`D<#-Fni=~OOV+*E;x#w%q@D7Io$*rf zf7n5#;ihd@Bp$FZFywN;N<(%I4i1Kfv`drM^IufGl?QFZfZ8z(3=Av`3=ByrY5Jg6 z4i^Ih2Lq_XJ9(*qD)X(pOPkLM>=p$vCZ83M+q_cEgAv5p{6)PF!f4fu;sS|G_IHrp z{MYykSakA6chSw9W)GQQGLv=QaBLQ^v|$GcZ1#6p4N>;ju^J>Wx!UO%n09ei0n;Gu z4bB^x!5kC!U@+a~4wl@!(VdM2EU?jCYVwYEf}5Xu&w~iG1w?@)Ha`wn0kOF+xCSIJ znK#50OoxVi2h;wc>L7Y^WoR5k;jQq8Ac4vIA|Q4=jaUh`eDlPZS765Ex`Z&0ip|#( zx;a3M$*Gy{V0wKfIGiTe*GNy^`blInTh?MWki_OS1%_b8U%W)U+>h>j8R_Iks+b7F*q`m~)Mf_|YcE=z-4vm$!KnNP3Vv_?tm{>0^f zoaO$soLaZ({$I&|Z8pn--o>44eH$QZ`{m1*GXMFOwQl&Y?A|{=X2;>|1a+usc_i# z`KG*8G2dKg`x zl`Cm>Wqs^Z>s2wzJ~8vQZ#ZzJr}*bOuKun5>Pt4N7*xmoa=zaGW#cW2(h&7ajrL9a zEMgKR`^3#p8*@fg{VG3s|8xJ+Zz0;vu6L5&aWjSM)h8^wk;0+ME&njNQO5bkME6xf zKPFoBYTY#m@p0G`Af0k=V?uG7PvBx%p3GATtn-(Cd}+OfO;&2I`;n+6YxFZN`JM4~ zEql`VjbqIsL4DD#uiReu{It?HbgjSqqibD(cfnp&FeW+m0}*}muE@p*Z!xr~9T zd$&(5yM5=qg~Gq)35QI%zPB++?B{f$%MpJ(%TtV!LOvKQOP;^U?6LH_$MTS z&uj6MeYNMQwa0DV?qLHJW#=Rvwbhv!7#^~~iZW111}c{-tFAx_k$@T+m2WCtb zESKJVp|=@QM4VfyKUw!X$L8J%dV(N5oA)iug)5tUp;u&c?BYDI(#_|VUKRo?S+b)V zQZgy+)dUGlUU*h%bHU!tyAZmhzykDssD61X|ofsB@F6Un)(`MzWD;S353&Z_eR(IcT$F*K)SQ7q66y#Dbz<`R zR~ld&ZoQIbYEzp$OHG;|P5WfU*V0Vy)hADQEiqYIgHIbxI-s#d|GY341A~SL1A`32 zSSZ;rx&JjJ&Fp1`R3n6XKUw|_B!0c$NHe{# zn5^(dWU_!I8-@cXzL941n!NUnx(=ug{`G|`*M@g%y5E4q07rqw*dtLIa zv}~CZ0|R8pp&+p&1LQ^IAP#&h&1gS4_pO8i$bv;&)_sl43=A{a&|RG7Jh{qQX7Y(Q zkXXC$R+>?N@|(9xU~52zv`*H22Qj2vOi%G3GXsMrJGvoj+$SG!mzjL>9mJ3c@1z;G zPG0j)QyXM=!Kx2@pg>k*U|eYNYov~)lS z1A|^cQGQlxatX)`ZT9uzk`AEd#mwLVBQm4r_22vweJ^AX~|$`8^^SHma23|E=F z>jOk6@U67W&IpKi(lT>W(G&EfkJ5|}Cd+&T7f_SEKT0$8#7tfgqX{>2!AEJv%E@~^ zLIVEbM`^}OlmC8{um^=8x6GqzkcW7n9s_v?f)g?!R_di^mSm>q7Xkd$*fk7H#Ae3BQFnM=@EI8F7hm7K9X{Os{lNHKE zbwKtYMN0s3@vH$g1w!$ZPgW?`0woTxrR#6(RBd8pU?^l_U{HssfRde6lNHKkCx7}Z z0S>1`~s@*9K*zql8g)tyBHZ5 zRN#t049@P!iQnZW8-0V=>-kNZsibFe;&<7}6M8r%cYlKee^J0`+`m4%?iI!^Xf+Ab?&8)J@j^38@64eo8ZKJUe;AS<+ss1l%rm{zq SH=GrjobXGWZRHD4`~UzGFFuz5 delta 7076 zcmbRBmHF=%X5IjAW)=|!4h{~6;@uY~@-{PD?YuZ~vMO`vx{H%1a>-7-AzJ??t=v=W ziMEi(ABTx*6Z!XNxo!z{$;z3a#i6xrQ;TV5LX#(heVWzWmB#m8Ry^$~O3vT$#$xe< zEq?V4;eR>fzPelVeXA_Lu5fw5eU#~0L zwYhAg`P9=Xr+3!4wQB{`ACB5m^?XfD{j&0uUu|>sUSD8&b#3qQHJ8>j)cdh<{!nAD zh&Xk2%4Q}d%>}8s-+QC>8Rvhl(V2dJ>V8p<<3X2=uU9YKdd1qH`0m+z^76}HuRPQv z+t9=&yfs54AnD^rhFKd!-8~kp^qSKt*1~$GC)O_g?w0hRokE7UlRow;OfCP*_Ju*| z#xmu4tqoguP40Yq!?8q7wBvZt>$MWP;x`xks|e-Vbg4{u_lDcL84vt!+C}O_m7mZN zn=iAX@qnDL6%TX#MsIH;g*>Iky-bX3DxXuWlf`B4dA_`xyNHdEdGD8VUWe<19a&hm zEh(z}edo~G%-t4gzUMdY?_KG1YnJr(F3ZYqJz18swd*-emjAPVQnzSAi^B>naX%CL z;9*b1kOE#UFud zbQ;D?+5K8=-6Qp#r)SM5$~E_im@&=#Zrm14PTlDz#k)kN?{Jdp`&b`Uwa`Oh8Sjqg zdunI1AD*={ajER?e4~|*#k6lnuy0-I73(#}Ramw1IrHMy)}&iL*p7-0(x(ICHhg!ty=O^lj+LmF9_APE$eXkDeKs|?Y-p{ z@lKBt-j{Z|YwC~Aw{iA8@&AhHvFi!#rq6TLE~j6S&S#oFwZq7?D6;p|Rr$c3S?A)) zzqy61`#S4!$okWlFE$ie>}a~?lC2=}W@5M1RbjI!p-9hSOyk)o^{6%s}n&0NR&NH6wXX)N@_gLhgL-qPUlI`Xv-gtRA zG|v9hx-XeKFD-w1Dqz~ohqEr9Pd)QcP4z-w^@+>N1Yc`$-H|+Vud(t@(iz*b_*G^v zR%~PZXJEG=@@I#jt9xL}j4AO(`MdIMe7|ZQ54*5fCjMaA_Uq}7Oa13LMLPy;i=4Xm z182G1{CjuB4@qA9?Einw_obH~7S+#tsV7j|bK>!wZ!OBNVz-ojzAM;O8QW7UmoLBj z<)>>ik3PM7V834eNhOxI%zqv+|9}0RF?!1P3$^d(HWam<+@P$rKy%@qLl*lNb8}w3 zy(YeEE#J+|b(vw=pHCOg+5ZE_eU&2Y9n{T$^0{=_M-z!$d9y22kz5 z38@}}c3+%)n@z1gBs*9*T%yj;BO)S}M{)#K~uzTE$^JNWk;UalJ^Gv}PHzW4gGUH-pc&-FE^W3~hZBgyx>8rA`*FS9+Q)4+6|1>h9 z{%=yESHiOkdmdzqUCqo6wO&-*R=-oWt$c5Qc08-uGQ*^4oB7Vo>=IfytNF>4}~Ri|+4kPOZ^1aPj%{JF0cr zoD$3Y$J{YnKRjK{_Vdkz%Jb!~N<}SBJeKNB+3Z>LLgTp8t+$J38u#T{?C4zYv9HX1 z^K_<@ArI@Xv%m*+4frBFwwt1dlvUaixUeRS&scKn10oaU&Br1?th{41@Z1{ zq-rMz`^>s9d*Pew?zd(x<2Z7v@^Zzun$=Dwar_^p1vuwuWJTVMo%*&pb4&MHzkpD4 z+hR$x<{cS4^@V~xK6=3&ENqosAJ16!t2j*C{b1gVYM$TQU)+3XCBfvQa$qxXMaJu|;Rt>7c)y~;12-k%9x z!a6T;qSgDgsbcdU{gn{g^t-`BN!=-Ms#I{q>VB;;Uotm>sXk zm*2Wu!?x@OV*4-Yvs8O8SAqEV9sCQMjNWbjWjN&nb6v_-$tM{fg&*rB%T1ChteWjAYO1tE z=}eOTgNPY*jfUNYEUyGt_14QVg7WAmH~pv8%nS^tSs{58l11}(gW7Cb^9FwHfa{;ce?->^e4p7Oq^BolT)c1d{@QQlmhykTzCXX8$)ZtTC5mO&DedCz zUhgJ7J;uBHQDom!FBTRn@w2nj_9WC>aepkixAn{%hXcmi-ggYmVlHh_VR1^{mR$Xq zY3;=uCXMOdmfp_VWiKaiYn@Wk~PjT{;zgEao*eG^8 z^V*D}Q&)L=|4Ll^$Q38bF>776p0?t~n@idzTd3B5jGFvI&0co-N2`fn**M(NCvTjx z$m@l~VQC#3?TJNussc1SjhCE!^6c@wqMNIZOy2qP^h{Un*PeS$Cavn7^K#~?y1w^4 zk%`lN9;|sashGDaEloyz%F{&-Dp_xyOj)rw$m-rPYbGmKpINTj%cEQt^xJOqJiK|Y zi-aTZ%<a?doI7>J=lrvAb{6}rb(DM6#xfrF)QAJuF80dtdTV%z)X$23^6BU8$klId zs=Bu~8|atqy!R=sO!Mum$XD02zIB;SPh1@~uk`7(XQ~?4SG<%toH^6iDCSh)kGUa& zj{@A@|Gzr@x=yr~n6LZMy|!;{{CYR+%(-`}$cQ8Ra_&uz&I4uklf2Vz%6kaObbV(j z%b%z6WVTl5-8H2L!<<*w*1E{n2hWk=;%S>aZPC>?kHZ`8&uOpOR%q(B`$4pH#MAXZ z1b;EFi`p>z{M~)a-T3E5@XE%#EH$y(*#4gR#i4s_mn;ACEXaKzSmG?vY@eg}YC(ga z+}`8ruU0loyEw{i>i@*Tw<^h8<9KJ_iVFuGs3p$If4eN)UpRcl!KM3}?4}1KZ#`G9 z`fr);nZ5QB8SkCHux8!RuRj#neBZIo{>X&{-s9O8g}u`Rbeq?j_SkX8KMK0W=-hj^ zpjNU%C{Myl^q=9ebh+fDv<%Ucp>yWTtb4fjqJzqX)GGxm+g4s&Ai?X}WV|?K_qVl| zB!gQyWvy-=E)RDptBp8(=Q_t-_ut7W>22YO^%oVtsOx5jvneeMee!;NtcgbPN5;im z4>aqi&4`{lxzgpwo5iK}We)|43uj!EPqgd*G)Kejht1heyGF;DBLdG)8>AJ;n3a3| zajt1s{-NjhP`c+)b=p6{a}A9T#Q(jl?Bf2>8@FHi>GR)Nwv&5n${$%9O<9@2690%T zChV}AlxTXzm9R%ERzFfJy{mXz_fDGZyGhkEMY$%LHi*9CsCo3?T7YZKL+uvT7MJ}; zmJ2-=nk;l(_1&kF|9-RQ7WsyTu43{&rvG8)eaZR%*+FHU{em;5hgcXGLOGDjx=%|% z%@OIzy05q<-{D`wT)g|@-Pu?`0-Fzcp9C`|_XR|O1zrcNfY>-KxCSIJSv15IOvi?N z2h-u9>L7Y^V`v;i;iK?}Ac4upA|PhJjaUh`bo0!ZS765EwuCT{ip}>Ex;a3M$+?;C zV0wEdBuwsSUSb0YY~E5}2xd%vQKknHnC!h+dh&|Ta`mmj(f-1YBL9}%&RwX(5z6h< zS|k{~M@Qq{ibqR}GS|+CxO7b2IOq7=2b-d&uT}lWH~$a6-4B<=o%?Tlf?4LcyPTQgR2jZwzUn5l|UA6_Xj^8RHjIU>rM|~J$8GPM&Hc9S?Tl@o*W~6+xt`7Dr*za{iOAiG*_W2qulka+amMOZ z46}p`MN{t_V7cVdWTf|_iT#m!i>A?kUYCUj|8`Ye6k4bHN!4l59d%wGO((Xgzqft( zzQkMb(Tp^S|4)DIc*<7fzeYA%X*e>sqT5{9Sd}vleBo( zyZbSzO?wpar`cz{CvS0wAM^BrnZL4I?}$`Pe(%wKfGg`wj#;?fp{M1GYnZ|dbo*9^ z91>jS?aj9CF`McAvQ(T3$ep$_y_n6Ol ze*N1uJNFiz7Q4FTRU^+X<)8e?B{!#iU2yO~m&sFJ#kXyzwm%pAKhOV_(8}9;870=R z+^PCE!MytMoD~(i_k~^u$@={ilId_j+NK z7}qv$`IgLayy{%M=c=vKWco@CCdu$Vt&f=U#HA{6*Z$_<>tCka`~Qo# z&D!EG<4pCFGo8=WdcBmL6Z$BIT|9f1*~E7Vl`h>q8By%o%FOXrJEmT`AC#fnvf0Vg z@x5Z3$-x;*CZ4>I$F}*)`DDIs3-2@OC-WFrTeO?bTCTe)SK2#~^EAu+ghzVsT4k;T z9QeCojnvJ1%NJcW&6Aa$qTg#{mbrZK4b?}|VvAFvxlUGoU%8oQ>t3o$b=oMAyO zi;8z&+&r!73Z#I@tQR3hqefaN)YE@dncH)*|&2V zm@)ZTmo8Z8?S;CN{l9T+_U<+YOKfiJ@dGm^doR}C%-EL?DH2{U)!)2mf|(#l&*s|; zbHPeBdoP{~mfrk&>183X)WIFqkkZF~uO>)f^1ic5n|t^EhLjTf&MHk#_{p((>oGQP zxwm=W+3Tz@Ws~3i)v!gA6<#Tu7Vo|ofUKVdnZr;fz`&4{lBOTv&B(;X zz{SA8!2lWw1$jVr22`%3vLLk>tU`nV($WUiHXB|^Gai_H=9Pv#$OfjnpDrjdGB9jl zWMGg)v7v6V@M{flSlYdoW_qqZdF^Y7$;Gdwz(NyVOEXqXUh^7~JZ`;~X1qH2+iP&K zKUv|8G~@HhHg7b+7Myv|drXF%fkB0zfdMr<9!zd|1JSYWjWnavP!KgPcA6ZJf?T1_p*l3=AO8BRM?JiGe{cIVZ8WxFE4413h^1-b!1T zJ41plC9xzCJ#+#Vaas2@GBYsDU}IpALNb`O5mUX8CmNN zF|xEIGY7-Saxp!{gUk#Jn(XLCE}7i;4r1imchXF2y(eGvmYF>79S=Ad3RZpKlVML6?PrfgMH7wEzYNA5UjjzhGBT7$7Hr?Dx`= zjlm2IDM@-sDQW1k^WRG|GECn6UeXd|LBU5Ory~pu43&)F6ozDlM+gIhUO`cQR%&ty z$PDB}$ol~lpPC<}6+mVz`sB?o#Kgc*%EG{)h-3l-Lr&=A38Bi9*L~yxD?IDE?AjCt z28Lq{3=B#r3eSd5{ur*pk8V%iTWOh%5s;uy%gjkd5BkZnAElXYL`?n@ArH4?x2t~a z3}yxfCpHEKbreflVkWPM(F7?3$LrpY(u{?ZZ+?Wt^1qML7N-&z7=m0KU3^{ja#KKV zK?>CXZkb2bd<+Z>JPZsBAR1wG#N@zFvS1?%KS?t#n%w(I63koqNt)?Y=Hz#o3g9vU z6jXKY+EZS$GBA{LGcZUaOkiMOm_J$YvldvJ-DhdW%afx%D}hr9a>=fNqJw4f?9b+4 zHS2HeRBd8pU?^ll_j1nUkDtxJrfPkWW^|tH_C*2A%lsnER8%v0b&Y~H$e&1Yi&7*B zpjdcl^2IOmU<+&bVh@=yGBBKFWMGg*QS)K)#V^8>t=o7f>wo0|TV?lEnyIjTvcOmI z$wgm9z(Sp0rJ0mF!9sh#ihxZ-Hbe-S!?0)ahp&p@vwKctza@0e`(O=j|&9UPPA{eW1!_J=g1=;V_> zAZhF64{0XHy_2i9%C2~lA1Q<^bxvd>Qqu!j=X&wV(Vm4RV4FM3Hoha`Ru1_oOZbZyL&6@Ni02%lfljFFQwe(A9Fya0tM03N{p ArvLx|