开启左侧

给点播放声音的新思路

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

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

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

×
本帖最后由 Harlotte 于 2024-5-18 15:24 编辑
: E- y8 d; m; x( o
5 x: m, B- w( C# S7 i9 M. b4 ]- K; M2 O9 n+ x& i, z
最近在研究JS 做了一个简单的逻辑来播放声音
4 W) h5 s  U9 s5 x# H. p
  1. var pit = 1;//初始化音高(速度)
    % j: X) t3 i) J0 [8 r; q0 v1 V
  2. var wheelsounds = ["mtr:df5g_wheel1","mtr:df5g_wheel2","mtr:df5g_wheel3"]
    5 ~# {) c1 u# \& p+ }/ {' X; T
  3. function create(ctx, state, train) {
    5 t) a' W$ q  ~7 M" {
  4.     state.number = new Array();
    " {0 c" z; ?3 N! o
  5.     state.soundsspeed = 0;//初始化速度* n' R. C2 t3 O  p( S
  6.     state.speedsub = 0;
    5 D! R  n4 ?- `3 F6 K+ u2 Q: u
  7.     for(let i = 0; i < 100; i++){
    7 y2 x5 ?- O) k
  8.         state.number[i]=0;//初始化数组
    / u5 `! f4 R: i1 H; ^- x( W  X4 j: a; |
  9.     }
    # k% o* n/ d9 f- Q2 o" @& w
  10. }
    3 p) o" I7 k3 Q! [0 ?" `9 G
  11. $ z7 u. S, [- `" A8 W
  12. function render(ctx, state, train) {
    7 O  K8 q1 t, |# f  K
  13.     ctx.setDebugInfo("sounds=",1);//记录声音程序已启动
    + I/ G) q  q7 @6 k( b/ r
  14.     pit = 1 + train.speed() / 40;//更新音高(速度)
    8 J) C: n; |6 O. l" Q7 a, }+ f
  15.     let gmk = getCurrentTrackModelKey(ctx,state,train);//获取当前轨道的自定义轨道名称    2 W( Z' z' R5 Q: Y
  16.     state.speedsub = (train.speed() - state.soundsspeed) * Timing.delta() * 1000000;//计算速度差# j$ e& @0 N/ @# E% r
  17.     ctx.setDebugInfo("speedsub=",state.speedsub)
    7 C' R  Q1 d7 m0 w+ l
  18.     if(train.isOnRoute()&&gamerunning==1){//如果工作
    : u: \' `' M0 ?* D2 P* B( N, k
  19.         for (let i = 0; i < train.trainCars(); i++) {
    - |5 h5 M9 B4 p4 p9 L  ^
  20.             ctx.setDebugInfo("soundsrun",1);//记录声音开启1 ^) }% u! T$ Y- N
  21.             if(state.speedsub<-1){//如果车辆减速+ M2 t5 }* v% h7 e" Q
  22.                 ctx.setDebugInfo("shache",1);//记录刹车7 y: J2 e: Z+ C  b
  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$ h0 a. b4 |6 A
  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
    9 s/ r4 w  P6 v
  25.             }else if(state.speedsub>1){//如果车辆加速
    & K' G) W( j9 k
  26.                 ctx.setDebugInfo("addspeed",1);//记录加速
    5 r/ X( z9 S4 l0 p3 ~  f. u2 S
  27.                 state.number[2]=sound(ctx,"mtr:df5g_engine",i,soundspos.engine,pit,state.number[2],20,grnn(0.8,1));//播放加速声
    ! D) ?- t, t. t+ M+ v9 z$ c
  28.             }
    0 w3 p' W: Q/ ?1 B  G1 Z
  29.             state.number[1]=sound(ctx,"mtr:df5g_engine2",i,soundspos.engine,pit,state.number[1],16,1);//播放怠速声
    8 X2 y8 _6 e# d1 J" c- V
  30.             if(gmk.indexOf("horn")!=-1){//如果在轨道名称里找到了horn,则播放鸣笛声
    ; v7 I) ?* ^  o0 A! E2 [
  31.                 ctx.setDebugInfo("horn",1);//记录鸣笛声开启2 H9 f+ P( H' `5 l1 X
  32.                 state.number[3]=sound(ctx,"mtr:df5g_horn",i,soundspos.horn,1,state.number[3],32,5);//播放鸣笛声,单位是秒,推荐是5秒左右,可以根据需要调整 我这里是因为音频不合适循环播放,实际音频在1s左右
    ' x3 @# ?& I, s" O# E" w  ]( Q
  33.             }
    7 f9 H  s1 r  `, |+ r2 ?
  34.             if(train.speed()*20*3.6>5){
    1 K5 D6 [# C7 R
  35.                 state.number[4]=sound(ctx,"mtr:df5g_wheelrun",i,soundspos.braking2,pit,state.number[4],16,9);//播放普通轮轨声
    ; Y" U/ l1 Y  a1 v9 p3 w
  36.                 state.number[4]=sound(ctx,"mtr:df5g_wheelrun",i,soundspos.braking1,pit,state.number[4],16,9);//播放普通轮轨声* P( Y/ G: F( j7 W
  37.             }6 O1 Z7 H4 c$ @1 ?8 S7 V) ^) f
  38.             if(train.speed()>0&&grnn(0,20+train.speed()/30)>19){
    5 E% P; S" P. c: m
  39.                 state.number[5]=sound(ctx,wheelsounds[Math.floor(grnn(0,3))],i,soundspos.braking2,0.8,state.number[5],32,0.05);//播放撞轨声1 D) s5 C- R( }% D. U
  40.                 state.number[5]=sound(ctx,wheelsounds[Math.floor(grnn(0,3))],i,soundspos.braking1,0.8,state.number[5],32,0.05);//播放撞轨声
      w; J- W" p: p3 Y# f+ b9 ]
  41.             }
    " K- J6 a' N8 [  W
  42.         }
    0 |; R8 ?5 y2 H- V& b9 X$ M0 K4 A: [
  43.     }
    5 x- G5 C7 W9 [! ~/ Z; S  C
  44.     state.soundsspeed = train.speed();//更新速度4 d1 l+ j5 {5 z( n6 m% w( a
  45.     for(let i=0;i<4;i++){: n, X. G2 p, p
  46.         ctx.setDebugInfo(i+"=",state.number[i]);
    4 v- }# y( j2 P* y
  47.     }
    : A6 x& S: G8 I. p7 l; ?0 Z; X
  48. }# }) z0 T+ \' y+ g
  49. function sound(ctx,name2,i,vect,pit,nu,ll,long){//播放声音pit是音高(速度) nu是一个数组,用来记录播放时间,ll是音频响度,long是循环播放时间5 e9 O+ W# _- |  s# {& T
  50.     if(Timing.elapsed()>nu){//如果时间超过了播放时间! l6 i" a3 V, U+ J5 P* y: v
  51.         ctx.playCarSound(Resources.id(name2) , i , vect.x() , vect.y() , vect.z() , ll , pit);//播放
    % L% k. A  O  {$ N7 }1 g9 d
  52.         nu = Timing.elapsed()+long;   //更新播放时间: ?3 Y8 |5 C% w+ n* B
  53.     }" ?* Y- n6 O' H8 ~) h9 x9 U8 a2 _
  54.     return nu;//返回新的播放时间
    7 X5 {. k! N  x4 V/ d
  55. }
    4 u, S) _+ P9 G& f. g3 F
  56. function grnn(min, max) {//随机小数3 g( z$ F" P9 y- J$ Z
  57.     return  Math.random()*(max-min)+min;" Y( _- O5 O; ^: r! I) V6 X  e
  58. }  s: b  H" \" f8 r3 S7 A- O+ f9 f
  59. function getCurrentTrackModelKey(ctx, state, train) {//获取当前轨道的自定义轨道名称,让ai写的
    2 l. O% s& x  z* O; Z. O3 ^6 H
  60.     // 获取列车从车库开出的距离3 ~$ |( w3 |6 R/ D; Z  |
  61.     let railProgress = train.railProgress();
    3 D: e9 F# p! e# x9 \$ r
  62.     // 获取当前轨道的索引
    $ `& a+ E) v; ^- D
  63.     let currentRailIndex = train.getRailIndex(railProgress, true);2 l/ {* _( D7 G8 T9 S( N
  64.     // 检查当前轨道索引是否有效
    4 v* f& d* r/ e1 s
  65.     if (currentRailIndex >= 0 && currentRailIndex < train.path().size()) {( D4 O1 F% Y/ M# d- w2 U2 Q% H  H$ p
  66.         // 获取当前路径数据对象
    6 O* b0 Y8 H: F0 M& b0 I: Q/ m; ?6 \
  67.         let currentPathData = train.path().get(currentRailIndex);
    9 P8 h* ]% C0 u9 c! I) Y/ Q
  68.         // 获取当前轨道使用的自定义轨道名称
    - Z+ z8 r. L. t5 ]8 A: u
  69.         let trackModelKey = currentPathData.rail.getModelKey();
    * B8 r9 t' F3 N; T: E9 u4 a3 z
  70.         return trackModelKey;
    * K0 k7 P' l" `, {7 l
  71.     }
    : x* C! }! m- ^6 l5 N( ~8 |
  72.     return null; // 或者是一个默认值7 w' ?/ L8 |+ A- g+ X. B6 q1 B
  73. }
复制代码
相比bve 用这种方式可以搞更多的逻辑,随机叠加音频,实测效果非常不错( P! T# f2 d: j1 e) c6 V8 x
有事加我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
8 v, V+ ^8 N' e9 }( c; u7 Q8 {# sbve声音要方便一些吧,他有可视化可预览的编辑工具
, W6 T' l+ [; U$ x! x8 r# K
嘶 主要是这个把 我懒得学了
有事加我QQ: 3435494979
huliawsl 2024-5-17 21:12:04
本帖最后由 huliawsl 于 2024-5-17 22:09 编辑 * b7 q7 o1 p% o+ A4 ^$ I+ L3 T. r

% R( l3 F5 I# r6 c9 v# E相较于此,我还是认为bve格式会更简单
屑搞3d的 https://space.bilibili.com/403409690
mtrbbs的私信咱很少看 如果需要联系咱可以尝试其他途径
楼主 Harlotte 作者认证 2024-5-18 09:21:18
本帖最后由 Harlotte 于 2024-5-18 15:18 编辑
, u" o- q3 b6 ~5 c1 G8 Y! r
huliawsl 发表于 2024-5-17 21:120 y4 }& a/ \. v' a
相较于此,我还是认为bve格式会更简单

8 u, [) F+ y" U" D! g# Q🤔不过吧 这么做花样可以更多倒是
有事加我QQ: 3435494979
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

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