sample.bmx 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161
  1. Strict
  2. Const SF_MONO8=1
  3. Const SF_MONO16LE=2
  4. Const SF_MONO16BE=3
  5. Const SF_STEREO8=4
  6. Const SF_STEREO16LE=5
  7. Const SF_STEREO16BE=6
  8. Const SF_STDFORMAT=SF_STEREO16BE
  9. Global BytesPerSample[]=[0,1,2,2,2,4,4]
  10. Global ChannelsPerSample[]=[0,1,1,1,2,2,2]
  11. Function CopySamples( in_buf:Byte Ptr,out_buf:Byte Ptr,format,count )
  12. MemCopy out_buf,in_buf,Size_T(count*BytesPerSample[format])
  13. End Function
  14. Function ConvertSamples( in_buf:Byte Ptr,in_format,out_buf:Byte Ptr,out_format,count )
  15. If in_format=out_format
  16. CopySamples in_buf,out_buf,out_format,count
  17. Else If in_format=SF_STDFORMAT
  18. ConvertSamplesFromStdFormat in_buf,out_buf,out_format,count
  19. Else If out_format=SF_STDFORMAT
  20. ConvertSamplesToStdFormat in_buf,out_buf,in_format,count
  21. Else
  22. Local tmp_buf:Byte[count*BytesPerSample[SF_STDFORMAT]]
  23. ConvertSamplesToStdFormat in_buf,tmp_buf,in_format,count
  24. ConvertSamplesFromStdFormat tmp_buf,out_buf,out_format,count
  25. EndIf
  26. End Function
  27. Function ConvertSamplesToStdFormat( in_buf:Byte Ptr,out_buf:Byte Ptr,format,count )
  28. If format=SF_STDFORMAT
  29. CopySamples in_buf,out_buf,format,count
  30. Return
  31. EndIf
  32. Local in:Byte Ptr=in_buf,out:Byte Ptr=out_buf
  33. Local out_end:Byte Ptr=out+count*BytesPerSample[SF_STDFORMAT]
  34. Select format
  35. Case SF_MONO8
  36. While out<>out_end
  37. Local t=in[0]*257-$8000
  38. out[0]=t Shr 8
  39. out[1]=t
  40. out[2]=t Shr 8
  41. out[3]=t
  42. in:+1;out:+4
  43. Wend
  44. Case SF_MONO16LE
  45. While out<>out_end
  46. Local t=in[1] Shl 8 | in[0]
  47. out[0]=in[1]
  48. out[1]=in[0]
  49. out[2]=in[1]
  50. out[3]=in[0]
  51. in:+2;out:+4
  52. Wend
  53. Case SF_MONO16BE
  54. While out<>out_end
  55. out[0]=in[0]
  56. out[1]=in[1]
  57. out[2]=in[0]
  58. out[3]=in[1]
  59. in:+2;out:+4
  60. Wend
  61. Case SF_STEREO8
  62. While out<>out_end
  63. Local x=in[0]*257-$8000
  64. Local y=in[1]*257-$8000
  65. out[0]=x Shr 8
  66. out[1]=x
  67. out[2]=y Shr 8
  68. out[3]=y
  69. in:+2;out:+4
  70. Wend
  71. Case SF_STEREO16LE
  72. While out<>out_end
  73. out[0]=in[1]
  74. out[1]=in[0]
  75. out[2]=in[3]
  76. out[3]=in[2]
  77. in:+4;out:+4
  78. Wend
  79. Default
  80. RuntimeError "Unimplemented sample format conversion"
  81. End Select
  82. End Function
  83. Function ConvertSamplesFromStdFormat( in_buf:Byte Ptr,out_buf:Byte Ptr,format,count )
  84. If format=SF_STDFORMAT
  85. CopySamples in_buf,out_buf,format,count
  86. Return
  87. EndIf
  88. Local out:Byte Ptr=out_buf,in:Byte Ptr=in_buf
  89. Local in_end:Byte Ptr=in+count*BytesPerSample[SF_STDFORMAT]
  90. Select format
  91. Case SF_MONO8
  92. While in<>in_end
  93. Local x=in[0] Shl 8 | in[1]
  94. Local y=in[2] Shl 8 | in[3]
  95. If x & $8000 x:|$ffff0000
  96. If y & $8000 y:|$ffff0000
  97. Local t=(x+y)/2
  98. out[0]=(t+$8000)/257
  99. in:+4;out:+1
  100. Wend
  101. Case SF_MONO16LE
  102. While in<>in_end
  103. Local x=in[0] Shl 8 | in[1]
  104. Local y=in[2] Shl 8 | in[3]
  105. If x & $8000 x:|$ffff0000
  106. If y & $8000 y:|$ffff0000
  107. Local t=(x+y)/2
  108. out[0]=t
  109. out[1]=t Shr 8
  110. in:+4;out:+2
  111. Wend
  112. Case SF_MONO16BE
  113. While in<>in_end
  114. Local x=in[0] Shl 8 | in[1]
  115. Local y=in[2] Shl 8 | in[3]
  116. If x & $8000 x:|$ffff0000
  117. If y & $8000 y:|$ffff0000
  118. Local t=(x+y)/2
  119. out[0]=t Shr 8
  120. out[1]=t
  121. in:+4;out:+2
  122. Wend
  123. Case SF_STEREO8
  124. While in<>in_end
  125. Local x=in[0] Shl 8 | in[1]
  126. Local y=in[2] Shl 8 | in[3]
  127. If x & $8000 x:|$ffff0000
  128. If y & $8000 y:|$ffff0000
  129. out[0]=(x+$8000)/257
  130. out[1]=(y+$8000)/257
  131. in:+4;out:+2
  132. Wend
  133. Case SF_STEREO16LE
  134. While in<>in_end
  135. out[0]=in[1]
  136. out[1]=in[0]
  137. out[2]=in[3]
  138. out[3]=in[2]
  139. in:+4;out:+4
  140. Wend
  141. Default
  142. RuntimeError "Unimplemented sample format conversion"
  143. End Select
  144. End Function