def change_octave( nth_event: int, n_octaves: int, novent_line: lily.NOventLine, change_main_pitches: bool = True, change_acciaccatura_pitches: bool = True, ) -> None: if change_main_pitches: novent_line[nth_event].pitch = [ p + ji.JIPitch([n_octaves]) for p in novent_line[nth_event].pitch ] if novent_line[nth_event].acciaccatura and change_acciaccatura_pitches: novent_line[nth_event].acciaccatura.mu_pitches = tuple( p + ji.JIPitch([n_octaves]) for p in novent_line[nth_event].acciaccatura.mu_pitches) previous_abjad_note = novent_line[nth_event].acciaccatura.abjad novent_line[nth_event].acciaccatura.abjad = abjad.Note( abjad.NamedPitch( name=previous_abjad_note.written_pitch.pitch_class.name, octave=previous_abjad_note.written_pitch.octave.number + n_octaves, ), abjad.Duration(previous_abjad_note.written_duration), )
def add_glissando( nth_event: int, scale_degrees: tuple, novent_line: lily.NOventLine, durations: tuple = tuple([]), verse_maker: mus.SegmentMaker = None, adapt_by_changed_structure: bool = False, ): n_scale_degrees = len(scale_degrees) assert verse_maker or durations or n_scale_degrees in (1, 2) if not durations: if n_scale_degrees == 2: durations = (novent_line[nth_event].duration, ) elif n_scale_degrees > 2: durations = tuple( fractions.Fraction(nv.delay) for nv in split_by_structure( nth_event, n_scale_degrees - 1, novent_line, verse_maker=verse_maker, change_novent_line=False, adapt_by_changed_structure=adapt_by_changed_structure, )) assert len(durations) == len(scale_degrees) - 1 novent = novent_line[nth_event].copy() normalized_pitch = novent.pitch[0].normalize() instrument = globals_.PITCH2INSTRUMENT[normalized_pitch] octave = novent.pitch[0].octave pitch_zone = tuple( p.register(octave) for p in sorted( tuple( p.copy() for p in globals_.SCALE_PER_INSTRUMENT[instrument]))) pitch_zone = functools.reduce( operator.add, (tuple(p + ji.JIPitch([n - 1]) for p in pitch_zone) for n in range(3)), ) pitch_null_idx = pitch_zone.index(novent.pitch[0]) durations += (0, ) interpolation_line = [] for relative_pitch_class, duration in zip(scale_degrees, durations): pc = relative_pitch_class % 7 octave = relative_pitch_class // 7 pitch = pitch_zone[pc + pitch_null_idx] + ji.JIPitch( [octave]) - novent.pitch[0] interpolation_line.append(old.PitchInterpolation(duration, pitch)) novent_line[nth_event].glissando = old.GlissandoLine( interpolations.InterpolationLine(interpolation_line))
def harmonic_synthesis(poly_per_interlocking: tuple): import pyteq for poly_idx, poly in enumerate(poly_per_interlocking): for melody_idx, voice in enumerate(poly): voice = old.Melody(voice[:280]) melody = [ pyteq.PyteqTone( ji.JIPitch(t.pitch, multiply=250), t.delay, t.duration, volume=t.volume, impedance=2, q_factor=0.2, string_length=9.9, sustain_pedal=1, ) if t.pitch != mel.TheEmptyPitch else pyteq.PyteqTone( t.pitch, t.delay, t.duration) for t in voice ] instr_range = tuple(n for n in range(10, 125)) f = pyteq.Pianoteq(melody, available_midi_notes=instr_range) f.export2wav( "pianoteq_output/glitter_{0}_{1}".format(poly_idx, melody_idx), # preset='"Kalimba Spacey"', preset='"Celtic Harp Bright"', )
def mk_empty_attack( duration: float, volume: float, frequency: float = 35, hammer_noise: float = 3, impedance: float = 0.3, cutoff: float = 0.3, q_factor: float = 5, string_length: float = 0.8, strike_point: float = 1 / 2, hammer_hard_piano: float = 1, hammer_hard_mezzo: float = 1.5, hammer_hard_forte: float = 2, blooming_energy: float = 0, ) -> midiplug.PyteqTone: """Helps making percussive sounds with Pianoteq.""" return midiplug.PyteqTone( ji.JIPitch(ji.r(1, 1), multiply=frequency), duration, duration, volume=volume, hammer_noise=hammer_noise, impedance=impedance, cutoff=cutoff, q_factor=q_factor, string_length=string_length, strike_point=strike_point, hammer_hard_piano=hammer_hard_piano, hammer_hard_mezzo=hammer_hard_mezzo, hammer_hard_forte=hammer_hard_forte, blooming_energy=blooming_energy, )
def render(self, name: str, cadence: old.Cadence) -> subprocess.Popen: seq = [] for chord in cadence: dur = float(chord.delay) if chord.pitch != mel.TheEmptyPitch and bool(chord.pitch): size = len(chord.pitch) for idx, pi in enumerate(chord.pitch): if idx + 1 == size: de = float(dur) else: de = 0 if pi != mel.TheEmptyPitch: if chord.volume: volume = chord.volume else: volume = self.volume tone = midiplug.PyteqTone( ji.JIPitch(pi, multiply=self.CONCERT_PITCH), de, dur, volume=volume, ) else: tone = midiplug.PyteqTone( mel.TheEmptyPitch, de, dur, volume=self.volume ) seq.append(tone) else: seq.append(old.Rest(dur)) pt = midiplug.Pianoteq(tuple(seq), self.available_midi_notes) return pt.export2wav(name, 1, self.preset, self.fxp)
def simple_synthesis(melodies: tuple, make_diva=True): import random random.seed(10) import pyteq for idx, voice in enumerate(melodies): # voice = old.Melody(voice[:120]).tie() voice = old.Melody(voice[:200]) if make_diva: melody_diva = [ pyteq.DivaTone( ji.JIPitch(t.pitch, multiply=250), t.delay, t.duration, glissando=t.glissando, volume=t.volume, ) if t.pitch != mel.TheEmptyPitch else pyteq.PyteqTone( t.pitch, t.delay, t.duration) for t in voice ] pyteq.Diva(melody_diva).export( "pianoteq_output/test_diva{0}.mid".format(idx)) melody_pteq = [ pyteq.PyteqTone( ji.JIPitch(t.pitch, multiply=250), t.delay, t.duration, volume=t.volume, glissando=t.glissando, # impedance=random.uniform(2.801, 2.98), q_factor=random.uniform(0.201, 0.28), string_length=random.uniform(8.9, 9.8), sustain_pedal=1, ) if t.pitch != mel.TheEmptyPitch else pyteq.PyteqTone( t.pitch, t.delay, t.duration) for t in voice ] f = pyteq.Pianoteq(melody_pteq, available_midi_notes=tuple(n for n in range(20, 125))) f.export2wav("pianoteq_output/test{0}".format(idx), preset='"Concert Harp Daily"')
def __init__( self, tempo_factor: float, pitches: tuple, rhythm: binr.Compound, discard_rests: bool = True, ): self.__tempo_factor = tempo_factor self.__pitches = pitches self.__rhythm = rhythm melody = old.Melody( old.Tone(ji.JIPitch(p, multiply=globals.CONCERT_PITCH), r * tempo_factor) if not p.is_empty else old. Rest(r * tempo_factor) for p, r in zip(pitches, rhythm)) if discard_rests: melody = melody.discard_rests() super().__init__(melody, attack=0.08, decay=0.05, release=0.25)
def make_data(self) -> tuple: """set orc and sco attributes.""" start_per_attack, duration_per_attack, volume_per_attack = ( self.find_start_and_duration_and_volume()) orc_lines = [] sco_lines = [] for instr_idx, start, duration, volume in zip( range(len(start_per_attack)), start_per_attack, duration_per_attack, volume_per_attack, ): valid_pitches = functools.reduce( operator.add, tuple( tuple( ji.JIPitch(p, multiply=globals.CONCERT_PITCH).register( octave).freq for octave in self._octaves) for p in next(self._chord)[0]( *globals.MALE_SOIL.harmonic_primes_per_bar[ self.segment._bar_number])), ) orc_data, sco_data = next(self._sample_maker)( instrument_idx=instr_idx + 1, start=start, duration=duration, volume=volume, pitch=valid_pitches, ) orc_lines.extend(orc_data + ("", )) sco_lines.extend(sco_data) self._orc = "\n".join(orc_lines) self._sco = "\n".join(sco_lines)
def __call__(self, name: str, cadence: old.JICadence) -> None: seq = [] for chord in cadence: dur = float(chord.delay) if chord.pitch != mel.TheEmptyPitch and bool(chord.pitch): size = len(chord.pitch) for idx, pi in enumerate(chord.pitch): if idx + 1 == size: de = float(dur) else: de = 0 tone = pyteq.PyteqTone( ji.JIPitch(pi, multiply=self.CONCERT_PITCH), de, dur, volume=self.volume, ) seq.append(tone) else: seq.append(old.Rest(dur)) pt = pyteq.Pianoteq(tuple(seq), self.available_midi_notes) pt.export2wav(name, 1, self.preset, self.fxp)
def make_diva_sequence(self, voice: tuple, tempo_factor: float) -> tuple: diva_sequence = [] for tone in voice: delay = tone.delay * tempo_factor if tone.pitch.is_empty: dt = old.Rest(delay) else: div_synth_args = { arg: next(self.init_arguments[arg]) for arg in self.init_arguments } dt = midiplug.DivaTone(ji.JIPitch( tone.pitch, multiply=globals.CONCERT_PITCH), delay, delay, volume=tone.volume, **div_synth_args) diva_sequence.append(dt) return tuple(diva_sequence)
p0 += ji.r(2, 1) p1 += ji.r(2, 1) p2 = p1 + ji.r(4, 1) p3 = p0 + ji.r(4, 1) PITCHES_POSITIVE.append(p0) PITCHES_POSITIVE.append(p2) PITCHES_NEGATIVE.append(p1) PITCHES_NEGATIVE.append(p3) if __name__ == "__main__": import pyteqNew as pyteq for idx, pitches in enumerate([PITCHES_POSITIVE, PITCHES_NEGATIVE]): if idx < 1: name = "Positive" else: name = "Negative" for p_idx, pitch in enumerate(sorted(pitches)): local_name = name + str(p_idx) melody = [ pyteq.MidiTone(ji.JIPitch(pitch, multiply=CONCERT_PITCH), 4, 4, volume=1) ] harp_range = tuple(n for n in range(20, 125)) f = pyteq.Pianoteq(melody, available_midi_notes=harp_range) f.export2wav(local_name, preset='"Erard Player"')
def render(self, path: str) -> subprocess.Popen: adapted_rhythms = [ rhythm * self.__tempo_factor for rhythm in self.__rhythm ] adapted_rhythms[-1] += self.__overlaying_time melody = old.Melody( tuple( old.Tone(p, r, r, volume=v) for p, r, v in zip( self.__pitches, adapted_rhythms, self.__dynamics))) is_consonant_pitch_per_tone = tuple( self.__is_not_dissonant_pitch_per_tone) spectrum_profile_per_tone = tuple(self.__spectrum_profile_per_tone) if self.convert_dissonant_tones2glissandi: melody = self._convert_dissonant_tones2glissandi(melody) if self.__tremolo is not None: info = self.__tremolo(melody, is_consonant_pitch_per_tone, spectrum_profile_per_tone) melody, is_consonant_pitch_per_tone, spectrum_profile_per_tone = info for modulator in self.modulator: melody = modulator(melody) sequence = [] for tone, is_not_dissonant_pitch, spectrum_profile in zip( melody, is_consonant_pitch_per_tone, spectrum_profile_per_tone): pitch, rhythm, volume, glissando = ( tone.pitch, tone.delay, tone.volume, tone.glissando, ) if pitch.is_empty: tone = pteqer.mk_empty_attack( rhythm, next(self.empty_attack_dynamic_maker)) else: if is_not_dissonant_pitch: parameters = dict(self.parameter_non_dissonant_pitches) else: parameters = dict(self.parameter_dissonant_pitches) for par in parameters: value = parameters[par] if isinstance(value, infit.InfIt): parameters[par] = next(value) elif (isinstance(value, float) or isinstance(value, int) or value is None): parameters[par] = value else: msg = "Unknown value type: {}.".format(type(value)) raise TypeError(msg) if parameters["pinch_harmonic_pedal"] == 1: if parameters["pinch_harmonic_pedal"]: pitch -= ji.r(2, 1) tone = midiplug.PyteqTone( ji.JIPitch(pitch, multiply=globals.CONCERT_PITCH), rhythm, rhythm, volume=volume, glissando=glissando, spectrum_profile_3=spectrum_profile[0], spectrum_profile_5=spectrum_profile[1], spectrum_profile_6=spectrum_profile[0], spectrum_profile_7=spectrum_profile[2], **parameters, ) sequence.append(tone) pteq = midiplug.Pianoteq(tuple(sequence)) return pteq.export2wav(path, preset=self.preset, fxp=self.fxp)
def _notate(name: str, instrument: str, scale: tuple) -> None: for add_harmonics in (False, True): if add_harmonics: harmonics_dict = { key: value[0] for key, value in globals_.RATIO2ARTIFICAL_HARMONIC_PITCHCLASS_AND_ARTIFICIAL_HARMONIC_OCTAVE.items() } if instrument == "violin": clef = abjad.Clef("treble") header_distance = -0.4 elif instrument == "viola": clef = abjad.Clef("alto") header_distance = -1 elif instrument == "cello": clef = abjad.Clef("bass") header_distance = -1 else: raise NotImplementedError(instrument) staff = abjad.Staff([]) for idx, pitch in enumerate(scale): abjad_pitch = lily.convert2abjad_pitch(pitch, globals_.RATIO2PITCHCLASS) if add_harmonics: ( _, octave, ) = globals_.RATIO2ARTIFICAL_HARMONIC_PITCHCLASS_AND_ARTIFICIAL_HARMONIC_OCTAVE[ pitch.register(0) ] harmonic_pitch = lily.convert2abjad_pitch( pitch + ji.JIPitch([octave]), harmonics_dict ) chord = abjad.Chord( sorted([abjad_pitch, harmonic_pitch]), abjad.Duration(1) ) abjad.tweak(chord.note_heads[1]).style = "harmonic" staff.append(chord) else: staff.append(abjad.Note(abjad_pitch, abjad.Duration(1))) abjad.attach(lily.mk_no_time_signature(), staff[0]) abjad.attach(abjad.TimeSignature((len(staff), 1)), staff[0]) abjad.attach(clef, staff[0]) abjad.attach( abjad.LilyPondLiteral( "\\override Score.SpacingSpanner.strict-note-spacing = ##t", format_slot="before", ), staff[0], ) abjad.attach( abjad.LilyPondLiteral("\\newSpacingSection", format_slot="before"), staff[0] ) abjad.attach( abjad.LilyPondLiteral( "\\override Score.SpacingSpanner.base-shortest-duration =" " #(ly:make-moment" + " 1/8)", format_slot="before", ), staff[0], ) abjad.attach( abjad.LilyPondLiteral("\\accidentalStyle dodecaphonic", "before"), staff[0], ) sco = abjad.Score([staff]) if add_harmonics: descr = "scale for {} with artificial harmonics".format(instrument) else: descr = "scale for {}".format(instrument) header_block = abjad.Block("header") header_block.piece = abjad.Markup( abjad.MarkupCommand( "center-column", [ abjad.MarkupCommand("fontsize", -1.5), abjad.MarkupCommand("smallCaps"), descr, abjad.MarkupCommand("vspace", header_distance), ], ) ) final_file_name = "{}/pictures/scale_{}".format(name, instrument) if add_harmonics: final_file_name = "{}_artificial_harmonics".format(final_file_name) lily.make_small_example(sco, final_file_name, header_block=header_block)