Generate a tone .pb example ?

Just starting out? Need help? Post your questions and find answers here.
vmars316
Enthusiast
Enthusiast
Posts: 464
Joined: Fri Jun 29, 2012 12:24 am
Contact:

Generate a tone .pb example ?

Post by vmars316 »

TIA ,
How can I generate a tone (a specific Frequency , perhaps A 440 ) ?
I see Frequency examples , but they come from a .ogg file .
Can't find any docs for Beep .
A simple example like:
[Play Tone] Button , [Stop Play] Button .
vmars.us Win11 x64 , Martin Guitar 000-16 (1995)
"All things in moderation , except for love and forgiveness."
infratec
Always Here
Always Here
Posts: 6817
Joined: Sun Sep 07, 2008 12:45 pm
Location: Germany

Re: Generate a tone .pb example ?

Post by infratec »

Maybe something like that:

https://www.purebasic.fr/english/viewto ... 06#p467606

Code: Select all

Structure RIFFStructure
  Riff.a[4]
  Length.l
  Wave.a[4]
EndStructure


Structure fmtStructure
  fmt.a[4]
  Length.l
  Format.u
  Channels.u
  SampleRate.l
  BytesPerSecond.l
  BlockAlign.u
  BitsPerSample.u
EndStructure


Structure dataStructure
  Signature.a[4]
  Length.l
EndStructure



Procedure.i CreateSine24BitMonoWAV(SampleRate.i, Freq.i)
  
  Protected.i i, n, Points, HeaderSize, DataSize, File, Value
  Protected.d StepWidth, Angle
  Protected *WAVBuffer, *RiffPtr.RIFFStructure, *fmtPtr.fmtStructure, *dataPtr.dataStructure, *audioPtr
  
  
  Points = SampleRate / Freq
  
  Debug "Points per wave: " + Str(Points)
  
  HeaderSize = SizeOf(RIFFStructure)
  HeaderSize + SizeOf(fmtStructure)
  HeaderSize + SizeOf(dataStructure)
  
  DataSize + (Points * 3)
  
  *WAVBuffer = AllocateMemory(HeaderSize + DataSize)
  If *WAVBuffer
    
    *RiffPtr = *WAVBuffer
    PokeS(@*RiffPtr\Riff, "RIFF", 4, #PB_Ascii|#PB_String_NoZero)
    *RiffPtr\Length = HeaderSize + DataSize - 8
    PokeS(@*RiffPtr\Wave, "WAVE", 4, #PB_Ascii|#PB_String_NoZero)
    
    *fmtPtr = *WAVBuffer + SizeOf(RIFFStructure)
    PokeS(@*fmtPtr\fmt, "fmt ", 4, #PB_Ascii|#PB_String_NoZero)
    *fmtPtr\Length = SizeOf(fmtStructure) - 8
    *fmtPtr\Format = 1
    *fmtPtr\Channels = 1
    *fmtPtr\SampleRate = SampleRate
    *fmtPtr\BitsPerSample = 24
    *fmtPtr\BlockAlign = *fmtPtr\Channels * ((*fmtPtr\BitsPerSample + 7) / 8)
    *fmtPtr\BytesPerSecond = *fmtPtr\SampleRate * *fmtPtr\BlockAlign
    
    *dataPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure)
    PokeS(@*dataPtr\Signature, "data", 4, #PB_Ascii|#PB_String_NoZero)
    *dataPtr\Length = DataSize
    
    *audioPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure) + SizeOf(dataStructure) ; just behind the wav header
    
    StepWidth = 2 * #PI / Points
    For n = 0 To Points - 1
      Value = Sin(Angle) * 8385000  ; max. $7FFFFF -> 100% better 80% -> 6710880 ($666660)
      PokeA(*audioPtr + 2, (Value >> 16) & $FF)
      PokeA(*audioPtr + 1, (Value >> 8) & $FF)
      PokeA(*audioPtr + 0, (Value) & $FF)
      Angle + StepWidth
      *audioPtr + 3
    Next n
    
  EndIf
  
  ProcedureReturn *WAVBuffer
  
EndProcedure



If InitSound()
  
  *Buffer = CreateSine24BitMonoWAV(48000, 440)
  If *Buffer
    
;     If CreateFile(0, "Sine24BitMono.wav")
;       WriteData(0, *Buffer, MemorySize(*Buffer))
;       CloseFile(0)
;     EndIf
    
    Sound = CatchSound(#PB_Any, *Buffer)
    If Sound
      PlaySound(Sound, #PB_Sound_Loop)
      Delay(3000)
      StopSound(Sound)
    EndIf
    FreeMemory(*Buffer)
  EndIf
EndIf
Or simply:
https://docs.microsoft.com/en-us/window ... piset-beep

Code: Select all

Beep_(440, 3000)
But you can not stop Beep_(). So my solution is more what you want.
vmars316
Enthusiast
Enthusiast
Posts: 464
Joined: Fri Jun 29, 2012 12:24 am
Contact:

Re: Generate a tone .pb example ?

Post by vmars316 »

Thank you very much , infratec !

Your "Re: Audio MultiTone 48000 Hz @ 24 Bit" Answer is quite interesting also .
viewtopic.php?p=467606#p467606

Thanks
vmars.us Win11 x64 , Martin Guitar 000-16 (1995)
"All things in moderation , except for love and forgiveness."
infratec
Always Here
Always Here
Posts: 6817
Joined: Sun Sep 07, 2008 12:45 pm
Location: Germany

Re: Generate a tone .pb example ?

Post by infratec »

If you save the file to disk and open it with Audacity, you can 'see' the wave.
vmars316
Enthusiast
Enthusiast
Posts: 464
Joined: Fri Jun 29, 2012 12:24 am
Contact:

Re: Generate a tone .pb example ?

Post by vmars316 »

Thanks again !
vmars.us Win11 x64 , Martin Guitar 000-16 (1995)
"All things in moderation , except for love and forgiveness."
matalog
Enthusiast
Enthusiast
Posts: 165
Joined: Tue Sep 05, 2017 10:07 am

Re: Generate a tone .pb example ?

Post by matalog »

infratec wrote: Tue Aug 02, 2022 9:14 pm Maybe something like that:

viewtopic.php?p=467606#p467606

Code: Select all

Structure RIFFStructure
  Riff.a[4]
  Length.l
  Wave.a[4]
EndStructure


Structure fmtStructure
  fmt.a[4]
  Length.l
  Format.u
  Channels.u
  SampleRate.l
  BytesPerSecond.l
  BlockAlign.u
  BitsPerSample.u
EndStructure


Structure dataStructure
  Signature.a[4]
  Length.l
EndStructure



Procedure.i CreateSine24BitMonoWAV(SampleRate.i, Freq.i)
  
  Protected.i i, n, Points, HeaderSize, DataSize, File, Value
  Protected.d StepWidth, Angle
  Protected *WAVBuffer, *RiffPtr.RIFFStructure, *fmtPtr.fmtStructure, *dataPtr.dataStructure, *audioPtr
  
  
  Points = SampleRate / Freq
  
  Debug "Points per wave: " + Str(Points)
  
  HeaderSize = SizeOf(RIFFStructure)
  HeaderSize + SizeOf(fmtStructure)
  HeaderSize + SizeOf(dataStructure)
  
  DataSize + (Points * 3)
  
  *WAVBuffer = AllocateMemory(HeaderSize + DataSize)
  If *WAVBuffer
    
    *RiffPtr = *WAVBuffer
    PokeS(@*RiffPtr\Riff, "RIFF", 4, #PB_Ascii|#PB_String_NoZero)
    *RiffPtr\Length = HeaderSize + DataSize - 8
    PokeS(@*RiffPtr\Wave, "WAVE", 4, #PB_Ascii|#PB_String_NoZero)
    
    *fmtPtr = *WAVBuffer + SizeOf(RIFFStructure)
    PokeS(@*fmtPtr\fmt, "fmt ", 4, #PB_Ascii|#PB_String_NoZero)
    *fmtPtr\Length = SizeOf(fmtStructure) - 8
    *fmtPtr\Format = 1
    *fmtPtr\Channels = 1
    *fmtPtr\SampleRate = SampleRate
    *fmtPtr\BitsPerSample = 24
    *fmtPtr\BlockAlign = *fmtPtr\Channels * ((*fmtPtr\BitsPerSample + 7) / 8)
    *fmtPtr\BytesPerSecond = *fmtPtr\SampleRate * *fmtPtr\BlockAlign
    
    *dataPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure)
    PokeS(@*dataPtr\Signature, "data", 4, #PB_Ascii|#PB_String_NoZero)
    *dataPtr\Length = DataSize
    
    *audioPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure) + SizeOf(dataStructure) ; just behind the wav header
    
    StepWidth = 2 * #PI / Points
    For n = 0 To Points - 1
      Value = Sin(Angle) * 8385000  ; max. $7FFFFF -> 100% better 80% -> 6710880 ($666660)
      PokeA(*audioPtr + 2, (Value >> 16) & $FF)
      PokeA(*audioPtr + 1, (Value >> 8) & $FF)
      PokeA(*audioPtr + 0, (Value) & $FF)
      Angle + StepWidth
      *audioPtr + 3
    Next n
    
  EndIf
  
  ProcedureReturn *WAVBuffer
  
EndProcedure



If InitSound()
  
  *Buffer = CreateSine24BitMonoWAV(48000, 440)
  If *Buffer
    
;     If CreateFile(0, "Sine24BitMono.wav")
;       WriteData(0, *Buffer, MemorySize(*Buffer))
;       CloseFile(0)
;     EndIf
    
    Sound = CatchSound(#PB_Any, *Buffer)
    If Sound
      PlaySound(Sound, #PB_Sound_Loop)
      Delay(3000)
      StopSound(Sound)
    EndIf
    FreeMemory(*Buffer)
  EndIf
EndIf
Or simply:
https://docs.microsoft.com/en-us/window ... piset-beep

Code: Select all

Beep_(440, 3000)
But you can not stop Beep_(). So my solution is more what you want.
That's a great program to get started making sounds in PB.

Is there something that limits that method of having accuracy at higher frequencies?

You may hear what I mean if you run this, some of the notes seem to be not very accurate for the C Major Scale.

Code: Select all

Structure RIFFStructure
  Riff.a[4]
  Length.l
  Wave.a[4]
EndStructure

Global t.i=0
Structure fmtStructure
  fmt.a[4]
  Length.l
  Format.u
  Channels.u
  SampleRate.l
  BytesPerSecond.l
  BlockAlign.u
  BitsPerSample.u
EndStructure


Structure dataStructure
  Signature.a[4]
  Length.l
EndStructure


Dim bp.i(256)
                        DataSection
                          Data.i 0,2,4,5,7,9,11,12
                        EndDataSection
                        For x=0 To 7
                          Read bp(x)
                          Next 


Procedure.i CreateSine24BitMonoWAV(SampleRate.i, Freq.i)
  
  Protected.i i, n, Points, HeaderSize, DataSize, File, Value
  Protected.d StepWidth, Angle
  Protected *WAVBuffer, *RiffPtr.RIFFStructure, *fmtPtr.fmtStructure, *dataPtr.dataStructure, *audioPtr
  
  
  Points = SampleRate / Freq
  
  Debug "Points per wave: " + Str(Points)

  
  HeaderSize = SizeOf(RIFFStructure)
  HeaderSize + SizeOf(fmtStructure)
  HeaderSize + SizeOf(dataStructure)
  
  DataSize + (Points * 3)
  
  *WAVBuffer = AllocateMemory(HeaderSize + DataSize)
  If *WAVBuffer
    
    *RiffPtr = *WAVBuffer
    PokeS(@*RiffPtr\Riff, "RIFF", 4, #PB_Ascii|#PB_String_NoZero)
    *RiffPtr\Length = HeaderSize + DataSize - 8
    PokeS(@*RiffPtr\Wave, "WAVE", 4, #PB_Ascii|#PB_String_NoZero)
    
    *fmtPtr = *WAVBuffer + SizeOf(RIFFStructure)
    PokeS(@*fmtPtr\fmt, "fmt ", 4, #PB_Ascii|#PB_String_NoZero)
    *fmtPtr\Length = SizeOf(fmtStructure) - 8
    *fmtPtr\Format = 1
    *fmtPtr\Channels = 1
    *fmtPtr\SampleRate = SampleRate
    *fmtPtr\BitsPerSample = 24
    *fmtPtr\BlockAlign = *fmtPtr\Channels * ((*fmtPtr\BitsPerSample + 7) / 8)
    *fmtPtr\BytesPerSecond = *fmtPtr\SampleRate * *fmtPtr\BlockAlign
    
    *dataPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure)
    PokeS(@*dataPtr\Signature, "data", 4, #PB_Ascii|#PB_String_NoZero)
    *dataPtr\Length = DataSize
    
    *audioPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure) + SizeOf(dataStructure) ; just behind the wav header
    
    StepWidth = 2 * #PI / Points
    For n = 0 To Points - 1
      Value = (Sin(Angle)) * (838000)  ; max. $7FFFFF -> 100% better 80% -> 6710880 ($666660)
      PokeA(*audioPtr + 2, (Value >> 16) & $FF)
      PokeA(*audioPtr + 1, (Value >> 8) & $FF)
      PokeA(*audioPtr + 0, (Value) & $FF)
      Angle + StepWidth
      *audioPtr + 3
    Next n
    
  EndIf
  
  ProcedureReturn *WAVBuffer
  
EndProcedure
t=0

Repeat
If InitSound()
  
  *Buffer = CreateSine24BitMonoWAV(48000,Pow(2,bp(t)/12)*2092.992)
  Debug Pow(2,bp(t)/12)*2093
  If *Buffer
    
;     If CreateFile(0, "Sine24BitMono.wav")
;       WriteData(0, *Buffer, MemorySize(*Buffer))
;       CloseFile(0)
;     EndIf
    
    Sound = CatchSound(#PB_Any, *Buffer)
    If Sound
      PlaySound(Sound, #PB_Sound_Loop)
      Delay(1200)
      StopSound(Sound)
    EndIf
    FreeMemory(*Buffer)
  EndIf
EndIf
t=t+1
If t>7
  t=0
  EndIf
Until t>=256
AZJIO
Addict
Addict
Posts: 1317
Joined: Sun May 14, 2017 1:48 am

Re: Generate a tone .pb example ?

Post by AZJIO »

Without optimization. Notes could be precomputed into an array.
viewtopic.php?p=550222#p550222

Code: Select all

Structure RIFFStructure
  Riff.a[4]
  Length.l
  Wave.a[4]
EndStructure


Structure fmtStructure
  fmt.a[4]
  Length.l
  Format.u
  Channels.u
  SampleRate.l
  BytesPerSecond.l
  BlockAlign.u
  BitsPerSample.u
EndStructure


Structure dataStructure
  Signature.a[4]
  Length.l
EndStructure



Procedure.i CreateSine24BitMonoWAV(SampleRate.i, Freq.i)
  
  Protected.i i, n, Points, HeaderSize, DataSize, File, Value
  Protected.d StepWidth, Angle
  Protected *WAVBuffer, *RiffPtr.RIFFStructure, *fmtPtr.fmtStructure, *dataPtr.dataStructure, *audioPtr
  
  
  Points = SampleRate / Freq
  
;   Debug "Points per wave: " + Str(Points)
  
  HeaderSize = SizeOf(RIFFStructure)
  HeaderSize + SizeOf(fmtStructure)
  HeaderSize + SizeOf(dataStructure)
  
  DataSize + (Points * 3)
  
  *WAVBuffer = AllocateMemory(HeaderSize + DataSize)
  If *WAVBuffer
    
    *RiffPtr = *WAVBuffer
    PokeS(@*RiffPtr\Riff, "RIFF", 4, #PB_Ascii|#PB_String_NoZero)
    *RiffPtr\Length = HeaderSize + DataSize - 8
    PokeS(@*RiffPtr\Wave, "WAVE", 4, #PB_Ascii|#PB_String_NoZero)
    
    *fmtPtr = *WAVBuffer + SizeOf(RIFFStructure)
    PokeS(@*fmtPtr\fmt, "fmt ", 4, #PB_Ascii|#PB_String_NoZero)
    *fmtPtr\Length = SizeOf(fmtStructure) - 8
    *fmtPtr\Format = 1
    *fmtPtr\Channels = 1
    *fmtPtr\SampleRate = SampleRate
    *fmtPtr\BitsPerSample = 24
    *fmtPtr\BlockAlign = *fmtPtr\Channels * ((*fmtPtr\BitsPerSample + 7) / 8)
    *fmtPtr\BytesPerSecond = *fmtPtr\SampleRate * *fmtPtr\BlockAlign
    
    *dataPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure)
    PokeS(@*dataPtr\Signature, "data", 4, #PB_Ascii|#PB_String_NoZero)
    *dataPtr\Length = DataSize
    
    *audioPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure) + SizeOf(dataStructure) ; just behind the wav header
    
    StepWidth = 2 * #PI / Points
    For n = 0 To Points - 1
      Value = Sin(Angle) * 8385000  ; max. $7FFFFF -> 100% better 80% -> 6710880 ($666660)
      PokeA(*audioPtr + 2, (Value >> 16) & $FF)
      PokeA(*audioPtr + 1, (Value >> 8) & $FF)
      PokeA(*audioPtr + 0, (Value) & $FF)
      Angle + StepWidth
      *audioPtr + 3
    Next n
    
  EndIf
  
  ProcedureReturn *WAVBuffer
  
EndProcedure


Declare StartTrack()
Global temp.f=0.6 ; коэффициент темпа
Global Tone=0


Procedure _Beep(nota.f,octave.f=4,Duration.f=200,pause.f=0)
	Protected Frequency
	Frequency=440.0*Pow(2, (nota + Tone)/12.0+ octave+1.0/6.0 - 4.0)
; 	Debug Frequency
	*Buffer = CreateSine24BitMonoWAV(48000, Frequency)
	If *Buffer
		Sound = CatchSound(#PB_Any, *Buffer)
		If Sound
			PlaySound(Sound, #PB_Sound_Loop)
			Delay(Duration/temp)
			StopSound(Sound)
		EndIf
		FreeMemory(*Buffer)
	EndIf
	
	If pause
		Delay(pause/temp)
	EndIf
EndProcedure

If InitSound()
	StartTrack()
EndIf




Procedure StartTrack()

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)

_Beep(1,4,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(6,5,100)

_Beep(1,4,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(6,5,100)

_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(6,5,100)

_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(6,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(10,4,100)
_Beep(5,5,100)
_Beep(10,5,100)
_Beep(10,4,100)
_Beep(5,5,100)
_Beep(10,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(10,4,100)
_Beep(5,5,100)
_Beep(10,5,100)
_Beep(10,4,100)
_Beep(5,5,100)
_Beep(10,5,100)

_Beep(1,4,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(7,4,100)
_Beep(10,4,100)
_Beep(3,5,100)

_Beep(1,4,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(7,4,100)
_Beep(10,4,100)
_Beep(3,5,100)

_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(8,5,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(8,5,100)

_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(8,5,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(8,5,100)

_Beep(12,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(12,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(3,3,100)
_Beep(10,3,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(1,5,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(1,5,100)

_Beep(3,3,100)
_Beep(10,3,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(1,5,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(1,5,100)

_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(12,4,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(12,4,100)

_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(12,4,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(12,4,100)

_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(2,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(2,5,100)

_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(2,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(2,5,100)

_Beep(6,3,100)
_Beep(10,3,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)

_Beep(6,3,100)
_Beep(10,3,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)

_Beep(6,3,100)
_Beep(9,3,100)
_Beep(3,4,100)
_Beep(6,4,100)
_Beep(12,4,100)
_Beep(3,4,100)
_Beep(6,4,100)
_Beep(12,4,100)

_Beep(6,3,100)
_Beep(9,3,100)
_Beep(3,4,100)
_Beep(6,4,100)
_Beep(12,4,100)
_Beep(3,4,100)
_Beep(6,4,100)
_Beep(12,4,100)

_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(5,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(5,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(3,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(3,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(1,3,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(1,3,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(1,3,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(11,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(1,3,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(11,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(6,2,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(6,2,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(7,2,100)
_Beep(1,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(4,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(4,4,100)

_Beep(7,2,100)
_Beep(1,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(4,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(4,4,100)

_Beep(9,2,100)
_Beep(6,3,100)
_Beep(12,3,100)
_Beep(1,4,100)
_Beep(3,4,100)
_Beep(12,3,100)
_Beep(1,4,100)
_Beep(3,4,100)

_Beep(9,2,100)
_Beep(6,3,100)
_Beep(12,3,100)
_Beep(1,4,100)
_Beep(3,4,100)
_Beep(12,3,100)
_Beep(1,4,100)
_Beep(3,4,100)

_Beep(8,2,100)
_Beep(6,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)

_Beep(8,2,100)
_Beep(6,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)

_Beep(8,2,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(8,2,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(4,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(7,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(7,4,100)

_Beep(8,2,100)
_Beep(4,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(7,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(7,4,100)

_Beep(8,2,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)

_Beep(8,2,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(1,2,100)
_Beep(1,3,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)

_Beep(1,2,100)
_Beep(1,3,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)

_Beep(1,2,100)
_Beep(1,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(1,4,100)
_Beep(10,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(6,3,100)
_Beep(3,3,100)
_Beep(6,3,100)
_Beep(3,3,100)

; _Beep(1,2,100)
; _Beep(1,3,100)
; _Beep(8,4,100)
; _Beep(12,4,100)
; _Beep(3,5,100)
; _Beep(6,5,100)
; _Beep(3,5,100)
; _Beep(12,4,100)
; _Beep(8,4,100)
; _Beep(12,4,100)
; _Beep(8,4,70,30)
; _Beep(8,4,100)
; _Beep(6,4,100)
; _Beep(8,4,100)
; _Beep(6,4,200)
; _Beep(5,4,100)

; _Beep(1,3,900)

_Beep(1,2,100)
_Beep(1,3,100)
_Beep(8,4,100)
_Beep(12,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(3,5,100)
_Beep(12,4,100)
_Beep(8,4,100)
_Beep(12,4,100)
_Beep(8,4,100)
_Beep(8,4,100)
_Beep(6,4,100)
_Beep(8,4,100)
_Beep(6,4,100)
_Beep(5,4,100)

_Beep(1,3,900)
EndProcedure
End
Olli
Addict
Addict
Posts: 1071
Joined: Wed May 27, 2020 12:26 pm

Re: Generate a tone .pb example ?

Post by Olli »

@AZJIO

It is some of the famous Beepthoven. :mrgreen:
matalog
Enthusiast
Enthusiast
Posts: 165
Joined: Tue Sep 05, 2017 10:07 am

Re: Generate a tone .pb example ?

Post by matalog »

AZJIO wrote: Mon Oct 24, 2022 5:16 am Without optimization. Notes could be precomputed into an array.
viewtopic.php?p=550222#p550222

Code: Select all

Structure RIFFStructure
  Riff.a[4]
  Length.l
  Wave.a[4]
EndStructure


Structure fmtStructure
  fmt.a[4]
  Length.l
  Format.u
  Channels.u
  SampleRate.l
  BytesPerSecond.l
  BlockAlign.u
  BitsPerSample.u
EndStructure


Structure dataStructure
  Signature.a[4]
  Length.l
EndStructure



Procedure.i CreateSine24BitMonoWAV(SampleRate.i, Freq.i)
  
  Protected.i i, n, Points, HeaderSize, DataSize, File, Value
  Protected.d StepWidth, Angle
  Protected *WAVBuffer, *RiffPtr.RIFFStructure, *fmtPtr.fmtStructure, *dataPtr.dataStructure, *audioPtr
  
  
  Points = SampleRate / Freq
  
;   Debug "Points per wave: " + Str(Points)
  
  HeaderSize = SizeOf(RIFFStructure)
  HeaderSize + SizeOf(fmtStructure)
  HeaderSize + SizeOf(dataStructure)
  
  DataSize + (Points * 3)
  
  *WAVBuffer = AllocateMemory(HeaderSize + DataSize)
  If *WAVBuffer
    
    *RiffPtr = *WAVBuffer
    PokeS(@*RiffPtr\Riff, "RIFF", 4, #PB_Ascii|#PB_String_NoZero)
    *RiffPtr\Length = HeaderSize + DataSize - 8
    PokeS(@*RiffPtr\Wave, "WAVE", 4, #PB_Ascii|#PB_String_NoZero)
    
    *fmtPtr = *WAVBuffer + SizeOf(RIFFStructure)
    PokeS(@*fmtPtr\fmt, "fmt ", 4, #PB_Ascii|#PB_String_NoZero)
    *fmtPtr\Length = SizeOf(fmtStructure) - 8
    *fmtPtr\Format = 1
    *fmtPtr\Channels = 1
    *fmtPtr\SampleRate = SampleRate
    *fmtPtr\BitsPerSample = 24
    *fmtPtr\BlockAlign = *fmtPtr\Channels * ((*fmtPtr\BitsPerSample + 7) / 8)
    *fmtPtr\BytesPerSecond = *fmtPtr\SampleRate * *fmtPtr\BlockAlign
    
    *dataPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure)
    PokeS(@*dataPtr\Signature, "data", 4, #PB_Ascii|#PB_String_NoZero)
    *dataPtr\Length = DataSize
    
    *audioPtr = *WAVBuffer + SizeOf(RIFFStructure) + SizeOf(fmtStructure) + SizeOf(dataStructure) ; just behind the wav header
    
    StepWidth = 2 * #PI / Points
    For n = 0 To Points - 1
      Value = Sin(Angle) * 8385000  ; max. $7FFFFF -> 100% better 80% -> 6710880 ($666660)
      PokeA(*audioPtr + 2, (Value >> 16) & $FF)
      PokeA(*audioPtr + 1, (Value >> 8) & $FF)
      PokeA(*audioPtr + 0, (Value) & $FF)
      Angle + StepWidth
      *audioPtr + 3
    Next n
    
  EndIf
  
  ProcedureReturn *WAVBuffer
  
EndProcedure


Declare StartTrack()
Global temp.f=0.6 ; коэффициент темпа
Global Tone=0


Procedure _Beep(nota.f,octave.f=4,Duration.f=200,pause.f=0)
	Protected Frequency
	Frequency=440.0*Pow(2, (nota + Tone)/12.0+ octave+1.0/6.0 - 4.0)
; 	Debug Frequency
	*Buffer = CreateSine24BitMonoWAV(48000, Frequency)
	If *Buffer
		Sound = CatchSound(#PB_Any, *Buffer)
		If Sound
			PlaySound(Sound, #PB_Sound_Loop)
			Delay(Duration/temp)
			StopSound(Sound)
		EndIf
		FreeMemory(*Buffer)
	EndIf
	
	If pause
		Delay(pause/temp)
	EndIf
EndProcedure

If InitSound()
	StartTrack()
EndIf




Procedure StartTrack()

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)

_Beep(1,4,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(6,5,100)

_Beep(1,4,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(6,5,100)

_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(6,5,100)

_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(6,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(10,4,100)
_Beep(5,5,100)
_Beep(10,5,100)
_Beep(10,4,100)
_Beep(5,5,100)
_Beep(10,5,100)

_Beep(1,4,100)
_Beep(5,4,100)
_Beep(10,4,100)
_Beep(5,5,100)
_Beep(10,5,100)
_Beep(10,4,100)
_Beep(5,5,100)
_Beep(10,5,100)

_Beep(1,4,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(7,4,100)
_Beep(10,4,100)
_Beep(3,5,100)

_Beep(1,4,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(7,4,100)
_Beep(10,4,100)
_Beep(3,5,100)

_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(8,5,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(8,5,100)

_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(8,5,100)
_Beep(8,4,100)
_Beep(3,5,100)
_Beep(8,5,100)

_Beep(12,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(12,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(3,3,100)
_Beep(10,3,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(1,5,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(1,5,100)

_Beep(3,3,100)
_Beep(10,3,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(1,5,100)
_Beep(3,4,100)
_Beep(7,4,100)
_Beep(1,5,100)

_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(12,4,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(12,4,100)

_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(12,4,100)
_Beep(3,4,100)
_Beep(8,4,100)
_Beep(12,4,100)

_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(2,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(2,5,100)

_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(2,5,100)
_Beep(5,4,100)
_Beep(8,4,100)
_Beep(2,5,100)

_Beep(6,3,100)
_Beep(10,3,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)

_Beep(6,3,100)
_Beep(10,3,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)
_Beep(3,4,100)
_Beep(10,4,100)
_Beep(3,5,100)

_Beep(6,3,100)
_Beep(9,3,100)
_Beep(3,4,100)
_Beep(6,4,100)
_Beep(12,4,100)
_Beep(3,4,100)
_Beep(6,4,100)
_Beep(12,4,100)

_Beep(6,3,100)
_Beep(9,3,100)
_Beep(3,4,100)
_Beep(6,4,100)
_Beep(12,4,100)
_Beep(3,4,100)
_Beep(6,4,100)
_Beep(12,4,100)

_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(1,5,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(1,5,100)

_Beep(5,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(5,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(3,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(3,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(1,3,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(1,3,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(1,3,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(11,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(1,3,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(11,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(6,2,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(6,2,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(7,2,100)
_Beep(1,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(4,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(4,4,100)

_Beep(7,2,100)
_Beep(1,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(4,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(4,4,100)

_Beep(9,2,100)
_Beep(6,3,100)
_Beep(12,3,100)
_Beep(1,4,100)
_Beep(3,4,100)
_Beep(12,3,100)
_Beep(1,4,100)
_Beep(3,4,100)

_Beep(9,2,100)
_Beep(6,3,100)
_Beep(12,3,100)
_Beep(1,4,100)
_Beep(3,4,100)
_Beep(12,3,100)
_Beep(1,4,100)
_Beep(3,4,100)

_Beep(8,2,100)
_Beep(6,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)

_Beep(8,2,100)
_Beep(6,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(3,4,100)

_Beep(8,2,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(8,2,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(5,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(4,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(7,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(7,4,100)

_Beep(8,2,100)
_Beep(4,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(7,4,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(7,4,100)

_Beep(8,2,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)

_Beep(8,2,100)
_Beep(5,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(8,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(1,4,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(8,2,100)
_Beep(3,3,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)
_Beep(8,3,100)
_Beep(12,3,100)
_Beep(6,4,100)

_Beep(1,2,100)
_Beep(1,3,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)

_Beep(1,2,100)
_Beep(1,3,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)
_Beep(8,3,100)
_Beep(11,3,100)
_Beep(5,4,100)

_Beep(1,2,100)
_Beep(1,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(1,4,100)
_Beep(6,4,100)
_Beep(1,4,100)
_Beep(10,3,100)
_Beep(6,3,100)
_Beep(10,3,100)
_Beep(6,3,100)
_Beep(3,3,100)
_Beep(6,3,100)
_Beep(3,3,100)

; _Beep(1,2,100)
; _Beep(1,3,100)
; _Beep(8,4,100)
; _Beep(12,4,100)
; _Beep(3,5,100)
; _Beep(6,5,100)
; _Beep(3,5,100)
; _Beep(12,4,100)
; _Beep(8,4,100)
; _Beep(12,4,100)
; _Beep(8,4,70,30)
; _Beep(8,4,100)
; _Beep(6,4,100)
; _Beep(8,4,100)
; _Beep(6,4,200)
; _Beep(5,4,100)

; _Beep(1,3,900)

_Beep(1,2,100)
_Beep(1,3,100)
_Beep(8,4,100)
_Beep(12,4,100)
_Beep(3,5,100)
_Beep(6,5,100)
_Beep(3,5,100)
_Beep(12,4,100)
_Beep(8,4,100)
_Beep(12,4,100)
_Beep(8,4,100)
_Beep(8,4,100)
_Beep(6,4,100)
_Beep(8,4,100)
_Beep(6,4,100)
_Beep(5,4,100)

_Beep(1,3,900)
EndProcedure
End
Brilliant, it reminds me of the many Bach tunes I used to listen to on my ZX Spectrum.

Does anyone know if there is a way to remove the clicks between each of the notes?
matalog
Enthusiast
Enthusiast
Posts: 165
Joined: Tue Sep 05, 2017 10:07 am

Re: Generate a tone .pb example ?

Post by matalog »

I think if the playsound() was only stopped - with stopsound() when it has definitely come to the end of a loop, and never half way through one, than it wouldn't click, as it is likely that the click is due to a jump in volumes, whereas the waves that this program outputs are always complete, and that means that they aoways finish and start at 0 volume.

In summary the waves created should be fine, we just need a way to end a sound by definitely knowing that one full wave sample has be completed, never half way through.
AZJIO
Addict
Addict
Posts: 1317
Joined: Sun May 14, 2017 1:48 am

Re: Generate a tone .pb example ?

Post by AZJIO »

Pre-creation of notes.

first way

Code: Select all

Declare StartTrack(g)
Global temp.f = 1 ; tempo
Global Tone = -12
Global Dim aNota(8, 12)


Procedure _Beep(gener, nota, octave = 4, Duration.f = 200, pause.f = 0)
	Protected Frequency
	If gener
		Frequency = 440.0*Pow(2, (nota + Tone) / 12.0 + octave + 1.0 / 6.0 - 4.0)
		If Not aNota(octave, nota)
			aNota(octave, nota) = CreateSine24BitMonoWAV(48000, Frequency)
		EndIf
	Else
; 		Debug Frequency
		If aNota(octave, nota)
			Sound = CatchSound(#PB_Any, aNota(octave, nota))
			If Sound
				PlaySound(Sound, #PB_Sound_Loop)
				Delay(Duration / temp)
				StopSound(Sound)
			EndIf
		EndIf
		If pause
			Delay(pause / temp)
		EndIf
	EndIf
EndProcedure

If InitSound()
	StartTrack(1)
	StartTrack(0)

	For i = 1 To 8
		For j = 1 To 12
			If aNota(i, j)
				FreeMemory(aNota(i, j))
			EndIf
		Next
	Next
EndIf

End

Procedure StartTrack(g)
	For i = 1 To 2
		_Beep(g,5,5,130)
		_Beep(g,7,5,130)
		_Beep(g,11,5,130)
		_Beep(g,7,5,130)
		_Beep(g,11,5,130)
		_Beep(g,12,5,130)
		_Beep(g,11,5,450,70)
		_Beep(g,7,5,130,130)
		_Beep(g,7,5,130)
		_Beep(g,5,5,250,130)
		_Beep(g,7,5,260)
		_Beep(g,5,5,65,65)
		_Beep(g,7,5,260)
		_Beep(g,5,5,65,65)
		_Beep(g,7,5,86,130)
		_Beep(g,7,5,65,65)
		_Beep(g,8,5,65,65)
		_Beep(g,8,5,130,130)
		_Beep(g,8,5,170,350)
	Next
EndProcedure
second way

Code: Select all

Declare StartTrack()
Global temp.f = 1 ; tempo
Global Tone = -12
Global Dim aNota(8, 12)
Global octave, nota


For octave = 1 To 8
	For nota = 1 To 12
		aNota(octave, nota) = CreateSine24BitMonoWAV(48000,  440.0*Pow(2, (nota + Tone) / 12.0 + octave + 1.0 / 6.0 - 4.0))
	Next
Next


Procedure _Beep(nota, octave = 4, Duration.f = 200, pause.f = 0)
	Protected Sound
	If aNota(octave, nota) ; move check of generated notes to array generator
		Sound = CatchSound(#PB_Any, aNota(octave, nota))
		If Sound
			PlaySound(Sound, #PB_Sound_Loop)
			Delay(Duration / temp)
			StopSound(Sound)
		EndIf
	EndIf
	If pause
		Delay(pause / temp)
	EndIf
EndProcedure

If InitSound()
	StartTrack()

	For octave = 1 To 8
		For nota = 1 To 12
			If aNota(octave, nota) ; move check of generated notes to array generator
				FreeMemory(aNota(octave, nota))
			EndIf
		Next
	Next
EndIf

End

Procedure StartTrack()
	Protected i
	For i = 1 To 2
		_Beep(5,5,130)
		_Beep(7,5,130)
		_Beep(11,5,130)
		_Beep(7,5,130)
		_Beep(11,5,130)
		_Beep(12,5,130)
		_Beep(11,5,450,70)
		_Beep(7,5,130,130)
		_Beep(7,5,130)
		_Beep(5,5,250,130)
		_Beep(7,5,260)
		_Beep(5,5,65,65)
		_Beep(7,5,260)
		_Beep(5,5,65,65)
		_Beep(7,5,86,130)
		_Beep(7,5,65,65)
		_Beep(8,5,65,65)
		_Beep(8,5,130,130)
		_Beep(8,5,170,350)
	Next
EndProcedure
matalog wrote: Mon Oct 24, 2022 8:11 pm In summary the waves created should be fine, we just need a way to end a sound by definitely knowing that one full wave sample has be completed, never half way through.
at a sampling rate of 48 kHz, a 1 kHz frequency division accounts for 48 bytes per wave. Within 1 second, there are 1000 such waves. Most likely, we will not notice the breaking of the wave by ear. The problem is most likely that the inclusion of the PlaySound function is accompanied by interference, similarly to StopSound.
You can try to glue the notes into one sequence in order to execute the PlaySound and StopSound functions once

2. It is not necessary to copy 1000 lines of code to add a comment from one line
Olli
Addict
Addict
Posts: 1071
Joined: Wed May 27, 2020 12:26 pm

Re: Generate a tone .pb example ?

Post by Olli »

I also had this way any years before when I tried to test sounds.

The simplest way is use two channels :

Code: Select all

----    ----   (frequency a)
   ------  ------ (frequency b)
By using the option #PB_Sound_MultiChannel, the hardware works to merge two different sounds. I was surprised by the erase of this "tick", but I was not insured anymore, because it requires a good synchronizing.

Code: Select all

======---
   =======---
'=' means a full volume sound.
'---' means a decreasing volume sound.
I was empty of time referencies. This is okay : while we do not want to change one of the durations, it stays simple.
But if we want to change one of the durations (the main one, or the decreasing one), this requires a quantity of equations which does not differ anymore between a multi-channel made sound, and a single composed wav chunk.
vmars316
Enthusiast
Enthusiast
Posts: 464
Joined: Fri Jun 29, 2012 12:24 am
Contact:

Re: Generate a tone .pb example ?

Post by vmars316 »

Wow , thats great info Folks !
Thanks
vmars.us Win11 x64 , Martin Guitar 000-16 (1995)
"All things in moderation , except for love and forgiveness."
Olli
Addict
Addict
Posts: 1071
Joined: Wed May 27, 2020 12:26 pm

Re: Generate a tone .pb example ?

Post by Olli »

A little drop to celebrate !

Code: Select all

structure wav
 array w.w(21)
endStructure
initSound()
*wav.wav = allocateMemory(sizeOf(wav) )
initializeStructure(*wav, wav)
base64decoder(ascii("UklGRgAAAABXQVZFZm10IBAAAAABAAEARKwAAIhYAQACABAAZGF0YQ"), 56, @*wav\w(0), 40)
with *wav
 wMax = 62800
 reDim \w(wMax + 22)
 size = (wMax + 23) * 2
 PokeL(@\w(2), size - 8)
 PokeL(@\w(20), size - 44)
 ampli.d = 800
 for i = 0 to wMax
  \w(i + 22) = cos(i / (7 - sin(t.d) ) ) * ampli
  ampli * 0.999
  t + 0.00015
 next
 snd = catchSound(#pb_any, @\w(0) )
 repeat
  playSound(snd, #pb_sound_multiChannel)
  delay(400)
 until inputRequester("", "Just press enter to play", "")
endWith
AZJIO
Addict
Addict
Posts: 1317
Joined: Sun May 14, 2017 1:48 am

Re: Generate a tone .pb example ?

Post by AZJIO »

Code: Select all

; Base64DecoderBuffer(Ascii("UklGRgAAAABXQVZFZm10IBAAAAABAAEARKwAAIhYAQACABAAZGF0YQ"), 56, @*wav\w(0), 40)
Base64Decoder("UklGRgAAAABXQVZFZm10IBAAAAABAAEARKwAAIhYAQACABAAZGF0YQ", @*wav\w(0), 40)
Post Reply