YARP
Yet Another Robot Platform
ServerSoundGrabber.cpp
Go to the documentation of this file.
1/*
2 * SPDX-FileCopyrightText: 2006-2021 Istituto Italiano di Tecnologia (IIT)
3 * SPDX-FileCopyrightText: 2006 Julio Gomes
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
8
9#include <yarp/os/Bottle.h>
11#include <yarp/os/LogStream.h>
12#include <yarp/os/Time.h>
13#include <yarp/os/Vocab.h>
14
16
17
18namespace {
19YARP_LOG_COMPONENT(SERVERSOUNDGRABBER, "yarp.device.ServerSoundGrabber")
20}
21
23#ifdef DEBUG_TIME_SPENT
24 : last_time(yarp::os::Time::now())
25#endif
26{
27}
28
30{
31 if (mic != nullptr) {
32 close();
33 }
34}
35
47{
48 yarp::os::Value* name;
49 if (config.check("subdevice", name)) {
50 yCDebug(SERVERSOUNDGRABBER, "Subdevice %s", name->toString().c_str());
51 if (name->isString()) {
52 // maybe user isn't doing nested configuration
54 p.fromString(config.toString());
55 p.put("device", name->toString());
56 poly.open(p);
57 } else {
58 poly.open(*name);
59 }
60 } else {
61 yCError(SERVERSOUNDGRABBER, "\"--subdevice <name>\" not set for server_soundgrabber");
62 return false;
63 }
64
65 if (poly.isValid()) {
66 poly.view(mic);
67 } else {
68 yCError(SERVERSOUNDGRABBER, "cannot make <%s>", name->toString().c_str());
69 return false;
70 }
71
72 if (mic == nullptr) {
73 yCError(SERVERSOUNDGRABBER, "failed to open interface");
74 return false;
75 }
76
77 //set the streaming port
78 std::string portname = "/sound_grabber";
79 if (config.check("name", name)) {
80 portname = name->asString();
81 }
82 if (streamingPort.open(portname) == false) {
83 yCError(SERVERSOUNDGRABBER) << "Unable to open port" << portname;
84 return false;
85 }
86
87 //set the RPC port
88 if (rpcPort.open(portname + "/rpc") == false) {
89 yCError(SERVERSOUNDGRABBER) << "Unable to open port" << portname + "/rpc";
90 return false;
91 }
92 rpcPort.setReader(*this);
93
94 //wait a little and then start
96
97 //mic->startRecording();
98 this->start();
99
100 return true;
101}
102
104{
105 if (mic != nullptr) {
106 stop();
107 mic = nullptr;
108
109 streamingPort.interrupt();
110 streamingPort.close();
111 rpcPort.interrupt();
112 rpcPort.close();
113
114 return true;
115 }
116 return false;
117}
118
120{
121 while (!isStopping()) {
122#ifdef DEBUG_TIME_SPENT
123 double current_time = yarp::os::Time::now();
124 yCDebug(SERVERSOUNDGRABBER) << current_time - last_time;
125 last_time = current_time;
126#endif
127
128 if (mic != nullptr) {
130#ifdef PRINT_DEBUG_MESSAGES
131 {
132 audio_buffer_size buf_max;
133 audio_buffer_size buf_cur;
134 mic->getRecordingAudioBufferMaxSize(buf_max);
136 yCDebug(SERVERSOUNDGRABBER) << "BEFORE Buffer status:" << buf_cur.getBytes() << "/" << buf_max.getBytes() << "bytes";
137 }
138#endif
139 mic->getSound(snd, 44100, 44100, 0.0);
140#ifdef PRINT_DEBUG_MESSAGES
141 {
142 audio_buffer_size buf_max;
143 audio_buffer_size buf_cur;
144 mic->getRecordingAudioBufferMaxSize(buf_max);
146 yCDebug(SERVERSOUNDGRABBER) << "AFTER Buffer status:" << buf_cur.getBytes() << "/" << buf_max.getBytes() << "bytes";
147 }
148#endif
149#ifdef PRINT_DEBUG_MESSAGES
150 yCDebug(SERVERSOUNDGRABBER) << "Sound size:" << snd.getSamples() * snd.getChannels() * snd.getBytesPerSample() << " bytes";
151 yCDebug(SERVERSOUNDGRABBER);
152#endif
153 stamp.update();
154 streamingPort.setEnvelope(stamp);
155 streamingPort.write(snd);
156 }
157 }
158 yCInfo(SERVERSOUNDGRABBER, "Sound grabber stopping");
159}
160
162{
163 yarp::os::Bottle command;
164 yarp::os::Bottle reply;
165 bool ok = command.read(connection);
166 if (!ok) {
167 return false;
168 }
169 reply.clear();
170
171 if (command.get(0).asString() == "start") {
172 mic->startRecording();
173 reply.addVocab32(VOCAB_OK);
174 } else if (command.get(0).asString() == "stop") {
175 mic->stopRecording();
176 reply.addVocab32(VOCAB_OK);
177 } else if (command.get(0).asString() == "help") {
178 reply.addVocab32("many");
179 reply.addString("start");
180 reply.addString("stop");
181 } else {
182 yCError(SERVERSOUNDGRABBER) << "Invalid command";
183 reply.addVocab32(VOCAB_ERR);
184 }
185
186 yarp::os::ConnectionWriter* returnToSender = connection.getWriter();
187 if (returnToSender != nullptr) {
188 reply.write(*returnToSender);
189 }
190 return true;
191}
constexpr yarp::conf::vocab32_t VOCAB_OK
Definition: GenericVocabs.h:15
constexpr yarp::conf::vocab32_t VOCAB_ERR
Definition: GenericVocabs.h:17
bool close() override
Close the DeviceDriver.
bool open(yarp::os::Searchable &config) override
Configure with a set of options.
bool read(yarp::os::ConnectionReader &connection) override
Read this object from a network connection.
void run() override
Main body of the new thread.
bool view(T *&x)
Get an interface to the device driver.
Definition: DeviceDriver.h:88
virtual bool getSound(yarp::sig::Sound &sound, size_t min_number_of_samples, size_t max_number_of_samples, double max_samples_timeout_s)=0
Get a sound from a device.
virtual bool getRecordingAudioBufferCurrentSize(yarp::dev::AudioBufferSize &size)=0
virtual bool getRecordingAudioBufferMaxSize(yarp::dev::AudioBufferSize &size)=0
virtual bool stopRecording()=0
Stop the recording.
virtual bool startRecording()=0
Start the recording.
bool isValid() const
Check if device is valid.
Definition: PolyDriver.cpp:196
bool open(const std::string &txt)
Construct and configure a device by its common name.
Definition: PolyDriver.cpp:140
A simple collection of objects that can be described and transmitted in a portable way.
Definition: Bottle.h:64
void addVocab32(yarp::conf::vocab32_t x)
Places a vocabulary item in the bottle, at the end of the list.
Definition: Bottle.cpp:164
bool read(ConnectionReader &reader) override
Set the bottle's value based on input from a network connection.
Definition: Bottle.cpp:240
Value & get(size_type index) const
Reads a Value v from a certain part of the list.
Definition: Bottle.cpp:246
void clear()
Empties the bottle of any objects it contains.
Definition: Bottle.cpp:121
bool write(ConnectionWriter &writer) const override
Output a representation of the bottle to a network connection.
Definition: Bottle.cpp:230
void addString(const char *str)
Places a string in the bottle, at the end of the list.
Definition: Bottle.cpp:170
An interface for reading from a network connection.
virtual ConnectionWriter * getWriter()=0
Gets a way to reply to the message, if possible.
An interface for writing to a network connection.
bool write(const PortWriter &writer, const PortWriter *callback=nullptr) const override
Write an object to the port.
Definition: Port.cpp:436
void setReader(PortReader &reader) override
Set an external reader for port data.
Definition: Port.cpp:511
void interrupt() override
Interrupt any current reads or writes attached to the port.
Definition: Port.cpp:383
bool setEnvelope(PortWriter &envelope) override
Set an envelope (e.g., a timestamp) to the next message which will be sent.
Definition: Port.cpp:547
void close() override
Stop port activity.
Definition: Port.cpp:363
bool open(const std::string &name) override
Start port operation, with a specific name, with automatically-chosen network parameters.
Definition: Port.cpp:79
A class for storing options and configuration information.
Definition: Property.h:33
void fromString(const std::string &txt, bool wipe=true)
Interprets a string as a list of properties.
Definition: Property.cpp:1063
void put(const std::string &key, const std::string &value)
Associate the given key with the given string.
Definition: Property.cpp:1015
A base class for nested structures that can be searched.
Definition: Searchable.h:63
virtual bool check(const std::string &key) const =0
Check if there exists a property of the given name.
virtual std::string toString() const =0
Return a standard text representation of the content of the object.
void update()
Set the timestamp to the current time, and increment the sequence number (wrapping to 0 if the sequen...
Definition: Stamp.cpp:124
static void delaySystem(double seconds)
Definition: SystemClock.cpp:29
bool stop()
Stop the thread.
Definition: Thread.cpp:81
bool isStopping()
Returns true if the thread is stopping (Thread::stop has been called).
Definition: Thread.cpp:99
bool start()
Start the new thread running.
Definition: Thread.cpp:93
A single value (typically within a Bottle).
Definition: Value.h:43
virtual bool isString() const
Checks if value is a string.
Definition: Value.cpp:156
std::string toString() const override
Return a standard text representation of the content of the object.
Definition: Value.cpp:356
virtual std::string asString() const
Get string value.
Definition: Value.cpp:234
Class for storing sounds See Audio in YARP for additional documentation on YARP audio.
Definition: Sound.h:25
size_t getBytesPerSample() const
Get the number of bytes per sample.
Definition: Sound.cpp:414
size_t getChannels() const
Get the number of channels of the sound.
Definition: Sound.cpp:424
size_t getSamples() const
Get the number of samples contained in the sound.
Definition: Sound.cpp:419
#define yCInfo(component,...)
Definition: LogComponent.h:171
#define yCError(component,...)
Definition: LogComponent.h:213
#define yCDebug(component,...)
Definition: LogComponent.h:128
#define YARP_LOG_COMPONENT(name,...)
Definition: LogComponent.h:76
double now()
Return the current time in seconds, relative to an arbitrary starting point.
Definition: Time.cpp:121