开启左侧

给点播放声音的新思路

[复制链接]
Harlotte 作者认证 2024-5-17 06:00:22

还没有账号?赶快去注册吧!

您需要 登录 才可以下载或查看,没有账号?立即注册

×
本帖最后由 Harlotte 于 2024-5-18 15:24 编辑 / T6 L( y: l# l# ^
+ [# `9 Q" `* s- O: |3 P3 q, ~
1 `0 U; p) u( l) |1 f+ W. Y
最近在研究JS 做了一个简单的逻辑来播放声音
: ]4 y! l5 c. v" o5 h5 D
  1. var pit = 1;//初始化音高(速度)0 M+ y2 `9 N: h3 v
  2. var wheelsounds = ["mtr:df5g_wheel1","mtr:df5g_wheel2","mtr:df5g_wheel3"]
    " m+ H1 e4 u1 `
  3. function create(ctx, state, train) {
    2 |: d6 e+ z8 V
  4.     state.number = new Array();, }. g+ S% x4 O* x6 p  M: V
  5.     state.soundsspeed = 0;//初始化速度
    9 M' E7 b4 j6 D$ ^8 R! F! C0 r0 t
  6.     state.speedsub = 0;1 J6 y! i$ m& z1 Q0 f2 g
  7.     for(let i = 0; i < 100; i++){
    ) _- C6 D$ ~; ?+ {
  8.         state.number[i]=0;//初始化数组
    " G. x( C( k3 i, N* q
  9.     }
    5 r& y+ {: w" ?! k+ X4 Z! `  x3 K
  10. }
    : ]+ R7 |5 c$ L. ^1 G
  11. ' s) m" ?$ w4 X
  12. function render(ctx, state, train) {
    6 b# A7 E9 Q7 d' i& @1 V$ ?) B
  13.     ctx.setDebugInfo("sounds=",1);//记录声音程序已启动
    7 Q; m7 c% @( {3 ~
  14.     pit = 1 + train.speed() / 40;//更新音高(速度)
    1 a2 E3 U! b. Z( O
  15.     let gmk = getCurrentTrackModelKey(ctx,state,train);//获取当前轨道的自定义轨道名称    9 z  R* \6 q: ?5 `
  16.     state.speedsub = (train.speed() - state.soundsspeed) * Timing.delta() * 1000000;//计算速度差1 S0 A1 @7 f: S3 a3 O* ]$ X- O
  17.     ctx.setDebugInfo("speedsub=",state.speedsub)
    ) ^% N& C' g- `  _3 A& k
  18.     if(train.isOnRoute()&&gamerunning==1){//如果工作
    ( w% s8 a2 U* [! c8 ^" G, K$ r
  19.         for (let i = 0; i < train.trainCars(); i++) {
    3 k6 e" E) K( x" f; z5 ~8 `: s
  20.             ctx.setDebugInfo("soundsrun",1);//记录声音开启. L4 w% Y+ N% O- a6 o' |
  21.             if(state.speedsub<-1){//如果车辆减速$ A, X$ ?. ]7 x) n. J6 m$ \
  22.                 ctx.setDebugInfo("shache",1);//记录刹车
    $ G4 A  ]; i. b7 Y7 C  l1 d+ r
  23.                 state.number[0]=sound(ctx,"mtr:df5g_shache",i,soundspos.braking1,pit,state.number[0],16,0.03+train.speed()*20*3.6/800);//更新返回时间 播放刹车声在转向架1
    * n, f8 b- m3 P3 _3 _9 h
  24.                 state.number[0]=sound(ctx,"mtr:df5g_shache",i,soundspos.braking2,pit,state.number[0],16,0.03+train.speed()*20*3.6/800);//更新返回时间 播放刹车声在转向架2
    3 H1 i/ Y7 n& t/ x8 W4 H
  25.             }else if(state.speedsub>1){//如果车辆加速3 |, X( o- h' t, s& Z. c
  26.                 ctx.setDebugInfo("addspeed",1);//记录加速
    - I* ~" l8 ^+ D
  27.                 state.number[2]=sound(ctx,"mtr:df5g_engine",i,soundspos.engine,pit,state.number[2],20,grnn(0.8,1));//播放加速声
    7 u/ o* M! z9 u: H) K
  28.             }
    & i1 Q  H3 R( l" X9 R
  29.             state.number[1]=sound(ctx,"mtr:df5g_engine2",i,soundspos.engine,pit,state.number[1],16,1);//播放怠速声
    ' Z3 i6 s  l. E1 S* n, ~
  30.             if(gmk.indexOf("horn")!=-1){//如果在轨道名称里找到了horn,则播放鸣笛声
    8 \9 P( G% I$ s$ ~
  31.                 ctx.setDebugInfo("horn",1);//记录鸣笛声开启
    ' P- `7 l; `  _+ B) l
  32.                 state.number[3]=sound(ctx,"mtr:df5g_horn",i,soundspos.horn,1,state.number[3],32,5);//播放鸣笛声,单位是秒,推荐是5秒左右,可以根据需要调整 我这里是因为音频不合适循环播放,实际音频在1s左右5 {  s# V5 g5 \) [# H1 t" P* V$ o
  33.             }1 K7 M3 H/ h+ P& w$ p2 A
  34.             if(train.speed()*20*3.6>5){
    9 C7 J$ Z1 C0 Z1 S% T  U
  35.                 state.number[4]=sound(ctx,"mtr:df5g_wheelrun",i,soundspos.braking2,pit,state.number[4],16,9);//播放普通轮轨声
    ! e: m% o* i5 B# a2 d% s
  36.                 state.number[4]=sound(ctx,"mtr:df5g_wheelrun",i,soundspos.braking1,pit,state.number[4],16,9);//播放普通轮轨声; Q& ?3 V6 g" y+ d9 m, `
  37.             }  w) T9 p' ~6 t# b  e# B$ C
  38.             if(train.speed()>0&&grnn(0,20+train.speed()/30)>19){) O" L1 w- X; q% J& L- j) E
  39.                 state.number[5]=sound(ctx,wheelsounds[Math.floor(grnn(0,3))],i,soundspos.braking2,0.8,state.number[5],32,0.05);//播放撞轨声
    " f3 V1 }& g# [2 j% ~
  40.                 state.number[5]=sound(ctx,wheelsounds[Math.floor(grnn(0,3))],i,soundspos.braking1,0.8,state.number[5],32,0.05);//播放撞轨声
    * t# g: u0 Z9 s/ U& q$ I+ a
  41.             }: q- R* P4 h* y6 P8 p$ ?
  42.         }
    % n7 ]# l  V$ Y- R  F
  43.     }
    & V% _* o" }! n& v# w5 J4 E
  44.     state.soundsspeed = train.speed();//更新速度
    9 R- e! r$ n) Q- G& o  j2 U
  45.     for(let i=0;i<4;i++){
    2 {* V# Y9 z1 N; ?
  46.         ctx.setDebugInfo(i+"=",state.number[i]);
    , V( u+ ]1 [/ t6 R* h3 s7 g' h. _5 N/ M7 C
  47.     }0 m' J$ }" l: T: V" C
  48. }
    " R- ^% k! Z% S0 b# a
  49. function sound(ctx,name2,i,vect,pit,nu,ll,long){//播放声音pit是音高(速度) nu是一个数组,用来记录播放时间,ll是音频响度,long是循环播放时间
    ! W9 o: b" h4 ?3 y) `" R; i, E: y- H
  50.     if(Timing.elapsed()>nu){//如果时间超过了播放时间2 y% E! v9 u9 E+ }! S, @# z
  51.         ctx.playCarSound(Resources.id(name2) , i , vect.x() , vect.y() , vect.z() , ll , pit);//播放
    ) d4 T( X1 _& i% P$ q7 M* l
  52.         nu = Timing.elapsed()+long;   //更新播放时间
    3 t9 ?/ o" c& r
  53.     }
    : x. g/ J# y. r+ {4 \4 U( N
  54.     return nu;//返回新的播放时间
    8 Y- u( R& h# b# E. k
  55. }
    ' N9 j% a  \; u9 N# K3 z
  56. function grnn(min, max) {//随机小数
    , S9 Y, G3 }' `, p1 z: J
  57.     return  Math.random()*(max-min)+min;
      U! ?# e( z/ V5 o8 \- p4 O6 t
  58. }6 _+ X: C( e  U- X
  59. function getCurrentTrackModelKey(ctx, state, train) {//获取当前轨道的自定义轨道名称,让ai写的
    ! x9 Z  {% ?4 d
  60.     // 获取列车从车库开出的距离
    * U. y! I% T$ U: N9 ]) M# l
  61.     let railProgress = train.railProgress();
    5 e7 W! W* J  K! |
  62.     // 获取当前轨道的索引/ w& v( [; b5 o/ t2 @6 J1 {" Y
  63.     let currentRailIndex = train.getRailIndex(railProgress, true);; H* [: |! X) ^. f- y1 k1 O# b
  64.     // 检查当前轨道索引是否有效' E5 `5 p1 a  O
  65.     if (currentRailIndex >= 0 && currentRailIndex < train.path().size()) {5 d/ L$ Y3 j1 N
  66.         // 获取当前路径数据对象
    8 R, o% ?5 X) U- P( ^6 c& E, x
  67.         let currentPathData = train.path().get(currentRailIndex);
    5 i% ?+ G" t/ V
  68.         // 获取当前轨道使用的自定义轨道名称
    9 F* N  z6 S$ z6 ^' ?8 G
  69.         let trackModelKey = currentPathData.rail.getModelKey();
    , K* U8 F' A; y# s
  70.         return trackModelKey;
    & K( g6 x9 _! x3 d* A. I: h" V
  71.     }! Q; T5 O- L) U2 E- c  C
  72.     return null; // 或者是一个默认值
    ! O# c: F! a8 x7 ?2 J
  73. }
复制代码
相比bve 用这种方式可以搞更多的逻辑,随机叠加音频,实测效果非常不错! ]4 ]' P% @$ f$ m5 ?" T
有事加我QQ: 3435494979
要什么名字 作者认证 2024-5-17 17:04:29
bve声音要方便一些吧,他有可视化可预览的编辑工具
LG STUDIO(原CLARSC)成员,制作MTR追加hmmsim/openbve列车及线路,如果有事请通过QQ联络
楼主 Harlotte 作者认证 2024-5-17 19:17:25
要什么名字 发表于 2024-5-17 17:04
- x7 ?4 [/ ~: h. n( S0 l2 fbve声音要方便一些吧,他有可视化可预览的编辑工具

9 {8 {/ |+ V2 V9 q嘶 主要是这个把 我懒得学了
有事加我QQ: 3435494979
huliawsl 2024-5-17 21:12:04
本帖最后由 huliawsl 于 2024-5-17 22:09 编辑   P& b; V9 `$ Y* @  f3 h
' u5 ?! w' l2 v' H
相较于此,我还是认为bve格式会更简单
屑搞3d的 https://space.bilibili.com/403409690
mtrbbs的私信咱很少看 如果需要联系咱可以尝试其他途径
楼主 Harlotte 作者认证 2024-5-18 09:21:18
本帖最后由 Harlotte 于 2024-5-18 15:18 编辑
- Y  S1 ^0 M5 B
huliawsl 发表于 2024-5-17 21:12
* h; W! x5 b+ g/ }5 c相较于此,我还是认为bve格式会更简单

- d. a# y3 D6 u0 K+ i🤔不过吧 这么做花样可以更多倒是
有事加我QQ: 3435494979
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

快速回复 返回顶部 返回列表