|
还没有账号?赶快去注册吧!
您需要 登录 才可以下载或查看,没有账号?立即注册
×
6 [8 o5 K( r5 W! Q3 s0 e0 S4 u; W' q# s5 l G5 C1 f. E. E& v
前情提要:此Mod 现名ANTE (Aphrodite's Nemo's Transit Expansion) 即由 我(Aphrodite) 进行后续更新的NTE 请勿与NTE混为一谈,切忌找zbx问关于ANTE的新特性。/ L) P! g' v3 N$ n, X
$ A D% U+ `6 j1 w* f' p. \! ~3 x ^6 B
这两天为装饰物件添加了对右击响应的支持。
# B, y8 ~" L& _3 y8 [, E* V" j, n
$ Z# S4 m F6 q8 ~6 a9 E同时我改良了DrawCall系列的继承关系,为自定义DrawCall内容提供了支持。
8 a* v. M: Y$ J! N h5 r' m ^* e! O
为了能不受限于在render函数中添加绘制调用,我为装饰物件和列车的上下文添加了drawCalls(Map<Object, DrawCall>),现在可以在任何时间任何线程添加、修改、删除绘制调用。9 `: U7 @: W7 ^! @3 T- [* B0 R8 ^6 e
5 x; @' k" F- O# c: o8 ]
下面是一段示例代码,实现了在右击装饰物件时(不是用刷子)时在玩家头部生成一个始终面向摄像机并向上匀速运动的面的效果。
! T5 W5 f4 l I3 P: y2 ]; }- importPackage(java.nio);3 I! c$ `% C1 U2 G8 B( V
- 9 p9 x" M' n1 N0 d
- let model = ModelManager.loadRawModel(Resources.manager(), Resources.idr("face.obj"), null);// 法线 -z. q; I) k1 f4 `, L' J
- model = ModelManager.uploadVertArrays(model);) Z2 m% x" { _
3 B2 P# E+ r& x# D5 V+ V6 r- function create(ctx, state, entity) {
( s5 O: {; J$ a$ K- e% j8 ^1 ^ b - state.num = 0;
: r1 f$ t' y1 i - }
) P$ F& O* R. Z ?# l6 p - $ M2 C! A8 Q6 N: D( w/ h
- function beClicked(ctx, state, entity, player) {// player: WapperedEntity 包装了 Entity(Player) 为js提供一些基本的方法和属性# t$ O1 ` O5 p& S% ^' k
- let p = player.getPosition();
; _' k2 T% V' u2 `( @. `( j% k - p.add(0, 1.5, 0);// 假定头在脚底往上1.5m
* c2 O S0 w( t' c - ctx.setDebugInfo("Clicked on ", "shift: " + player.isShiftKeyDown(), "look angle: " + player.getLookAngle(), "from: " + p,"time: " + Date.now(), p);
' a! B- i) G: c; K5 Y/ h1 v - let ti = Date.now();2 L' e3 W! E+ a- H' d% p# K$ d* p
- // DrawCall为一个接口 仅有一个commit方法
. D1 \2 W2 ^; g' m, k: j+ H - let call = new DrawCall({commit: (drawScheduler, basePose, worldPose, light) => {// 差不多是这样的 包含commit方法的对象 -> 转换为DrawCall对象" C6 v; ^7 J% P# M( k9 V
- try {
7 m8 d( a: n5 \% m% a r - let pose = worldPose.copy();5 e' Z' g3 S2 @* @) j3 a% \
- pose.translate(p);
- p& s) M& C/ t3 Z - pose.translate(0, (Date.now() - ti) / 1000 * 0.4, 0);
% T$ N# S& h4 t3 R; j2 r' z6 J" Y - 3 q0 P1 o; S% Q' I# ^: z
- let buf = FloatBuffer.allocate(16);4 o+ S; k' {4 V5 Z" G! z
- pose.store(buf);% C, B& [0 v9 ~" B
- 3 F- I6 l. r* I6 G0 [
- buf.put(0, 1);5 O3 P5 H; t& j* r. w
- buf.put(1, 0);
( W6 X* Q' K2 @2 i* S- K4 }. m6 t, U - buf.put(2, 0);
: U/ N% _+ s( L& }* h - buf.put(3, 0);
$ m7 `* }9 x5 R G; C& m
% p; B" i* n' Q- buf.put(4, 0);
& a% c8 o1 Y/ F" a - buf.put(5, 1);
. J: R7 i4 P7 Z; M* B0 s - buf.put(6, 0);; i: D$ e4 k/ a: e8 o8 A; @
- buf.put(7, 0);
e: {) _" q$ V3 C - " w9 q' z- @$ H. q" Z6 P
- buf.put(8, 0);- @) ^( O* `' L* s& F# _
- buf.put(9, 0);
! j6 c- I# o* \4 B8 ` - buf.put(10, 1);
9 J( ], g$ d }; [, b, l$ |" r - buf.put(11, 0);
3 o4 e- A5 R) o1 Q
6 }, E+ L/ y* x i- pose.load(buf);// 清空旋转信息 始终面向摄像机
2 Q9 B! b5 j1 t( g* y3 b" I9 ~8 D- N
s) t- N4 W3 m8 r; Z- drawScheduler.enqueue(model, pose, light);
5 i$ A' E. Z+ T$ c# W" V7 | - } catch (e) {
+ z1 h. I5 t" K% e) v - ctx.setDebugInfo("Error", e.toString());5 k: Q3 m2 N' Y# ^; W
- }( B3 S/ z% H l0 ?( Y4 p8 E
- }});1 Y; `! ^' i( E* a( ]0 Y
- ctx.drawCalls.put(state.num, call);
7 k4 D& ?" j- A - // 亦可以直接使用 ctx.drawCalls.put(state.num, (drawScheduler, basePose, worldPose, light) => {...}); _6 N8 r' h6 b' T& o' Z
- // 即 function -> lambda表达式(java) -> DrawCall对象/ J/ {: X; ^5 Z3 b) v+ @) l# E1 _
- state.num++;
2 E9 L" r# N& E7 {7 ~$ d - }
复制代码
$ U3 y% x7 N; H" I+ H) h5 A& z, |6 c ?
请注意 beClicked 只会在当前客户端执行一次 若需要多端同步请将数据保存在 entity.data 中(
& \/ I( A) X/ M
1 ?! C( l3 Q* I+ h |
|