recording_with_microphone.rst 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164
  1. :article_outdated: True
  2. .. _doc_recording_with_microphone:
  3. Recording with microphone
  4. =========================
  5. Godot supports in-game audio recording for Windows, macOS, Linux, Android and
  6. iOS.
  7. A simple demo is included in the official demo projects and will be used as
  8. support for this tutorial:
  9. `<https://github.com/godotengine/godot-demo-projects/tree/master/audio/mic_record>`_.
  10. You will need to enable audio input in the :ref:`Audio > Driver > Enable Input<class_ProjectSettings_property_audio/driver/enable_input>` project setting, or you'll just get empty audio files.
  11. The structure of the demo
  12. -------------------------
  13. The demo consists of a single scene. This scene includes two major parts: the
  14. GUI and the audio.
  15. We will focus on the audio part. In this demo, a bus named ``Record`` with the
  16. effect ``Record`` is created to handle the audio recording.
  17. An ``AudioStreamPlayer`` named ``AudioStreamRecord`` is used for recording.
  18. .. image:: img/record_bus.png
  19. .. image:: img/record_stream_player.png
  20. .. tabs::
  21. .. code-tab:: gdscript GDScript
  22. var effect
  23. var recording
  24. func _ready():
  25. # We get the index of the "Record" bus.
  26. var idx = AudioServer.get_bus_index("Record")
  27. # And use it to retrieve its first effect, which has been defined
  28. # as an "AudioEffectRecord" resource.
  29. effect = AudioServer.get_bus_effect(idx, 0)
  30. .. code-tab:: csharp
  31. private AudioEffectRecord _effect;
  32. private AudioStreamSample _recording;
  33. public override void _Ready()
  34. {
  35. // We get the index of the "Record" bus.
  36. int idx = AudioServer.GetBusIndex("Record");
  37. // And use it to retrieve its first effect, which has been defined
  38. // as an "AudioEffectRecord" resource.
  39. _effect = (AudioEffectRecord)AudioServer.GetBusEffect(idx, 0);
  40. }
  41. The audio recording is handled by the :ref:`class_AudioEffectRecord` resource
  42. which has three methods:
  43. :ref:`get_recording() <class_AudioEffectRecord_method_get_recording>`,
  44. :ref:`is_recording_active() <class_AudioEffectRecord_method_is_recording_active>`,
  45. and :ref:`set_recording_active() <class_AudioEffectRecord_method_set_recording_active>`.
  46. .. tabs::
  47. .. code-tab:: gdscript GDScript
  48. func _on_record_button_pressed():
  49. if effect.is_recording_active():
  50. recording = effect.get_recording()
  51. $PlayButton.disabled = false
  52. $SaveButton.disabled = false
  53. effect.set_recording_active(false)
  54. $RecordButton.text = "Record"
  55. $Status.text = ""
  56. else:
  57. $PlayButton.disabled = true
  58. $SaveButton.disabled = true
  59. effect.set_recording_active(true)
  60. $RecordButton.text = "Stop"
  61. $Status.text = "Recording..."
  62. .. code-tab:: csharp
  63. private void OnRecordButtonPressed()
  64. {
  65. if (_effect.IsRecordingActive())
  66. {
  67. _recording = _effect.GetRecording();
  68. GetNode<Button>("PlayButton").Disabled = false;
  69. GetNode<Button>("SaveButton").Disabled = false;
  70. _effect.SetRecordingActive(false);
  71. GetNode<Button>("RecordButton").Text = "Record";
  72. GetNode<Label>("Status").Text = "";
  73. }
  74. else
  75. {
  76. GetNode<Button>("PlayButton").Disabled = true;
  77. GetNode<Button>("SaveButton").Disabled = true;
  78. _effect.SetRecordingActive(true);
  79. GetNode<Button>("RecordButton").Text = "Stop";
  80. GetNode<Label>("Status").Text = "Recording...";
  81. }
  82. }
  83. At the start of the demo, the recording effect is not active. When the user
  84. presses the ``RecordButton``, the effect is enabled with
  85. ``set_recording_active(true)``.
  86. On the next button press, as ``effect.is_recording_active()`` is ``true``,
  87. the recorded stream can be stored into the ``recording`` variable by calling
  88. ``effect.get_recording()``.
  89. .. tabs::
  90. .. code-tab:: gdscript GDScript
  91. func _on_play_button_pressed():
  92. print(recording)
  93. print(recording.format)
  94. print(recording.mix_rate)
  95. print(recording.stereo)
  96. var data = recording.get_data()
  97. print(data.size())
  98. $AudioStreamPlayer.stream = recording
  99. $AudioStreamPlayer.play()
  100. .. code-tab:: csharp
  101. private void OnPlayButtonPressed()
  102. {
  103. GD.Print(_recording);
  104. GD.Print(_recording.Format);
  105. GD.Print(_recording.MixRate);
  106. GD.Print(_recording.Stereo);
  107. byte[] data = _recording.Data;
  108. GD.Print(data.Length);
  109. var audioStreamPlayer = GetNode<AudioStreamPlayer>("AudioStreamPlayer");
  110. audioStreamPlayer.Stream = _recording;
  111. audioStreamPlayer.Play();
  112. }
  113. To playback the recording, you assign the recording as the stream of the
  114. ``AudioStreamPlayer`` and call ``play()``.
  115. .. tabs::
  116. .. code-tab:: gdscript GDScript
  117. func _on_save_button_pressed():
  118. var save_path = $SaveButton/Filename.text
  119. recording.save_to_wav(save_path)
  120. $Status.text = "Saved WAV file to: %s\n(%s)" % [save_path, ProjectSettings.globalize_path(save_path)]
  121. .. code-tab:: csharp
  122. private void OnSaveButtonPressed()
  123. {
  124. string savePath = GetNode<LineEdit>("SaveButton/Filename").Text;
  125. _recording.SaveToWav(savePath);
  126. GetNode<Label>("Status").Text = string.Format("Saved WAV file to: {0}\n({1})", savePath, ProjectSettings.GlobalizePath(savePath));
  127. }
  128. To save the recording, you call ``save_to_wav()`` with the path to a file.
  129. In this demo, the path is defined by the user via a ``LineEdit`` input box.