dobutokO2 0.6.1.0 → 0.7.0.0
raw patch · 4 files changed
+247/−14 lines, 4 filesdep +mmsyn2
Dependencies added: mmsyn2
Files
- CHANGELOG.md +4/−0
- DobutokO/Sound.hs +229/−5
- README.markdown +11/−6
- dobutokO2.cabal +3/−3
CHANGELOG.md view
@@ -47,3 +47,7 @@ * Sixth version revised A. Fixed issue with 'signsFromString' function that leads to performance penalty and to cycling. +## 0.7.0.0 -- 2020-03-10++* Seventh version. Added new explicit dependency (mmsyn2) that earlier was implicit. Added the opportunity to define in how many times the amplitude+for the second lower note is greater than for the main one and to define the music intervals for the notes (if any). Some improvements for the documentation.
DobutokO/Sound.hs view
@@ -32,6 +32,7 @@ , uniqOberTonesV2 , uniqOberSoXSynth2 , uniqOberSoXSynthN3+ , uniqOberSoXSynthN4 -- *** Uses a file for information , uniqOberSoXSynthNGen , uniqOberSoXSynthNGen3@@ -50,13 +51,16 @@ , syllableStr , signsFromString , prependZeroes+ , intervalsFromString+ , dNote ) where +import CaseBi import Numeric import Control.Exception (onException) import System.Environment (getArgs) import Data.List (isPrefixOf,sort)-import Data.Maybe (isJust,fromJust)+import Data.Maybe (isJust,isNothing,fromJust) import Data.Char (isDigit) import qualified Data.Vector as V import System.Process@@ -66,6 +70,7 @@ import System.Directory import SoXBasics import Processing_mmsyn7ukr+import Melodics.Ukrainian -- | 'V.Vector' of musical notes in Hz. notes :: V.Vector Double@@ -329,6 +334,55 @@ if ampL1 < 0.01 then oberSoXSynthN2 n 0.01 time3 zs tts vec0 else oberSoXSynthN2 n ampL1 time3 zs tts vec0 +-- | Function to create a melody for the given arguments. 'String' is used to provide a rhythm. The main component of the sound includes the lower pure quint, which+-- can be in the same octave or in the one with the number lower by one. The first 'Double' argument from the range [0.01..1.0] is used as a maximum amplitude+-- for obertones. If it is set to 1.0 the obertones amplitudes are just the maximum ones, otherwise they are multiplied by the parameter and this results+-- in their becoming more silent ones. The second 'Double' argument is a basic sound duration. The default one is 0.5 (second). Please, check before executing+-- whether there is no \"x.wav\", \"test*\", \"result*\" and \"end.wav\" files in the current directory, because they can be overwritten.+-- The third 'String' argument is used to define the intervals for the notes if any.+-- The third 'Double' parameter basically is used to define in how many times the volume for the second lower note is less than the volume of+-- the main note. If it is rather great, it can signal that the volume for the second note obertones are greater than for the main note obetones.+-- The last one is experimental feature.+oberSoXSynthN3 :: Int -> Double -> Double -> Double -> String -> String -> String -> V.Vector Double -> IO ()+oberSoXSynthN3 n ampL time3 dAmpl zs tts vs vec0+ | compare ampL 0.01 /= LT && compare ampL 1.0 /= GT = + let (t, ws) = splitAt 1 . syllableStr n $ zs+ m = length ws+ zeroN = numVZeroesPre vec0+ v3 = intervalsFromString vs+ l = length vs+ v2 = V.map (\yy -> time3 * fromIntegral (yy * m) / fromIntegral (head t)) . V.fromList $ ws in V.imapM_ (\j x -> do + let note0 = closestNote x -- zs is obtained from the command line arguments+ note1 = dNote (V.unsafeIndex v3 (j `rem` l)) note0+ v0 = oberTones2 note0 tts+ v1 = if isNothing note1 then V.empty+ else oberTones2 (fromJust note1) tts+ oberSoXSynthHelpN vec = V.imapM_ (\i (noteN, amplN) -> readProcessWithExitCode (fromJust (showE "sox"))+ ["-r22050", "-n", "test" ++ prependZeroes zeroN (show (i + 2)) ++ ".wav", "synth", showFFloat (Just 4) (V.unsafeIndex v2 (j `rem` m)) $ show 0,"sine",+ showFFloat (Just 4) noteN $ show 0, "vol", showFFloat (Just 4) (amplN * ampL) $ show 0] "") vec+ oberSoXSynthHelpN2 vec = V.imapM_ (\i (noteN, amplN) -> readProcessWithExitCode (fromJust (showE "sox"))+ ["-r22050", "-n", "testQ" ++ prependZeroes zeroN (show (i + 2)) ++ ".wav", "synth", showFFloat (Just 4) (V.unsafeIndex v2 (j `rem` m)) $ show 0,+ "sine", showFFloat (Just 4) noteN $ show 0, "vol", showFFloat (Just 4) (if dAmpl * amplN * ampL > 1.0 then 1.0 else dAmpl * amplN * ampL) $+ show 0] "") vec + soxSynthHelpMain0 note01 = readProcessWithExitCode (fromJust (showE "sox")) ["-r22050", "-n", "testA" ++ prependZeroes zeroN "1" ++ ".wav",+ "synth", showFFloat (Just 4) (V.unsafeIndex v2 (j `rem` m)) $ show 0,"sine", showFFloat (Just 4) note01 $ show 0] ""+ soxSynthHelpMain1 note02 = readProcessWithExitCode (fromJust (showE "sox")) ["-r22050", "-n", "testB" +++ prependZeroes zeroN "1" ++ ".wav", "synth", showFFloat (Just 4) (V.unsafeIndex v2 (j `rem` m)) $ show 0,"sine", showFFloat (Just 4) note02 $+ show 0, "vol", showFFloat (Just 4) (if dAmpl > 1.0 then 1.0 else dAmpl) $ show 0] ""+ if isNothing note1 then do { soxSynthHelpMain0 note0+ ; oberSoXSynthHelpN v0 }+ else do { soxSynthHelpMain0 note0+ ; soxSynthHelpMain1 (fromJust note1)+ ; oberSoXSynthHelpN v0+ ; oberSoXSynthHelpN2 v1}+ paths0 <- listDirectory "."+ let paths = sort . filter (isPrefixOf "test") $ paths0+ _ <- readProcessWithExitCode (fromJust (showE "sox")) (["--combine", "mix"] ++ paths ++ ["result" ++ prependZeroes zeroN (show j) ++ ".wav","vol","0.3"]) ""+ mapM_ removeFile paths ) vec0+ | otherwise = let ampL1 = ampL - (fromIntegral . truncate $ ampL) in+ if ampL1 < 0.01 then oberSoXSynthN3 n 0.01 time3 dAmpl zs tts vs vec0+ else oberSoXSynthN3 n ampL1 time3 dAmpl zs tts vs vec0+ -- | Similar to 'oberSoXSynthN', but uses a sound file to obtain the information analogous to 'V.Vector' in the latter one. Besides, the function lifts -- the frequencies to the octave with the given by 'Int' parameter number (better to use from the range [1..8]). The first 'Double' argument from -- the range [0.01..1.0] is used as a maximum amplitude for obertones. If it is set to 1.0 the obertones amplitudes are just maximum ones,@@ -378,9 +432,38 @@ path2s <- listDirectory "." let paths3 = sort . filter (isPrefixOf "result") $ path2s _ <- readProcessWithExitCode (fromJust (showE "sox")) (paths3 ++ ["end.wav"]) ""- mapM_ removeFile paths3 - + mapM_ removeFile paths3 +-- | Similar to 'oberSoXSynthN2', but uses a sound file to obtain the information analogous to 'V.Vector' in the latter one. Besides, the function lifts+-- the frequencies to the octave with the given by 'Int' parameter number (better to use from the range [1..8]). The first 'Double' argument from+-- the range [0.01..1.0] is used as a maximum amplitude for obertones. If it is set to 1.0 the obertones amplitudes are just maximum ones,+-- otherwise they are multiplied by the parameter and this results in their becoming more silent ones.+-- The second 'Double' argument is a basic sound duration. The default one is 0.5 (second). Please, check before executing+-- whether there is no \"x.wav\", \"test*\", \"result*\" and \"end.wav\" files in the current directory, because they can be overwritten.+-- +-- For better usage the 'FilePath' should be a filepath for the .wav file.+-- The second 'String' argument is used to define signs of the harmonics coefficients in the generated sounds.+-- The third 'String' argument is used to define the intervals for the notes if any.+-- The third 'Double' parameter basically is used to define in how many times the volume for the second lower note is less than the volume of+-- the main note. If it is rather great, it can signal that the volume for the second note obertones are greater than for the main note obetones.+-- The last one is experimental feature.+oberSoXSynthNGen3 :: FilePath -> Int -> Double -> Double -> Double -> String -> String -> String -> IO ()+oberSoXSynthNGen3 file m ampL time3 dAmpl zs tts vs = do+ duration0 <- durationA file+ let n = truncate (duration0 / 0.001)+ vecA <- V.generateM n (\k -> do { (_, _, herr) <- readProcessWithExitCode (fromJust (showE "sox")) [file, "-n", "trim", showFFloat (Just 4)+ (fromIntegral k * 0.001) $ show 0, "0.001", "stat"] ""+ ; let line0s = lines herr+ noteN1 = takeWhile isDigit . dropWhile (not . isDigit) . concat . drop 13 . take 14 $ line0s+ ; if null noteN1 then return (11440::Int)+ else let noteN2 = read (takeWhile isDigit . dropWhile (not . isDigit) . concat . drop 13 . take 14 $ line0s)::Int in return noteN2 })+ let vecB = putInOctaveV m . V.map fromIntegral . V.filter (/= (11440::Int)) $ vecA+ oberSoXSynthN3 n ampL time3 dAmpl zs tts vs vecB+ path2s <- listDirectory "."+ let paths3 = sort . filter (isPrefixOf "result") $ path2s+ _ <- readProcessWithExitCode (fromJust (showE "sox")) (paths3 ++ ["end.wav"]) ""+ mapM_ removeFile paths3 + -- | Additional function to prepend zeroes to the given 'String'. The number of them are just that one to fulfill the length to the given 'Int' parameter. prependZeroes :: Int -> String -> String prependZeroes n xs @@ -527,6 +610,79 @@ if ampL1 < 0.01 then uniqOberSoXSynthN3 n 0.01 time3 zs wws tts vec0 else uniqOberSoXSynthN3 n ampL1 time3 zs wws tts vec0 +-- | Function to create a melody for the given arguments. The first 'String' is used to provide a rhythm. The second one -- to provide a timbre.+-- The timbre for another given text usually differs, but can be the same. This gives an opportunity to practically and quickly+-- synthesize differently sounding intervals. The first 'Double' argument from the range [0.01..1.0] is used as a maximum amplitude for obertones.+-- If it is set to 1.0 the obertones amplitudes are just maximum ones, otherwise they are multiplied by the parameter and this results in+-- their becoming more silent ones. The main component of the sound is in the given octave with a number given+-- by 'Int' parameter. Besides, another main component of the sound includes the lower pure quint, which can be in the same octave or in the one with+-- the number lower by one. The second 'Double' argument is a basic sound duration. The default one is 0.5 (second). Please, check before executing+-- whether there is no \"x.wav\", \"test*\", \"result*\" and \"end.wav\" files in the current directory, because they can be overwritten.+-- The third 'String' argument is used to define signs of the harmonics coefficients in the generated sounds.+-- The fourth 'String' argument is used to define the intervals for the notes if any.+-- The third 'Double' parameter basically is used to define in how many times the volume for the second lower note is less than the volume of+-- the main note. If it is rather great, it can signal that the volume for the second note obertones are greater than for the main note obetones.+-- The last one is experimental feature.+uniqOberSoXSynthN4 :: Int -> Double -> Double -> Double -> String -> String -> String -> String -> V.Vector Double -> IO ()+uniqOberSoXSynthN4 n ampL time3 dAmpl zs wws tts vs vec0+ | compare ampL 0.01 /= LT && compare ampL 1.0 /= GT =+ let (t, ws) = splitAt 1 . syllableStr n $ zs+ m = length ws+ zeroN = numVZeroesPre vec0+ v3 = intervalsFromString vs+ l = length vs+ v2 = V.map (\yy -> time3 * fromIntegral (yy * m) / fromIntegral (head t)) . V.fromList $ ws in V.imapM_ (\j x -> do + let note0 = closestNote x -- zs ? vec0 -- are they related to the one object? No, they are obtained from different sources.+ note1 = dNote (V.unsafeIndex v3 (j `rem` l)) note0+ v0 = uniqOberTonesV2 note0 wws tts+ v1 = if isNothing note1 then V.empty+ else uniqOberTonesV2 (fromJust note1) wws tts+ uniqOberSoXSynthHelpN vec = V.imapM_ (\i (noteN, amplN) -> readProcessWithExitCode (fromJust (showE "sox"))+ ["-r22050", "-n", "test" ++ prependZeroes zeroN (show (i + 2)) ++ ".wav", "synth", showFFloat (Just 4) (V.unsafeIndex v2 (j `rem` m)) $ show 0,"sine",+ showFFloat (Just 4) noteN $ show 0, "vol", showFFloat (Just 4) (amplN * ampL) $ show 0] "") vec+ uniqOberSoXSynthHelpN2 vec = V.imapM_ (\i (noteN, amplN) -> readProcessWithExitCode (fromJust (showE "sox"))+ ["-r22050", "-n", "testQ" ++ prependZeroes zeroN (show (i + 2)) ++ ".wav", "synth", showFFloat (Just 4) (V.unsafeIndex v2 (j `rem` m)) $ show 0,+ "sine", showFFloat (Just 4) noteN $ show 0, "vol", showFFloat (Just 4) (if dAmpl * amplN * ampL > 1.0 then 1.0 else dAmpl * amplN * ampL) $ show 0] "") vec + soxSynthHelpMain0 note01 = readProcessWithExitCode (fromJust (showE "sox")) ["-r22050", "-n", "testA" +++ prependZeroes zeroN "1" ++ ".wav", "synth", showFFloat (Just 4) (V.unsafeIndex v2 (j `rem` m)) $ show 0,"sine", showFFloat (Just 4) note01 $+ show 0] ""+ soxSynthHelpMain1 note02 = readProcessWithExitCode (fromJust (showE "sox")) ["-r22050", "-n", "testB" +++ prependZeroes zeroN "1" ++ ".wav", "synth", showFFloat (Just 4) (V.unsafeIndex v2 (j `rem` m)) $ show 0,"sine", showFFloat (Just 4) note02 $+ show 0, "vol", showFFloat (Just 4) (if dAmpl > 1.0 then 1.0 else dAmpl) $ show 0] ""+ if isNothing note1 then do { soxSynthHelpMain0 note0+ ; uniqOberSoXSynthHelpN v0 }+ else do { soxSynthHelpMain0 note0+ ; soxSynthHelpMain1 (fromJust note1)+ ; uniqOberSoXSynthHelpN v0+ ; uniqOberSoXSynthHelpN2 v1}+ paths0 <- listDirectory "."+ let paths = sort . filter (isPrefixOf "test") $ paths0+ _ <- readProcessWithExitCode (fromJust (showE "sox")) (["--combine", "mix"] ++ paths ++ ["result" ++ prependZeroes zeroN (show j) ++ ".wav","vol","0.3"]) ""+ mapM_ removeFile paths ) vec0+ | otherwise = let ampL1 = ampL - (fromIntegral . truncate $ ampL) in+ if ampL1 < 0.01 then uniqOberSoXSynthN4 n 0.01 time3 dAmpl zs wws tts vs vec0+ else uniqOberSoXSynthN4 n ampL1 time3 dAmpl zs wws tts vs vec0 ++-- | Function is used to get numbers of intervals from a Ukrainian 'String'. It is used internally in the 'uniqOberSoXSynthN4' function.+intervalsFromString :: String -> V.Vector Int+intervalsFromString vs = vStrToVInt . convertToProperUkrainian $ vs++vStrToVInt :: V.Vector String -> V.Vector Int+vStrToVInt = V.map strToInt++strToInt :: String -> Int+strToInt =+ getBFst' (0, V.fromList [("а", 12), ("б", 4), ("в", 7), ("г", 3), ("д", 4), ("дж", 5), ("дз", 5), ("е", 12), ("ж", 3), ("з", 8), ("и", 12), + ("й", 7), ("к", 10), ("л", 7), ("м", 7), ("н", 7), ("о", 12), ("п", 10), ("р", 7), ("с", 10), ("т", 2), ("у", 12), ("ф", 2), ("х", 2),+ ("ц", 11), ("ч", 11), ("ш", 1), ("і", 12), ("ґ", 9)]) ++-- | Function to get from the number of semi-tones and a note a 'Maybe' note for the second note if any. If there is no need to obtain such a note,+-- then the result is 'Nothing'.+dNote :: Int -> Double -> Maybe Double+dNote n note+ | n == 0 || compare note (V.unsafeIndex notes 0) == LT || compare note (V.unsafeIndex notes 107) == GT = Nothing+ | otherwise = Just (note / 2 ** (fromIntegral n / 12))+ -- | Similar to 'uniqOberSoXSynthN', but uses a sound file to obtain the information analogous to 'V.Vector' in the latter one. -- Besides, the function lifts the frequencies to the octave with the given by 'Int' parameter number (better to use from the range [1..8]). -- The first 'Double' argument from the range [0.01..1.0] is used as a maximum amplitude for obertones. If it is set to 1.0 the@@ -578,8 +734,39 @@ path2s <- listDirectory "." let paths3 = sort . filter (isPrefixOf "result") $ path2s _ <- readProcessWithExitCode (fromJust (showE "sox")) (paths3 ++ ["end.wav"]) ""- mapM_ removeFile paths3 + mapM_ removeFile paths3 +-- | Similar to 'uniqOberSoXSynthN', but uses a sound file to obtain the information analogous to 'V.Vector' in the latter one. +-- Besides, the function lifts the frequencies to the octave with the given by 'Int' parameter number (better to use from the range [1..8]).+-- The first 'Double' argument from the range [0.01..1.0] is used as a maximum amplitude for obertones. If it is set to 1.0 the+-- obertones amplitudes are just the maximum ones, otherwise they are multiplied by the parameter and this results in their becoming more silent ones.+-- The second 'Double' argument is a basic sound duration. The default one is 0.5 (second). Please, check before executing+-- whether there is no \"x.wav\", \"test*\", \"result*\" and \"end.wav\" files in the current directory, because they can be overwritten.+--+-- For better usage the 'FilePath' should be a filepath for the .wav file.+-- The third 'String' argument is used to define signs of the harmonics coefficients in the generated sounds.+-- The fourth 'String' argument is used to define the intervals for the notes if any.+-- The third 'Double' parameter basically is used to define in how many times the volume for the second lower note is less than the volume of+-- the main note. If it is rather great, it can signal that the volume for the second note obertones are greater than for the main note obetones.+-- The last one is experimental feature.+uniqOberSoXSynthNGen4 :: FilePath -> Int -> Double -> Double -> Double -> String -> String -> String -> String -> IO ()+uniqOberSoXSynthNGen4 file m ampL time3 dAmpl zs wws tts vs = do+ duration0 <- durationA file+ let n = truncate (duration0 / 0.001)+ vecA <- V.generateM n (\k -> do {+ (_, _, herr) <- readProcessWithExitCode (fromJust (showE "sox")) [file, "-n", "trim", show (fromIntegral k * 0.001),+ "0.001", "stat"] ""+ ; let line0s = lines herr+ noteN0 = takeWhile isDigit . dropWhile (not . isDigit) . concat . drop 13 . take 14 $ line0s+ ; if null noteN0 then return (11440::Int)+ else let noteN1 = read (takeWhile isDigit . dropWhile (not . isDigit) . concat . drop 13 . take 14 $ line0s)::Int in return noteN1 })+ let vecB = putInOctaveV m . V.map fromIntegral . V.filter (/= (11440::Int)) $ vecA+ uniqOberSoXSynthN4 n ampL time3 dAmpl zs wws tts vs vecB+ path2s <- listDirectory "."+ let paths3 = sort . filter (isPrefixOf "result") $ path2s+ _ <- readProcessWithExitCode (fromJust (showE "sox")) (paths3 ++ ["end.wav"]) ""+ mapM_ removeFile paths3 + -- | Function that actually makes processing in the @dobutokO2@ executable. Please, check before executing -- whether there is no \"x.wav\", \"test*\", \"result*\" and \"end.wav\" files in the current directory, because they can be overwritten. dobutokO2 :: IO ()@@ -607,12 +794,26 @@ ampL = read ampLS::Double time3 = read time2::Double oberSoXSynthNGen2 file octave1 ampL time3 (unwords . drop 2 $ args) tts- _ -> do+ "4" -> do [_,_,octave,ampLS,time2,wws,tts] <- mapM (recAndProcess file) (if exist2 then [0,2,3,4,5,6,7] else [1..7]) let octave1 = read octave::Int ampL = read ampLS::Double time3 = read time2::Double uniqOberSoXSynthNGen3 file octave1 ampL time3 (unwords . drop 2 $ args) wws tts+ "5" -> do+ [_,_,octave,ampLS,time2,tts,dAmpl0,vs] <- mapM (recAndProcess file) (if exist2 then [0,2,3,4,5,7,8,9] else [1,2,3,4,5,7,8,9])+ let octave1 = read octave::Int+ ampL = read ampLS::Double+ time3 = read time2::Double+ dAmpl = read dAmpl0::Double+ oberSoXSynthNGen3 file octave1 ampL time3 dAmpl (unwords . drop 2 $ args) tts vs+ _ -> do+ [_,_,octave,ampLS,time2,wws,tts,dAmpl0,vs] <- mapM (recAndProcess file) (if exist2 then [0,2,3,4,5,6,7,8,9] else [1..9])+ let octave1 = read octave::Int+ ampL = read ampLS::Double+ time3 = read time2::Double+ dAmpl = read dAmpl0::Double+ uniqOberSoXSynthNGen4 file octave1 ampL time3 dAmpl (unwords . drop 2 $ args) wws tts vs -- | Function records and processes the sound data needed to generate the \"end.wav\" file in the 'dobutokO2' function. Please, check before executing -- whether there is no \"x.wav\" file in the current directory, because it can be overwritten.@@ -715,6 +916,29 @@ putStrLn "The process was not successful may be because of the not valid data. Please, specify the valid data as requested." putStrLn "_______________________________________________________________________" recAndProcess file 7)+ | x == 8 = onException (do+ putStr "Please, specify in how many times the amplitude for the second lower note (if any) is greater than the amplitude for the main note. "+ putStrLn "The number is in the range [0.1..2.0]. The default one is 1.0"+ putStrLn "To use the default value, you can simply press Enter."+ dAmpl0 <- getLine+ if null dAmpl0 then return "1.0"+ else let dAmpl1 = (read (filter (\z -> isDigit z || z == '.') $ dAmpl0)::Double) in+ if compare dAmpl1 0.1 /= LT && compare dAmpl1 2.0 /= GT then return (showFFloat (Just 4) dAmpl1 $ show 0)+ else let mantissa = dAmpl1 - (fromIntegral . truncate $ dAmpl1)+ ceilP = (truncate dAmpl1::Int) `rem` 2 in+ if ceilP == 0 then return ("0." ++ (showFFloat (Just 4) mantissa $ show 0))+ else return $ show ceilP ++ "." ++ (showFFloat (Just 4) mantissa $ show 0)) (do+ putStrLn "The process was not successful may be because of the not valid data. Please, specify the valid data as requested."+ putStrLn "_______________________________________________________________________"+ recAndProcess file 8)+ | x == 9 = onException (do+ putStrLn "Please, input the Ukrainian text that will be used to define intervals to be used to produce the lower note for the given main one: "+ vs <- getLine+ if null vs then return "й"+ else return vs) (do+ putStrLn "The process was not successful may be because of the not valid data. Please, specify the valid data as requested."+ putStrLn "_______________________________________________________________________"+ recAndProcess file 9) | otherwise = onException (do putStrLn "Please, input the Ukrainian text that will be used to create a special timbre for the notes: " wws <- getLine
README.markdown view
@@ -13,23 +13,28 @@ For the executable you enter in the terminal: -dobutokO2 {1 | 2 | 3 | 4} {fileName} {Ukrainian text}+dobutokO2 {1 | 2 | 3 | 4 | 5 | 6} {fileName} {Ukrainian text} where filename is: the full name of the file to be recorded in the current directory or the full absolute path to the sound .wav file (or other one format that is supported by your SoX installation) to obtain sound information from. -If the first command line argument equals to "1" or "3" then the executable+If the first command line argument equals to "1", or "3", or "5", then the executable uses the oberTones funcions, so for the given parameters the obertones are the same for every call. The "3" adittionally gives an opportunity to specify the signs for the harmonics coefficients for obertones by additional-String. Otherwise, it uses uniqOberTones functions, which+String. And the "5" additionally to that one functionality provided by "3" gives+an opportunity to specify in how many times the amplitude for the second lower note+(if any) is greater, than the amplitude for the main note and specify the intervals+to be used for every note. Otherwise, the executable uses uniqOberTones functions, which can have different obertones because of the provided the second, additional,-text. The last one is used to generate the obertones. In such a case, another-text gives the other obertones. If you specify something else, except "1", or "2",-or "3", then the program uses uniqOberTones functions and (similarly to "3" option)+text. The third one is used to generate the obertones. In such a case, another+text gives the other obertones. If you specify something else, except "1", or "3",+or "5", then the program uses uniqOberTones functions and (similarly to "3" option) it uses additional String to define signs for the harmonics coefficients for obertones.+If you specify the "6" option, then the program behaves like for the "5" option,+but generates obertones using additional String. After the program executing (it takes some time) there is a file "end.wav" in the directory. This is the resulting melody generated.
dobutokO2.cabal view
@@ -2,7 +2,7 @@ -- documentation, see http://haskell.org/cabal/users-guide/ name: dobutokO2-version: 0.6.1.0+version: 0.7.0.0 synopsis: A program and a library to create experimental music from a mono audio and a Ukrainian text description: It can also create a timbre for the notes homepage: https://hackage.haskell.org/package/dobutokO2@@ -20,7 +20,7 @@ exposed-modules: Main, DobutokO.Sound -- other-modules: -- other-extensions:- build-depends: base >=4.7 && <4.14, vector >=0.11 && <0.14, process >=1.4 && <1.8, mmsyn3 >=0.1.4 && <1, mmsyn7s >=0.6.6 && <1, directory >=1.2.5 && <1.6, mmsyn7ukr >=0.15.3 && <1+ build-depends: base >=4.7 && <4.14, vector >=0.11 && <0.14, process >=1.4 && <1.8, mmsyn3 >=0.1.4 && <1, mmsyn7s >=0.6.6 && <1, directory >=1.2.5 && <1.6, mmsyn7ukr >=0.15.3 && <1, mmsyn2 >=0.1.7 && <1 -- hs-source-dirs: default-language: Haskell2010 @@ -28,6 +28,6 @@ main-is: Main.hs -- other-modules: -- other-extensions:- build-depends: base >=4.7 && <4.14, vector >=0.11 && <0.14, process >=1.4 && <1.8, mmsyn3 >=0.1.4 && <1, mmsyn7s >=0.6.6 && <1, directory >=1.2.5 && <1.6, mmsyn7ukr >=0.15.3 && <1+ build-depends: base >=4.7 && <4.14, vector >=0.11 && <0.14, process >=1.4 && <1.8, mmsyn3 >=0.1.4 && <1, mmsyn7s >=0.6.6 && <1, directory >=1.2.5 && <1.6, mmsyn7ukr >=0.15.3 && <1, mmsyn2 >=0.1.7 && <1 -- hs-source-dirs: default-language: Haskell2010