Warning: ob_start(): function 'compress_handler' not found or invalid function name in /www/htdocs/xfmantis/core.php on line 18

SYSTEM WARNING: Cannot modify header information - headers already sent by (output started at /www/htdocs/xfmantis/core.php:18)

SYSTEM WARNING: Cannot modify header information - headers already sent by (output started at /www/htdocs/xfmantis/core.php:18)

SYSTEM WARNING: Cannot modify header information - headers already sent by (output started at /www/htdocs/xfmantis/core.php:18)

SYSTEM WARNING: Cannot modify header information - headers already sent by (output started at /www/htdocs/xfmantis/core.php:18)

SYSTEM WARNING: Cannot modify header information - headers already sent by (output started at /www/htdocs/xfmantis/core.php:18)

SYSTEM WARNING: Cannot modify header information - headers already sent by (output started at /www/htdocs/xfmantis/core.php:18)

SYSTEM WARNING: Cannot modify header information - headers already sent by (output started at /www/htdocs/xfmantis/core.php:18)

SYSTEM WARNING: Cannot modify header information - headers already sent by (output started at /www/htdocs/xfmantis/core.php:18)

BLENDER_v225REND X1SRd\LSRimport/exportcreen.D]_4$lDc.^1 DATAD]M]DATA]M]D]1DATA]M^]1DATA^Md^]DATAd^M^^DATA^M^d^DATA^M<_^DATA<_M_^DATA_M_<_PDATA_M_PDATA4N|]]DATA|N4D]^DATAN |D]d^DATA NT^^DATATN d^^DATANT]^DATAN,]<_DATA,Nt^<_DATAtN,d^^DATANt^<_DATANLd^_DATALN^_DATANL^_DATAN$<__DATA$N__DATAlO<D]d^^^CTTt4FDATATClDdCD@ ]CC(BDC?z?DcDATA<O$l^]]<_131112DATA$O<__<_^E='=o?SSS  .*<ԮԮDATAhI\ $,%"?  "DATA\B $?C7w[A$?zCy2 A** #< #<`jFzD ĭ,OB?C7w[ADATA >T\$????????E='=o?SA:A??SAg  B?=C DATATC< $DdCDv@CC(BDC?z?DATAD<ET$h#LOAD TEXT FILEc:\Program\Python20\walkomatic\lab\mport\..\walkomatic0.49.7.py.ndo  EDATAO$d^^__x&@m~@AHMMMM N*l$\$\DATA>Tv5?? 4>%?=&pAvQ?Lg5?_!(4??[ړ=7OA&pE@??A6/x&@u5Q?55+UJ~@KBK+uOAQA~b~5T>.n3 +&3>$_]1˜BH-֟Bq>ªAA(@p?xhfPYAg  B?=C"a?   DATATF0A'GA{wnAqeAJ A@CC #<@$DATA,]OB@gDATA,]OB2@mDATA,]TOB@2@jDATA,T]LA[*ArDATA,]$TLA@[*AqDATA,$]SC@ffDcDATABTzC AzC A #< #<`jFzD OBDATAClDdCDv@CC(BDC?z?DATADlESAVE FILERYd:\models\python\walkomatic\1.blend\Text\ordinary footwalkerntitled.blendend0@SRdLt\SRscreen|L<DcL1DATA|MDATAM |1DATA MT1DATATM DATAMTDATAM,DATA,MtDATAtM,DATAMtDATAMDATALN DATANL|TDATAN$|DATA$NlTDATAlN$DATANl,DATAND tDATADN,tDATANDDATANDATANd,DATAdNtDATANdDATAN<tDATA<N,DATAOT|T dllDATAlCDdCD5x=RdCC(BDC?z?DATATO<, tdDATA<OT,| m=:=o?[$$DATA$>????????| m=:=o?p=A}A??p=Ag  B? #<CiiDATAO<t??PףdDATABzC̽̌?zC@ #< #<`jFzD OBzC̽̌?DATA>??? ???? A???PA A!O?j?}GCHB? Ag  B? #<C@h@hSRdtLSRscreen.002 $l4|DcL1DATA MTDATATM 1DATAMT1DATAM,DATA,MtDATAtM,DATAMtDATAMLDATALMDATAMLDATAM$DATA$MDATAlNTDATANl DATAND ,DATADNtDATAND,tDATANTDATANdDATAdNDATANd,LDATAN<LDATA<NDATAN<tDATANLDATAN\LDATA\NDATAN\$DATAN4$DATA4N$DATA|OL ,tdddDATAdCDdCD6x=RdCC(BDC?z?DATALO4|TdDATA4OL,Lt8=i>o?uubdDATADzCAzCAbb A@FB= A DATA>????????8=i>o?fffAD&@??fffAg  B? #<CDATADESAVE FILE/pics/blender/rt1.blendkDATAO4$8=H>o?{{Vd|DATADzCAzCA1||1 A@FB= A DATA>|????????8=H>o?fffA*@??fffAg  B? #<C>>DATAD|ESAVE FILE/pics/blender/rt1.blendkDATAOL$8=>o?{{VdaDATAB`B̽̌?B̽̌?VV #< #<`jFzD SQB̽̌?DATA`>a????????8=>o?fffA@??fffAg  B? #<CzzDATADaE`SAVE FILE/pics/blender/rt1.blendkSCDc<SC1g`f >lO@ gdd??< 63=fff?=fff?_@??////footwalkernder///#DATA`8Tf DATATf8<` ADATA<8DTf8>DATAD8< DATA8|D84DATA|8${ <DATA$8|8 <DATA84$~DATA48f ~$,DATAf8)d????OB<5gOBEmpty.001>?7w?????????>?7w??????Dd?? #=?>=?@???OB54<OBEmpty.002|(r<7w@@??????_;__;-?1_?(r<6w@@?????Ddy? #=?>=?@???ttDATA,Y,DATA`tYConst?OB45 OBEmpty.0035|7o?????????5|7o??????Dd?? #=?>=?@???OB 5>4OBEmpty.004>?7o?????????>?7o??????Dd?? #=?>=?@???OB>5A OBEmpty.005\5|j$k?????????5|j$k??????Dd?? #=?>=?@???OBA5j>OBEmpty.006>?j$k?????????>?j$k??????Dd?? #=?>=?@???OBj5mAOBGL Light 1 q pA?)??R;?3;?M>?4+> ?*?4B>? pA?????)U>?r>:+ ?CYV*?ʞ>?*2;4rd;>5?Dd??)d??>)d????OBm5,jOBGL Light 2001 r:DA@=׿m!@}?(?v?SE@&@?&>4+?> ?P*?>V>oy>:DA@=׿m!@?????PY>;>r>:b+?} ?0>*3 *?>Yn$ATm2?Dd??)d??>)d????OB,5t!mOBPlaneĭEXX(r<7w?????????(r<7w??????DOBd?? #=?>=?@???OBt!5 <,OBArmatureJ?|@@(r<6w@@????3???a73?i!3??i!i!3?|@@??`;-.? 1?'r6wA@?Dd?? #=?>=?@???DATA\n????w?7=S9 7V?&;ᔍy?"4p7?BoneDATA\n4o????w?4Z<`.5Zm?ARs:56uPs?(>c&4?Bone.001DATA|T><o:DATA`TdT>Const?DATA,3 DATA`dT3Const.001?DATA4ot\nTd????>;P6?|6=?Ѳ9a96=@;a?Xq4?Bone.002DATA,ZADATA`ZConst?DATAtL4o????0?c<;d=,? 2D}4?9qG4#*2?Bone.003DATALt?????7=v73?~U9.W;?3̖Դ~?Bone.004DATAL????n?]<x]X?Fƺ’D}:?Ua3-;H3?Bone.005DATA| R <o:DATA`^ RConst?DATA, X4DATA`^ XConst.001?DATA^????:KI:;?T6=?ֽ6=ꨜ1hq-?Bone.006DATA,tX>DATA` tXConst?DATA  ????6?hd3ed=.?XmX4?|z,v4?Bone.007DATAJOB <5t!OBEmpty5|7w?????????5|7w??????Dd?? #=?>=?@???OB5 <OBGrid\h >lO0?ԡAԡAԡA??ԡAԡAԡA >lO0??????Dd?? #=?>=?@???MEE2IMEPlane%DYDYd@4???DATAPd/????DATA *ME\h2IMEGrid$/\???DATAP\/{o^sN|=[k-:c ־l*9gL)%1ƽ!!=1=H)%>9g>(>j>>>c ?9?Zk-?{=?sN?^?{o???{o{o?{o^?{osN?{o{=?{oZk-?{o9?{oc ?{o>{o>{oj>{o(>{o9g>{oH)%>{o1={o!={o!{o1ƽ{oL)%{o9g{o*{ol{o־{o{oc {o:{o[k-{o|={osN{o^{o{o{o{o^{o^^^sN^|=^[k-^:^c ^^־^l^*^9g^L)%^1ƽ^!^!=^1=^H)%>^9g>^(>^j>^>^>^c ?^9?^Zk-?^{=?^sN?^^?^{o?^?^?sN{o?sN^?sNsN?sN{=?sNZk-?sN9?sNc ?sN>sN>sNj>sN(>sN9g>sNH)%>sN1=sN!=sN!sN1ƽsNL)%sN9gsN*sNlsN־sNsNc sN:sN[k-sN|=sNsNsN^sN{osNsN|={o|=^|=sN|=|=|=[k-|=:|=c |=|=־|=l|=*|=9g|=L)%|=1ƽ|=!|=!=|=1=|=H)%>|=9g>|=(>|=j>|=>|=>|=c ?|=9?|=Zk-?|={=?|=sN?|=^?|={o?|=?|=?[k-{o?[k-^?[k-sN?[k-{=?[k-Zk-?[k-9?[k-c ?[k->[k->[k-j>[k-(>[k-9g>[k-H)%>[k-1=[k-!=[k-![k-1ƽ[k-L)%[k-9g[k-*[k-l[k-־[k-[k-c [k-:[k-[k-[k-|=[k-sN[k-^[k-{o[k-[k-:{o:^:sN:|=:[k-:::c ::־:l:*:9g:L)%:1ƽ:!:!=:1=:H)%>:9g>:(>:j>:>:>:c ?:9?:Zk-?:{=?:sN?:^?:{o?:?:?c {o?c ^?c sN?c {=?c Zk-?c 9?c c ?c >c >c j>c (>c 9g>c H)%>c 1=c !=c !c 1ƽc L)%c 9gc *c lc ־c c c c :c [k-c |=c sNc ^c {oc c {o^sN|=[k-:c ־l*9gL)%1ƽ!!=1=H)%>9g>(>j>>>c ?9?Zk-?{=?sN?^?{o???־{o?־^?־sN?־{=?־Zk-?־9?־c ?־>־>־j>־(>־9g>־H)%>־1=־!=־!־1ƽ־L)%־9g־*־l־־־־c ־:־[k-־|=־sN־^־{o־־l{ol^lsNl|=l[k-l:lc ll־lll*l9glL)%l1ƽl!l!=l1=lH)%>l9g>l(>lj>l>l>lc ?l9?lZk-?l{=?lsN?l^?l{o?l?l?*{o?*^?*sN?*{=?*Zk-?*9?*c ?*>*>*j>*(>*9g>*H)%>*1=*!=*!*1ƽ*L)%*9g***l*־**c *:*[k-*|=*sN*^*{o**9g{o9g^9gsN9g|=9g[k-9g:9gc 9g9g־9gl9g*9g9g9gL)%9g1ƽ9g!9g!=9g1=9gH)%>9g9g>9g(>9gj>9g>9g>9gc ?9g9?9gZk-?9g{=?9gsN?9g^?9g{o?9g?9g?L)%{o?L)%^?L)%sN?L)%{=?L)%Zk-?L)%9?L)%c ?L)%>L)%>L)%j>L)%(>L)%9g>L)%H)%>L)%1=L)%!=L)%!L)%1ƽL)%L)%L)%9gL)%*L)%lL)%־L)%L)%c L)%:L)%[k-L)%|=L)%sNL)%^L)%{oL)%L)%1ƽ{o1ƽ^1ƽsN1ƽ|=1ƽ[k-1ƽ:1ƽc 1ƽ1ƽ־1ƽl1ƽ*1ƽ9g1ƽL)%1ƽ1ƽ1ƽ!1ƽ!=1ƽ1=1ƽH)%>1ƽ9g>1ƽ(>1ƽj>1ƽ>1ƽ>1ƽc ?1ƽ9?1ƽZk-?1ƽ{=?1ƽsN?1ƽ^?1ƽ{o?1ƽ?1ƽ?!{o?!^?!sN?!{=?!Zk-?!9?!c ?!>!>!j>!(>!9g>!H)%>!1=!!=!!!1ƽ!L)%!9g!*!l!־!!c !:![k-!|=!sN!^!{o!!!={o!=^!=sN!=|=!=[k-!=:!=c !=!=־!=l!=*!=9g!=L)%!=1ƽ!=!!=!=!=1=!=H)%>!=9g>!=(>!=j>!=>!=>!=c ?!=9?!=Zk-?!={=?!=sN?!=^?!={o?!=?!=?1={o?1=^?1=sN?1={=?1=Zk-?1=9?1=c ?1=>1=>1=j>1=(>1=9g>1=H)%>1=1=1=!=1=!1=1ƽ1=L)%1=9g1=*1=l1=־1=1=c 1=:1=[k-1=|=1=sN1=^1={o1=1=H)%>{oH)%>^H)%>sNH)%>|=H)%>[k-H)%>:H)%>c H)%>H)%>־H)%>lH)%>*H)%>9gH)%>L)%H)%>1ƽH)%>!H)%>!=H)%>1=H)%>H)%>H)%>9g>H)%>(>H)%>j>H)%>>H)%>>H)%>c ?H)%>9?H)%>Zk-?H)%>{=?H)%>sN?H)%>^?H)%>{o?H)%>?H)%>?9g>{o?9g>^?9g>sN?9g>{=?9g>Zk-?9g>9?9g>c ?9g>>9g>>9g>j>9g>(>9g>9g>9g>H)%>9g>1=9g>!=9g>!9g>1ƽ9g>L)%9g>9g9g>*9g>l9g>־9g>9g>c 9g>:9g>[k-9g>|=9g>sN9g>^9g>{o9g>9g>(>{o(>^(>sN(>|=(>[k-(>:(>c (>(>־(>l(>*(>9g(>L)%(>1ƽ(>!(>!=(>1=(>H)%>(>9g>(>(>(>j>(>>(>>(>c ?(>9?(>Zk-?(>{=?(>sN?(>^?(>{o?(>?(>?j>{o?j>^?j>sN?j>{=?j>Zk-?j>9?j>c ?j>>j>>j>j>j>(>j>9g>j>H)%>j>1=j>!=j>!j>1ƽj>L)%j>9gj>*j>lj>־j>j>c j>:j>[k-j>|=j>sNj>^j>{oj>j>>{o>^>sN>|=>[k->:>c >>־>l>*>9g>L)%>1ƽ>!>!=>1=>H)%>>9g>>(>>j>>>>>>c ?>9?>Zk-?>{=?>sN?>^?>{o?>?>?>{o?>^?>sN?>{=?>Zk-?>9?>c ?>>>>>j>>(>>9g>>H)%>>1=>!=>!>1ƽ>L)%>9g>*>l>־>>c >:>[k->|=>sN>^>{o>>c ?{oc ?^c ?sNc ?|=c ?[k-c ?:c ?c c ?c ?־c ?lc ?*c ?9gc ?L)%c ?1ƽc ?!c ?!=c ?1=c ?H)%>c ?9g>c ?(>c ?j>c ?>c ?>c ?c ?c ?9?c ?Zk-?c ?{=?c ?sN?c ?^?c ?{o?c ??c ??9?{o?9?^?9?sN?9?{=?9?Zk-?9?9?9?c ?9?>9?>9?j>9?(>9?9g>9?H)%>9?1=9?!=9?!9?1ƽ9?L)%9?9g9?*9?l9?־9?9?c 9?:9?[k-9?|=9?sN9?^9?{o9?9?Zk-?{oZk-?^Zk-?sNZk-?|=Zk-?[k-Zk-?:Zk-?c Zk-?Zk-?־Zk-?lZk-?*Zk-?9gZk-?L)%Zk-?1ƽZk-?!Zk-?!=Zk-?1=Zk-?H)%>Zk-?9g>Zk-?(>Zk-?j>Zk-?>Zk-?>Zk-?c ?Zk-?9?Zk-?Zk-?Zk-?{=?Zk-?sN?Zk-?^?Zk-?{o?Zk-??Zk-??{=?{o?{=?^?{=?sN?{=?{=?{=?Zk-?{=?9?{=?c ?{=?>{=?>{=?j>{=?(>{=?9g>{=?H)%>{=?1={=?!={=?!{=?1ƽ{=?L)%{=?9g{=?*{=?l{=?־{=?{=?c {=?:{=?[k-{=?|={=?sN{=?^{=?{o{=?{=?sN?{osN?^sN?sNsN?|=sN?[k-sN?:sN?c sN?sN?־sN?lsN?*sN?9gsN?L)%sN?1ƽsN?!sN?!=sN?1=sN?H)%>sN?9g>sN?(>sN?j>sN?>sN?>sN?c ?sN?9?sN?Zk-?sN?{=?sN?sN?sN?^?sN?{o?sN??sN??^?{o?^?^?^?sN?^?{=?^?Zk-?^?9?^?c ?^?>^?>^?j>^?(>^?9g>^?H)%>^?1=^?!=^?!^?1ƽ^?L)%^?9g^?*^?l^?־^?^?c ^?:^?[k-^?|=^?sN^?^^?{o^?^?{o?{o{o?^{o?sN{o?|={o?[k-{o?:{o?c {o?{o?־{o?l{o?*{o?9g{o?L)%{o?1ƽ{o?!{o?!={o?1={o?H)%>{o?9g>{o?(>{o?j>{o?>{o?>{o?c ?{o?9?{o?Zk-?{o?{=?{o?sN?{o?^?{o?{o?{o??{o???{o??^??sN??{=??Zk-??9??c ??>?>?j>?(>?9g>?H)%>?1=?!=?!?1ƽ?L)%?9g?*?l?־??c ?:?[k-?|=?sN?^?{o??DATA -/*! "!#"$#%$&%'&(')(*)+*,+-,.-/.0/10 21 32 43 54 65 768798:9;:<;=<>=?>>?@A=>AB <=BC ;<CD :;DE 9:EF 89FG 78GH 67HI 56IJ 45JK 34KL 23LM 12MN 01NO /0OP ./PQ -.QR ,-RS +,ST *+TU )*UV ()VW '(WX &'XY %&YZ $%Z[ #$[\ "#\] !"]^ !^_ _^a`^]ba]\cb\[dc[ZedZYfeYXgfXWhgWVihVUjiUTkjTSlkSRmlRQnmQPonPOpoONqpNMrqMLsrLKtsKJutJIvuIHwvHGxwGFyxFEzyED{zDC|{CB}|BA~}A@~~}~ |} {| z{ yz xy wx vw uv tu st rs qr pq op no mn lm kl jk ij hi gh fg ef de cd bc ab `a                                                                  ! "!#"$#%$&%'&(')(*)+*,+-,.-/.0/10 21  32  43  54  65 768798:9;:<;=<>=?>>?@A=>AB <=BC ;<CD :;DE 9:EF 89FG 78GH 67HI 56IJ 45JK 34KL 23LM 12MN 01NO /0OP ./PQ -.QR ,-RS +,ST *+TU )*UV ()VW '(WX &'XY %&YZ $%Z[ #$[\ "#\] !"]^ !^_ _^a`^]ba]\cb\[dc[ZedZYfeYXgfXWhgWVihVUjiUTkjTSlkSRmlRQnmQPonPOpoONqpNMrqMLsrLKtsKJutJIvuIHwvHGxwGFyxFEzyED{zDC|{CB}|BA~}A@~~}~ |} {| z{ yz xy wx vw uv tu st rs qr pq op no mn lm kl jk ij hi gh fg ef de cd bc ab `a                                                                       ! "!#"$#%$&%'&(')(*)+*,+-,.-/.0/10 21  32  43  54  65 768798:9;:<;=<>=?>>?@A=>AB <=BC ;<CD :;DE 9:EF 89FG 78GH 67HI 56IJ 45JK 34KL 23LM 12MN 01NO /0OP ./PQ -.QR ,-RS +,ST *+TU )*UV ()VW '(WX &'XY %&YZ $%Z[ #$[\ "#\] !"]^ !^_ _^a`^]ba]\cb\[dc[ZedZYfeYXgfXWhgWVihVUjiUTkjTSlkSRmlRQnmQPonPOpoONqpNMrqMLsrLKtsKJutJIvuIHwvHGxwGFyxFEzyED{zDC|{CB}|BA~}A@~~}~ |} {| z{ yz xy wx vw uv tu st rs qr pq op no mn lm kl jk ij hi gh fg ef de cd bc ab `a                                                                       ! "!#"$#%$&%'&(')(*)+*,+-,.-/.0/10 21  32  43  54  65 768798:9;:<;=<>=?>>?@A=>AB <=BC ;<CD :;DE 9:EF 89FG 78GH 67HI 56IJ 45JK 34KL 23LM 12MN 01NO /0OP ./PQ -.QR ,-RS +,ST *+TU )*UV ()VW '(WX &'XY %&YZ $%Z[ #$[\ "#\] !"]^ !^_ _^a`^]ba]\cb\[dc[ZedZYfeYXgfXWhgWVihVUjiUTkjTSlkSRmlRQnmQPonPOpoONqpNMrqMLsrLKtsKJutJIvuIHwvHGxwGFyxFEzyED{zDC|{CB}|BA~}A@~~}~ |} {| z{ yz xy wx vw uv tu st rs qr pq op no mn lm kl jk ij hi gh fg ef de cd bc ab `a                               CAltpCACamera=B?AB?LAqrLALamp 1????'B4Bhdi>??@ B4B?@@LArqLALamp 21???A4B>??? B4B?@@IPP|IPcenter.001lOBDATAP)lT?C$ AOB(rVN<@XJ<AtF<ArC< A?<AcO;<A(7<A2< A/.<$A*<+Ap%<0A݂!<4AJB<;A<@Aۆ<DA<KA <PA@<TAX<[A#U;`A;dAV;kA;pAL;tAG;{Aj;A;~A\;A;Ar;~A5΃;Aoo;Ax[;~AρG;AP/;ATc;~Av;A:A8:~Aᬏ:A" @:A9~AG9AHgAB\~AMRAaJA_~A]A31A:~A9D+A@A9R~AvVcA6wA%~A9`AApϝ~AaAAʵ~AA}QŻAY˻~A5kһAٻAr߻~AAKA'[~AjAB2 ?Bx8B}B?BB8` Bu ? B  B, B ? B B B$ ?Bst B! B ?B& B Bj?B`BBPb?BVBh Bß?!B"B߻$BSջ?%B ̻&BN(B?)B*BhP,B-?-B|.B"V0Bd4?1B"2BRʺ4B<p?5B6B :8Bn :?9B@L;:BU!D;B6;@B/;?AB<BBt<DB,<?EB ;< FB"<HB(r<?IBB<JB'=LBUm,=?MBvR=NB0=PB5h=?QB=RB=TB=?UB_=VB>XB=>?YBĆ >ZB.0>\B=>?]BK>^B[>`B,j>?aBx>bB=>dB>?eB&>fBg>hB+>?iBwG>jB%^>lB}>?mB,>nB&>pBs.>?qB6>rB l>tB>?uB86?vB?xB( ? ?yB?zB#C?|B,? ?}B{"?~B7)?B.?Bu14?`B:?Bν@?B~F?`B%M?BS?BFY?`B%a?Bxg?Blm?`Bu?BD|?Bmt?`B3?BT?B͌?`B ?B?BV,?`B.?BO?B?`Bzl?B! ?Bӯ?`B|T?B?Bݻ?`Bx?BU?Bg3?`B?B?B7?`Bu?B?Bg#?`BA?Bs?B?`B)J?B?Bd?`B@Bi@BR@`B @B T @B@`B@BT@Bui@`Bz@B@B @`B$@B%'@B"7*@`B" .@BS1@Bv4@`BϷ8@B ><@Bu?@`B1D@BG@BK@`BP@B T@ƟBX@`B]@B!jb@֟Bf@`Bl@BYq@韲B1:v@`B]|@BԀ@B~@`Bن@B@Bc@`BE5@BF@BZ@`B1@Bp@韺Bg@`B@B*@⟼B@`B(ԯ@Bc@۟B@`B_@B@ӟB@`BT@B$@˟B/@`B(@B@ßB@`BWP@BQ@BV@`B>@BOT@B0l@`Bj@B@B[A`B_ABABA`B> ABt ABEA`BsuABABҸA`BNABrABnA}`Bt,ABO!A{Bs#At`B) &AB+(ArBL*Ak`B,AB.AiBP1Ab`B3ABU5A`B7AY`Bg:AB8|AP`BAABCAOB&EAH`BGAB%IAFBKA?`B NABPA>BpQA8`BRTABI>VA7B(XA0`BqZABO\A/BY*^A)`Ba`AB.bA)BcA"`BZfABPgA"B?iA`BkABCmABnA`BpABkrABsA`BuABhKwABxA`B{zAB{ABT8}A`B~AB ABiA`BdABABgA`B/ABEAB@2A`BĄAB4A BݣA_B$AB|AbBOԆA5`B^BO͇A|`BNAC#HAOC{A7CACAz^CADATA<_%r!?7w?7w?7w4#?w@w0@{w,@w>w@@?v!S@vl@;,v@:uZ@Gu @9t@t@hs @r@rt@Qqx @ep@Óo@n @mAlAbk} AjA۝iAhA=Eg A$f$Ae+Ac0A^b4A$a;A_@AN^DA\KA][PA{YTAїXy[AV`AhUdASfkA!RpAbPntAOO{A,MAK*AIAPHA"\FA|D AOBA@ A=?Av"=A_;~A%9ꂝAmr7A5~A@3؂AƜ1Az/~A-łA+A)~A'A%A#~A!A\A'i~AtAA~AttAZAPp~A^A:D Ay? [~A!:IAAIE~AY3APxAa/~AJAUA;~A A6(A ~AAB>BBB>BBB> B( B B> BNxBFB㏞>BڋB}B>BvBJB' >BBxB` q>BOiB` BiX>!BP"BG$B>@>%BM8&B7/(B(>)BQ!*B,B|>-Bm w.B]0B "w>1B?cm2B׿4BФʿn>5BZe6Bą8Bf>9B㓿]:B=BBXW>B4;@Bn#Z>ABp SBB&DB'_S>EB6IBAJBno=LBJ(>O>MBKt>cNBjr>PB>r>QB[>RB ?TB3?>UB{+?VBaq>?XBM?>YB\?ZBWgn?\B6|?>]BT?^B_?`Bb0?>aBpʚ?bB?dB?>eBG?fB+?hB?>iB?jBh?lB,?>mB?nBs#?pBY?>qB_?rB?tB?>uB?vBg?xB?>yB@zBӲ@|B$@>}B&5 @~B @B{ @xB4@x`B+@Bn@yB@z`Bp@Bw@{B+@{`B@B!@}B#@}`B#>&@Bi0(@~B"*@`Bw,@Bf.@B T0@|`BU2@B^4@|BN{6@x`B"8@B֝:@yB]u<@y`B>@Bd@@zB'B@y`BX=D@B]E@zBAG@z`BI@B:K@{BL@z`BN@BOP@{BvQ@{`B_S@B.U@|BV@{`B\mX@BY@|BE[@{`B,\@BQ^@|Bn_@|`BJa@Bb@}B(c@|`Bne@BЬf@}Bg@|`Bai@B_j@}B̾k@|`B#m@BBn@}Byao@|`Bcp@Bq@}Br@|`Bt@Bu@}B6v@|`BZ:w@B)x@}By@|`B.z@B, {@}B{@}`BV|@B}@}B~@|`Bn@BJ@~BLo@~`Bր@B+@}Bـ@r`Bf@Bi"@|BhI@`Bm*@B(@B{'@`B,@B.@B1@`B2@B4@B#6@`B8@B9@B ;@`B<@B>@Bl?@`B@@B!B@BPC@`BD@BE@BF@`BG@BH@BI@`BJ@B]K@BL@`BL@BM@BN@`BN@B3O@BO@`B!P@BtP@BP@`BQ@BHQ@BzQ@`BQ@BQ@BQ@`BQ@BQ@BQ@`BQ@BbQ@B8Q@`BP@BP@BiP@`BP@BO@BFO@`BN@BMN@BM@`B8M@BL@B L@`BiK@BJ@B)J@`B[I@BH@BG@`BG@BYF@BE@`BD@BC@BC@`BB@B@B=@`B<@B;@B:@`B9@B8@B8@`B6@B6@B15@`B#4@BI3@Bo2@`Bj1@B0@B/@`B.@B.@B?-@`BT,@B+@B*@`B *@Bb)@B(@`B'@Bg'@B&@`Bc8@B%@B@`B!@BQ$@B'@`B#@CH#@OC"@6C"@C"@w^C"@DATA<$%!?@@?@@?@@?@@@@@ @@@,@@@@@@@ S@@@l@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@A@@A@@ A@@A@@A@@A@@ A@@$A@@+A@@0A@@4A@@;A@@@A@@DA@@KA@@PA@@TA@@[A@@`A@@dA@@kA@@pA@@tA@@{A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@A@@~A@@A@@B@@?B@@B@@B@@?B@@B@@B@@? B@@ B@@ B@@? B@@B@@B@@?B@@B@@B@@?B@@B@@B@@?B@@B@@B@@?B@@B@@ B@@?!B@@"B@@$B@@?%B@@&B@@(B@@?)B@@*B@@,B@@?-B@@.B@@0B@@?1B@@2B@@4B@@?5B@@6B@@8B@@?9B@@:B@@B@@@B@@?AB@@BB@@DB@@?EB@@FB@@HB@@?IB@@JB@@LB@@?MB@@NB@@PB@@?QB@@RB@@TB@@?UB@@VB@@XB@@?YB@@ZB@@\B@@?]B@@^B@@`B@@?aB@@bB@@dB@@?eB@@fB@@hB@@?iB@@jB@@lB@@?mB@@nB@@pB@@?qB@@rB@@tB@@?uB@@vB@@xB@@?yB@@zB@@|B@@?}B@@~B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B@@B@@B@@`B?@B@@B@@`B@@B@@B?@`B?@B@@B@@`B@@B@@B@@`Bb$@@B@@B?@`B?@B@@Bf@@`B@@C@@OCR?@6C@@C@@w^C@@IPPIPlfoot.003OBDATAP)x? C[AOB%5|DATAP)? C7wQ@OB%7wDATAP)č? C??OB%?DATAx%%5|?5|MX@5|=@ש|@5|@?|@0|@5|@VL|@Am|!A} 5A-}LAW}`AO~qsA8{AQj33AhjޖAgA&AAԟAAA{B,B BҟBB B} BffBBB2#Bz B0$B#;*B<{/B*u.p3B_p:Bc:Bc:Bc$8Bc:BcMaABcnBcnBcnBcnBcnBcnBcZtBffxB0|F}BH^Bt+=B>rB8A!?SBV?̋B6?XB?vBM#?BI`?B{l?Bb?BI`?BU?B\j?BI`?BE^?B_?BI`?Bb?~FB+@33ByO@B&~@BJ@Bc@NJBt.@?BTA̿Bt ABSAB ABrA7BPA BABrA_BFABABrABkABWpABrABzAB">A33BPASB`AYBpAB{AKBAAB"ABABA8BIAB[A(BABAB[ABAC[A C[A LC[ADATA%%7w?7wgY@7w@Cw@7w@5w@7w@7w@9w9A)p!Ai 6AB`MAS`AeFtAgx8`AO\"33A%(pUAAO AO AO H AO AO ²AO BO BO BO BBO  B]@ BdffB[B^~BdK B$Bil>*B2/B=>=3BC ?:BQ.?:BP.?:BP.?$8B5-?:BP.?LaAB.?{mB.?nBP.?NnB( .?mB,.?nBP.? nB9.?OtB?ffxB@1}Bm0@ BaE@BWY@[jBm@UBσ@̋Bw@B)ԍ@Be@BL@B@Bg@BL@B@RBX@BL@B]@B$@BL@yB@[BB\@33BĞ@B@FB>ܡ@B>@nB՟@^B`@̿BHQ@BD@BN@BQ@BMR@BQ@BQ@B7Q@BQ@BQ@BQ@BQ@BQ@BQ@GB-K@33BYF@AB<@@Bm6@B0@nB*@^Bj%@B"@Bw @;B@Bi"@'B$@B#@Bi"@Bs@Ci"@ Ci"@ LCi"@DATAč%%???PX@?J@p7?@?$@?@$?@?@% ?A?!A?4A}o?LA8?`A33?xsA-?oAd?33A?A; ?Ae?A?A?A?A?A?g=A?B?yB?yBn?B?B:R?V B?ffB?PABh?"B? B33?$B?H*B-q?/B?~3B?:B?:B?:B?:B?:B?:B?&)mB/D?nB?*nB??mBG?nB?nB4s?$tBt?ffxB?m>}B)?鐁B(D?B33? oB>"?`Bd?̋B?nB?pBǕ?B?Bk?CBn?B?B5R?Bj?B?B?B?B?B?@B?33B?bBxf?B33?B33? oB33?`B?̿B?atB÷?'Bt?B?Be}?vBx?B?B%R?B?B?B?B?B?B?@B?33B?bB|f?B<;?B33?oB*+?`Bm?B?BK ?YB?8?B?!B?Bh?B?B{ ?C? C? LC?IPP\IPlfoot.004OBDATAP)$? Cu][AOB%5|DATAP$)\~? C7oQ@OB%7oDATAP)$? C??OB%?DATA%%5|?5|KX@5|<@ԩ|@5|@@|@0|@5|@VL|@A|!Aw,} 5A}LAɕ}`A2qsAg{A33A覀jޖA$AӀA\߀AဿA߀A\߀AK݀BӀB\߀ BဿB߀B\߀ BM݀ BHffBu]BBw#B8ځ BO<$B,ƽ*Blz/BwrWp3Bl:BfZ:BfZ:BfZ$8BfZ:BfZMaABfZnBfZnBfZnBfZnBfZnBfZnBfZtBq"ffxBD}B <B>B+?/rBi?`QB?̋B??>B@vBI @Bmh @Bn @Bi @Bmh @Bb @Bh @Bmh @Beh @Blh @Bmh @Bsh @EBsJ@33Bo@5B0@yB*@Bc@슺B3+@AB'A̿BtABmAB ABr"A7BP#A B"ABr"A_BF!AB"ABr"ABk"ABWp"ABr"ABz"AB!FA33BXASBhAYBxABwAKBAAB"ABABA8BIAB[A(BABAB[ABAC[A C[A LC[ADATA\~%%7o?7ogY@7o@Co@7o@5o@7o@7o@9o9A)h!Aa 6ABXMAK`Ae>tAjx0`AR\33A)(pUAAOAOAOH AOAO²AOBOBOBOBBO B ]@ B dffB[B q3B+ B]$BOo8<*B/>/Bp/?73B+ ?9B㤖?:B?4:B=?9B?:B?5:Bז?mB4?nB?nB?nB?nB?nB?NtBQ@ffxB :-@}BEL@KB!,_@Bd:q@@jBEz@WB@̋B@ᴍBVF@B@B@BU@B@B@B<@B@B@B4@B@B@BG@$EBy@33BK@Bn@B@B>@nBh@^By^@̿BHQ@BF@BN@BQ@BMR@BQ@BQ@B7Q@BQ@BQ@BQ@BQ@BQ@BQ@GB-K@33BYF@AB<@@Bm6@B0@nB*@^Bj%@B"@Bw @;B@Bi"@'B$@B#@Bi"@Bs@Ci"@ Ci"@ LCi"@DATA%%???X@?@/9?@?@ ?@Q?@?^@ ?;A ?!A?5A<)?OLAt?`A33?qsAp?~A%?33A? A[?ZA@?A?TA ?A?A?tA ?B8 ?B? B?B*?B? B? B?ffB?AB+?&B? B33?$B6n?*B"?/B?_3B?9BH?:B?:B?:B?:B?:BY?mBd?nB?nB?nB?nB?nB?tBR?ffxB?A}B+? B?B33?oB-}?_B?̋B?LǍB?;rB?B?oBc?Bn?B?#B}?Bd?B?B?B?B?B?vGBU?33B?B+? B?B33?oB/}?_B?̿B?zB?B̆?B?nBG}?mB{?B?BpL?B?B?B?B?B?B?vGBQ?33B?B+? B?B33?oBp?_B'?B?cB1?fB:?B?B?Bo?B?Bj ?C? C? LC?IPP\ĭIPlfoot.005|TOBDATAP|)$? CQAOB%5|DATAP)T|,? Cj$kQ@OB%j$kDATAPT)? C?33?OB%?DATA$%%5|?5|KX@5|<@ԩ|@5|@@|@0|@5|@VL|@A|!A;} 5A}LA}`AlaqsAꃀ{Aƀ33A/̀jޖA|ЀAsAA! ACAAByB B BBB B BqffBBB#B BҀF$B $*BHz/Bpvp3Bdi:B͹T:BιT:BιT$8BιT:BιTMaABιTnBѹTnBιTnB͹TnBιTnBιTnBϹTtB-ȾffxBcVC}B0>Bp?B_?qB1?OBK?̋BՇ@B@wB@Bf=@BC@B>@Bf=@B7@B=@Bf=@B^=@Be=@Bf=@Bl=@9DBv]@33Bz@&B@WB(@B/@B@BB_ A̿BAABJh!AB!AB>'A7BS(A Bt`'AB>'A_B&ABa'AB>'AB7'AB$='AB>'ABG'ABPKA33B\ASBaqmAYB}ABSAKBl AABAB'ABIYA9BNABQA(B_RABQABQABQACQA CQA LCQADATA,%%j$k?j$kgY@j$k@v$k@j$k@h$k@j$k@j$k@l$k7A\c!AF\ 6A}SMA;RF`A9tA+`A33A^[ pUAAOANANH ANAN²ANBOBNBNB:BN B@ BtʯffBf [B]5Bm B)$B{"'<*B}>/B9|?73Beh?9Bh?:B\.?4:B:?9B0?:B\.?5:BP#?mB.?nB\.?nBJ.?nBY.?nB\.?nBk.?[MtBY#@ffxBX?@ }B]@Bo@Blb@MjB@XB@̋B @۵B-@B@BՁ@Bځ@Bց@BՁ@Bҁ@BӁ@BՁ@BՁ@(DB=@BՁ@KB3@B:@33B@VBӢ@đBA@B>@ nB:@^BC@̿BHQ@B\@BT@BQ@B*Q@BQ@BQ@B?R@BQ@BQ@BQ@BQ@BQ@BQ@GB-K@33BYF@AB<@@Bm6@B0@nB*@^Bj%@B"@Bw @;B@Bi"@'B$@B#@Bi"@Bs@Ci"@ Ci"@ LCi"@DATA%%???X@?@-9?@?@!?@Q?@?^@ ?);AFc?!A? 5A޸?LAS@?`A33?{sA\?tA5@33A33?17A?ASB?A?HAx?A?A?xA ?B9 ?B? B?B*?B? B?Ď B`?ffB?yBB޻?)B >? B33?$B_?*B1@/B33?3Bi?9BI?:B?:B?:B?:B?:BY?mBd?nB?nB?nB?nB?nB?ŽtB`?ffxB?yB}B?唁B 1?B33? sB m?]B@̋B33?эB?B?B?B?B?B?B?B?B?B?B?B?B?aGBa?33B?=Bĺ?唵Bn0?B33? sBm?]B΂@̿B33?B}?B?B?B?CB?B?B?ZOB?B?B?iBוn?B?Bg?FBIf?33B?B?Bȸ?B33?rB?]B]@B33?B: ?U!BĪ?B?UBn? B}?B?B?>C? C? LC?IPPĭ \IPObIpoĬ$?zCy2 AOBDATAPĬ)d?C@OB(rK;]<gA#B?B?썘B?rL|[k)֧BX@BԀ@B@}u4B[AC[A C[A   DATA,:%o7w?7wdA7w B2HBr _`B2?E]:gd9~B @B_4@mBZ@rw|B{y@Bi"@ZB@eBi"@Ci"@Ci"@DATA,%B???NA? WW)W B?HB?`B?EW]WgWB?B?vB?rW|WWB?B?B?WWWB?C?C?WWWDATA,%B?NA <<)< BHB`BE<]<g<BBvBr<|<<BBB<<<BCC<<<DATA,%B?NA <<)< BHB`BE<]<g<BBvBr<|<<BBB<<<BCC<<<DATA,d%B?2wA <<'<A`=HBcaBe1?=]<g))B=BkB s|NBBBB]JJ BCiCJJJIPPIPrfoot.003OBDATAP)$$?Cn}?[AOB*>?DATAP$),?C7wJD@OB*7wDATAP)$4?C??OB*?DATA $%*2?>??>?ֳ?>?ߏ?!?33@>?:@?i@Ձ?@Ł?tp@?@0?ff@v?'@R?@?@?@?1@?@?2AҀ?Af?A?A?A3?A?A?A8?̸A ?AH#?GA6}?A?~?Ak~?{A1C~?33An}?jA}?B ~?B] ~? B$~?B0!~?B] ~? B>~?:B\ ~?:B] ~?:B] ~?$8B~?:B] ~?=!=B[=~?$AB|?ffDB,?CIBS1?%OB?TB\T?qXB8?^B|?cB=?fgB,?mB?nB?<nB?mB; ?nB?2nB?B?B?B?B?B?B ?FBe?33B;@ʡB@,B@B^-@|Bf{A@]UBk@̥BԀ@B{@BE@BF@BF@BF@BF@BE@BF@BF@BF@BP@BF@Ba@sB@33BOT@\}B A(BAB.AtbB!?AxBoVAB.bAʑBdiABgABCmAJBbXnA7BwemABCmABHlA>BF#mABCmABxImABDDmABCmABG=mABhA33B|A<CAC|ˈAC[A7C A]CAfC[A CA C:A C[A CA CA C[A CAC[AC[A LC[ADATA ,%*t2?7w?7wڳ?7wУ?[Jx33@7wX:@`jwi@.v@t-@qe@v off@iK@c@[@haU@rQ!@aT@haU/V@w`Z!AYAhaUEAKT9AcDUAhaU]AUXA88̸A7)yAUiAAϲA/"A33A5Ao lB8QXB91X.B*XB#0XB91X8B6X^o9B^D:B91X:B (\9BX:B91Xo :BX7T?BoffDB~#HB=NB?TB?{?EXBl?T^B&4?cBT!?/cgB '?mB?nB?;nB?mB? ?nB?2nB?B?B?B?B?B?B ?DB` @33B@ڝB"@B4)@BK0@mB^7@\]B@@̥BDD@hBJF@eB${D@B]D@B%XD@B\D@B]D@BcD@BcD@B]D@B\D@B]D@B]D@B_D@GB͎D@33BD@ABxD@BwD@BJD@nBD@^B/D@B}D@ֳBD@dBώD@BqD@BkD@BpD@BqD@BrwD@BtwD@BqD@BpD@BqD@BqD@BrD@GBSD@33BhKD@PCAD@CED@CDD@7CDD@_CED@fCDD@ CBDD@ C,D@ CDD@ CID@ CFD@ CDD@ C>D@CDD@CDD@ LCDD@DATA 4%*p????l??R?$?33@?q9@.? h@i?@33?@w?;,@?ff@?@?@?@?@?1@?@?2A?NRAY/D?A?UAD?AG?A? ?DATAP,),<?C7oJD@OB*7oDATAP,),?C??OB*?DATA 4%*2?>??>?ֳ?>?ߏ?v?33@>?:@j?i@Ӂ?@$?sp@|?@?ff@i?'@A?@΀?@΀?@΀?1@Ӏ?@΀?2A?AÀ?A΀?A>р?Aaπ?A΀?À?A?̸Ap?A|~?GA}?A}?AV~?{Av}?33A)c}?jA}?B}?B}? BL}?B}?B}? B}?:B}?:B}?:B}?$8B@}?:B}?L!=BQs}?d$AB y?ffDB0Ԁ?>EIBȆ?r'OB~?TBo?XBP?^Bէ?cBG?&egB~?mB@?nBi|?;nBO?mB~?nBi|?2nB!q?B;?Bi|?B?z?B{?Bi|?B~?DB2@33B @Bk/@ϜBY8@BL@4|B&Ea@TBsx@̥BԐ@RB@BE@BF@BF@BF@BF@BE@BF@BF@BF@BP@BF@Ba@sB@33B'A\}BA(B&AB6AtbB!GAxBo^AB.jAʑBdqABoABCuAJBbXvA7BweuABCuABHtA>BF#uABCuABxIuABDDuABCuABG=uABhA33B|A<CAC|ˌAC[A7C A]CAfC[A CA C:A C[A CA CA C[A CAC[AC[A LC[ADATA <%*t2?7o?7oڳ?7oУ?[Jp33@7oX:@`joi@.n@l-@ie@v gff@aK@[@S@haM@rI!@aL@haM/V@w`R!AQAhaMEAKL9AcDMAhaM]AMXA:0̸A:!yAUiAѡAϲA/"A33A:i5A| LBEQ8BF18.B*8B008BF188B68\o9B^$:BF18:B)(<9B8:BF18n :B`74r?BunffDB*4HB?NBȉ?TB?XB[7?9^B@cBvm @kgBh@mB^@nBQ@nBPu@mBW@nBQ@;nB5@B '@BQ@B @B4@BQ@Bu@IB_"@33B(@sBx0@B"4@BL8@mBz<@H^BB@̥BDD@BE@dB{D@B]D@B&XD@B\D@B]D@BcD@BcD@B]D@B\D@B]D@B]D@B_D@GB͎D@33BD@ABxD@BwD@BJD@nBD@^B/D@B}D@ֳBD@dBώD@BqD@BkD@BpD@BqD@BrwD@BtwD@BqD@BpD@BqD@BqD@BrD@GBSD@33BhKD@PCAD@CED@CDD@7CDD@_CED@fCDD@ CBDD@ C,D@ CDD@ CID@ CFD@ CDD@ C>D@CDD@CDD@ LCDD@DATA %*V9????dz??30?m?33@?9@=?H_i@E?@33?橛@,X?9@l?ff@?”@?@?@?@?1@?@?2A?sBAF?A?YA%̅?AzV?A?>3A9r?B&Au?̸A? A? LA?A33?ԿA_?~A}?33A? AC]?-B@?B?*B ?B?B?:B ?9B8 ?:B? :B?9B*?:B? :B?@B?ffDB?AIB+?&OB?TB33?XB6n?^B"?cB?_gB?mBH?nB?nB?nB?nB?nBY?Bd?B?B?B?B?B?vGBR?33B?B+? B?B33?oB-}?_B?̥B?LǧB?;rB?B?oBc?Bn?B?#B}?Bd?B?B?B?B?B?vGBU?33B?B+? B?B33?oB/}?_B?B?zB?B̆?B?nBG}?mB{?B?BpL?B?B?B?B?B?B?vGBQ?33B?yPC+?C?C33?7Cp?C~'?fC?C>? C:? C? C? C? C? CD ?C?C? LC?IPPIPrfoot.005OBDATAP)L'?C}?QAOB*>?DATAPL)1?Cj$kJD@OB*j$kDATAP)L$?C?33?OB*?DATA '%*2?>??>?ֳ?>?ߏ??33@>?:@?i@ҁ?@?tp@7?@ ?ff@b?(@c7?@?@?@?1@€?@?2Aˤ?AI?A?A?A?A?A?A?̸A.?AhX~?GA|?Ab}?A~?{As}?33A}?jA|?BrU}?B/l}? Bp}?Bm}?B/l}? Bh}?:B0l}?:B/l}?:B/l}?$8B}?:B/l}?X!=B7|?$AB Nx?ffDB2ˀ?UFIB?(OB&2?TB?rXB (?^B0?cB)?dgB(@mB֏@nB@;nB@mBĮ@nB@2nB@Bح@B@B@B@B@B@CB#@33B(0@B0A@BJ@B7_@{BWt@TBe@̥B&n@7B*%@B߬@B߬@B߬@B߬@B߬@B߬@B߬@B߬@B߬@BB@B߬@B@sBD=@33BvA\}B\A(Bg*AB;AtbB_LAxBByABzABEzABzABzAB zABcA33BA<C%jAC1ACQA7C;qA^C4UAfCQA COA CNA CQA CaRA CQA CQA CQACQACQA LCQADATA 1%*t2?j$k?j$kڳ?j$kУ?}k33@j$kX:@ji@bNi@Fg-@#ee@HBkj?NBt?TB=?XB@^BC@cB#%@{dgBt @mB @nB!@=nB!@mB8!@nB!@2nBe!@BG!@B!@B !@B!@B!@B!@IFBD)/@33BD3@ꟘBI9@B:@B=@nB?@^B B@̥BDD@ijBZiE@dB{D@B]D@B'XD@B\D@B]D@BcD@BcD@B]D@B\D@B]D@B]D@B_D@GB͎D@33BD@ABxD@BwD@BJD@nBD@^B/D@B}D@ֳBD@dBώD@BqD@BkD@BpD@BqD@BrwD@BtwD@BqD@BpD@BqD@BqD@BrD@GBSD@33BhKD@PCAD@CED@CDD@7CDD@_CED@fCDD@ CBDD@ C,D@ CDD@ CID@ CFD@ CDD@ C>D@CDD@CDD@ LCDD@DATA $%*;????:dz??&??33@?m9@֣?i@Q'?@33?/@C?E@@ff@33?@N?@ ?@?@?@Q?@?j@?BAF?A?YAY̅?AkV?A?I3A՟r?%AΑ?̸A?HA~?WSAQ?A33?AWK?tA54@33A33?37AB?KBIB?B?$B|?B?B?<B ?9B9 ?:B? :B?9B*?:B? :B?Ď@B`?ffDB?yBIB޻?)OB >?TB33?XB_?^B1@cB33?gBi?mBI?nB?nB?nB?nB?nBY?Bd?B?B?B?B?B?aGB`?33B? DATA$>@DATA$l>!DATAl$?&DATAlt?(@ DATAD?DATAD$@DATADl@DATA@ DATAd@#DATAdDA7`DDATAdA'DATA<BDATA<\B.DATA<B@TDATA CDATA\TCDATA\C!DATA\CDATA4,DDATA4|tDbDATA|4D!!DATA |E&ayMDATA T\E(DATAT EDATAT FDATA,TFDATA,tF DATAt,F#DATAt,GDATALtGDATALGDATALHDATA$LH7DATA$lH%DATAl$ I.DATAltIFREEDATADIDATADJFREEDATADLJDATAJ1DATAdJ!gsfiDATAd$K(1DATAdK(DATA<K DATA<=$PDATAD>>=l DATA>>D>DATA>?>'DATA?d?>TUDATAd???hADATA??d? ADATA?<@?l+uADATA<@@?.DATA@@<@ADATA@A@dDATAA\A@6ADATA\AAADATAAA\A<.kADATAA4BA6DATA4B|BA #DATA|BB4BdDATAB C|BP @DATA CTCB DATATCC ClDATACCTC1DATAC,DC DATA,DtDCDDATAtDD,DDATADEtDDATAELEDL(@DATALEEEADATAEELEH@DATAE$FEt2DATA$FlFEDATAlFF$F95|DATAFFlFAFDATAFDGFGADATADGGF|DATAGGDGDATAGHG DATAHdHGD3DATAdHHH<DATAHHdH$MDATAH*'ADATAW$XW>'TDATA$XlXWl>mDATAlXX$X-ADATAXXlXLDATAXDYXDATADYYXADATAYYDYDATAYZYLkADATAZdZYDATAdZZZ<DATAZZdZD8DATAZ<[Z=DATA<[[Z4DATA[[<[ADATA[\[DATA\\\[DATA\\\\TDATA\\\\CDATA\4]\DATA4]|]\*DATA|]]4]*DATA] ^|]ADATA ^T^]$DATAT^^ ^|Τ}DATA^^T^DATA^,_^+ADATA,_t_^DATAt__,_DATA_`t_$0DATA`L`_DATAL```DATA``L` DATA`$a`d'DATA$ala`DATAlaa$ah@DATAaala\DATAaDba#$E@DATADbba&DATAbbDbT/DATAbcb)ADATAcdcb$@~:DATAdccc.ADATAccdcEDATAcDATA|ff4ft$DATAf g|fADATA gTgf$DATATgg g|@DATAggTgDATAg,hg-DATA,hthgjADATAthh,hADATAhith!DATAiLihl1DATALiiiDATAiiLi  DATAi$jiT2 ADATA$jljiDATAljj$je@DATAjjlj,ADATAjDkjDATADkkjADATAkkDk$IDATAklkhDATAldlk@DATAdlll<*DATAlldl2DATAlDATA܄$4)ADATA$l܄!D_DATAl$?DATAll-DATAD8DATADL DATAԆDADATAԆ1DATAdԆDSDATAdhDATAdCDATA<|EDDATA<CADATÄ<lDATÄZ@@DATA\̈ DATA\D 5DATA\ )DATA4!DATA4|L!DATA|Ċ4!ADATAĊ |!DATA TĊ4"ADATAT "DATAT"<ADATA,\#ADATA,t#DATAt,# 8DATAt$$ADATAL|$DATAL$/ADATA܍L,%04s,ADATA܍$%#X(DATA$l܍%;DATAl$d&DATAl&6ADATAD'#ADATADl' $?DATAԏD'6ADATAԏ$(ADATA$lԏT(DATAl$(!DATAl)&DATAD\)%ADATAD))X?DATAԑD*1DATAԑ*.DATAdԑ*2DATAdT+DATAd+*DATA<+(DATA<\,!ADATA̓<,.DATA̓-%DATA\̓t-4DATA\-)DATA\D.ADATA4|.DATA4|.)HDATA|ĕ4,/2DATAĕ |/DATA Tĕ/*ADATAT T02+1ADATAT02DATA,0'ADATA,tL13 DADATAt,15iDATAt2w?DATALT2ADATAL2DATAܘL3 ADATAܘ$\305RegisterGUI()DATA>DATA$>#================================DATA(?def ImportFunction (importName, type):DATA,t?#================================ DATA? global gFilename DATA$@ global gAlertDATAl@BDATA @ try:DATA$@ FILE=open (importName,"r")DATA8DA directory, Name = os.path.split(gFilename.val)DATA(A words = string.split(Name,".")DATAB Name = words[0]DATA0\B ObjImport(FILE, Name, gFilename.val) DATAB FILE.close()DATA C gAlert = 4DATATC Draw ()DATAC except IOError:.nDATAC gAlert=2DATA,D Draw ()DATAtDDATA$D#================================DATA(Edef ExportFunction (exportName, type):DATA,\E#================================ DATAE global gFilename DATA F global gAlertDATATFDATA F try:0DATA$F FILE=open (exportName,"r")DATA,G FILE.close()DATAtG gAlert = 1DATAG Draw ()ADATAH except IOError:DATA8LH directory, Name = os.path.split(gFilename.val)DATA(H if os.path.isdir(directory):DATA0 I ExportFunctionOK(exportName, type)DATAtI Draw ()DATAI else:EDATAJ gAlert = 5DATALJ Draw ()DATAJ DATA$J#================================fiDATA,$Kdef ExportFunctionOK (exportName, type):bigDATA,K#================================ DATAK global gFilename DATA 0:6-ADATAO gAlert = 3DATA \O else:DATAO gAlert = 4DATAO FILE.flush()uDATA4P FILE.close()uDATA|PDATAP#========================= DATA( Qdef ObjImport(file, Name, filename):endDATA dQ#========================= DATAQ vcount = 0uDATAR vncount = 0DATALR vtcount = 0vDATAR fcount = 0uDATAR gcount = 0uDATA$S setcount = 0uDATAlS groupflag = 0rDATAS objectflag = 0DATAS mtlflag = 0DATADT baseindex = 0DATAT basevtcount = 0DATAT basevncount = 0DATAU matindex = 0 creDATAdUDATAU pointList = []DATAU uvList = []DATA,V normalList = []DATAtV faceList = []DATAV materialList = []dDATAW uv = [] DATA LW lines = file.readlines()DATAW linenumber = 1DATAWDATA$X for line in lines:DATA$lX words = string.split(line)DATA(X if words and words[0] == "#":EEDATA$Y pass # ignore commentsDATA(tY elif words and words[0] == "v":DATA Y vcount = vcount + 1DATA $Z x = float(words[1])DATA |Z y = float(words[2])DATA Z z = float(words[3])DATA(,[ pointList.append([x, y, z])DATA[DATA,[ elif words and words[0] == "vt":DATA$$\ vtcount = vtcount + 1DATA |\ u = float(words[1])DATA \ v = float(words[2])DATA$,] uvList.append([u, v])EEDATA]DATA,] elif words and words[0] == "vn":DATA$$^ vncount = vncount + 1DATA |^ i = float(words[1])DATA ^ j = float(words[2])DATA ,_ k = float(words[3])DATA,_ normalList.append([i, j, k])DATA_W %DATA($` elif words and words[0] == "f":DATA |` fcount = fcount + 1DATA(` vi = [] # vertex indicesDATA(,a ti = [] # texture indicesDATA(a ni = [] # normal indices.wDATA a words = words[1:]DATA 4b lcount = len(words)DATA,b for index in (xrange(lcount)):tDATA8b if string.find(words[index], "/") == -1:DATA0\c vindex = int(words[index])DATAHc if vindex < 0: vindex = baseindex + vindex + 1 d DATA( 1 and vtn[1]:2DATA,,g tindex = int(vtn[1])JDATAHg if tindex < 0: tindex = basevtcount +tindex + 1- DATA( h ti.append(tindex)DATAdhDATA0h if len(vtn) > 2 and vtn[2]: DATA,i nindex = int(vtn[2])DATAHli if nindex < 0: nindex = basevncount +nindex + 1DATA8i ni.append(nindex) DATA4Lj faceList.append([vi, ti, ni, matindex])DATAjDATA(j elif words and words[0] == "o":DATA$Dk ObjectName = words[1]DATAk objectflag = 1DATA0k #print "Name is %s" % ObjectNamedDATA\lDATA(l elif words and words[0] == "g":DATAl groupflag = 1DATA Dm index = len(words)DATA m if objectflag == 0:DATA m objectflag = 1DATA Ln if index > 1:DATA<n ObjectName = string.join(words[1:],"_")DATA<o GroupName = string.join(words[1:],"_") DATAo else:DATA,o ObjectName = "Default" DATA,Dp GroupName = "Default" DATA8p #print "Object name is %s" % ObjectNameDATA8q #print "Group name is %s" % GroupNameDATA|q else:DATA q if index > 1:?DATA<r GroupName = string.join(words[1:],"_") DATAr else:DATA,r GroupName = "Default" DATA8Ds #print "Group name is %s" % GroupName(DATAs DATA s if mtlflag == 0:DATAL 0: DATA$u baseindex = vcountDATA(v basevncount = vncount DATA(\v basevtcount = vtcountADATAvDATA0v elif words and words[0] == "mtllib":DATA(Tw # try to export materialsDATA8w directory, dummy = os.path.split(filename)DATA<x filename = os.path.join(directory, words[1])DATAx try:DATA,x file = open(filename, "r")DATA 0:DATA8 material = matlist[matindex]dDATA,l material.R = Kd[0]DATA,ԇ material.G = Kd[1]DATA,< material.B = Kd[2]DATA0 material.SpecR = Ks[0]DATA0  material.SpecG = Ks[1]DATA0t material.SpecB = Ks[2]DATA@܉ alpha = 1 - ((Ka[0]+Ka[1]+Ka[2])/3)DATA0T material.Alpha = alphaDATA else:DATA( mtlflag = 0DATAlDATA, line = file.readline()EDATA  file.close()DATAdQDATA0 elif words and words[0] == "usemtl":?DATA  #if mtlflag == 1:DATA \ name = words[1]DATAL matindex = AddMeshMaterial(name, materialList, matindex) DATA< # elif words: DATA4 # print "%s: %s" % (linenumber, words)DATA$ linenumber = linenumber + 1DATAD file.close()DATADATAď # import in BlenderDATA  DATA(D print "import into Blender ..." DATA  mesh = NMesh.GetRaw ()oDATADATA , i = 0DATAt while i < vcount: DATA  x, y, z = pointList[i] DATA  vert=NMesh.Vert(x, y, z)DATA l mesh.verts.append(vert)?DATA Ē i=i+1DATA DATAD if vtcount > 0:DATA mesh.has_uvco = 1DATA, print ("Object has uv coordinates")DATAL NDATA  if len(materialList) > 0:DATA$ܔ mesh.mats = materialList DATA4DATAl total = len(faceList)CDATA ĕ i = 0DATA DATAD for f in faceList:DATA if i%1000 == 0:DATA8Ԗ print ("Progress = "+ str(i)+"/"+ str(total))DATA<DATAt i = i + 1DATA$ vi, ti, ni, matindex = fDATA face=NMesh.Face()DATA$l if len(materialList) > 0:DATA Ę face.mat = matindexDATADATAT limit = len(vi)DATA( setcount = setcount + len(vi)DATA c = 0 DATA< DATA,t while c < limit: DATAܚ m = vi[c]-1DATA,$ if vtcount > 0 and len(ti) > c:DATA n = ti[c]-1DATA, if vncount > 0 and len(ni) > c:DATAL p = ni[c]-1DATADATAܜ if vtcount > 0:DATA 4 u, v = uvList[n] DATAp # multiply uv coordinates by 2 and add 1. Apparently blender uses uv range of 1 to 3 (not 0 to 1). DATA04 mesh.verts[m].uvco[0] = (u*2)+1DATA0 mesh.verts[m].uvco[1] = (v*2)+1DATADATA< if vncount > 0:DATA( if p > len(normalList):DATAd print("normal len = " +str(len(normalList))+ " vector len = " +str(len(pointList)))DATA( print("p = " +str(p))hBDATA(ܠ x, y, z = normalList[p] DATA(4 mesh.verts[m].no[0] = xDATA( mesh.verts[m].no[1] = yDATA( mesh.verts[m].no[2] = zutoDATA< c = c+1 DATA DATA if len(vi) < 5:DATA, for index in vi: DATA0l face.v.append (mesh.verts[index-1])DATAԣ DATA  if vtcount > 0: DATA d for index in ti:DATA( u, v = uvList[index-1]DATA( face.uv.append((u,v))DATAl DATA$ mesh.faces.append(face) DATACDATA04 print "all other (general) polygons ..."DATA for f in faceList:DATA$ vi, ti, ni, matindex = f DATA< if len(vi) > 4:DATA, # export the polygon as edgesDATA< print ("Odd face, vertices = "+ str(len(vi)))DATA(d for i in range(len(vi)-2):DATA$ face = NMesh.Face()DATA, if len(materialList) > 0:d DATA(| face.mat = matindexDATA4ԩ face.v.append(mesh.verts[vi[0]-1])DATA4< face.v.append(mesh.verts[vi[i+1]-1])DATA4 face.v.append(mesh.verts[vi[i+2]-1])DATA DATA D if vtcount > 0: DATA$ if len(ti) > i+2:DATA, u, v = uvList[ti[0]-1]DATA,\ face.uv.append((u,v))DATA0Ĭ u, v = uvList[ti[i+1]-1]DATA,, face.uv.append((u,v))DATA0 u, v = uvList[ti[i+2]-1]DATA, face.uv.append((u,v))DATAdDATA( mesh.faces.append(face)DATA DATA , NMesh.PutRaw(mesh, Name,1)DATADATA8 print ("Total number of vertices is "+ str(vcount))DATA<$ print ("Total number of faces is "+ str(len(faceList)))DATA8 print ("Total number of sets is "+ str(setcount))DATADATA<DATA4t print("Finished importing " +str(Name)+ ".obj")DATAܱCDATA,#=========================================DATA4|def AddMeshMaterial(name, materialList, matindex):DATA,#=========================================DATAL DATA index = 0DATA̳ found = 0 DATA  limit = len(materialList)DATAlDATA while index < limit:DATA( if materialList[index] == name:DATAD matindex = index CDATA found = 1DATA index = limitDATA, index = index + 1DATAt DATA if found == 0: DATA  materialList.append(name)DATA(L matindex = len(materialList)-1 DATA  DATA return matindexDATA47DATA,l#=========================================DATA(Ըdef AddGlobalMaterial (name, matindex):DATA,,#=========================================DATA DATA̹ index = 0DATA found = 02DATA\ matindex = 0DATA MatList = Material.Get()DATA limit = len(MatList)DATAD1DATA| while index < limit:DATA(Ļ if MatList[index].name == name:DATA matindex = index DATAt found = 1DATA index = limitDATA index = index + 1tDATALDATA if found == 0:DATA,̽ material = Blender210.Material(name)DATA4 matindex = indexDATA| DATA return matindexDATADATA$4#================================DATA$def ObjExport(FILE, Name, type):DATA$#================================CDATA< global returncodeDATA global vertexcountDATA global uvcountDATA global TransformDATA\ global multiflagDATA global exporttypeDATADATA$ vertexcount = 0DATAl uvcount = 0DATA returncode = 0{DATA( print("Writing %s..." % Name) DATAXT FILE.write("# Wavefront OBJ (1.0) exported by lynx's OBJ import/export script\n\n")DATADATA$ Objects = Object.GetSelected()DATAl if Objects == []:DATA0 print("You have not selected an object!")DATA returncode = 4DATAd else:DATA for object in Objects:DATA MtlList = []DATA0< if len(Objects) > 1 or exporttype > 1:DATA8 Transform = CreateMatrix(object, Transform)DATA$  multiflag = 1 DATAd mesh = object.dataDATA ObjName = mesh.nameDATA$ has_uvco = mesh.has_uvcoDATAlDATA4 FILE.write("# Meshname:\t%s\n" % ObjName)DATA DATAD faces = mesh.facesBDATA  materials = mesh.matsDATA  Vertices = mesh.vertsDATA,L GlobalMaterials = Material.Get()u>DATADATAL if len(materials) > 1 and len(GlobalMaterials) > 0 and type < 4:DATA4t CreateMtlFile(Name, materials, MtlList)ADATA;DATA< # Total Vertices and faces; comment if not usefulDATAD FILE.write("# Total number of Faces:\t%s\n" % len(faces))DATAH FILE.write("# Total number of Vertices:\t%s\n" % len(Vertices))DATA|DATA FILE.write("\n") BDATA DATA4D # print first image map for uvcoords to useDATA@ # to be updated when we get access to other texturesDATAP$ if mesh.has_uvco: FILE.write("# UV Texture:\t%s\n\n" % mesh.has_uvco)DATA@DATAL if len(materials) > 1 and len(GlobalMaterials) > 0 and type < 3:DATAPl UseLayers(faces, Vertices, MtlList, has_uvco, FILE, ObjName, Name)DATAL elif len(materials) > 1 and len(GlobalMaterials) > 0 and type == 3:DATAL| UseMtl(faces, Vertices, MtlList, has_uvco, FILE, ObjName, Name)@DATA else: DATA@L Standard(faces, Vertices, has_uvco, FILE, ObjName)DATA DATA4#================================================DATA4ddef CreateMtlFile (name, MeshMaterials, MtlList):DATA4#================================================?DATA4 global gFilename DATA|DATA  # try to export materialsDATA8  directory, mtlname = os.path.split(gFilename.val)DATA t mtlname = name + ".mtl"=DATA4 filename = os.path.join(directory, mtlname)DATA$4 file = open(filename, "w")DATADATA< file.write("# Materials for %s.\n" % (name + ".obj"))DATA,< file.write("# Created by Blender.\n")DATAl file.write("# These files must be in the same directory for the materials to be read correctly.\n\n")DATALDATA  MatList = Material.Get()DATADATA counter = 1DATA\ found = 0 DATADATA( for material in MeshMaterials:DATA 4 for mtl in MtlList:e?DATA  if material == mtl:DATA found = 1DATA<DATA$t MtlList.append(material) DATA DATA if found == 0: DATA4l file.write("newmtl %s \n" % material)DATA index = 0DATA( while index < len(MatList):DATA4t if material == MatList[index].name:DATA( mtl = MatList[index]DATA(4 index = len(MatList)DATA found = 1DATA4 index = index + 1 DATALDATA if found == 1:DATA$ alpha = mtl.Alpha9DATAT4 file.write(" Ka %s %s %s \n" % (1-alpha, 1-alpha, 1-alpha))DATAL file.write(" Kd %s %s %s \n" % (mtl.R, mtl.G, mtl.B))DATAXD file.write(" Ks %s %s %s \n" % (mtl.SpecR, mtl.SpecG, mtl.SpecB))DATA0 file.write(" illum 1\n")DATA4 else:DATA@| file.write(" Ka %s %s %s \n" % (0, 0, 0))>DATA@ file.write(" Kd %s %s %s \n" % (1, 1, 1))?DATA@l file.write(" Ks %s %s %s \n" % (1, 1, 1))?DATA0 file.write(" illum 1\n")DATALNYDATA found = 0ADATADATA file.flush()DATAL file.close()DATA DATA@#===========================================================DATA<Ddef Standard(faces, Vertices, has_uvco, FILE, ObjName): ADATA@#=========================================================== DATA4 global vertexcount?DATA global uvcountDATA global multiflagDATADATAT uvPtrs = []DATA uvList = []DATADATA, FILE.write("o %s\n\n" % (ObjName)) @DATA, FILE.write("g %s\n\n" % (ObjName)) DATA DATA$ for v in Vertices: DATA| vert = v.co DATA  if multiflag == 1:DATA, vert = Alter(vert, Transform) DATA x, y, z = vert_ADATA DATA4$ FILE.write("v %s %s %s\n" % (x, y, z))DATADATA uv_flag = 0DATA  for face in faces:DATA(d for uv in face.uv: DATA found = 0DATA  index = len(uvList)DATA\ limit = 0DATA$ if len(uvList)-200 > 0:DATA( limit = len(uvList)-200BDATA0T while index > limit and found == 0:DATA, uv_value = uvList[index-1]DATAD$ if uv[0] == uv_value[0] and uv[1] == uv_value[1]:DATA0 uvPtrs.append(index+uvcount)DATA found = 1DATA$\ index = index - 1DATA if found == 0:DATA$  uvList.append(uv)އDATA$d index = len(uvList)DATA, uvPtrs.append(index+uvcount)DATA$ u, v = uvDATA4| FILE.write("vt %s %s\n" % (u, v))DATA  uv_flag = 1 DATA<DATA(t if has_uvco and uv_flag == 0:DATA  for v in Vertices: DATA $ u, v, z = v.uvco DATA| u = (u-1)/2DATA  v = (v-1)/2 DATA0 FILE.write("vt %s %s\n" % (u, v))DATADATA for v in Vertices: DATA$ x, y, z = v.no ADATA4l FILE.write("vn %s %s %s\n" % (x, y, z))DATA DATA  p = 0DATAT uvindex = 0DATA total = len(faces)DATADATA, for face in faces:DATA p = p+10DATA if (p%1000) == 0:DATAL$ print ("Progress = "+ str(p)+ " of "+ str(total) +" faces")BDATADATA FILE.write("f ")>DATA,< for index in range(len(face.v)):ADATA4 v = face.v[index].index + vertexcountDATA$  if len(face.uv) > 0:DATAHd FILE.write("%s/%s/%s " % (v+1, uvPtrs[uvindex], v+1))DATA$ uvindex = uvindex+1DATA4 elif has_uvco:DATA< FILE.write("%s/%s/%s " % (v+1, v+1, v+1))cDATA( else: DATA4\ FILE.write("%s//%s " % (v+1, v+1))ADATA FILE.write("\n")ADATADATA4T vertexcount = vertexcount + len(Vertices)DATA( uvcount = uvcount + len(uvList)DATADATA@L print("Export of " +str(ObjName)+ ".obj finished.\n")DATADATAH#=====================================================================DATALtdef UseLayers(faces, Vertices, MtlList, has_uvco, FILE, ObjName, Name): cDATAH#===================================================================== DATAt global vertexcountDATA global uvcountDATA global multiflagDATA\DATA uvPtrs = []DATA uvList = []@DATA$DATA8\ FILE.write("mtllib %s\n\n" % (Name + ".mtl"))DATA, FILE.write("g %s\n\n" % (ObjName)) BDATA, DATAd for v in Vertices: ADATA vert = v.co DATA  if multiflag == 1:DATA0\ vert = Alter(vert, Transform) DATA x, y, z = vertDATA4 FILE.write("v %s %s %s\n" % (x, y, z))DATADATA uv_flag = 0DATA0 for m in range(len(MtlList)): DATA l for face in faces:DATA  if face.mat == m:DATA$  for uv in face.uv:DATA t  found = 0DATA(  index = len(uvList)DATA $  limit = 0DATA,|  if len(uvList)-200 > 0:DATA0  limit = len(uvList)-200DATA8L  while index > limit and found == 0:DATA4  uv_value = uvList[index-1]DATAL  if uv[0] == uv_value[0] and uv[1] == uv_value[1]:cDATA8  uvPtrs.append(index+uvcount)DATA$  found = 1DATA,d  index = index - 1>DATA$  if found == 0:DATA,$ uvList.append(uv)BBDATA, index = len(uvList)DATA4 uvPtrs.append(index+uvcount)DATA$\ u, v = uvDATA< FILE.write("vt %s %s\n" % (u, v))DATA(, uv_flag = 1 DATADATA( if has_uvco and uv_flag == 0:DATA  for v in Vertices: DATA l u, v, z = v.uvco DATA u = (u-1)/2DATA(  v = (v-1)/2 DATA0d FILE.write("vt %s %s\n" % (u, v))DATAۄADATA for v in Vertices: DATA$\ x, y, z = v.no DATA4 FILE.write("vn %s %s %s\n" % (x, y, z))DATADATAT total = len(faces)DATA p = 0H=DATA uvindex = 0DATA0< for m in range(len(MtlList)): DATA4 FILE.write("usemtl %s\n" % (MtlList[m])) DATA  for face in faces:DATA d if face.mat == m:DATA p = p+1DATA$ if (p%1000) == 0:DATAP\ print ("Progress = "+ str(p)+ " of "+ str(total) +" faces")DATADATA$ FILE.write("f ")DATA4t for index in range(len(face.v)):DATA< v = face.v[index].index + vertexcount P>DATA(T if len(face.uv) > 0:DATAL FILE.write("%s/%s/%s " % (v+1, uvPtrs[uvindex], v+1))DATA,4 uvindex = uvindex+1>DATA$ elif has_uvco:DATA@ FILE.write("%s/%s/%s " % (v+1, v+1, v+1))DATA0l else: DATA< FILE.write("%s//%s " % (v+1, v+1))DATA$L FILE.write("\n")DATADATA4 vertexcount = vertexcount + len(Vertices) DATATD print("Export of " +str(ObjName)+ ".obj using material layers finished.\n") DATA DATAD#==================================================================DATAH|def UseMtl(faces, Vertices, MtlList, has_uvco, FILE, ObjName, Name): DATAD#==================================================================DATAl global vertexcount DATA global multiflagDATA DATA8D  FILE.write("mtllib %s\n\n" % (Name + ".mtl")) DATA,  FILE.write("o %s\n\n" % (ObjName))ADATA! DATAL! index = 0l@DATA! VertexList = []DATA ! for vertex in Vertices:DATA 4" VertexList.append(-1)DATA" index = index + 1DATA@" print("number of vertices is " +str(len(VertexList)))DATA\#DATA# Totalindex = 0DATA# ix = 0DATA$$ NewVertexList = []DATA|$ NewVertexCo = []DATA0$ for m in range(len(MtlList)): DATA4,% # Group name is the name of the mesh DATA$% if MtlList[m]: DATA<% FILE.write("g %s\n" % (MtlList[m]+str(m+1))) DATAd& else:ɈDATA8& FILE.write("g %s\n" % ("Null"+str(m+1)))DATA$' FILE.write("s off\n\n") DATA l' cDATA8' FILE.write("usemtl %s\n\n" % (MtlList[m])) DATA( DATA T( for face in faces:DATA ( if face.mat == m:DATA() for vertex in face.v:DATA(\) v = vertex.index DATA,) if VertexList[v] < 0:cDATA4* VertexList[v] = TotalindexpDATA0* NewVertexList.append(v)DATA4* Totalindex = Totalindex + 1DATAT+ DATA,+ for v_old in NewVertexList: ADATA,+ vert = Vertices[v_old].co DATA$\, if multiflag == 1:DATA0, vert = Alter(vert, Transform) DATA(- x, y, z = vert DATA8t- FILE.write("v %s %s %s\n" % (x, y, z))DATA,- NewVertexCo.append([x,y,z])DATAD.DATA|. if has_uvco:DATA,. for v_old in NewVertexList:cDATA4,/ u, v, z = Vertices[v_old].uvco @DATA / u = (u-1)/2DATA,/ v = (v-1)/2 ?DATA4T0 FILE.write("vt %s %s\n" % (u, v))DATA0DATA(0 for v_old in NewVertexList: DATA4L1 x, y, z = Vertices[v_old].no DATA81 FILE.write("vn %s %s %s\n" % (x, y, z))DATA2 DATA T2 for face in faces:DATA 2 if face.mat == m:DATA$3 FILE.write("f ")DATA4\3 for index in range(len(face.v)):DATA,3 v = face.v[index].indexDATA,,4 v_new = VertexList[v] @DATA84 if has_uvco: DATAL4 FILE.write("%s/%s/%s " % (v_new+1, v_new+1, v_new+1))DATA05 else: DATAD5 FILE.write("%s//%s " % (v_new+1, v_new+1))DATA$d6 FILE.write("\n")o@DATA6DATA6 FILE.write("\n")DATAL7DATA 7 NewVertexList = []DATAP7 print("Group " +str(m+1)+ " of " +str(len(MtlList))+ " finished.")DATAd8 DATAL8 print("Export of " +str(ObjName)+ ".obj using groups finished.\n")DATA$9DATA,\9#========================================BDATA(9def CreateMatrix(object, Transform):DATA,T#========================================DATA  Mx = []DATA  My = []>DATA L Mz = []DATA  T1 = []BDATA Transform = []DATA$DATA\ angle = object.RotXDATA Mx.append([1, 0, 0])DATA y = math.cos(angle)DATA4 z = -math.sin(angle)DATA| Mx.append([0, y, z])DATA y = math.sin(angle)DATA  z = math.cos(angle)DATAT Mx.append([0, y, z])DATA%ADATA angle = object.RotYDATA x = math.cos(angle)DATAd z = math.sin(angle)DATA My.append([x, 0, z])DATA My.append([0, 1, 0])DATA< x = -math.sin(angle)DATA z = math.cos(angle)DATA My.append([x, 0, z])DATADATAL angle = object.RotZDATA x = math.cos(angle)DATA y = -math.sin(angle)DATA$ Mz.append([x, y, 0])DATAl x = math.sin(angle)DATA y = math.cos(angle)DATA Mz.append([x, y, 0])DATAD Mz.append([0, 0, 1])DATADATA m0 = Mx[0]DATA  m1 = Mx[1]DATAT m2 = Mx[2]DATA for row in My:DATA x, y, z = rowDATA(, nx = x*m0[0] + y*m1[0] + z*m2[0]DATA( ny = x*m0[1] + y*m1[1] + z*m2[1]DATA( nz = x*m0[2] + y*m1[2] + z*m2[2]DATA 4 T1.append([nx, ny, nz])DATADATA m0 = T1[0]DATA  m1 = T1[1]DATAT m2 = T1[2]DATA for row in Mz:DATA x, y, z = rowEDATA(, nx = x*m0[0] + y*m1[0] + z*m2[0]DATA( ny = x*m0[1] + y*m1[1] + z*m2[1]DATA( nz = x*m0[2] + y*m1[2] + z*m2[2]6DATA$4  Transform.append([nx, ny, nz])DATA ?DATA@  Transform.append([object.SizeX, object.SizeY, object.SizeZ])DATA@<  Transform.append([object.LocX, object.LocY, object.LocZ])DATA  DATA  return Transform DATA4 DATA(l #======================================DATA def Alter(vect, Transform):DATA( #======================================DATA t  v2 = []DATA  nv = []DATA DATA<  x, y, z = vectDATA  sx, sy, sz = Transform[3]DATA  lx, ly, lz = Transform[4]DATA4DATAl v2.append(x*sx)DATA v2.append(y*sy)DATA v2.append(z*sz)DATADDATA$| for index in range(len(vect)):DATAt t = Transform[index]DATA8̩ nv.append(v2[0]*t[0] + v2[1]*t[1] +v2[2]*t[2])ADATA NDATA4 nv[0] = nv[0]+lxDATA| nv[1] = nv[1]+lyDATAĪ nv[2] = nv[2]+lzDATA DATAD return nvTXdįUtTXOBJIO_wings_fix.py\,İTdQDATA0\c:\blenderplugs\python\OBJIO\OBJIO_wings_fix.pyDATAİ JADATA Tİ$&DATAT |5DATATDATA,,СDATA,tJ@DATAt, E uDATAtIDATAL GDATAL(BDATAܳLDATAܳ$$DATA$lܳlHDATAl$I`DATAl|DATAD4DATADJDATAԵDGDATAԵLDATAdԵ@DATAdKDATAdKDATA<,WDATA<NDATA̷<<DATA̷tDATA\̷ODATA\DMDATA\HDATA4TIDATA4|WDATA|Ĺ4dJ'DATAĹ |DATA TĹDDATAT |IFREEDATATNDATA,PDATA,tODATAt,MDATAt$NDATALNDATAL4<CDATAܼLDATAܼ$FREEDATA$lܼ,WDATAl$UDATAl<TDATADWDATADLUDATAԾDX@DATAԾlXDATAdԾDATAdLnDATAdRDATA< WDATA<UDATA<NDATARDATA\,NBDATA\DATA\W DATA4tWDATA4|? DATA|4tDATA |DATA T vDATAT ,!,DATATL2 20DATA, m DATA,tlDATAt,\pDATAtDATAL<SDATAL#DATALDATA$T! uDATA$lADATAl$DATAl!LDATADtDATAD!DATAD$DATA\4DATAd0DATAd,)?DATAdDATA<DATA< DATA<\ DATA DATA\ DATA\4 ug-0DATA\| ToDATA4 DATA4| DATA|4T DATA | DATA T DATAT < !DATAT DATA, !DATA,t4 DATAt,l  DATAt  DATAL  DATALD FREEDATALFREEDATA$, DATA$lDATAl$t/DATAlDATAD$DATAD\!DATADDATA!0DATAdT)?DATAd)9:DATAdDATA<,DATA< DATA< @DATADATA\\DATA\DATA\DATA44ܺDATA4||CDATA|4 DATA | DATA TD!0ADATAT DATAT!DATA,<DATA,ttceneDATAt,!DATAtDATALL!DATALCDATALDATA$DDATA$lDATAl$DATAlDATADdDATADDATADDATA<,DATAdDATAd$DATAdTDATA<DATA<DATA<<DATA,DATA\CDATA\T#DATA\/FREEDATA4DATA4|\&DATA|4DATA |DATA TD DATAT "uCDATATexDATA,< FREEDATA,t %DATAt, DATAt4!%DATAL!DATAL!DATAL,"DATA$"DATA$l"8DATAl$#0DATAll#DATAD#0DATAD#!DATADD$DATA$!DATAd$DATAd,%DATAdt%DATA<%DATA<%"DATA<L&#DATA&DATA\&DATA\$'DATA\l'DATA4'DATA4| (DATA|4D(DATA |(0DATA T(DATAT L)0DATAT)DATA, */DATA,tt*DATAt,*vDATAtT+5DATAL+6DATAL$,DATAL|,'DATA$,fDATA$ll-JDATAl$-1DATAl\.DATAD.DATAD /QDATAD/JDATA$01DATAd0DATAd0DATAd 1DATA<d1?DATA<17DATA<D2<DATA2DATA\3DATA\L3DATA\3QDATA4,4<DATA4|4DATA|44DATA |45DATA T5VDATAT 6;DATAT6DATA,6DATA,t7DATAt,t7*DATAt7;DATALT8DATAL8 DATAL8DATA$<9EDATA$l95DATAl$: DATAld:!DATAD:DATAD;!DATAD\;!DATA;DATAd;!DATAdD< DATAd<!DATA<<!DATA<<=DATA<=!DATA= DATA\$>DATA\\>!DATA\>&DATA4 ?(DATA4|t?DATA|4?DATA |@DATA T<@ DATAT @#DATAT@7DATA,DA'DATA,tADATAt,A.DATAt\BDATALBDATALBDATAL4CDATA$|CDATA$lCDATAl$ DDATAlDD!DATADD&DATADD(DATAD\EDATAEDATAdEDATAd$F DATAdlF#DATA<FDATA< GDATA<TGDATAGDATA\G7DATA\LH%DATA\H.DATA4 IDATA4|TIDATA|4IDATA |IDATA T,JDATAT dJ!DATATJ(DATA,$K(DATA,tKDATAt,KDATAtLDATALdLDATALL DATALL4DATA$\M$DATA$lMDATAl$M!DATAlTNDATADNDATADN DATAD=|DATA4>|>=ԌDATA|>>4>,HDATA> ?|>DATA ?T?>1DATAT?? ?d#DATA??T?DATA?,@?DATA,@t@?<DATAt@@,@DATA@At@&DATAALA@DATALAAAlDATAAALA DATAA$BADATA$BlBA4DATAlBB$BDATABBlBDATABDCB< DATADCCBDATACCDCDATACDCDATADdDC\*DATAdDDDēDATADDdDDATADDATA|Ć4l>DATAĆ |>DATA TĆ\-DATAT DATATDATA,DDATA,t|DATAt,DATAt DATALD<DATAL8DATA܉L4=DATA܉$DATA$l܉DATAl$LDATAlDATADDATADDATAԋD\DATAԋ*DATAdԋ*DATAddDATAdDATA<DATA<<DATA̍<+DATA̍DATA\̍TDATA\0DATA\DATA4<DATA4|DATA|ď4'DATAď |4DATA Tď|DATAT DATAT#DATA,t&DATA,t/DATAt,4)DATAt@DATAL.DATAL|DATAܒL DATAܒ$,DATA$lܒ DATAl$"DATAl4+DATADDATAD0DATAԔD\DATAԔDATAdԔ$DATAdDDATAdDATA<DATA<<DATA̖<-DATA̖DATA\̖4DATA\!DATA\1DATA4LDATA4| DATA|Ę4DATAĘ |DATA TĘlDATAT DATATDATA,DDATA,tIDATAt,$DATAt\DATAL*DATAL2DATAܛL!DATAܛ$EDATA$lܛT#DATAl$DATAl9DATAD|'DATAD2DATAԝD<DATAԝDATAdԝ0DATAd4&DATAdDATA<<DATA<<DATA̟<tFDATA̟HDATA\̟tGDATA\DATA\DDATA4DATA4|DATA|ġ4 DATAġ |TDATA TġDATAT 4DATAT<*DATA,DATA,tDATAt,4DATAt|DATAL-DATAL<DATAܤL0DATAܤ$DATA$lܤ4DATAl$|-DATAlDATAD<DATAD#DATAԦDDATAԦD 'DATAdԦ DATAd +DATAd\ .DATA< 7DATA<, 1DATĄ< HDATĄ 6DATA\̨ #DATA\ (DATA\D "DATA4 (DATA4|*DATA|Ī4l3DATAĪ | DATA TĪ,8DATAT $DATATDATA,4$DATA,tDATAt,DATAt<DATAL&DATAL-DATAܭLDDATAܭ$|DATA$lܭ!DATAl$,1DATAlDATADDATAD$ DATAԯDlDATAԯ$-DATA$lԯ3DATAl$DATAlDATAD4DATAD|!DATAԱDNDATAԱ\DATAdԱ DATAd0DATAdT9DATA<'DATA<$KDATA̳<)DATA̳!DATA\̳l?DATA\-DATA\L8DATA4 DATA4|DATA|ĵ4T1DATAĵ |SDATA TĵDDATAT |CDATATEDATA,lCDATA,tDATAt,<DATAtDATAL5DATAL$ )DATAܸL DATAܸ$ DATA$lܸ !DATAl$T!DATAl!DATAD"DATAD\"<DATAԺD"DATAԺ #DATAdԺT# DATAd#DATAd#DATA<<$/DATA<$0DATA̼< %#DATA̼d%;DATA\̼%DATA\$&6DATA\&#DATA4& DATA4|,'6DATA|ľ4'DATAľ |'DATA Tľ$(DATAT |(&DATAT(%DATA,,))DATA,t)1DATAt,).DATAtd*2DATAL*DATAL+*DATALl+(DATA$+!DATA$l,,.DATAl$,%DATAl,4DATADT-)DATAD-DATAD-DATA<.)DATAd.2DATAd /DATAdd/*DATA</2DATA<40DATA<l0'DATA03DATA\,15DATA\1DATA\1DATA4$2DATA4||2 DATA|420DATA |<3*DATA T3)DATAT  44DATATt4KDATA,4-DATA,td5@DATAt,5 DATAt46DATALl6DATAL6DATAL6DATA$T7MDATA$l7DATAl$8IDATAl8DATAD8)DATAD<9$DATAD9)DATA9 DATAdD: DATAd: DATAd: DATA<;DATA<d;DATA<;DATA;DATA\,<DATA\t<DATA\<DATA4=DATA4|L=DATA|4=DATA |=DATA T>DATAT \>DATAT>DATA,>DATA,t4?DATAt,|?DATAt?DATAL @DATALT@DATAL@DATA$@DATA$lADATAl$dADATAlADATADADATADDATA$\>#================================DATA(>def ImportFunction (importName, type):DATA, ?#================================ DATAt? global gFilename DATA? global gAlertDATA@DATA <@ try:DATA$@ FILE=open (importName,"r")DATA8@ directory, Name = os.path.split(gFilename.val)DATA(DA words = string.split(Name,".")DATAA Name = words[0]DATA0A ObjImport(FILE, Name, gFilename.val) DATA\B FILE.close()DATAB gAlert = 4DATAB Draw ()DATA4C except IOError:DATA|C gAlert=2DATAC Draw ()DATA DDATA$DD#================================DATA(Ddef ExportFunction (exportName, type):DATA,D#================================ DATA\E global gFilename DATAE global gAlertDATAEDATA $F try:DATA$lF FILE=open (exportName,"r")DATAF FILE.close()DATA G gAlert = 1DATATG Draw ()DATAG except IOError:DATA8G directory, Name = os.path.split(gFilename.val)DATA(LH if os.path.isdir(directory):DATA0H ExportFunctionOK(exportName, type)DATA I Draw ()DATATI else:DATAI gAlert = 5DATAI Draw ()DATA,J DATA$dJ#================================DATA,Jdef ExportFunctionOK (exportName, type):DATA,$K#================================ DATAK global gFilename DATAK global gAlertDATAL global returncodeDATAdLDATA$L FILE=open (exportName,"w")DATA8L directory, Name = os.path.split(gFilename.val)DATA(\M words = string.split(Name,".")DATAM Name = words[0]DATA$M ObjExport(FILE, Name, type)DATATN if returncode > 0:DATAN gAlert = 3DATA N else:DATA 1 and vtn[1]:DATA,f tindex = int(vtn[1])DATAH,g if tindex < 0: tindex = basevtcount +tindex + 1DATA(g ti.append(tindex)DATAgDATA04h if len(vtn) > 2 and vtn[2]:DATA,h nindex = int(vtn[2])DATAHi if nindex < 0: nindex = basevncount +nindex + 1DATA8|i ni.append(nindex) DATA4i faceList.append([vi, ti, ni, matindex])DATALjDATA(j elif words and words[0] == "o":DATA$j ObjectName = words[1]DATA4k objectflag = 1DATA0k #print "Name is %s" % ObjectNameDATAkDATA(,l elif words and words[0] == "g":DATAl groupflag = 1DATA l index = len(words)DATA 4m if objectflag == 0:DATA m objectflag = 1DATA m if index > 1:DATA< 1:DATA<q GroupName = string.join(words[1:],"_") DATA,r else:DATA,tr GroupName = "Default" DATA8r #print "Group name is %s" % GroupNameDATADs DATA |s if mtlflag == 0:DATALs matindex = AddMeshMaterial(GroupName,materialList, matindex)DATA$\t gcount = gcount + 1 DATAtDATAt if fcount > 0: DATA$Du baseindex = vcountDATA(u basevncount = vncountDATA(u basevtcount = vtcountDATALvDATA0v elif words and words[0] == "mtllib":DATA(v # try to export materialsDATA8Dw directory, dummy = os.path.split(filename)DATA<w filename = os.path.join(directory, words[1])DATA$x try:DATA,lx file = open(filename, "r")DATAx except:DATA8y print "no material file %s" % filenameDATAy else:DATAy mtlflag = 1DATA,$z file = open(filename, "r")DATA(z line = file.readline()DATAz while line:DATA0<{ words = string.split(line)DATA8{ if words and words[0] == "newmtl":DATA( | name = words[1]DATA8d| line = file.readline() # Ns ?DATA4| words = string.split(line)DATA\4} while (words[0] != "Ka" and words[0] != "Kd" and words[0] != "Ks"): DATA8} line = file.readline() # KaDATA84~ words = string.split(line)DATA,~ if words[0] == "Ka":DATA0 Ka = [float(words[1]),DATA0l float(words[2]),DATA0 float(words[3])]DATA8< line = file.readline() # KdDATA4 words = string.split(line)DATA,  if words[0] == "Kd":DATA0t Kd = [float(words[1]),DATA0܁ float(words[2]),DATA0D float(words[3])]DATA8 line = file.readline() # Ks DATA4 words = string.split(line)DATA,| if words[0] == "Ks":DATA0 Ks = [float(words[1]),DATA0L float(words[2]),DATA0 float(words[3])]DATADATADT matindex = AddGlobalMaterial(name, matindex) DATA0̅ matlist = Material.Get() DATA,4 if len(matlist) > 0:DATA8 material = matlist[matindex]DATA, material.R = Kd[0]DATA,l material.G = Kd[1]DATA,ԇ material.B = Kd[2]DATA,< material.SpecR = 0DATA, material.SpecG = 0DATA,  material.SpecB = 0DATA$t alpha = 1DATA0̉ material.Alpha = alphaDATA4 else:DATA( mtlflag = 0DATADATA, line = file.readline()DATA  file.close()DATA܋DATA0 elif words and words[0] == "usemtl":DATA | #if mtlflag == 1:DATA Ԍ name = words[1]DATAL, matindex = AddMeshMaterial(name, materialList, matindex) DATA # elif words: DATA4 # print "%s: %s" % (linenumber, words)DATA$d linenumber = linenumber + 1DATA file.close()DATADATA< # import in BlenderDATA DATA( print "import into Blender ..." DATA  mesh = NMesh.GetRaw ()DATAlDATA  i = 0DATA while i < vcount: DATA 4 x, y, z = pointList[i] DATA  vert=NMesh.Vert(x, y, z)DATA  mesh.verts.append(vert)DATA < i=i+1DATADATA if vtcount > 0:DATA mesh.has_uvco = 1DATA,\ print ("Object has uv coordinates")DATAē DATA  if len(materialList) > 0:DATA$T mesh.mats = materialList DATADATA total = len(faceList)DATA < i = 0DATADATA for f in faceList:DATA if i%1000 == 0:DATA8L print ("Progress = "+ str(i)+"/"+ str(total))DATADATA i = i + 1DATA$4 vi, ti, ni, matindex = fDATA face=NMesh.Face()DATA$ if len(materialList) > 0:DATA < face.mat = matindexDATADATA̘ limit = len(vi)DATA( setcount = setcount + len(vi)DATAl c = 0 DATA DATA, while c < limit: DATAT m = vi[c]-1DATA, if vtcount > 0 and len(ti) > c:DATA n = ti[c]-1DATA,\ if vncount > 0 and len(ni) > c:DATAě p = ni[c]-1DATADATAT if vtcount > 0:DATA  u, v = uvList[n] DATAp # multiply uv coordinates by 2 and add 1. Apparently blender uses uv range of 1 to 3 (not 0 to 1). DATA0 mesh.verts[m].uvco[0] = (u*2)+1DATA0 mesh.verts[m].uvco[1] = (v*2)+1DATA|DATA if vncount > 0:DATA(  if p > len(normalList):DATAdd print("normal len = " +str(len(normalList))+ " vector len = " +str(len(pointList)))DATA( print("p = " +str(p))DATA(T x, y, z = normalList[p] DATA( mesh.verts[m].no[0] = xDATA( mesh.verts[m].no[1] = yDATA(\ mesh.verts[m].no[2] = zDATA c = c+1 DATA DATA4 if len(vi) < 5:DATA,| for index in vi: DATA0 face.v.append (mesh.verts[index-1])DATAL DATA if vtcount > 0: DATA ܣ for index in ti:DATA(4 u, v = uvList[index-1]DATA( face.uv.append((u,v))DATA DATA$ mesh.faces.append(face) DATAtDATA0 print "all other (general) polygons ..."DATA for f in faceList:DATA$\ vi, ti, ni, matindex = f DATA if len(vi) > 4:DATA, # export the polygon as edgesDATA<d print ("Odd face, vertices = "+ str(len(vi)))DATA(ܧ for i in range(len(vi)-2):DATA$4 face = NMesh.Face()DATA, if len(materialList) > 0:DATA( face.mat = matindexDATA4L face.v.append(mesh.verts[vi[0]-1])DATA4 face.v.append(mesh.verts[vi[i+1]-1])DATA4 face.v.append(mesh.verts[vi[i+2]-1])DATADATA  if vtcount > 0: DATA$ if len(ti) > i+2:DATA,l u, v = uvList[ti[0]-1]DATA,ԫ face.uv.append((u,v))DATA0< u, v = uvList[ti[i+1]-1]DATA, face.uv.append((u,v))DATA0  u, v = uvList[ti[i+2]-1]DATA,t face.uv.append((u,v))DATAܭDATA( mesh.faces.append(face)DATAl DATA  NMesh.PutRaw(mesh, Name,1)DATADATA84 print ("Total number of vertices is "+ str(vcount))DATA< print ("Total number of faces is "+ str(len(faceList)))DATA8 print ("Total number of sets is "+ str(setcount))DATA|DATADATA4 print("Finished importing " +str(Name)+ ".obj")DATATDATA,#=========================================DATA4def AddMeshMaterial(name, materialList, matindex):DATA,\#=========================================DATAIJ DATA index = 0DATAD found = 0 DATA  limit = len(materialList)DATADATA while index < limit:DATA(d if materialList[index] == name:DATA matindex = index DATA found = 1DATA\ index = limitDATA index = index + 1DATA DATA$ if found == 0: DATA l materialList.append(name)DATA(Ķ matindex = len(materialList)-1 DATA  DATAd return matindexDATADATA,#=========================================DATA(Ldef AddGlobalMaterial (name, matindex):DATA,#=========================================DATA  DATAD index = 0DATA found = 0DATAԹ matindex = 0DATA MatList = Material.Get()DATAt limit = len(MatList)DATADATA while index < limit:DATA(< if MatList[index].name == name:DATA matindex = index DATA found = 1DATA4 index = limitDATA| index = index + 1DATAļDATA if found == 0:DATA,D material = Blender210.Material(name)DATA matindex = indexDATA DATA, return matindexDATAtDATA$#================================DATA$def ObjExport(FILE, Name, type):DATA$\#================================DATA global returncodeDATA global vertexcountDATAD global uvcountDATA global TransformDATA global multiflagDATA global exporttypeDATAdDATA vertexcount = 0DATA uvcount = 0DATA, returncode = 0DATA(t print("Writing %s..." % Name) DATAX FILE.write("# Wavefront OBJ (1.0) exported by lynx's OBJ import/export script\n\n")DATATDATA$ Objects = Object.GetSelected()DATA if Objects == []:DATA0, print("You have not selected an object!")DATA returncode = 4DATA else:DATA for object in Objects:DATAl MtlList = []DATA0 if len(Objects) > 1 or exporttype > 1:DATA8 Transform = CreateMatrix(object, Transform)DATA$ multiflag = 1 DATA mesh = object.dataDATA4 ObjName = mesh.nameDATA$ has_uvco = mesh.has_uvcoDATADATA4 FILE.write("# Meshname:\t%s\n" % ObjName)DATADATA faces = mesh.facesDATA  materials = mesh.matsDATA l Vertices = mesh.vertsDATA, GlobalMaterials = Material.Get()DATA,DATALd if len(materials) > 1 and len(GlobalMaterials) > 0 and type < 4:DATA4 CreateMtlFile(Name, materials, MtlList)DATATDATA< # Total Vertices and faces; comment if not usefulDATAD FILE.write("# Total number of Faces:\t%s\n" % len(faces))DATAH| FILE.write("# Total number of Vertices:\t%s\n" % len(Vertices))DATADATA, FILE.write("\n")DATADATA4 # print first image map for uvcoords to useDATA@$ # to be updated when we get access to other texturesDATAP if mesh.has_uvco: FILE.write("# UV Texture:\t%s\n\n" % mesh.has_uvco)DATA$DATAL\ if len(materials) > 1 and len(GlobalMaterials) > 0 and type < 3:DATAP UseLayers(faces, Vertices, MtlList, has_uvco, FILE, ObjName, Name)DATALl elif len(materials) > 1 and len(GlobalMaterials) > 0 and type == 3:DATAL UseMtl(faces, Vertices, MtlList, has_uvco, FILE, ObjName, Name)DATA| else: DATA@ Standard(faces, Vertices, has_uvco, FILE, ObjName)DATA< DATA4t#================================================DATA4def CreateMtlFile (name, MeshMaterials, MtlList):DATA4D#================================================DATA global gFilename DATADATA , # try to export materialsDATA8 directory, mtlname = os.path.split(gFilename.val)DATA  mtlname = name + ".mtl"DATA4D filename = os.path.join(directory, mtlname)DATA$ file = open(filename, "w")DATADATA<< file.write("# Materials for %s.\n" % (name + ".obj"))DATA, file.write("# Created by Blender.\n")DATAl file.write("# These files must be in the same directory for the materials to be read correctly.\n\n")DATADATA  MatList = Material.Get()DATATDATA counter = 1DATA found = 0 DATADATA(T for material in MeshMaterials:DATA  for mtl in MtlList:DATA  if material == mtl:DATA\ found = 1DATADATA$ MtlList.append(material) DATAD DATA if found == 0: DATA4 file.write("newmtl %s \n" % material)DATAL index = 0DATA( while index < len(MatList):DATA4 if material == MatList[index].name:DATA(T mtl = MatList[index]DATA( index = len(MatList)DATA found = 1DATA4\ index = index + 1 DATADATA if found == 1:DATA$T alpha = mtl.AlphaDATAT file.write(" Ka %s %s %s \n" % (1-alpha, 1-alpha, 1-alpha))DATAL4 file.write(" Kd %s %s %s \n" % (mtl.R, mtl.G, mtl.B))DATAX file.write(" Ks %s %s %s \n" % (mtl.SpecR, mtl.SpecG, mtl.SpecB))DATA0D file.write(" illum 1\n")DATA else:DATA@ file.write(" Ka %s %s %s \n" % (0, 0, 0))DATA@l file.write(" Kd %s %s %s \n" % (1, 1, 1))DATA@ file.write(" Ks %s %s %s \n" % (1, 1, 1))DATA0\ file.write(" illum 1\n")DATADATA found = 0DATADDATA| file.flush()DATA file.close()DATA  DATA@D#===========================================================DATA<def Standard(faces, Vertices, has_uvco, FILE, ObjName): DATA@4#=========================================================== DATA global vertexcountDATA global uvcountDATAL global multiflagDATADATA uvPtrs = []DATA uvList = []DATA\DATA, FILE.write("o %s\n\n" % (ObjName)) DATA, FILE.write("g %s\n\n" % (ObjName)) DATAd DATA for v in Vertices: DATA vert = v.co DATA < if multiflag == 1:DATA, vert = Alter(vert, Transform) DATA x, y, z = vertDATAT DATA4 FILE.write("v %s %s %s\n" % (x, y, z))DATADATA< uv_flag = 0DATA for face in faces:DATA( for uv in face.uv: DATA4 found = 0DATA | index = len(uvList)DATA limit = 0DATA$ if len(uvList)-200 > 0:DATA(t limit = len(uvList)-200DATA0 while index > limit and found == 0:DATA,4 uv_value = uvList[index-1]DATAD if uv[0] == uv_value[0] and uv[1] == uv_value[1]:DATA0 uvPtrs.append(index+uvcount)DATA| found = 1DATA$ index = index - 1DATA, if found == 0:DATA$ uvList.append(uv)DATA$ index = len(uvList)DATA,4 uvPtrs.append(index+uvcount)DATA u, v = uvDATA4 FILE.write("vt %s %s\n" % (u, v))DATA \ uv_flag = 1 DATADATA( if has_uvco and uv_flag == 0:DATA D for v in Vertices: DATA  u, v, z = v.uvco DATA u = (u-1)/2DATA < v = (v-1)/2 DATA0 FILE.write("vt %s %s\n" % (u, v))DATADATA4 for v in Vertices: DATA$ x, y, z = v.no DATA4 FILE.write("vn %s %s %s\n" % (x, y, z))DATAL DATA p = 0DATA uvindex = 0DATA total = len(faces)DATAlDATA for face in faces:DATA p = p+1DATAD if (p%1000) == 0:DATAL print ("Progress = "+ str(p)+ " of "+ str(total) +" faces")DATA$DATA\ FILE.write("f ")DATA, for index in range(len(face.v)):DATA4 v = face.v[index].index + vertexcountDATA$ if len(face.uv) > 0:DATAH FILE.write("%s/%s/%s " % (v+1, uvPtrs[uvindex], v+1))DATA$T uvindex = uvindex+1DATA elif has_uvco:DATA< FILE.write("%s/%s/%s " % (v+1, v+1, v+1))DATA(| else: DATA4 FILE.write("%s//%s " % (v+1, v+1))DATA< FILE.write("\n")DATADATA4 vertexcount = vertexcount + len(Vertices)DATA(4 uvcount = uvcount + len(uvList)DATADATA@ print("Export of " +str(ObjName)+ ".obj finished.\n")DATA<DATAHt#=====================================================================DATALdef UseLayers(faces, Vertices, MtlList, has_uvco, FILE, ObjName, Name): DATAHt#===================================================================== DATA global vertexcountDATAD global uvcountDATA global multiflagDATADATA  uvPtrs = []DATAT uvList = []DATADATA8 FILE.write("mtllib %s\n\n" % (Name + ".mtl"))DATA,< FILE.write("g %s\n\n" % (ObjName)) DATA DATA for v in Vertices: DATA4 vert = v.co DATA | if multiflag == 1:DATA0 vert = Alter(vert, Transform) DATA< x, y, z = vertDATA4 FILE.write("v %s %s %s\n" % (x, y, z))DATADATA4 uv_flag = 0DATA0| for m in range(len(MtlList)): DATA  for face in faces:DATA < if face.mat == m:DATA$ for uv in face.uv:DATA  found = 0DATA(D  index = len(uvList)DATA  limit = 0DATA,  if len(uvList)-200 > 0:DATA0\  limit = len(uvList)-200DATA8  while index > limit and found == 0:DATA4,  uv_value = uvList[index-1]DATAL  if uv[0] == uv_value[0] and uv[1] == uv_value[1]:DATA8  uvPtrs.append(index+uvcount)DATA$  found = 1DATA,  index = index - 1DATA$D  if found == 0:DATA,  uvList.append(uv)DATA, index = len(uvList)DATA4l uvPtrs.append(index+uvcount)DATA$ u, v = uvDATA<, FILE.write("vt %s %s\n" % (u, v))DATA( uv_flag = 1 DATADATA(4 if has_uvco and uv_flag == 0:DATA  for v in Vertices: DATA  u, v, z = v.uvco DATA< u = (u-1)/2DATA( v = (v-1)/2 DATA0 FILE.write("vt %s %s\n" % (u, v))DATADDATA| for v in Vertices: DATA$ x, y, z = v.no DATA4, FILE.write("vn %s %s %s\n" % (x, y, z))DATADATA total = len(faces)DATA$ p = 0DATAl uvindex = 0DATA0 for m in range(len(MtlList)): DATA4 FILE.write("usemtl %s\n" % (MtlList[m])) DATA  for face in faces:DATA  if face.mat == m:DATA4 p = p+1DATA$| if (p%1000) == 0:DATAP print ("Progress = "+ str(p)+ " of "+ str(total) +" faces")DATA\DATA$ FILE.write("f ")DATA4 for index in range(len(face.v)):DATA<T v = face.v[index].index + vertexcount DATA( if len(face.uv) > 0:DATAL$ FILE.write("%s/%s/%s " % (v+1, uvPtrs[uvindex], v+1))DATA, uvindex = uvindex+1DATA$ elif has_uvco:DATA@l FILE.write("%s/%s/%s " % (v+1, v+1, v+1))DATA0 else: DATA<L FILE.write("%s//%s " % (v+1, v+1))DATA$ FILE.write("\n")DATADATA4T vertexcount = vertexcount + len(Vertices) DATAT print("Export of " +str(ObjName)+ ".obj using material layers finished.\n") DATAD DATAD|#==================================================================DATAHdef UseMtl(faces, Vertices, MtlList, has_uvco, FILE, ObjName, Name): DATADl#==================================================================DATA global vertexcount DATA< global multiflagDATADATA8 FILE.write("mtllib %s\n\n" % (Name + ".mtl")) DATA,$  FILE.write("o %s\n\n" % (ObjName))DATA  DATA  index = 0DATA ! VertexList = []DATA T! for vertex in Vertices:DATA ! VertexList.append(-1)DATA" index = index + 1DATA@\" print("number of vertices is " +str(len(VertexList)))DATA"DATA # Totalindex = 0DATAT# ix = 0DATA# NewVertexList = []DATA# NewVertexCo = []DATA0<$ for m in range(len(MtlList)): DATA4$ # Group name is the name of the mesh DATA$ % if MtlList[m]: DATA<d% FILE.write("g %s\n" % (MtlList[m]+str(m+1))) DATA% else:DATA8$& FILE.write("g %s\n" % ("Null"+str(m+1)))DATA$& FILE.write("s off\n\n") DATA & DATA8,' FILE.write("usemtl %s\n\n" % (MtlList[m])) DATA' DATA ' for face in faces:DATA $( if face.mat == m:DATA(|( for vertex in face.v:DATA(( v = vertex.index DATA,,) if VertexList[v] < 0:DATA4) VertexList[v] = TotalindexDATA0) NewVertexList.append(v)DATA4d* Totalindex = Totalindex + 1DATA* DATA,+ for v_old in NewVertexList: DATA,l+ vert = Vertices[v_old].co DATA$+ if multiflag == 1:DATA0,, vert = Alter(vert, Transform) DATA(, x, y, z = vert DATA8, FILE.write("v %s %s %s\n" % (x, y, z))DATA,T- NewVertexCo.append([x,y,z])DATA-DATA- if has_uvco:DATA,<. for v_old in NewVertexList:DATA4. u, v, z = Vertices[v_old].uvco DATA / u = (u-1)/2DATA,d/ v = (v-1)/2 DATA4/ FILE.write("vt %s %s\n" % (u, v))DATA40DATA(l0 for v_old in NewVertexList: DATA40 x, y, z = Vertices[v_old].no DATA8,1 FILE.write("vn %s %s %s\n" % (x, y, z))DATA1 DATA 1 for face in faces:DATA $2 if face.mat == m:DATA$|2 FILE.write("f ")DATA42 for index in range(len(face.v)):DATA,<3 v = face.v[index].indexDATA,3 v_new = VertexList[v] DATA8 4 if has_uvco: DATALt4 FILE.write("%s/%s/%s " % (v_new+1, v_new+1, v_new+1))DATA04 else: DATADd5 FILE.write("%s//%s " % (v_new+1, v_new+1))DATA$5 FILE.write("\n")DATA46DATAl6 FILE.write("\n")DATA6DATA 6 NewVertexList = []DATAPT7 print("Group " +str(m+1)+ " of " +str(len(MtlList))+ " finished.")DATA7 DATAL8 print("Export of " +str(ObjName)+ ".obj using groups finished.\n")DATA8DATA,8#========================================DATA(<9def CreateMatrix(object, Transform):DATA,9#========================================DATA 9 Mx = []DATA D: My = []DATA : Mz = []DATA : T1 = []DATA; Transform = []DATAd;DATA; angle = object.RotXDATA; Mx.append([1, 0, 0])DATA,< y = math.cos(angle)DATAt< z = -math.sin(angle)DATA< Mx.append([0, y, z])DATA= y = math.sin(angle)DATAL= z = math.cos(angle)DATA= Mx.append([0, y, z])DATA=DATA> angle = object.RotYDATA\> x = math.cos(angle)DATA> z = math.sin(angle)DATA> My.append([x, 0, z])DATA4? My.append([0, 1, 0])DATA|? x = -math.sin(angle)DATA? z = math.cos(angle)DATA @ My.append([x, 0, z])DATAT@DATA@ angle = object.RotZDATA@ x = math.cos(angle)DATAA y = -math.sin(angle)DATAdA Mz.append([x, y, 0])DATAA x = math.sin(angle)DATAA y = math.cos(angle)DATA'DATATuu u(>DATAuuTu(DDATAu,vut)DDATA,vtvu)DDATAtvv,vd*4XDATAvwtv*EDATAwLwvD+ DATALwww+FDATAwwLw,DDATAw$xw|,EDATA$xlxw,HBDATAlxx$x|-#DATAxxlx-:DATAxDyxL.DATADyyx.%@DATAyyDy.FDATAyzyD/DATAzdzy/( DATAdzzz/CDATAzzdz\08DATAz<{z0CDATA<{{zL1DATA{{<{1GFREEDATA{|{ 2BDATA|\|{2C( DATA\|||2DDATA||\|t3DATA|4}|3"DATA4}|}|4EDATA|}}4}|4:DATA} ~|}4JnDATA ~T~}|5DDATAT~~ ~5DATA~~T~L6F( DATA~,~6ADATA,t~<76DATAt,7DATAt7DATAL$8DDATAL87DATA܀L9DATA܀$L9IBDATA$l܀95DATAl$<:DATAl:DATAD:lDATAD; %x1DATAԂD<;*DATAԂ;.DATAdԂ <ADATAd<DATAd<;DATA<T=6DATA<=?DATĀ<4>6( DATĀ>DATA\̄>DATA\ ?FREEDATA\D?DATA4|?DATA4|?FREEDATA|Ć4 @KDATAĆ |@Is |>DATA TĆA&DDATAT tADATATA@ DATA,AMDATA,tlBADATAt,BDATAt,C DATALtC?\DATALCDATA܉L$D:DATA܉$D5DATA$l܉EDATAl$LEDATAlEDATADEDATADE0DATAԋD\FDATAԋFDATAdԋF@DATAdGDATAdDATAd\hDATA<hDATA<h,DATĄ<TiDATĄiGDATA\̨$j/DATA\jDATA\j-DATA4,k"DATA4|kDATA|Ī4kDATAĪ |$l/DATA TĪlDATAT lDATATlDATA,DmDATA,t|mDATAt,m%DATAt n.DATALtn*DATALn:DATAܭLToDATAܭ$oDATA$lܭp=DATAl$|p=DATAlp>DATADlqXDATADrIDATAԯDrdDATAԯ$$s4DATA$lԯs4DATAl$s5DATAl\tWDATADt4DATADLu4DATAԱDu5DATAԱvDATAdԱtvSDATAdv3DATAddwQDATA<w;DATA<dx>DATA̳<xZDATA̳tyVDATA\̳yDATA\DzDATA\|z'DATA4zBDATA4|L{<DATA|ĵ4{DATAĵ |{:DATA Tĵt|ODATAT |DATATT}DATA,}DATA,t}DATAt,L~DATAt~DATAL~DATAL DATAܸLLDATAܸ$DATA$lܸ"DATAl$$DATAl\:DATADԀ`DATADl6DATAԺDԁ%DATAԺ,(DATAdԺDATAd:DATAdd>DATA<܃?DATA<T0DATA̼<,DATA̼$FDATA\̼DATA\+DATA\L>DATA4Ć>DATA4|<>DATA|ľ41DATAľ |DDATA Tľ&DATAT DATAT4+DATA,)DATA,t:DATAt,|%DATAtԊDATAL4DATAL$DATAL܋!DATA$4"DATA$lMDATAl$DATAllDATAD-DATAD DATADdDATADATAdIDATAdIDATAdIDATA<<DATA<DATA<\WDATA;DATA\\;DATA\Ԓ<DATA\LDATA4=DATA4| =DATA|4>DATA |DATA TD=DATAT =DATAT4>DATA,WDATA,t49DATAt,9DATAt$:DATAL%DATALFDATALlJDATA$'DATA$lL.DATAl$DATAl)DATADTUDATADܛ8DATADT9DATA̜1DATAd4DATAd'DATAdDATA<<1DATA<3DATA< 3DATAtDATA\̟(DATA\4,DATA\-DATA4DATA4|\DATA|4DATA |̡DATA T DATAT LDATATDATA,̢DATA,t$%DATAt,|(DATAtDATAL,DATALtDATAL7DATA$DATA$ll2DATAl$ԥ DATAl,DATADd5DATAD̦DATAD5DATAl#DATAdħLDATAdL5DATAd5DATA<$DATA<tDATA<DATADATA\\DATA\DATA\ DATA4TDATA4|$DATA|4DATA |<DATA TtDATAT ̬ DATAT-DATA,|DATA,t$DATAt, DATAtT`DATAL]DATALADATALDATA$46DATA$l9DATAl$DATAllDATADDATADDATADDDATADATAdDATAd$DATAdtDATA<7DATA<$7DATA<2DATADATA\LDATA\DATA\)DATA4T2DATA4| DATA|4DATA |< DATA TDATAT ܷ/DATATDDATA,CDATA,tCDATAt,DDATAt<DATAL|DATALĺBDATAL<BDATA$CDATA$l, DATAl$t8DATAl8DATADd9DATADܽDATAD4DATA|?DATAd@DATAdl0DATAdԿ#DATA<,DATA<DATA</DATA$"DATA\|CDATA\CDATA\lDDATA4<DATA4|\DATA|4BDATA |BDATA TCDATAT   DATATT8DATA,8DATA,tD9DATAt,DATAtDATAL\?DATAL@DATALLDATA$DATA$l DATAl$D)DATAl5DATAD?DATAD0DATAD DATA<DATAd/DATAd"DATAdT DATA<"DATA<CDATA<lCDATADDATA\\<DATA\DATA\BDATA4BDATA4| CDATA|4 DATA |8DATA TD8DATAT 9DATAT4DATA,DATA,t?DATAt,L@DATAt#DATAL)DATAL&DATAL2DATA$D<DATA$l*DATAl$$DATAl|+DATAD*DATADL>DATADDATADATAdT DATAdDATAdDATA<DATA<T DATA<DATADATA\LDATA\DATA\SDATA4D9DATA4|,DATA|4$4DATA |6DATA T6DATAT \6DATAT+DATA,,#DATA,t#DATAt,#DATAt4#DATAL#DATAL#DATAL<#DATA$#DATA$l#DATAl$D#DATAl#DATAD#DATADL#DATAD#DATA#DATAdT$DATAdDATAdDATA<LDATA<DATA<DATADATA\<DATA\tDATA\DATA47DATA4||DATA|41DATA |<DATA T9DATAT  (DATATtCDATA,LDATA,ttDATAt,+DATA t4)DATA L jDATAL   DjDATA  L yDATA $  DATA$ l  DATAl  $ 4DATA  l lDATA D  DATAD   DATA  D 4 DATA  DATA #20DATA<T # bruteforce (Tm) VirtauLight exporter for Blender v2.121-ODATA # version 1.2 4DATA$ # by jano lukac, jedovaty@yahoo.comDATAl DATA( # The latest version can be found here:DATA8 # http://www.drlukac.com/jano/fridge/vlightexport.pyDATAdDATAimport Blender210DATAimport os, re, sysDATA,from math import *DATAtfrom string import lowerDATADATADATA<#DATAt# Quick start:?DATA#DATA<# 1. Modify the two variables below: savePath and outFile.DATA@l# Please make sure savePath exists, and do not put extensionsDATA# to the outFileDATA<,# 2. Open this in Blender (if you haven't done so already)DATA0# 3. Press alt-p over this script in BlenderDATA8 # 4. Go to savePath dir and type vlight -a 8DATAHt# 5. While you wait, read through these comments and the VirtuaLightDATA# documentationDATA<4# 6. For the "GI" look, use a hemi-lamp with Y rotations:DATA# -90 <= rotY => 90DATA0# Read the Lights section below for more infoDATA\DATAsavePath = "c:/tmp/vlight/"DATAoutFile = "file"DATA4DATAl#DATA# Comments, Docs, NotesDATA#DATA@$# I highly recommend you edit the output .vib and .vs files.DATA4# See a little further down for help with lights.DATADATA@<# I expect you to read these comments.. if you don't, well, TS.DATADATA@# Running this script in blender will produce in your savePath:DATA d# 1. $outFile.vib # the sceneDATA # 2. $outFile.vs # materialsDATA<# 3. $filePath/Meshes/$mesh$appendor.vib # mesh structureDATADATA# Python notes:DATAD # If you use python > 2.0, change the "re" module to "pre" at allDATA,# occurances (i.e. search and replace).DATADATA($# Notes on supported Blender ObjectsDATA |# Camera:DATAL# If everything seems a bit skewed, change the FOV setting in this script.DATA L# Meshes:DATAH# All meshes export as TriangularPatches now, to maintain UV coords.DATAL # If you have stray vertices in a mesh (i.e. vertices but no face), youDATAD# will risk the chance of either having stray faces in the outputDATAD # VIB or an empty Solid[] structure. The empty Solid[] structDATAD# will also result with a "Parse Error". I currently have no wayDATA8# to fix this, so you will have to do it manually.DATAHd # If you get weird results, try to first "apply size/rot" to the mesh.DATAH # If you get a "parse error" in your .vib files, first check for anDATA@T!# empty Solid[] structure in the vib, then try renaming theDATAD!# mesh in Blender.. stuff like "Box", "Plane", and "Sphere" areDATA<D"# reserved in VirtuaLight, and will cause these errors.DATAD"# I made a basic attempt to fix this by prepending a "X" to everyDATAH4## name. It's ugly, but it works -- can be changed in the Optional1DATA## Mods sections below.0 1DATAL$# SetSmooth works on both triangles and qauds; however, to make it work,DATAH$# I had to manually convert quads to tris. If you don't trust this,NDATA4%# please convert your mesh to triangles first.DATALl%# If you have SetSmooth on quads, and have UV textures, then UV TexturesDATAH%# will be exported, but if you have problems, ctrl-t the mesh first.DATAl&# Materials:DATAH&# I default to PlainSurfaces, and just use basic settings, because,CONDATAD,'# although the settings are available in blender, I cannot get toDATA8'# them via python. You can manually transcribe them.DATA@ (# If you want to use textures, use FaceSelect mode in blenderDATA@(# to assign UV coordinates. Then read how to apply texturesDATAH(# in the VirtauLight sepcifications PDF included with said programDATAHt)# No access to blender's SpTr yet, so use alpha to determine Kt. ItypDATAH)# default to an Index of Refraction to 1.3333 (glass), and use theDATA8d*# material "Mir" RGB sliders to affect the colors.;DATAH*# You can change specularity type in the Optional mods section belowDATA D+# Lights:DATAH+# This is the fun one. VirtuaLight has SO MANY lights, it's not evenDATAH,# funny. I chose the corresponding lights based on functionality,DATAH|,# but *NOT* on name -- it's a bit confusing at fist, but you'll getdDATAL,# used to it. Here is how I translate between VirtuaLight and Blender:DATA$|-# AreaLight(bulb): Lamp + sphereDATA<-# AreaLight(plane): Lamp + square (not implemented yet)DATA L.# BlackHole: Lamp + negativeDATA.# DirectionalLight: SunDATA.# PointLight: LampDATA D/# SkyLight+Sunlight: HemiDATA/# SpotLight: SpotiFDATAD/# Note that "ClipEnd" will adjust VirtualLight's Falloff variableDATA<\0# (i.e. I couldn't find a suibtable value in blender)DATAD0# The QUAD button in lights (f2) will make certain lamps QuadraticDATAL1# instead of linear.eDATAH1# SunLight can be incredibly bright, consider commenting it out in theDATAD 2# scene vib file and using other lights instead. The Dist valueDATAD2# affects the SunLight shadow; energy affects SkyLight intensity.DATAH2# BlackHole element "Density" is set by lamp's Distance in blender.DATAt3#DATA$3# KnownBugs with output mechanism:DATAH4# The script itself should always work; however, the ouput may causedDATA<|4# parse errors with VirtuaLight (I handle most of them).DATAL4# Stray vertices will cause either a parse error (due to an empty Solid[]DDATAH|5# or extra faces in the output. Cannot be fixed without change inDATA5# Blender's python API.DATAHL6# I *think* VirtuaLight will work properly if Material and Mesh namesDATAD6# are identical. If you want to be on the safe side, make sureDATA8<7# all names in blender are unique before you export.DATA7#DATA7# Changes since 1.1:DATAH$8# - added initialization for abNormals variable, as it caused flukeDATA88# in some cases. Thanks to bladesman for finding it.DATA9# Changes since 1.0:DATALL9# - allow for unsmoothed quads and tris to retain UV coords by exportingDATA89# all mesh as TriangularPatches instead of Polygon.DATA<:# - divide by zero fixDATA:# - documentation fixDATA:#EEDATA;# Todo:DATA,<;# - Possible nurbs (blender api pending?)DATA0;# - Possible metaballs (blender api pending?)DATAD <# - Mini gui to modify stuff like lights, change mesh type, etc.EEDATA <# - Handle basic animationsDATA<<# - Someone with programming experience could convert someDATA8T=# blender procedural textures to VirtuaLight shadersBDATA@=# - Find work.. if anyone needs a Sysadmin or Network Admin inDATA84># the southern california area, please contact me ;]DATA>#DATA>DATA ?DATAD?#DATA|?# Optional ModificationsDATA?#DATAL @# I default rounding numbers to 4. If you want more precision, change thisDATAL@# But you NEED rounding, otherwise you might get numbers with "e" in themDATA(A# and VirtuaLight doesn't handle that.DATAtAr = 4rdDATAADATAPA# Change "specType" to tell what type of Specular Highlights you want defaultDATADlB# in your materials. I default to "Phong" because I like to say,DATAB# "BUI TUI PHONG!"DATA,CspecType = 0DATA@tCspecHighlight = ["Phong", "Blinn", "Cook", "Reitz", "Gaussian"]DATACDATA<$D# Change append symbol.. use only [a-z][A-Z][0-9] and/or _DATA8D# This symbol is appended to all meshes and materialsDATAEappendor = "X"DATALEDATAEDATAE#DATA4E# read further.. if you dare [maniacle laughter] DATA\F#DATAFDATAFREEDATAG#DATA(arealight+bulbDATA@܃ if lamp.mode[7] == "1": lampType = 0 # square->arealight+planeDATA4T if lamp.mode[5] == "1": lampType = 1 # negativeDATA0 # begin writing -- some will have to changeDATAH$ VIBFILE.write("// Lamp: %s\n" % name) # Thanks to JamesK for this oneDATA if lampType == 1:DATA, VIBFILE.write("%s (" % vlights[lampType])DATA@L VIBFILE.write("(%s,%s,%s), %s, " % (round(lampObj.loc[0],r),DATA@Ć round(lampObj.loc[1],r),DATA@< round(lampObj.loc[2],r),DATA4 lamp.Dist))DATAH VIBFILE.write("'%s,%s,%s'" % (1 - lamp.R, 1 - lamp.G, 1 - lamp.B))DATA( VIBFILE.write("*%s)\n" % lamp.Energ)DATA if lampType == 4:DATA,4 VIBFILE.write("%s (" % vlights[lampType])DATA, VIBFILE.write("%s, " % (lamp.Dist * 5))DATA< VIBFILE.write("'%s,%s,%s', " % (lamp.R, lamp.G, lamp.B))DATA(| VIBFILE.write("%s)\n" % lamp.Energ)DATAԊ # calculate sun lightDATA8 if lampObj.rot[1] <= 90 and lampObj.rot[1] >= -90:DATA( degrees = round(lampObj.rot[1],r)DATA$܋ hours = 12 - int(degrees / 15)DATA$4 minutes = 2 * int(degrees % 30)DATAP VIBFILE.write("SunLight(%02d:%02d, %s)\n\n" % (hours, minutes, lamp.Dist))DATA else: VIBFILE.write("\n")DATAl else:DATA0 VIBFILE.write("%s [\n" % vlights[lampType])DATA  # separate the differencesDATAd if lampType == 0:DATA if lamp.mode[7] == "0":DATAL VIBFILE.write("\tBulb ((%s,%s,%s), %s)\n" % (round(lampObj.loc[0],r),DATAL round(lampObj.loc[1],r),DATAL round(lampObj.loc[2],r),DATA@ lamp.Dist))DATA elif lampType == 2:DATAX\ lightFrom = parallelVector(lampObj.rot[0], lampObj.rot[1], lampObj.rot[2], (0,0,-1))DATA< VIBFILE.write("\t(%s,%s,%s)\n" % (round(lightFrom[0],r),DATA<\ round(lightFrom[1],r),DATA@Ԓ round(lightFrom[2],r)))DATAL elif lampType == 3:DATA@ VIBFILE.write("\t(%s,%s,%s)\n" % (round(lampObj.loc[0],r),DATA@  round(lampObj.loc[1],r),DATA@ round(lampObj.loc[2],r)))DATA elif lampType == 5:DATA@D VIBFILE.write("\t(%s,%s,%s), " % (round(lampObj.loc[0],r),DATA@ round(lampObj.loc[1],r),DATA@4 round(lampObj.loc[2],r)))DATAX lightFrom = parallelVector(lampObj.rot[0], lampObj.rot[1], lampObj.rot[2], (0,0,-1))DATA<4 VIBFILE.write("(%s,%s,%s), " % (round(lightFrom[0],r),DATA< round(lightFrom[1],r),DATA<$ round(lightFrom[2],r)))DATA( VIBFILE.write("%s, " % lamp.SpoSi)DATAH # NOTE: this value is supposed to be "Falloff," but I couldn't findDATALl # a suibtable replacement in blender for it -- so using clipEnd for nowDATA( VIBFILE.write("%s, " % lamp.ClipEnd)DATA0L VIBFILE.write("%s\n" % round(lamp.SpoBl,r))DATADATA, # put all similar attribs together hereDATAXT VIBFILE.write("\tIntensity '%s,%s,%s'*%s\n" % (lamp.R, lamp.G, lamp.B, lamp.Energ))DATA<ܛ # This one sets the quadratic thingy -- take a look atDATA<T # equation in blender for the quad1 and quad2 settings,DATA4̜ # maybe important to add as factor to INTENSITYDATA4 if lamp.mode[0] == "1":DATA( VIBFILE.write("\tDecay QUADRATIC\n")DATA if lamp.mode[6] == "1":DATA4< VIBFILE.write("\tLightingAttributes SHADOW\n")DATA4 elif lamp.mode[6] == "0" and lamp.mode[2] == "0":DATA4  VIBFILE.write("\tLightingAttributes SPECULAR\n")DATAt if lamp.mode[7] == "0":DATA,̟ VIBFILE.write("\tMediaInteraction\n")DATA04 if lampType != 5 and lamp.mode[3] == "1":DATA0 VIBFILE.write("\tGlow %s\n" % lamp.HaInt)DATA VIBFILE.write("]\n\n")DATA\DATADATA̡#DATA# mesh exportDATAL#DATAfor name in meshList:DATA̢ # Check for empty meshesDATA($ meshObj = Blender210.getObject(name)DATA,| mesh = Blender210.getMesh(meshObj.data)DATA faces = mesh.facesDATA, if not faces: continueDATAtDATA8 # Check for "." in name, then make sure name is uniqueDATA  fixedName = removeDot(name)DATA4l fixedName = prepareName(fixedName, fixedMeshList)DATA$ԥ fixedMeshList.append(fixedName)DATA,DATA8d print "Writing mesh %s as %s..." % (name, fixedName)DATA̦DATA8 meshFileName = ("%s/%s.vib" % (meshPath, fixedName))DATA$l MESHFILE = open(meshFileName, "w")DATAPħ MESHFILE.write("// Mesh Structure exported from Blender by bruteforce\n\n")DATA8L MESHFILE.write("Declare %s = Solid [\n" % fixedName)DATA8 VIBFILE.write("ReadArchive \"%s\"\n" % meshFileName)DATA( VIBFILE.write("%s [\n" % fixedName)DATAtDATA  materials = meshObj.materialsDATA vertices = mesh.verticesDATA\ vnormals = mesh.normalsDATA texcoords = mesh.texcoordsDATA  abNormals = 0DATATDATA( # get a list of materials for laterDATA for material in materials:DATA< try:DATA t materialList.index(material)DATA ̬ except:DATA0 if material: materialList.append(material)DATA|DATA( # You have to add textures yourselfDATA  if mesh.texture:DATAdT VSFILE.write("// Mesh %s has UV Coords applied to it. If you wish to add textures,\n" % name)DATA` VSFILE.write("// please read the VirtauLight docs for more info on adding UV Textures\n\n")DATAD print "Please read the VirtuaLight docs for adding UV Textures"DATADATA84 # the j is to keep track what iteration I'm on in theDATA< # "for face in faces" loop so I can make sure I'm on theDATA # right set of UV coordsDATAl j = 0DATA  totalFaces = len(faces) - 1DATA for face in faces:DATA D if face[3]: totalVerts = 4DATA else: totalVerts = 3DATADATA( # gets us a normalized face normalDATAt if not face[4]:DATA8 normals = calcNormal(face, vertices, totalVerts - 3)DATA8$ # if we have a divide by zero in normal calculation,DATA4 # then we absolutley have a stray vertex or twoDATA if normals == "stray":DATA L totalFaces = totalFaces - 1DATA abNormals = 1DATA, print "WARNING: stray vertices found"DATA4T print "WARNING: output may not be as expected"DATA continueDATADATA< # trianglesDATA if not (totalVerts - 3):DATA0ܷ MESHFILE.write("\tShape [TriangularPatch (")DATA D for i in range(totalVerts):DATAD MESHFILE.write("(%s,%s,%s), " % (round(vertices[face[i]][0],r),DATAD round(vertices[face[i]][1],r),DATAH round(vertices[face[i]][2],r)))DATA@ # use vertex normals if smoothed, else print face normalDATA| if face[4]:DATADĺ MESHFILE.write("(%s,%s,%s)" % (round(vnormals[face[i]][0],r),DATAD< round(vnormals[face[i]][1],r),DATAD round(vnormals[face[i]][2],r)))DATA , else:DATA<t MESHFILE.write("(%s,%s,%s)" % (round(normals[0],r),DATA< round(normals[1],r),DATA<d round(normals[2],r)))DATAܽ # add texcoords, if anyDATA4 if texcoords:DATA@| MESHFILE.write(" UV=%s,%s" % (round(texcoords[j][i][0],r),DATAD round(texcoords[j][i][1],r)))DATA4l if i != totalVerts - 1: MESHFILE.write(", ")DATA$Կ # create triangle if face is QUADDATA , # So who's your daddy now?DATA else:DATA0 MESHFILE.write("\tShape [TriangularPatch (")DATA$$ for i in range(totalVerts - 1):DATAD| MESHFILE.write("(%s,%s,%s), " % (round(vertices[face[i]][0],r),DATAD round(vertices[face[i]][1],r),DATAHl round(vertices[face[i]][2],r)))DATA@ # use vertex normals if smoothed, else print face normalDATA\ if face[4]:DATAD MESHFILE.write("(%s,%s,%s)" % (round(vnormals[face[i]][0],r),DATAD round(vnormals[face[i]][1],r),DATAD round(vnormals[face[i]][2],r)))DATA  else:DATA<T MESHFILE.write("(%s,%s,%s)" % (round(normals[0],r),DATA< round(normals[1],r),DATA<D round(normals[2],r)))DATA # add texcoords, if anyDATA if texcoords:DATA@\ MESHFILE.write(" UV=%s,%s" % (round(texcoords[j][i][0],r),DATAD round(texcoords[j][i][1],r)))DATAL if i != totalVerts - 2:DATA MESHFILE.write(", ")DATA  else:DATA,D if materials and materials[face[5]]:DATA8 fixedMatName = removeDot(materials[face[5]], 0)DATA@ fixedMatName = prepareName(fixedMatName, materialList, 0)DATA4 MESHFILE.write(") %s ]+\n" % fixedMatName)DATA  else:DATA < MESHFILE.write(") ]+\n")DATA0 MESHFILE.write("\tShape [TriangularPatch (")DATA$ for i in range(totalVerts - 1):DATAT I = i + 2DATA$ if I > (totalVerts - 1): I = 0DATAD MESHFILE.write("(%s,%s,%s), " % (round(vertices[face[I]][0],r),DATADl round(vertices[face[I]][1],r),DATAH round(vertices[face[I]][2],r)))DATA@\ # use vertex normals if smoothed, else print face normalDATA if face[4]:DATAD MESHFILE.write("(%s,%s,%s)" % (round(vnormals[face[I]][0],r),DATAD round(vnormals[face[I]][1],r),DATAD  round(vnormals[face[I]][2],r)))DATA  else:DATA< MESHFILE.write("(%s,%s,%s)" % (round(normals[0],r),DATA<D round(normals[1],r),DATA< round(normals[2],r)))DATA4 # add texcoords, if anyDATA if texcoords:DATA@ MESHFILE.write(" UV=%s,%s" % (round(texcoords[j][I][0],r),DATADL round(texcoords[j][I][1],r)))DATA$ if I != 0: MESHFILE.write(", ")DATA, # if the face has material, add it hereDATA( if materials and materials[face[5]]:DATA4 fixedMatName = removeDot(materials[face[5]], 0)DATA@D fixedMatName = prepareName(fixedMatName, materialList, 0)DATA, MESHFILE.write(") %s ]" % fixedMatName)DATA $ else: MESHFILE.write(") ]")DATA,| # if faces still exist, csg them with (+)DATA, if j == totalFaces: MESHFILE.write("\n")DATA@L elif j == totalFaces - 1 and abNormals: MESHFILE.write("\n")DATA  else: MESHFILE.write("+\n")DATADATA T j = j + 1DATADATA abNormals = 0DATADATA$T # Prints out the final materialDATA MESHFILE.write("]\n\n")DATA MESHFILE.close()DATALDATADATAT # I apply the transformations DIRECT, rather than using Blender's "loc, rot, size"DATA<D # because I was getting some weird ass results. *shrug*DATA0 #VIBFILE.write("\tTransformationStack [\n")DATA8$ VIBFILE.write("\tTransform (\n\t\t\t%s,%s,%s,%s," \DATA8 "\n\t\t\t%s,%s,%s,%s," \DATA8 "\n\t\t\t%s,%s,%s,%s," \DATA8\ "\n\t\t\t%s,%s,%s,%s" \DATA, "\n\t\t)" % (DATA$, round(meshObj.matrix[0][0],r),DATA$ round(meshObj.matrix[0][1],r),DATA$ round(meshObj.matrix[0][2],r),DATA$4 round(meshObj.matrix[0][3],r),DATA$ round(meshObj.matrix[1][0],r),DATA$ round(meshObj.matrix[1][1],r),DATA$< round(meshObj.matrix[1][2],r),DATA$ round(meshObj.matrix[1][3],r),DATA$ round(meshObj.matrix[2][0],r),DATA$D round(meshObj.matrix[2][1],r),DATA$ round(meshObj.matrix[2][2],r),DATA$ round(meshObj.matrix[2][3],r),DATA$L round(meshObj.matrix[3][0],r),DATA$ round(meshObj.matrix[3][1],r),DATA$ round(meshObj.matrix[3][2],r),DATA(T round(meshObj.matrix[3][3],r)))DATA #VIBFILE.write("\t]\n")DATA VIBFILE.write("]\n\n")DATALDATADATA#DATA# material exportDATA<#DATAtmaterialList.sort()DATAfor name in materialList:DATA8 # Check for "." in name, then make sure name is uniqueDATA | fixedName = removeDot(name)DATA4 fixedName = prepareName(fixedName, fixedMatList)DATA < fixedMatList.append(fixedName)DATA< print "Writing material %s as %s..." % (name, fixedName)DATA,  material = Blender210.getMaterial(name)DATADt VSFILE.write("Declare %s = Shader [ PlainSurface [\n" % fixedName)DATAP VSFILE.write("\tColor '%s,%s,%s'\n" % (material.R, material.G, material.B))DATAt if material.Emit >= 0.1:DATA, VSFILE.write("\tKa %s\n" % material.Emit)DATA,4 VSFILE.write("\tKd %s\n" % material.Ref)DATAl VSFILE.write("\tKs (%s, '%s,%s,%s')\n" % (material.Spec, material.SpecR, material.SpecG, material.SpecB))DATAlD VSFILE.write("\t%sSpecularBRDF %s\n" % (specHighlight[specType], (-45*material.Hard)/254 + (45*255)/254))DATA| VSFILE.write("\tKt (%s, %s, '%s,%s,%s')\n" % (1.0 - material.Alpha, 1.333, material.MirR, material.MirG, material.MirB))DATA VSFILE.write("\t]\n]\n\n")DATADATA4DATAlVIBFILE.close()DATAVSFILE.close()DATADATA$4print "GI Blender... complete\n"DATAsys.stdout.flush()TXd,%^TXwalkomatic0.49.7.pyxH-{DATA4xc:\Program\Python20\walkomatic\walkomatic0.49.7.pymDATA-|-4&FREEDATA|-4--<>FREEDATA4-\|-$YFREEDATA\4-=FREEDATA\HFREEDATALFREEDATAw7FREEDATA4 XFREEDATA4 \FREEDATA\<4 <FREEDATA<\Լ>FREEDATA<FREEDATA|PVFREEDATA#l]FREEDATA#l#$aFREEDATAl#$##UmFREEDATA$#"l#rFREEDATA""$#,TFREEDATA"T"dFREEDATAT42"DMFREEDATA421TMFREEDATA1|242WFREEDATA|221YFREEDATA2 3|2FREEDATA 3T32LDFREEDATAT3L" 3LYFREEDATAL",/T3XFREEDATA,/t/L"M13 0DATAt//,/03 0DATA/t/@26 0DATAԺ/$B23 0DATAԺA74 0DATAdԺK25 0DATAdd226 0DATAdDJ38 0DATA<D22 0DATA<lC65 0DATA̼< `05 0DATA̼ a89 0DATA\̼Dw503 0DATA\18 0DATA\<56 0DATA416 0DATA4|L78 0DATA|ľ4K96 0DATAľ |v(61 0DATA Tľ10 0DATAT Y99 0DATAԃT62 0DATAԃ17 0DATAdԃtv-44 0DATAdY02 0DATAd|)68 0DATA<60 0DATA<#69 0DATA̅<D14 0DATA̅ 14 0DATA\̅*58 0DATA\12 0DATA4\L99 0DATA4| v.13 0DATA| 4ć02 0DATA T|\23 0DATAT 45 0DATATD67 0DATAt, 00 0DATAt~29 0DATAtu*72 0DATAL24 tDATA (t;>27 tDATAt (57 tDATA t\$52 tDATA D!53 tDATAD  55 tDATA<Dd86 tDATA<C53 tDATA<m002 tDATA|05 tDATA|TDm+78 tDATAT|l+97 tDATAT79 tDATA4979 tDATAԑt@19 tDATAԑ}lJ01 tDATA}T[ԑ#82 tDATAT[Z}!77 tDATAZXT[l43 tDATAXDSZ18 tDATADStNXl014 tDATAtNLDS29 tDATALItNt26 tDATAIoLTe.36 tDATAolIn81 tDATAloC02 tDATAēl832 tDATAē,@71 tDATATyē KDATATy8ndeDATATlTybde fDATATl$d4 0 .DATA$nTld/29 0DATAnT$$58 0DATAT`n46 0DATA`,Td/22 0DATA,t`Lp54 0DATAtY,$'50 0DATAYht=83 0DATAhsY|'76 0DATAshDATAvs,2 21DATAv>2 21DATA>|Yv< 2 21DATA|Yԗ>02-DDATAԗV|Yc(01-DDATAVԗL02-DDATAV*75 0DATA4DATA4DATA\wIDATAS"DATAS<]!DATA<]S< uDATAL3<] uDATAL3t uDATAt|L3D93 tDATA|9t$DATA9B|%DATAB69DWDATA6$BtDATA$l6X64 0DATAl,$c44 0DATA,4-l-i29 0DATA4-L,[52 0DATAL4-|e38 0DATALLc,91 0DATAD605 0DATAD;L$82 0DATA;;D:DATA;L;sSDATAL M;<CDATA MpLb3DATApp MDqTDATAp\&p|b4DATA\&&p8DATA&.\&CDATA..&b391 tDATA.G.mT2 22DATAGLG.a4DATALGD G,<42 tDATAD  LGC87 0DATA <D Da337 0DATA< kTDATA\<`4DATA\WDATA\<?DATALt`.DATALF4CDATAFFL `/DATAFTxFfDATATxxFt?d65 tDATAx/Tx_2yDATA/0x875 tDATA0la/<_+2 21DATAlaa0963 tDATAa|Jla^,2 21DATA|JaJ 14 tDATAԗ|Jl^)57 tDATAԗ<^02 21DATA<ԗ]513 tDATAB< 2 21DATABBĺDATABpB4]702-DDATApqBL<` DATAqpDDATAsq@2 22DATAstD/n12 0DATAt|sC uDATA|ďtl21 0DATAďt,|\3 uDATAt,$ď, hDATA$,t,lDATA, b$t58 0DATA bTb,D11 0DATATb 1 b_pDATA 1T1TbG55 tDATAT1 1|DATA|T14`DATA|trč`DATAtrr|d\1DATAr,qtr[5`DATA,qtqr DATAtq4m,qq`DATA4m|mtqCDATA|m,/4m$=`DATA,//|mt/70 0DATA/<_,/>75 0DATA<__/mDATA_ć<__ DATAćT_ \DATAT$kćjDATA$klkTB60.tDATAlk$kqn(MaDATAlkdG26 0DATAd uDATAd8DATAdlDATA48DATA4,STjJDATA,StS4G11 tDATAtS,SDY.tgaDATAStSt<ame,DATASeT$DATAeeSDDATAeLF:DATA4 done=1DATAč DATA4d\ # Then we'll build the IPO for the left foot:EEDATA8[ sfootipo = makeIPO('lfoot', 'Linear', 'Constant')DATA$ cpf = currentProxyFrame = FF.tgDATAq ()DATAD # this one starts in hold-mode (waits for right foot to finish)DATA@$ sfootloc = getOffset(proxy, cpf, -1, HS/2, forwardOffset)DATAt/ sfootframe = cpf36.DATA@ sfootframe, sfootloc = hold(sfootipo, sfootloc, cpf, MT/2)"DATAm ()DATA_ done = 0010DATA  while not done:DATAj cpf += CTDATAD targetloc = getOffset(proxy, cpf, -1, HS/2, forwardOffset)EDATAt sfootframe, sfootloc = move(sfootipo, sfootloc, targetloc, sfootframe, MT,proxy, -1, HS/2, forwardOffset).tDATAHd sfootframe, sfootloc = hold(sfootipo, sfootloc, sfootframe, LT)DATA if cpf>LF:DATA done=1DATAl{DATA if addCenter:DATALTj # And to finish it off, let's put something in the middle of this:lDATAH # This will simply add a third target floating above the proxy.DATA\D # It will respect the specified lift axis, hence useful as parent for an armaturegaDATA@t ctargetipo = makeIPO('center', 'Linear', 'Constant')DATA(T for cframe in range(FF, LF):DATAH targetloc = getLiftAxisOffset(proxy, cframe, CTDLA, CTD)DATA<, writeCurvePoint(ctargetipo, cframe, targetloc),DATAs ()DATAPb # Finished. Add the empties and link them to their respective IPOblocks.+ "DATA,[ leftikt = Object.New('Empty','leftikt')DATA0,[ rightikt = Object.New('Empty','rightikt')DATA$ print 'Added',leftikt,rightiktgDATAO if addCenter:DATA< centertarget = Object.New('Empty', 'centertarget')DATA,Z print 'Centertarget',centertargetDATA$ centertarget.layer = layergDATA$\ scene.link(centertarget).tgDATA( centertarget.link(ctargetipo)DATA  leftikt.layer = layerneDATAd rightikt.layer = layereDATA\. scene.link(leftikt)DATA scene.link(rightikt)nneDATA leftikt.link(sfootipo)eDATAl rightikt.link(ffootipo)DATA,\Z print whatsUp,'IPO:s',sfootipo,ffootipoDATAH< print '---------------------------------------------------------'DATA sys.stdout.flush()DATA DATA,Y#########################################doDATA,O# if everything's OK, let's get to work #DATA,t D<?ae`=d3abe]M1c3PM?`L?@ѳ?Z~9O=Z~;۽ 9;?ŧ? X@' 2?DATA4lLllBone.0014lm?P"@}0?????????w?4Z<`.5Zm?ARs:56uPs?(>c&4??*[=[n0,[֡?֌> 9@;?\h?>[Ҽ{<?uЍ,Ѝ>uo2,+pò?\?OK?3?my f>,fly @;MԲ9@;?^i?v?L;?DATAl4lBone.002)$ [0?????????>;P6?|6=?Ѳ9a96=@;a?Xq4?p?r"3ww3h؄?64B1>?vl?r3iv0}3r30}?ټI4?g4&ؿ??O3DbeJ?{35˚>dr<?DATAlBone.0033b2"B>?20?????????0?c<;d=,? 2D}4?9qG4#*2??M<<1548?+04Q>?<?72<2&=2̲?u 3? z5??v%ȸkӳ?4NJM? r<?DATA jLl\l\Bone.004d麳ŧ? X@b"B? ? ??????????7=v73?~U9.W;?3̖Դ~??7=973?W;?`X? 9>ҼY]?ae`= 3abe2d3i??`L?@?? [~v1=Z~U`VX?ç? X@?DATAl\ j,,Bone.00534lm?P"@0?????????n?]<x]X?Fƺ’D}:?Ua3-;H3??eM[=T:P[A?v;>w>?7>>q?uЍ.&Ѝ>uN?3\3p?\?VK???myf>* : flyC>?Wi?v?r?DATA,l\TTBone.006ka$ eS0?????????:KI:;?T6=?ֽ6=ꨜ1hq-?l?R4w.wM#4g?-G4J1>[VNw~?vl?24iv/r3ѵ?ټ?? 4z??F:y)ܳ?p4F˚>?DATAT,Bone.007 3b2"B>`Y30?????????6?hd3ed=.?XmX4?|z,v4??sY\<<3ֳ?3J>q\V?<?Cs<2)=2+?u ??I3$??Sꗳaֳ?F$3M??GLOB pP\DNA1D$SDNANAME*next*prev*first*lastxyzwxminxmaxyminymax*newid*libname[24]usflagpadid*idblock*filedataname[160]totcurvecurblocktypeshowkeypostotelemtypert*data*refkeyelemstr[32]elemsizecurvalblock*ipo*fromtotkeyslurphactkey**scripts*flagactscripttotscript*linelenblen*nameflagsnlineslines*curl*sellcurcselc*undo_bufundo_posundo_len*compiledsizeseekdrawzoomholdclipstaclipendnetstanetendlensdrawsizehololenhololen1scriptlink*anim*ibuf*mipmap[10]oklastframelastqualitytpageflagtotbindxrepyreptwstatwendbindcode*repbind*packedfilelastupdateanimspeedreserved1texcomaptomaptonegblendtype*object*texprojxprojyprojzmappingofs[3]size[3]texflagcolormodelrgbkdef_varcolfacnorfacvarfac*handle*pname*stnamesstypesvars*varstr*result*cfradata[32](*doit)()(*callback)()versionaipotypedata[16]*ima*cube[6]imat[4][4]stypenotlaycuberesnoisesizeturbulbrightcontrastrfacgfacbfacfiltersizenoisedepthnoisetypeimaflagcropxmincropymincropxmaxcropymaxxrepeatyrepeatextendframesoffsetsfrafie_ima*nor*plugin*coba*envfradur[4][2]modetotexenergydistspotsizespotblendhaintatt1att2bufsizesampshadspotsizebiassofttexactshadhalostep*mtex[8]layspecrspecgspecbmirrmirgmirbambrambbambgambemitangspectraalpharefspeczoffsaddkfacharseed1seed2mode2flarecstarclinecringchasizeflaresizesubsizeflareboostrgbselpr_typeseptexpr_backpr_lamppad1*renfrictionfhreflectfhdistxyfrictdynamodename[256]scaleselcolexpxexpyexpzradrad2smaxrad2*mat*imat*bbelemsdisp**mattotcolloc[3]rot[3]wiresizerendersizethreshvec[3][3]alfas[3][2]h1h2f1f2f3hidevec[4]s[2]mat_nrpntsupntsvresoluresolvorderuordervflaguflagv*knotsu*knotsv*bp*beztnurb*bevobj*textoncurve*path*keybev*orcopathlenbevresolwidthext1ext2spacemodespacinglinedistshearfsizexofyof*strfamily[24]*vfontmaxrcttotrctadrcodevartypetotvertipoextrapbitmaskv1v2v3v4punoedcode*tpageuv[4][2]col[4]transptiledef_nrweight*dwtotweightco[3]no[3]co[2]effect*mface*dface*tface*mvert*dvert*mcol*msticky*texcomesh*oc*sumohandletotfacesmoothreshsubdivsubdivrreserved2reserved3cubemapsizertfpntswtypeutypevtypew*defname[32]partypepar1par2par3parsubstr[32]*pardata*parent*track*action*pose*activeconconstraintChannelsnetworkdefbasedloc[3]orig[3]dsize[3]drot[3]quat[4]dquat[4]obmat[4][4]parentinv[4][4]colbitstransflagipoflagtrackflagupflagipowinscaflagscavisflagboundtypedupondupoffdupstadupendsfctimemassdampinginertiaformfactordummy_1rdampingsizefacdtdtxactcolpropsensorscontrollersactuatorsbbsize[3]dfrasactdefgameflaggameflag2anisotropicFriction[3]constraintsnlastripsmistypehorrhorghorbhorkzenrzengzenbzenkambkfastcolexposuregravityactivityBoxRadiusskytypemisimiststamistdistmisthistarrstargstarbstarkstarsizestarmindiststardiststarcolnoisedofstadofenddofmindofmaxhemiresmaxiterdrawtypesubshootpsubshootenodelimmaxsublamppamapamielmaelmimaxnodeconvergenceradfacgammasxsy*lpFormat*lpParmscbFormatcbParmsfccTypefccHandlerdwKeyFrameEverydwQualitydwBytesPerSeconddwFlagsdwInterleaveEvery*avicodecdatacfraefraimagesframaptoframelenblurfacedgeRedgeGedgeBfullscreenxplayyplayfreqplaydepthattribrt1rt2stereomodepad[3]maximsizexschyschxaspyaspxpartsypartssafetyborderwinposplanesimtypebufflagqualityscemodealphamodedogammaosafrs_secedgeintsame_mat_reduxpad_3[3]postmulpostgammapostaddpostigammabackbuf[160]pic[160]ftype[160]col[3]pad2pad3*camera*world*setbase*basact*groupcursor[3]*fcam*ed*radioframingzoomblendximyim*rectspacetype*areaviewmat[4][4]viewinv[4][4]persmat[4][4]persinv[4][4]viewquat[4]perspview*bgpic*localvdlocalviewlayactscenelockaroundcamzoomgridnearfarmxmymxomyogridlinesviewbutverthormaskmin[2]max[2]minzoommaxzoomscrollkeeptotkeepaspectkeepzoomrowbutv2d*editipoipokeytotipopinbutofschannelmenunrlockcursenscuractmainbmainbo*lockpointexnrtexfromshowgrouprectxrectycurymodeltypescriptblockpad3[7]*anim_linked_sipo*filelisttotfiletitle[24]dir[160]file[80]ofssortmaxnamelencollums*libfiledataretvalmenuact(*returnfunc)()*menupoopsvisiflag*imageimanrcurtile*texttopviewlinesfont_idlheightleftpix_per_linetxtscrolltxtbar*py_draw*py_event*py_button*py_globaldicttitle[28]fasesubfasemouse_move_redrawimafasedirslidirsli_linesdirsli_sxdirsli_eydirsli_exdirsli_himaslifileselmenuitemimasli_sximasli_eyimasli_eximasli_hdssxdssydsexdseydesxdesydeexdeeyfssxfssyfsexfseydsdhfsdhfesxfesyfeexfeeyinfsxinfsyinfexinfeydnsxdnsydnwdnhfnsxfnsyfnwfnhfole[128]dor[128]file[128]dir[128]*firstdir*firstfiletopdirtotaldirshilitetopfiletotalfilesimage_sliderslider_heightslider_spacetopimatotalimacurimaxcurimay*first_sel_ima*hilite_imatotal_selectedima_redraw*cmap*arg1dupflagsavetimetempdir[64]fontdir[64]renderdir[64]textudir[64]plugtexdir[64]plugseqdir[64]pythondir[64]sounddir[64]versionsvrmlflaggameflagsvertbaseedgebaseareabase*scenestartxendxstartyendysizexsizeyscenenrscreennrfullmainwinwinakt*newvvec*v1*v2*v3*v4*fullwinmat[4][4]headrctwinrctheadwinwinheadertypebutspacetypewinxwinyhead_swaphead_equalwin_swapwin_equalheadbutlenheadbutofscursorspacedatauiblocks*curscreendisplaymodefileflagsname[40]*se1*se2*se3nrdone*stripdatadir[80]orxoryname[80]*newseqstartstartofsendofsstartstillendstillmachinestartdispenddispmulhandsize*strip*curelemfacf0facf1*seq1*seq2*seq3seqbase*seqbasepmetastackbuttypestaendlifetimetotpartseednormfacobfacrandfactexfacrandlifeforce[3]dampnablavectsizedefvec[3]mult[4]life[4]child[4]mat[4]texmapcurmultstaticstep*keysheightnarrowspeedminfactimeoffs*obpremat[4][4]postmat[4][4]vec[3]faclenoalphaoeff[2]iterlastfralimbbaseeff[3]effg[3]effn[3]memslowtotytotxxyconstrainttotdefdef_scrolllimb_scrolldxdy*idlinkotypedataold*poin*oldpoinresetdistlastval*makeyqualqual2targetName[32]toggleName[32]value[32]maxvalue[32]materialName[32]damptimeranglerangeaxisdelaypropname[32]matname[32]axisflag*fromObjectsubject[32]body[32]pulsefreqtotlinks**linksinvertfreq2str[128]*mynewinputstotslinks**slinksvalvalopad5time*actblendinprioritystridelengthstrideaxissndnr*soundmakecopycopymadepad[1]trackvolume*melinVelocity[3]localflagforceloc[3]forcerot[3]linearvelocity[3]angularvelocity[3]addedlinearvelocity[3]anotherpad[4]butstabutendminmaxvisifacminloc[3]maxloc[3]minrot[3]maxrot[3]distributionint_arg_1int_arg_2float_arg_1float_arg_2toPropName[32]*toObjectbodyTypefilename[64]loadaniname[64]goaccellerationmaxspeedmaxrotspeedmaxtiltspeedrotdamptiltdampspeeddamp*sample*newpackedfile*snd_soundpanningattenuationpitchmin_gainmax_gaindistanceloopstartloopendchannelshighpriopad[6]gaindopplerfactordopplervelocitynumsoundsblendernumsoundsgameengine*gkeypadfokeygobjectgkey*activechildbaserollhead[3]tail[3]parmat[4][4]defmat[4][4]irestmat[4][4]posemat[4][4]bonebasechainbaseres1res2res3chanbase*achan*pchanactnrname[30]enforceoffset[3]orient[3]roll[3]*tartoleranceiterationssubtarget[32]cacheeff[3]cachemat[4][4]zminzmaxactstartactendstridelenrepeatblendoutTYPEcharucharshortushortintlongulongfloatdoublevoidLinkListBasevec2svec2ivec2fvec2dvec3ivec3fvec3dvec4ivec4fvec4drctirctfIDLibraryFileDataIpoKeyBlockKeyScriptLinkTextLineTextPackedFileCameraImageanimImBufMTexObjectTexPluginTexCBDataColorBandEnvMapLampWaveMaterialVFontVFontDataMetaElemMetaBallBoundBoxBezTripleBPointNurbCurvePathIpoCurveMFaceMFaceIntTFaceMDeformWeightBoneMDeformVertMVertMColMStickyMeshOcInfoLatticebDeformGroupbActionbPosebConstraintChannelWorldRadioBaseAviCodecDataRenderDataGameFramingSceneGroupFreeCameraBGpicView3DSpaceLinkScrAreaView2DSpaceInfoSpaceIpoSpaceButsSpaceSeqSpaceFiledirentryBlendHandleSpaceOopsSpaceImageSpaceNlaSpaceTextSpaceImaSelImaDirOneSelectableImaUserDefbScreenScrVertScrEdgeFileGlobalStripElemStripPluginSeqSequenceEditingEffectBuildEffPartEffParticleWaveEffDeformLimbIkaOopsbPropertybNearSensorbMouseSensorbTouchSensorbKeyboardSensorbPropertySensorbCollisionSensorbRadarSensorbRandomSensorbRaySensorbMessageSensorbSensorbControllerbExpressionContbPythonContbActuatorbAddObjectActuatorbActionActuatorbSoundActuatorbSoundbCDActuatorbEditObjectActuatorbSceneActuatorbPropertyActuatorbObjectActuatorbIpoActuatorbCameraActuatorbConstraintActuatorbGroupActuatorbRandomActuatorbMessageActuatorbGameActuatorbVisibilityActuatorbSamplebSoundListenerSpaceSoundGroupKeyObjectKeyGroupObjectbArmaturebPoseChannelbActionChannelSpaceActionbConstraintbKinematicConstraintbTrackToConstraintbRotateLikeConstraintbLocateLikeConstraintbActionConstraintbFollowPathConstraintbRotationConstraintbActionStripTLEN  0Ptdl(PPx4@H<0P <  L,@,(0D($pDhd @l8(,@0,HhH,(lDLP< <@Lx0848l@0pP<`|,,,88STRC                     !"# $%&'()*+,-./0 123 456789:; <!=>2 "?@ABCDEFGH%I#$J%K%LMNOPQRSTUVW!XYZ[&\]^_'`(abcdefghijklmnopq) rstuv wxyz{ |}*jkl~+*, '`##ABMN(#/p%#)+,-ijklmAB&%I.%/:ijkl\]&%/I01!X222/34 %/hg5 6777   6 5 8&4  ''%9/ gh/4 !"0#:::6 5 $%&'()*  +#;,-./01<,-./01= 23456>78?@>9:[A;<B~jklC=D"4 > %/ ? @ AAB@CBDCEDFEG H(IhgJKL[MNOPF QRST6U%GGGV 'OWXYZ[ \']'^%94H_I` Ja b > c d/efgghijklmnopqrstuvwxyz{|}~I     H4  K+i%&ILMMM'`N  O7N{=PQ'KQ# MRS L  HP OjIT #(a =  U&VVW'TU E!"#f$%&'()X *+,-./01234VVVWYVVWZVVW5X6 7 8%&9:;<=>[[VVW?@X6A=:B CDEFGHIJKsLZM\ VVWX6A ]VVW^NOPQRSTUV_WXYZ [\` VVWX6 ]:^ CaVVWX6#_ :`a >bVV>WX6cVVW bcd2=efghij k l m ndQVVWopqrs$%tuvwxyz{|}~eeff% [ gh   Qiiii jjjiiWWWiiiih%  k l%KlllMm mm/ln  rsv} wyz { |o ooo /ml%Q$Jnoo o  p   qqqrrr/sss' !"#$t%uuu&'()*v '+WXYZ,-./w ww/0/12xW34 56789:;<=%']XYZ>vU?@y yyABC Dz zzVEFG H I{VJK|}V/L~MNOPQVRSVTUVVWXVYVWZ[\']^_E`abV c'+def bghbEiV cjklmn'+ HoVpqrs[MN tuvwxtyz n'+D{V|}Q'VR'+ ~eh V'+&/X: VRZ'^_ gEV '+S |!X! %z2VVWX6ut >VWXYZ']'^%efgghijklnopqz{'+ R  ????] V8eggijk    gikV[I % bV[H  VVWX6H_:[>JJJ% %E[n'['[M'['['Ho'   [%HopENDB