76 WARNINGLOG( QString(
"Provided pitch out of bound [%1;%2]. Rounding to nearest allowed value." )
100 QString sFilename = pNode->
read_string(
"filename",
"",
false,
false, bSilent );
101 QString sAbsoluteFilename = sFilename;
104 ! sFilename.startsWith(
"/" ) ) {
106#ifdef H2CORE_HAVE_OSC
107 if ( pHydrogen->isUnderSessionManagement() ) {
118 if ( sFilename.left( 2 ) ==
"./" ||
119 sFilename.left( 2 ) ==
".\\" ) {
124 sFilename.right( sFilename.size() - 1 );
127 sFilename = sDrumkitPath +
"/" + sFilename;
128 sAbsoluteFilename = sFilename;
132 sFilename = sDrumkitPath +
"/" + sFilename;
133 sAbsoluteFilename = sFilename;
136 sFilename = sDrumkitPath +
"/" + sFilename;
137 sAbsoluteFilename = sFilename;
141 std::shared_ptr<Sample> pSample =
nullptr;
143 pSample = std::make_shared<Sample>( sFilename, drumkitLicense );
149 bool bIsModified = pNode->
read_bool(
"ismodified",
false,
true,
false,
true );
150 pSample->set_is_modified( bIsModified );
158 loops.
count = pNode->
read_int(
"loops", 0,
false,
false, bSilent );
160 pSample->set_loops( loops );
163 rubberband.
use = pNode->
read_int(
"userubber", 0,
false,
false, bSilent );
164 rubberband.
divider = pNode->
read_float(
"rubberdivider", 0.0,
false,
false, bSilent );
165 rubberband.
c_settings = pNode->
read_int(
"rubberCsettings", 1,
false,
false, bSilent );
166 rubberband.
pitch = pNode->
read_float(
"rubberPitch", 0.0,
false,
false, bSilent );
170 m_rubberBandCLIexecutable ) ) {
171 rubberband.
use =
false;
173 pSample->set_rubberband( rubberband );
179 XMLNode volumeNode = pNode->firstChildElement(
"volume" );
180 while ( ! volumeNode.isNull() ) {
181 pt.
frame = volumeNode.
read_int(
"volume-position", 0,
false,
false, bSilent );
182 pt.
value = volumeNode.
read_int(
"volume-value", 0,
false,
false , bSilent);
183 velocityEnvelope.push_back( pt );
184 volumeNode = volumeNode.nextSiblingElement(
"volume" );
186 pSample->set_velocity_envelope( velocityEnvelope );
189 XMLNode panNode = pNode->firstChildElement(
"pan" );
190 while ( ! panNode.isNull() ) {
191 pt.
frame = panNode.
read_int(
"pan-position", 0,
false,
false, bSilent );
192 pt.
value = panNode.
read_int(
"pan-value", 0,
false,
false, bSilent );
193 panEnvelope.push_back( pt );
194 panNode = panNode.nextSiblingElement(
"pan" );
196 pSample->set_pan_envelope( panEnvelope );
200 WARNINGLOG( QString(
"Sample file [%1] does not exist" )
201 .arg( sAbsoluteFilename ) );
204 auto pLayer = std::make_shared<InstrumentLayer>( pSample );
205 pLayer->set_start_velocity( pNode->
read_float(
"min", 0.0,
206 true,
true, bSilent ) );
207 pLayer->set_end_velocity( pNode->
read_float(
"max", 1.0,
208 true,
true, bSilent ) );
209 pLayer->set_gain( pNode->
read_float(
"gain", 1.0,
210 true,
false, bSilent ) );
211 pLayer->set_pitch( pNode->
read_float(
"pitch", 0.0,
212 true,
false, bSilent ) );
220 if ( pSample ==
nullptr ) {
221 ERRORLOG(
"No sample associated with layer. Skipping it" );
230 if ( pHydrogen->isUnderSessionManagement() ) {
236 if ( pSample->get_raw_filepath().startsWith(
'.' ) ) {
237 sFilename = pSample->get_raw_filepath();
248 sFilename = pSample->get_filename();
258 layer_node.
write_bool(
"ismodified", pSample->get_is_modified() );
259 layer_node.
write_string(
"smode", pSample->get_loop_mode_string() );
268 layer_node.
write_int(
"userubber",
static_cast<int>(rubberband.
use) );
273 for (
const auto& velocity : *pSample->get_velocity_envelope() ) {
275 volumeNode.
write_int(
"volume-position", velocity.frame );
276 volumeNode.
write_int(
"volume-value", velocity.value );
279 for (
const auto& pan : *pSample->get_pan_envelope() ) {
281 panNode.
write_int(
"pan-position", pan.frame );
282 panNode.
write_int(
"pan-value", pan.value );
291 sOutput = QString(
"%1[InstrumentLayer]\n" ).arg( sPrefix )
292 .append( QString(
"%1%2gain: %3\n" ).arg( sPrefix ).arg( s ).arg(
__gain ) )
293 .append( QString(
"%1%2pitch: %3\n" ).arg( sPrefix ).arg( s ).arg(
__pitch ) )
294 .append( QString(
"%1%2start_velocity: %3\n" ).arg( sPrefix ).arg( s ).arg(
__start_velocity ) )
295 .append( QString(
"%1%2end_velocity: %3\n" ).arg( sPrefix ).arg( s ).arg(
__end_velocity ) );
297 sOutput.append( QString(
"%1" )
298 .arg(
__sample->toQString( sPrefix + s, bShort ) ) );
300 sOutput.append( QString(
"%1%2sample: nullptr\n" ).arg( sPrefix ).arg( s ) );
304 sOutput = QString(
"[InstrumentLayer]" )
305 .append( QString(
" gain: %1" ).arg(
__gain ) )
306 .append( QString(
", pitch: %1" ).arg(
__pitch ) )
310 sOutput.append( QString(
", sample: %1\n" ).arg(
__sample->get_filepath() ) );
312 sOutput.append( QString(
", sample: nullptr\n" ) );
static QString sPrintIndention
String used to format the debugging string output of some core classes.
A container for a sample, being able to apply modifications on it.
static QString prepare_sample_path(const QString &fname)
Returns the basename if the given path is under an existing user or system drumkit path,...
static bool file_exists(const QString &path, bool silent=false)
returns true if the given path is an existing regular file
static Hydrogen * get_instance()
Returns the current Hydrogen instance __instance.
float get_gain() const
get the gain of the layer
void set_pitch(float pitch)
set the pitch of the layer
static std::shared_ptr< InstrumentLayer > load_from(XMLNode *pNode, const QString &sDrumkitPath, const License &drumkitLicense=License(), bool bSilent=false)
load an instrument layer from an XMLNode
float __start_velocity
the start velocity of the sample, 0.0 by default
float get_pitch() const
get the pitch of the layer
float __gain
ratio between the input sample and the output signal, 1.0 by default
float __pitch
the frequency of the sample, 0.0 by default which means output pitch is the same as input pitch
std::shared_ptr< Sample > __sample
the underlaying sample
void save_to(XMLNode *node, bool bFull=false)
save the instrument layer within the given XMLNode
InstrumentLayer(std::shared_ptr< Sample > sample)
constructor
~InstrumentLayer()
destructor
QString toQString(const QString &sPrefix="", bool bShort=true) const override
Formatted string version for debugging purposes.
std::shared_ptr< Sample > get_sample() const
get the sample of the layer
float get_start_velocity() const
get the start velocity of the layer
void load_sample(float fBpm=120)
Calls the H2Core::Sample::load() member function of __sample.
float __end_velocity
the end velocity of the sample, 1.0 by default
void set_sample(std::shared_ptr< Sample > sample)
set the sample of the layer
float get_end_velocity() const
get the end velocity of the layer
static constexpr float fPitchMin
Minimum support pitch value.
static constexpr float fPitchMax
Maximum support pitch value.
Wrapper class to help Hydrogen deal with the license information specified in a drumkit.
static Preferences * get_instance()
Returns a pointer to the current Preferences singleton stored in __instance.
set of loop configuration flags
int end_frame
the frame index where to end the new sample to
int start_frame
the frame index where to start the new sample from
LoopMode mode
one of the possible loop modes
int count
the counts of loops to apply
int loop_frame
the frame index where to start the loop from
set of rubberband configuration flags
int c_settings
TODO should be crispness, see rubberband -h.
float divider
TODO should be ratio : desired time ratio.
bool use
is rubberband enabled
static Loops::LoopMode parse_loop_mode(const QString &string)
parse the given string and rturn the corresponding loop_mode
std::vector< EnvelopePoint > VelocityEnvelope
define the type used to store velocity envelope points
XMLNode is a subclass of QDomNode with read and write values methods.
int read_int(const QString &node, int default_value, bool inexistent_ok=true, bool empty_ok=true, bool bSilent=false)
reads an integer stored into a child node
bool read_bool(const QString &node, bool default_value, bool inexistent_ok=true, bool empty_ok=true, bool bSilent=false)
reads a boolean stored into a child node
QString read_string(const QString &node, const QString &default_value, bool inexistent_ok=true, bool empty_ok=true, bool bSilent=false)
reads a string stored into a child node
float read_float(const QString &node, float default_value, bool inexistent_ok=true, bool empty_ok=true, bool bSilent=false)
reads a float stored into a child node
void write_float(const QString &node, const float value)
write a float into a child node
XMLNode createNode(const QString &name)
create a new XMLNode that has to be appended into de XMLDoc
void write_string(const QString &node, const QString &value)
write a string into a child node
void write_bool(const QString &node, const bool value)
write a boolean into a child node
void write_int(const QString &node, const int value)
write an integer into a child node
static NsmClient * get_instance()
QString getSessionFolderPath() const