diff --git a/app/build.gradle b/app/build.gradle index 35173c4..82aa929 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -62,6 +62,7 @@ implementation 'com.google.android.material:material:1.6.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.4' implementation 'androidx.gridlayout:gridlayout:1.0.0' + implementation 'org.jetbrains.kotlin:kotlin-reflect:1.7.20-Beta' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.3' androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' diff --git a/app/build.gradle b/app/build.gradle index 35173c4..82aa929 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -62,6 +62,7 @@ implementation 'com.google.android.material:material:1.6.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.4' implementation 'androidx.gridlayout:gridlayout:1.0.0' + implementation 'org.jetbrains.kotlin:kotlin-reflect:1.7.20-Beta' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.3' androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' diff --git a/app/src/main/java/com/lukas/music/instruments/Instrument.kt b/app/src/main/java/com/lukas/music/instruments/Instrument.kt index aaa9e02..b1f68ad 100644 --- a/app/src/main/java/com/lukas/music/instruments/Instrument.kt +++ b/app/src/main/java/com/lukas/music/instruments/Instrument.kt @@ -12,9 +12,10 @@ import com.lukas.music.song.note.Note import com.lukas.music.song.voice.BassVoice +import com.lukas.music.song.voice.Voice abstract class Instrument(var name: String) { - var voice = BassVoice(this) + var voice: Voice = BassVoice(this) abstract var waveform: Waveform abstract var volume: Float abstract var muted: Boolean diff --git a/app/build.gradle b/app/build.gradle index 35173c4..82aa929 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -62,6 +62,7 @@ implementation 'com.google.android.material:material:1.6.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.4' implementation 'androidx.gridlayout:gridlayout:1.0.0' + implementation 'org.jetbrains.kotlin:kotlin-reflect:1.7.20-Beta' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.3' androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' diff --git a/app/src/main/java/com/lukas/music/instruments/Instrument.kt b/app/src/main/java/com/lukas/music/instruments/Instrument.kt index aaa9e02..b1f68ad 100644 --- a/app/src/main/java/com/lukas/music/instruments/Instrument.kt +++ b/app/src/main/java/com/lukas/music/instruments/Instrument.kt @@ -12,9 +12,10 @@ import com.lukas.music.song.note.Note import com.lukas.music.song.voice.BassVoice +import com.lukas.music.song.voice.Voice abstract class Instrument(var name: String) { - var voice = BassVoice(this) + var voice: Voice = BassVoice(this) abstract var waveform: Waveform abstract var volume: Float abstract var muted: Boolean diff --git a/app/src/main/java/com/lukas/music/song/Song.kt b/app/src/main/java/com/lukas/music/song/Song.kt index 7f9823f..fc5421b 100644 --- a/app/src/main/java/com/lukas/music/song/Song.kt +++ b/app/src/main/java/com/lukas/music/song/Song.kt @@ -16,7 +16,7 @@ import com.lukas.music.util.Cycle class Song( - var root: Note, + root: Note, val beats: Int ) : Cycle(beats) { val chordProgression = ChordProgression() @@ -32,12 +32,25 @@ } } + var root: Note = root + set(value) { + field = value + stopAllInstruments() + } + + private fun stopAllInstruments() { + for (instrument in Instrument.instruments) { + instrument.stop() + } + } + init { for (i in 0 until beats) { this += i } wraparoundListeners += { chordProgression.step() + stopAllInstruments() } } diff --git a/app/build.gradle b/app/build.gradle index 35173c4..82aa929 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -62,6 +62,7 @@ implementation 'com.google.android.material:material:1.6.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.4' implementation 'androidx.gridlayout:gridlayout:1.0.0' + implementation 'org.jetbrains.kotlin:kotlin-reflect:1.7.20-Beta' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.3' androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' diff --git a/app/src/main/java/com/lukas/music/instruments/Instrument.kt b/app/src/main/java/com/lukas/music/instruments/Instrument.kt index aaa9e02..b1f68ad 100644 --- a/app/src/main/java/com/lukas/music/instruments/Instrument.kt +++ b/app/src/main/java/com/lukas/music/instruments/Instrument.kt @@ -12,9 +12,10 @@ import com.lukas.music.song.note.Note import com.lukas.music.song.voice.BassVoice +import com.lukas.music.song.voice.Voice abstract class Instrument(var name: String) { - var voice = BassVoice(this) + var voice: Voice = BassVoice(this) abstract var waveform: Waveform abstract var volume: Float abstract var muted: Boolean diff --git a/app/src/main/java/com/lukas/music/song/Song.kt b/app/src/main/java/com/lukas/music/song/Song.kt index 7f9823f..fc5421b 100644 --- a/app/src/main/java/com/lukas/music/song/Song.kt +++ b/app/src/main/java/com/lukas/music/song/Song.kt @@ -16,7 +16,7 @@ import com.lukas.music.util.Cycle class Song( - var root: Note, + root: Note, val beats: Int ) : Cycle(beats) { val chordProgression = ChordProgression() @@ -32,12 +32,25 @@ } } + var root: Note = root + set(value) { + field = value + stopAllInstruments() + } + + private fun stopAllInstruments() { + for (instrument in Instrument.instruments) { + instrument.stop() + } + } + init { for (i in 0 until beats) { this += i } wraparoundListeners += { chordProgression.step() + stopAllInstruments() } } diff --git a/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt new file mode 100644 index 0000000..8f43cac --- /dev/null +++ b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt @@ -0,0 +1,27 @@ +/* + * Copyright (C) 2022 Lukas Eisenhauer + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or(at your option) any later version. + * + * This program is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + */ + +package com.lukas.music.song.voice + +import com.lukas.music.instruments.Instrument +import com.lukas.music.song.note.Note + +class ChordVoice(instrument: Instrument) : Voice(instrument) { + override var noteActive: Array> = arrayOf( + Array(3) { false }, + Array(3) { true }, + Array(3) { false }, + Array(3) { true }, + ) + + override fun getNotes(root: Note, chordNotes: Array): Array { + return chordNotes + } +} \ No newline at end of file diff --git a/app/build.gradle b/app/build.gradle index 35173c4..82aa929 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -62,6 +62,7 @@ implementation 'com.google.android.material:material:1.6.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.4' implementation 'androidx.gridlayout:gridlayout:1.0.0' + implementation 'org.jetbrains.kotlin:kotlin-reflect:1.7.20-Beta' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.3' androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' diff --git a/app/src/main/java/com/lukas/music/instruments/Instrument.kt b/app/src/main/java/com/lukas/music/instruments/Instrument.kt index aaa9e02..b1f68ad 100644 --- a/app/src/main/java/com/lukas/music/instruments/Instrument.kt +++ b/app/src/main/java/com/lukas/music/instruments/Instrument.kt @@ -12,9 +12,10 @@ import com.lukas.music.song.note.Note import com.lukas.music.song.voice.BassVoice +import com.lukas.music.song.voice.Voice abstract class Instrument(var name: String) { - var voice = BassVoice(this) + var voice: Voice = BassVoice(this) abstract var waveform: Waveform abstract var volume: Float abstract var muted: Boolean diff --git a/app/src/main/java/com/lukas/music/song/Song.kt b/app/src/main/java/com/lukas/music/song/Song.kt index 7f9823f..fc5421b 100644 --- a/app/src/main/java/com/lukas/music/song/Song.kt +++ b/app/src/main/java/com/lukas/music/song/Song.kt @@ -16,7 +16,7 @@ import com.lukas.music.util.Cycle class Song( - var root: Note, + root: Note, val beats: Int ) : Cycle(beats) { val chordProgression = ChordProgression() @@ -32,12 +32,25 @@ } } + var root: Note = root + set(value) { + field = value + stopAllInstruments() + } + + private fun stopAllInstruments() { + for (instrument in Instrument.instruments) { + instrument.stop() + } + } + init { for (i in 0 until beats) { this += i } wraparoundListeners += { chordProgression.step() + stopAllInstruments() } } diff --git a/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt new file mode 100644 index 0000000..8f43cac --- /dev/null +++ b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt @@ -0,0 +1,27 @@ +/* + * Copyright (C) 2022 Lukas Eisenhauer + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or(at your option) any later version. + * + * This program is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + */ + +package com.lukas.music.song.voice + +import com.lukas.music.instruments.Instrument +import com.lukas.music.song.note.Note + +class ChordVoice(instrument: Instrument) : Voice(instrument) { + override var noteActive: Array> = arrayOf( + Array(3) { false }, + Array(3) { true }, + Array(3) { false }, + Array(3) { true }, + ) + + override fun getNotes(root: Note, chordNotes: Array): Array { + return chordNotes + } +} \ No newline at end of file diff --git a/app/src/main/java/com/lukas/music/song/voice/Voice.kt b/app/src/main/java/com/lukas/music/song/voice/Voice.kt index 1b3ead1..42865a5 100644 --- a/app/src/main/java/com/lukas/music/song/voice/Voice.kt +++ b/app/src/main/java/com/lukas/music/song/voice/Voice.kt @@ -12,6 +12,7 @@ import com.lukas.music.instruments.Instrument import com.lukas.music.song.note.Note +import kotlin.reflect.KClass abstract class Voice(val instrument: Instrument) { abstract var noteActive: Array> @@ -33,4 +34,13 @@ instrument.startNote(note) } } + + companion object { + val DEFAULT_VOICES = listOf>( + BassVoice::class, + ChordVoice::class, + ) + + val DEFAULT_VOICE_NAMES = listOf("Bass", "Chord") + } } \ No newline at end of file diff --git a/app/build.gradle b/app/build.gradle index 35173c4..82aa929 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -62,6 +62,7 @@ implementation 'com.google.android.material:material:1.6.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.4' implementation 'androidx.gridlayout:gridlayout:1.0.0' + implementation 'org.jetbrains.kotlin:kotlin-reflect:1.7.20-Beta' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.3' androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' diff --git a/app/src/main/java/com/lukas/music/instruments/Instrument.kt b/app/src/main/java/com/lukas/music/instruments/Instrument.kt index aaa9e02..b1f68ad 100644 --- a/app/src/main/java/com/lukas/music/instruments/Instrument.kt +++ b/app/src/main/java/com/lukas/music/instruments/Instrument.kt @@ -12,9 +12,10 @@ import com.lukas.music.song.note.Note import com.lukas.music.song.voice.BassVoice +import com.lukas.music.song.voice.Voice abstract class Instrument(var name: String) { - var voice = BassVoice(this) + var voice: Voice = BassVoice(this) abstract var waveform: Waveform abstract var volume: Float abstract var muted: Boolean diff --git a/app/src/main/java/com/lukas/music/song/Song.kt b/app/src/main/java/com/lukas/music/song/Song.kt index 7f9823f..fc5421b 100644 --- a/app/src/main/java/com/lukas/music/song/Song.kt +++ b/app/src/main/java/com/lukas/music/song/Song.kt @@ -16,7 +16,7 @@ import com.lukas.music.util.Cycle class Song( - var root: Note, + root: Note, val beats: Int ) : Cycle(beats) { val chordProgression = ChordProgression() @@ -32,12 +32,25 @@ } } + var root: Note = root + set(value) { + field = value + stopAllInstruments() + } + + private fun stopAllInstruments() { + for (instrument in Instrument.instruments) { + instrument.stop() + } + } + init { for (i in 0 until beats) { this += i } wraparoundListeners += { chordProgression.step() + stopAllInstruments() } } diff --git a/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt new file mode 100644 index 0000000..8f43cac --- /dev/null +++ b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt @@ -0,0 +1,27 @@ +/* + * Copyright (C) 2022 Lukas Eisenhauer + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or(at your option) any later version. + * + * This program is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + */ + +package com.lukas.music.song.voice + +import com.lukas.music.instruments.Instrument +import com.lukas.music.song.note.Note + +class ChordVoice(instrument: Instrument) : Voice(instrument) { + override var noteActive: Array> = arrayOf( + Array(3) { false }, + Array(3) { true }, + Array(3) { false }, + Array(3) { true }, + ) + + override fun getNotes(root: Note, chordNotes: Array): Array { + return chordNotes + } +} \ No newline at end of file diff --git a/app/src/main/java/com/lukas/music/song/voice/Voice.kt b/app/src/main/java/com/lukas/music/song/voice/Voice.kt index 1b3ead1..42865a5 100644 --- a/app/src/main/java/com/lukas/music/song/voice/Voice.kt +++ b/app/src/main/java/com/lukas/music/song/voice/Voice.kt @@ -12,6 +12,7 @@ import com.lukas.music.instruments.Instrument import com.lukas.music.song.note.Note +import kotlin.reflect.KClass abstract class Voice(val instrument: Instrument) { abstract var noteActive: Array> @@ -33,4 +34,13 @@ instrument.startNote(note) } } + + companion object { + val DEFAULT_VOICES = listOf>( + BassVoice::class, + ChordVoice::class, + ) + + val DEFAULT_VOICE_NAMES = listOf("Bass", "Chord") + } } \ No newline at end of file diff --git a/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt b/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt index 16aeaca..cca8ddd 100644 --- a/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt +++ b/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt @@ -20,6 +20,7 @@ import com.lukas.music.databinding.FragmentEditInstrumentBinding import com.lukas.music.instruments.Instrument import com.lukas.music.instruments.Waveform +import com.lukas.music.song.voice.Voice import com.lukas.music.ui.adapters.InstrumentViewHolder import com.lukas.music.util.setup import com.lukas.music.util.smartSetup @@ -51,6 +52,12 @@ binding.volumeText.text = "volume: $it%" instrument.volume = it.toFloat() / 100f } + binding.voiceSelection.setup( + Voice.DEFAULT_VOICE_NAMES, + Voice.DEFAULT_VOICES.indexOf(instrument.voice::class) + ) { + instrument.voice = Voice.DEFAULT_VOICES[it].constructors.first().call(instrument) + } binding.closeButton.setOnClickListener { dismiss() } diff --git a/app/build.gradle b/app/build.gradle index 35173c4..82aa929 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -62,6 +62,7 @@ implementation 'com.google.android.material:material:1.6.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.4' implementation 'androidx.gridlayout:gridlayout:1.0.0' + implementation 'org.jetbrains.kotlin:kotlin-reflect:1.7.20-Beta' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.3' androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' diff --git a/app/src/main/java/com/lukas/music/instruments/Instrument.kt b/app/src/main/java/com/lukas/music/instruments/Instrument.kt index aaa9e02..b1f68ad 100644 --- a/app/src/main/java/com/lukas/music/instruments/Instrument.kt +++ b/app/src/main/java/com/lukas/music/instruments/Instrument.kt @@ -12,9 +12,10 @@ import com.lukas.music.song.note.Note import com.lukas.music.song.voice.BassVoice +import com.lukas.music.song.voice.Voice abstract class Instrument(var name: String) { - var voice = BassVoice(this) + var voice: Voice = BassVoice(this) abstract var waveform: Waveform abstract var volume: Float abstract var muted: Boolean diff --git a/app/src/main/java/com/lukas/music/song/Song.kt b/app/src/main/java/com/lukas/music/song/Song.kt index 7f9823f..fc5421b 100644 --- a/app/src/main/java/com/lukas/music/song/Song.kt +++ b/app/src/main/java/com/lukas/music/song/Song.kt @@ -16,7 +16,7 @@ import com.lukas.music.util.Cycle class Song( - var root: Note, + root: Note, val beats: Int ) : Cycle(beats) { val chordProgression = ChordProgression() @@ -32,12 +32,25 @@ } } + var root: Note = root + set(value) { + field = value + stopAllInstruments() + } + + private fun stopAllInstruments() { + for (instrument in Instrument.instruments) { + instrument.stop() + } + } + init { for (i in 0 until beats) { this += i } wraparoundListeners += { chordProgression.step() + stopAllInstruments() } } diff --git a/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt new file mode 100644 index 0000000..8f43cac --- /dev/null +++ b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt @@ -0,0 +1,27 @@ +/* + * Copyright (C) 2022 Lukas Eisenhauer + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or(at your option) any later version. + * + * This program is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + */ + +package com.lukas.music.song.voice + +import com.lukas.music.instruments.Instrument +import com.lukas.music.song.note.Note + +class ChordVoice(instrument: Instrument) : Voice(instrument) { + override var noteActive: Array> = arrayOf( + Array(3) { false }, + Array(3) { true }, + Array(3) { false }, + Array(3) { true }, + ) + + override fun getNotes(root: Note, chordNotes: Array): Array { + return chordNotes + } +} \ No newline at end of file diff --git a/app/src/main/java/com/lukas/music/song/voice/Voice.kt b/app/src/main/java/com/lukas/music/song/voice/Voice.kt index 1b3ead1..42865a5 100644 --- a/app/src/main/java/com/lukas/music/song/voice/Voice.kt +++ b/app/src/main/java/com/lukas/music/song/voice/Voice.kt @@ -12,6 +12,7 @@ import com.lukas.music.instruments.Instrument import com.lukas.music.song.note.Note +import kotlin.reflect.KClass abstract class Voice(val instrument: Instrument) { abstract var noteActive: Array> @@ -33,4 +34,13 @@ instrument.startNote(note) } } + + companion object { + val DEFAULT_VOICES = listOf>( + BassVoice::class, + ChordVoice::class, + ) + + val DEFAULT_VOICE_NAMES = listOf("Bass", "Chord") + } } \ No newline at end of file diff --git a/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt b/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt index 16aeaca..cca8ddd 100644 --- a/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt +++ b/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt @@ -20,6 +20,7 @@ import com.lukas.music.databinding.FragmentEditInstrumentBinding import com.lukas.music.instruments.Instrument import com.lukas.music.instruments.Waveform +import com.lukas.music.song.voice.Voice import com.lukas.music.ui.adapters.InstrumentViewHolder import com.lukas.music.util.setup import com.lukas.music.util.smartSetup @@ -51,6 +52,12 @@ binding.volumeText.text = "volume: $it%" instrument.volume = it.toFloat() / 100f } + binding.voiceSelection.setup( + Voice.DEFAULT_VOICE_NAMES, + Voice.DEFAULT_VOICES.indexOf(instrument.voice::class) + ) { + instrument.voice = Voice.DEFAULT_VOICES[it].constructors.first().call(instrument) + } binding.closeButton.setOnClickListener { dismiss() } diff --git a/app/src/main/java/com/lukas/music/util/UIUtil.kt b/app/src/main/java/com/lukas/music/util/UIUtil.kt index 51d6026..5b7dbe3 100644 --- a/app/src/main/java/com/lukas/music/util/UIUtil.kt +++ b/app/src/main/java/com/lukas/music/util/UIUtil.kt @@ -114,5 +114,6 @@ ) spinnerSetupMain(arrayAdapter, target.get().ordinal) { target.set(items[it]) + callback(it) } } \ No newline at end of file diff --git a/app/build.gradle b/app/build.gradle index 35173c4..82aa929 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -62,6 +62,7 @@ implementation 'com.google.android.material:material:1.6.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.4' implementation 'androidx.gridlayout:gridlayout:1.0.0' + implementation 'org.jetbrains.kotlin:kotlin-reflect:1.7.20-Beta' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.3' androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' diff --git a/app/src/main/java/com/lukas/music/instruments/Instrument.kt b/app/src/main/java/com/lukas/music/instruments/Instrument.kt index aaa9e02..b1f68ad 100644 --- a/app/src/main/java/com/lukas/music/instruments/Instrument.kt +++ b/app/src/main/java/com/lukas/music/instruments/Instrument.kt @@ -12,9 +12,10 @@ import com.lukas.music.song.note.Note import com.lukas.music.song.voice.BassVoice +import com.lukas.music.song.voice.Voice abstract class Instrument(var name: String) { - var voice = BassVoice(this) + var voice: Voice = BassVoice(this) abstract var waveform: Waveform abstract var volume: Float abstract var muted: Boolean diff --git a/app/src/main/java/com/lukas/music/song/Song.kt b/app/src/main/java/com/lukas/music/song/Song.kt index 7f9823f..fc5421b 100644 --- a/app/src/main/java/com/lukas/music/song/Song.kt +++ b/app/src/main/java/com/lukas/music/song/Song.kt @@ -16,7 +16,7 @@ import com.lukas.music.util.Cycle class Song( - var root: Note, + root: Note, val beats: Int ) : Cycle(beats) { val chordProgression = ChordProgression() @@ -32,12 +32,25 @@ } } + var root: Note = root + set(value) { + field = value + stopAllInstruments() + } + + private fun stopAllInstruments() { + for (instrument in Instrument.instruments) { + instrument.stop() + } + } + init { for (i in 0 until beats) { this += i } wraparoundListeners += { chordProgression.step() + stopAllInstruments() } } diff --git a/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt new file mode 100644 index 0000000..8f43cac --- /dev/null +++ b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt @@ -0,0 +1,27 @@ +/* + * Copyright (C) 2022 Lukas Eisenhauer + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or(at your option) any later version. + * + * This program is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + */ + +package com.lukas.music.song.voice + +import com.lukas.music.instruments.Instrument +import com.lukas.music.song.note.Note + +class ChordVoice(instrument: Instrument) : Voice(instrument) { + override var noteActive: Array> = arrayOf( + Array(3) { false }, + Array(3) { true }, + Array(3) { false }, + Array(3) { true }, + ) + + override fun getNotes(root: Note, chordNotes: Array): Array { + return chordNotes + } +} \ No newline at end of file diff --git a/app/src/main/java/com/lukas/music/song/voice/Voice.kt b/app/src/main/java/com/lukas/music/song/voice/Voice.kt index 1b3ead1..42865a5 100644 --- a/app/src/main/java/com/lukas/music/song/voice/Voice.kt +++ b/app/src/main/java/com/lukas/music/song/voice/Voice.kt @@ -12,6 +12,7 @@ import com.lukas.music.instruments.Instrument import com.lukas.music.song.note.Note +import kotlin.reflect.KClass abstract class Voice(val instrument: Instrument) { abstract var noteActive: Array> @@ -33,4 +34,13 @@ instrument.startNote(note) } } + + companion object { + val DEFAULT_VOICES = listOf>( + BassVoice::class, + ChordVoice::class, + ) + + val DEFAULT_VOICE_NAMES = listOf("Bass", "Chord") + } } \ No newline at end of file diff --git a/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt b/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt index 16aeaca..cca8ddd 100644 --- a/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt +++ b/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt @@ -20,6 +20,7 @@ import com.lukas.music.databinding.FragmentEditInstrumentBinding import com.lukas.music.instruments.Instrument import com.lukas.music.instruments.Waveform +import com.lukas.music.song.voice.Voice import com.lukas.music.ui.adapters.InstrumentViewHolder import com.lukas.music.util.setup import com.lukas.music.util.smartSetup @@ -51,6 +52,12 @@ binding.volumeText.text = "volume: $it%" instrument.volume = it.toFloat() / 100f } + binding.voiceSelection.setup( + Voice.DEFAULT_VOICE_NAMES, + Voice.DEFAULT_VOICES.indexOf(instrument.voice::class) + ) { + instrument.voice = Voice.DEFAULT_VOICES[it].constructors.first().call(instrument) + } binding.closeButton.setOnClickListener { dismiss() } diff --git a/app/src/main/java/com/lukas/music/util/UIUtil.kt b/app/src/main/java/com/lukas/music/util/UIUtil.kt index 51d6026..5b7dbe3 100644 --- a/app/src/main/java/com/lukas/music/util/UIUtil.kt +++ b/app/src/main/java/com/lukas/music/util/UIUtil.kt @@ -114,5 +114,6 @@ ) spinnerSetupMain(arrayAdapter, target.get().ordinal) { target.set(items[it]) + callback(it) } } \ No newline at end of file diff --git a/app/src/main/res/layout/fragment_edit_instrument.xml b/app/src/main/res/layout/fragment_edit_instrument.xml index 71d616a..2d5cf09 100644 --- a/app/src/main/res/layout/fragment_edit_instrument.xml +++ b/app/src/main/res/layout/fragment_edit_instrument.xml @@ -61,7 +61,7 @@ android:id="@+id/close_button" android:layout_width="wrap_content" android:layout_height="wrap_content" - android:layout_marginTop="32dp" + android:layout_marginTop="16dp" android:layout_marginBottom="16dp" android:clickable="true" android:contentDescription="@string/close" @@ -69,7 +69,7 @@ app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toStartOf="parent" - app:layout_constraintTop_toBottomOf="@+id/volumeSeek" /> + app:layout_constraintTop_toBottomOf="@+id/voiceSelection" /> + + + + (beats) { val chordProgression = ChordProgression() @@ -32,12 +32,25 @@ } } + var root: Note = root + set(value) { + field = value + stopAllInstruments() + } + + private fun stopAllInstruments() { + for (instrument in Instrument.instruments) { + instrument.stop() + } + } + init { for (i in 0 until beats) { this += i } wraparoundListeners += { chordProgression.step() + stopAllInstruments() } } diff --git a/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt new file mode 100644 index 0000000..8f43cac --- /dev/null +++ b/app/src/main/java/com/lukas/music/song/voice/ChordVoice.kt @@ -0,0 +1,27 @@ +/* + * Copyright (C) 2022 Lukas Eisenhauer + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or(at your option) any later version. + * + * This program is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + */ + +package com.lukas.music.song.voice + +import com.lukas.music.instruments.Instrument +import com.lukas.music.song.note.Note + +class ChordVoice(instrument: Instrument) : Voice(instrument) { + override var noteActive: Array> = arrayOf( + Array(3) { false }, + Array(3) { true }, + Array(3) { false }, + Array(3) { true }, + ) + + override fun getNotes(root: Note, chordNotes: Array): Array { + return chordNotes + } +} \ No newline at end of file diff --git a/app/src/main/java/com/lukas/music/song/voice/Voice.kt b/app/src/main/java/com/lukas/music/song/voice/Voice.kt index 1b3ead1..42865a5 100644 --- a/app/src/main/java/com/lukas/music/song/voice/Voice.kt +++ b/app/src/main/java/com/lukas/music/song/voice/Voice.kt @@ -12,6 +12,7 @@ import com.lukas.music.instruments.Instrument import com.lukas.music.song.note.Note +import kotlin.reflect.KClass abstract class Voice(val instrument: Instrument) { abstract var noteActive: Array> @@ -33,4 +34,13 @@ instrument.startNote(note) } } + + companion object { + val DEFAULT_VOICES = listOf>( + BassVoice::class, + ChordVoice::class, + ) + + val DEFAULT_VOICE_NAMES = listOf("Bass", "Chord") + } } \ No newline at end of file diff --git a/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt b/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt index 16aeaca..cca8ddd 100644 --- a/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt +++ b/app/src/main/java/com/lukas/music/ui/fragments/EditInstrumentFragment.kt @@ -20,6 +20,7 @@ import com.lukas.music.databinding.FragmentEditInstrumentBinding import com.lukas.music.instruments.Instrument import com.lukas.music.instruments.Waveform +import com.lukas.music.song.voice.Voice import com.lukas.music.ui.adapters.InstrumentViewHolder import com.lukas.music.util.setup import com.lukas.music.util.smartSetup @@ -51,6 +52,12 @@ binding.volumeText.text = "volume: $it%" instrument.volume = it.toFloat() / 100f } + binding.voiceSelection.setup( + Voice.DEFAULT_VOICE_NAMES, + Voice.DEFAULT_VOICES.indexOf(instrument.voice::class) + ) { + instrument.voice = Voice.DEFAULT_VOICES[it].constructors.first().call(instrument) + } binding.closeButton.setOnClickListener { dismiss() } diff --git a/app/src/main/java/com/lukas/music/util/UIUtil.kt b/app/src/main/java/com/lukas/music/util/UIUtil.kt index 51d6026..5b7dbe3 100644 --- a/app/src/main/java/com/lukas/music/util/UIUtil.kt +++ b/app/src/main/java/com/lukas/music/util/UIUtil.kt @@ -114,5 +114,6 @@ ) spinnerSetupMain(arrayAdapter, target.get().ordinal) { target.set(items[it]) + callback(it) } } \ No newline at end of file diff --git a/app/src/main/res/layout/fragment_edit_instrument.xml b/app/src/main/res/layout/fragment_edit_instrument.xml index 71d616a..2d5cf09 100644 --- a/app/src/main/res/layout/fragment_edit_instrument.xml +++ b/app/src/main/res/layout/fragment_edit_instrument.xml @@ -61,7 +61,7 @@ android:id="@+id/close_button" android:layout_width="wrap_content" android:layout_height="wrap_content" - android:layout_marginTop="32dp" + android:layout_marginTop="16dp" android:layout_marginBottom="16dp" android:clickable="true" android:contentDescription="@string/close" @@ -69,7 +69,7 @@ app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toStartOf="parent" - app:layout_constraintTop_toBottomOf="@+id/volumeSeek" /> + app:layout_constraintTop_toBottomOf="@+id/voiceSelection" /> + + + + Instrument name: close this menu Waveform: + Voice: \ No newline at end of file