Compare commits

..

2 Commits

Author SHA1 Message Date
Rob Canning 434f10dfdc fill recorder with pause functionality now added 2024-03-06 13:08:40 +01:00
Rob Canning 3053079051 manual track selection via TK GUI 2024-03-02 11:09:53 +01:00
4 changed files with 182 additions and 304 deletions

View File

@ -1,6 +1,16 @@
<!DOCTYPE html>
<html lang="en">
<head>
<!-- Google tag (gtag.js) -->
<script async src="https://www.googletagmanager.com/gtag/js?id=G-KYQSVBZSME"></script>
<script>
window.dataLayer = window.dataLayer || [];
function gtag(){dataLayer.push(arguments);}
gtag('js', new Date());
gtag('config', 'G-KYQSVBZSME');
</script>
<title>{{show_name}}</title>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
@ -35,93 +45,39 @@
</div>
<header class="site-navbar py-4 absolute transparent" role="banner">
<div class="container">
<div class="row align-items-center">
<!-- <div class="col-3" data-aos="fade-down"> -->
<!-- <h1><a href="index.html" class="text-white h2">{{show_name}}</a></h1> -->
<!-- </div> -->
<div class="col-9" data-aos="fade-down">
<nav class="site-navigation position-relative text-right text-md-right" role="navigation">
<div class="d-inline-block ml-md-0 mr-auto py-3"><a href="#" class="site-menu-toggle js-menu-toggle text-white"><span class="icon-menu h3"></span></a></div>
<ul class="site-menu js-clone-nav d-none">
<li class="has-children">
<a href="index.html">Home</a>
<ul class="dropdown arrow-top">
<li><a href="#">Menu One</a></li>
<li><a href="#">Menu Two</a></li>
<li><a href="#">Menu Three</a></li>
<li class="has-children">
<a href="#">Sub Menu</a>
<ul class="dropdown">
<li><a href="#">Menu One</a></li>
<li><a href="#">Menu Two</a></li>
<li><a href="#">Menu Three</a></li>
</ul>
</li>
</ul>
</li>
<li class="has-children">
<a href="#">Dropdown</a>
<ul class="dropdown arrow-top">
<li><a href="#">Menu One</a></li>
<li><a href="#">Menu Two</a></li>
<li><a href="#">Menu Three</a></li>
</ul>
</li>
<li class="active"><a href="about.html">About</a></li>
<li><a href="contact.html">Contact</a></li>
</ul>
</nav>
</div>
</div>
</div>
</header>
<div class="site-blocks-cover overlay inner-page-cover" style="background-image: url({{episode_image}});" data-aos="fade" data-stellar-background-ratio="0.5">
<div class="container">
<div class="row align-items-center justify-content-center text-center">
<div class="col-md-8" style="background-color: rgba(0,0,0,0.5)" data-aos="fade-up" data-aos-delay="400">
<h2 style="background-color: black;" class="text-white font-weight-light mb-2 display-4">{{show_name}} | Episode #{{episode_number}} </h2>
<h2 class="text-white font-weight-light mb-2 display-4">{{show_name}} | Episode #{{episode_number}} </h2>
<p class="text-white font-weight-light">Latest Episode: #{{episode_number}} with music from: {{episode_artists}}</p>
<div class="text-white mb-3"><span class="text-white" style="color: white; background-color: black;" > Hosted by: {{episode_author}} | First broadcast: {{episode_date}} | <br> Total running time: {{episode_duration}}</small></span></div>
</div>
</div>
</div>
</div>
<!-- <div class="player mb-2"> -->
<audio id="player2" preload="none" controls style="max-width: 30%">
<source src="show.mp3" type="audio/mp3">
</audio>
<!-- </div> -->
<div class="container site-section">
<div class="text-white mb-4"><span class="text-white">Presented by: {{episode_author}} / Zavod Rizoma | {{episode_date}}</span>
</div>
<div class="text-white mb-3">
<span class="text-white" style="" >
Produced by Zavod Rizoma, Presented by: {{episode_author}}
<br> First broadcast: {{episode_date}}
<br> Total running time: {{episode_duration}}
</small>
</span>
</div>
</div>
</div>
</div>
</div>
<!-- <div class="container site-section"> -->
<div class="row justify-content-center">
<div class="col-md-12">
<h2>{{show_name}} | Episode #{{episode_number}} | {{episode_date}}</h2>
<div class="player mb-5">
<audio id="player2" preload="none" controls style="max-width: 100%">
<source src="show.mp3" type="audio/mp3">
</audio>
</div>
<em>Playtime: {{episode_duration}} | Show presented by: {{episode_author}} | First broadcast: {{episode_date}} | {{show_url}}</em>
<!-- {% for track in episode_playlist[0:] %} -->
<!-- <p><b> {{track}} </b> </p> -->
<!-- {% endfor %} -->
<table class="table table-striped">
<!-- <img src="{{episode_image}}" width="500"/> TODO MAKE THIS PRETTY -->
<!-- <TD class="c1"><IMG src="favicon.ico"></TD> -->
@ -141,7 +97,7 @@
<TD class="c1"><i>{{track[1]}}</i></TD>
<TD class="c2">{{track[2]}}</TD>
<TD class="c3">{{track[3]}}</TD>
<TD class="c4">{{track[4]}}</TD>
<TD class="//c4">{{track[4]}}</TD>
<TD class="c5">{{track[5]}}</TD>
<TD class="c5">{{track[6]}}</T>
@ -156,12 +112,11 @@
<p><a href="../../index.html" class="btn btn-primary btn-sm py-3 px-4 small">Back to Episode List</a></p>
</div>
</div>
</div>
</div>
</div>
<!-- </div> -->
<footer class="site-footer">
@ -296,15 +251,6 @@
</div>
</div>
<div class="row pt-5 mt-5 text-center">
<div class="col-md-12">
<p>
<!-- Link back to Colorlib can't be removed. Template is licensed under CC BY 3.0. -->
Copyright &copy;<script data-cfasync="false" src="/cdn-cgi/scripts/5c5dd728/cloudflare-static/email-decode.min.js"></script><script>document.write(new Date().getFullYear());</script> All rights reserved | This template is made with <i class="icon-heart-o" aria-hidden="true"></i> by <a href="https://colorlib.com" target="_blank" >Colorlib</a>
<!-- Link back to Colorlib can't be removed. Template is licensed under CC BY 3.0. -->
</p>
</div>
</div>
</div>
</footer>

View File

@ -2,6 +2,16 @@
<html lang="en">
<head>
<!-- Google tag (gtag.js) -->
<script async src="https://www.googletagmanager.com/gtag/js?id=G-KYQSVBZSME"></script>
<script>
window.dataLayer = window.dataLayer || [];
function gtag(){dataLayer.push(arguments);}
gtag('js', new Date());
gtag('config', 'G-KYQSVBZSME');
</script>
<title>{{show_name}}</title>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
@ -35,77 +45,18 @@
</div>
<header class="site-navbar py-4 absolute transparent" role="banner">
<div class="container">
<div class="row align-items-center">
<!-- <div class="col-3" data-aos="fade-down"> -->
<!-- <h1><a href="#" class="text-white h2">{{show_name}}</a></h1> -->
<!-- </div> -->
<div class="col-9" data-aos="fade-down">
<nav class="site-navigation position-relative text-right text-md-right" role="navigation">
<div class="d-inline-block ml-md-0 mr-auto py-3"><a href="#" class="site-menu-toggle js-menu-toggle text-white"><span class="icon-menu h3"></span></a></div>
<ul class="site-menu js-clone-nav d-none">
<li class="has-children active">
<a href="index.html">Home</a>
<ul class="dropdown arrow-top">
<li><a href="#">Menu One</a></li>
<li><a href="#">Menu Two</a></li>
<li><a href="#">Menu Three</a></li>
<li class="has-children">
<a href="#">Sub Menu</a>
<ul class="dropdown">
<li><a href="#">Menu One</a></li>
<li><a href="#">Menu Two</a></li>
<li><a href="#">Menu Three</a></li>
</ul>
</li>
</ul>
</li>
<li class="has-children">
<a href="#">Dropdown</a>
<ul class="dropdown arrow-top">
<li><a href="#">Menu One</a></li>
<li><a href="#">Menu Two</a></li>
<li><a href="#">Menu Three</a></li>
</ul>
</li>
<li><a href="about.html">About</a></li>
<li><a href="contact.html">Contact</a></li>
</ul>
</nav>
</div>
</div>
</div>
</header>
<div class="site-blocks-cover overlay" style="background-image: url(episode/{{episode_number}}/{{episode_image}});" data-aos="fade" data-stellar-background-ratio="0.5">
<div class="container">
<div class="row align-items-center justify-content-center text-center">
<div class="col-md-12" data-aos="fade-up" data-aos-delay="400">
<h2 class="tex font-weight-light mb-2 display-4">The Podcast {{show_name}}!</h2>
<p class="tex font-weight-light mb-2 display-4">The best alternative music from Slovenia, every week.</p>
<div class="col-md-12" style="background-color: rgba(0,0,0, 0.7)" data-aos="fade-up" data-aos-delay="400">
<h2 class="tex font-weight-light mb-2 display-4" style="margin:0; padding-bottom:0; margin-bottom:0">The Podcast {{show_name}}!</h2>
<p class="tex font-weight-light mb-2 display-4">The best alternative music from Slovenia, every week.</p>
<p class="text-white font-weight-light" >Latest Episode: #{{episode_number}} with music from: {{episode_artists}}</p>
<p><a href="episode/{{episode_number}}/index.html" class="btn btn-primary btn-sm py-3 px-4 small">Episode #{{episode_number}} Details and Player</a></p>
<div class="text-white mb-4"><span class="text-white">Produced by Zavod Rizoma and Presented by: {{episode_author}} {{episode_date}}</span>
<p class="text-white font-weight-light" >Latest Episode: #{{episode_number}} with music from: {{episode_artists}}</p>
<p><a href="episode/{{episode_number}}/index.html" class="btn btn-primary btn-sm py-3 px-4 small">Episode #{{episode_number}} Details and Player</a></p>
<div class="text-white mb-4"><span class="text-white">Presented by: {{episode_author}} / Zavod Rizoma | {{episode_date}}</span>
<div class="player">
<audio id="player2" preload="none" controls style="max-width: 100%">
<source src="episode/{{episode_number}}/show.mp3" type="audio/mp3">
</audio>
</div>
</div>
</div>
</div>
</div>
@ -129,7 +80,7 @@
<h3 class="font-weight-light"><a href="episode/{{episode.episode_number}}/index.html">Episode: # {{episode.episode_number}} </a></h3>
<div class="text-white mb-3"><span class="text-black-opacity-05">
<small>Presented by Rob Canning <span class="sep">/</span> {{episode.episode_date}} <span class="sep">/</span> {{episode.episode_duration}}</small></span></div>
<small>Presented by Rob Canning <span class="sep">/</span> {{episode.episode_date}} <span class="sep">/</span> {{episode.episode_duration}}</small></span></div>
<p class="mb-4"><b>On this weeks show music from: {{episode.episode_artists}} </b> </p>
</div>
@ -368,31 +319,9 @@
You can also subscribe to our RSS feed via Soundcloud <a href="https://soundcloud.com/uho-podcast" class="pl-3 pr-3"><span class="icon-soundcloud"></span></a> or Youtube <a href="https://www.youtube.com/@uho.podcast" class="pl-3 pr-3"><span class="icon-youtube"></span></a>
</div>
<!-- <div class="mb-5"> -->
<!-- <h3 class="footer-heading mb-2">Subscribe Newsletter</h3> -->
<!-- <form action="#" method="post"> -->
<!-- <div class="input-group mb-3"> -->
<!-- <input type="text" class="form-control border-secondary text-white bg-transparent" placeholder="Enter Email" aria-label="Enter Email" aria-describedby="button-addon2"> -->
<!-- <div class="input-group-append"> -->
<!-- <button class="btn btn-primary" type="button" id="button-addon2">Send</button> -->
<!-- </div> -->
<!-- </div> -->
<!-- </form> -->
<!-- </div> -->
</div>
</div>
<div class="row pt-5 mt-5 text-center">
<div class="col-md-12">
<p>
<!-- Link back to Colorlib can't be removed. Template is licensed under CC BY 3.0. -->
Copyright &copy;<script data-cfasync="false" src="/cdn-cgi/scripts/5c5dd728/cloudflare-static/email-decode.min.js"></script><script>document.write(new Date().getFullYear());</script> All rights reserved | This template is made with <i class="icon-heart-o" aria-hidden="true"></i> by <a href="https://colorlib.com" target="_blank" >Colorlib</a>
<!-- Link back to Colorlib can't be removed. Template is licensed under CC BY 3.0. -->
</p>
</div>
</div>
</div>

View File

@ -40,7 +40,6 @@ episode_author="Rob Canning"
show_short_description = '''The UhO! podcast presents an eclectic selection of independent music from Slovenia. The show aims to deliver as broad a range of genres as possible; banging techno, sludge, math rock, contemporary classical, doom, free improvisation, noise music, glitch, jazz skronk, field recordings, ambient, drone....etc etc... whatever the genre, you can be sure you are listening to the latest and most innovative music on offer in this part of the world. Hosted and compiled by Rob Canning, the show is published weekly by Zavod Rizoma and is broadcast in Slovenia on FM by mariborski radio študent: MARŠ. It as also available as a podcast. Use our RSS feed or search for UhO Podcast where ever you subscribe to podcasts'''
episode_number = args.episode
input_date = args.date
episode_date = datetime.datetime.now().strftime("%Y-%m-%d")
@ -70,21 +69,27 @@ def set_episode_date(input_date):
return episode_date
def get_intro():
intropath = "audio/intros"
intro = random.choice(os.listdir(intropath))
#final_playlist.insert(0, str(os.path.abspath(intropath)) + "/" + str(intro))
return str(str(intropath) + "/" + str(intro))
def get_midshow_CTA():
midshow_path = "audio/midshow_CTA"
midshow_CTA = random.choice(os.listdir(midshow_path))
#final_playlist.insert(0, str(os.path.abspath(intropath)) + "/" + str(intro))
return str(str(midshow_path) + "/" + str(midshow_CTA))
def select_specific_track(conn, episode_number, episode_duration):
filename = fd.askopenfilename()
cursor = conn.cursor()
cursor.execute("SELECT * FROM MUSIC_LIBRARY WHERE path = ? ", (filename, ))
r = cursor.fetchone()
print(filename)
return r
def choose_a_track(conn, episode_number, ):
def choose_a_track(conn, episode_number, choice ):
# random or specific file depending on value of "choice" argument
print("adding a track")
global episode_duration
global track_count
@ -95,13 +100,13 @@ def choose_a_track(conn, episode_number, ):
min_track_dur = 2
cursor = conn.cursor()
cursor.execute("SELECT * FROM MUSIC_LIBRARY ORDER BY RANDOM() LIMIT 1 ;")
r = cursor.fetchone() # FETCH ONE RANDOM TRACK FROM THE DATABASE
print(r)
# TODO lookup path and get complete db record
#name= fd.askopenfilename()
#print(name)
if choice == 0: # randomly select from database
cursor.execute("SELECT * FROM MUSIC_LIBRARY ORDER BY RANDOM() LIMIT 1 ;")
r = cursor.fetchone() # FETCH ONE RANDOM TRACK FROM THE DATABASE
print(r)
else: # select a specific file from db via GUI
r = select_specific_track(conn, episode_number, episode_duration)
song = str(r[9])
track_label = str(r[1])
@ -132,7 +137,7 @@ def choose_a_track(conn, episode_number, ):
#artist_abreviated.append(art)
#print(artist_abreviated)
if not track_year: # where missing metadata give a dummy value
track_year = "0000"
track_year = "0000" # TODO fixme
e = Table('EPISODES')
track_number = '{:0>2}'.format(track_count)
@ -158,7 +163,6 @@ def choose_a_track(conn, episode_number, ):
def check_archive(track_path):
cursor = conn.cursor()
cursor.execute("SELECT * FROM EPISODES WHERE path = ?", (track_path,))
data=cursor.fetchone()
@ -172,7 +176,6 @@ def check_archive(track_path):
#TODO limit number of KM Compilations in new function
def check_for_KM_compilation(track_album):
"TODO fix me"
# check if album is played already on this episode - maybe last 2 episodes >= or similar
cursor = conn.cursor()
@ -190,7 +193,6 @@ def check_for_KM_compilation(track_album):
def check_album(track_album):
# check if album is played already on this episode - maybe last 2 episodes >= or similar
cursor = conn.cursor()
cursor.execute("SELECT * FROM EPISODES WHERE album = ? AND episode = ?", (track_album,episode_number))
@ -222,7 +224,6 @@ def check_artist(track_artist):
track_count = 1
def create_episode_playlist(conn, episode_number):
global episode_duration
global archive
global track_count
@ -242,7 +243,7 @@ def create_episode_playlist(conn, episode_number):
# 56 mins of audio rest for fillers - aprox.
while episode_duration < 56 * 60 and track_count <= 12 :
print(track_count)
choose_a_track(conn, episode_number)
choose_a_track(conn, episode_number, 0)
modify_playlist(conn, episode_number, episode_duration)
@ -252,6 +253,8 @@ def playlist_replace_track(conn, episode_number, episode_duration):
global track_count
cursor = conn.cursor()
track_to_replace = int(input(">>>>>>>>>> Which track number would you like to REPLACE? : "))
specific_or_random = int(input(">>>>>>>>>> with a specific (1) or random track (0) : "))
# delete the old track
cursor.execute('DELETE FROM EPISODES WHERE episode = {0} AND track_number={1}'\
.format(episode_number, track_to_replace ))
@ -259,18 +262,15 @@ def playlist_replace_track(conn, episode_number, episode_duration):
# this is where the index number comes from in the below choose_a_track function
track_count = track_to_replace
# insert the new track
choose_a_track(conn, episode_number)
choose_a_track(conn, episode_number, specific_or_random)
conn.commit()
# get the new episode time
cursor.execute('SELECT SUM(trackdur) FROM EPISODES WHERE EPISODE=? ', [episode_number])
episode_duration = cursor.fetchone()[0]
modify_playlist(conn, episode_number, episode_duration)
def playlist_add_track(conn, episode_number, episode_duration):
global track_count
cursor = conn.cursor()
#track_to_add = int(input(">>>>>>>>>> Where would you like to ADD the track? : "))
@ -320,7 +320,6 @@ def playlist_delete_track(conn, episode_number, episode_duration):
def playlist_shuffle_tracks(conn, episode_number, episode_duration):
os.system("clear")
# shuffle the episode
cursor = conn.cursor()
@ -352,7 +351,6 @@ def playlist_shuffle_tracks(conn, episode_number, episode_duration):
def playlist_preview_track(conn, episode_number, episode_duration):
cursor = conn.cursor()
# preview a track --------------------------------------
preview_track = input(">>>>>>>> Which track would you like to preview : ")
@ -364,7 +362,6 @@ def playlist_preview_track(conn, episode_number, episode_duration):
def modify_playlist(conn, episode_number, episode_duration):
cursor = conn.cursor()
cursor.execute('SELECT * FROM EPISODES WHERE EPISODE=? ORDER BY track_number ASC', [episode_number])
preview = cursor.fetchall()
@ -388,7 +385,8 @@ def modify_playlist(conn, episode_number, episode_duration):
(l)isten to track
(n)EW (playlist),
(s)HUFFLE
(r)EPLACE
(r)EPLACE random
(c) choose specific track
(d)ELETE
(a)DD
@ -404,6 +402,9 @@ def modify_playlist(conn, episode_number, episode_duration):
elif user_input == 'r':
playlist_replace_track(conn, episode_number, episode_duration)
elif user_input == 'c':
select_specific_track(conn, episode_number, episode_duration)
elif user_input == 'l':
playlist_preview_track(conn, episode_number, episode_duration)
@ -423,12 +424,9 @@ def modify_playlist(conn, episode_number, episode_duration):
# ----------------------------------------------------------------------
def combine_images(columns, space, images, variants:int):
global show_cover
print(images)
set_episode_date(input_date)
rows = len(images) // columns
if len(images) % columns:
@ -512,7 +510,6 @@ def combine_images(columns, space, images, variants:int):
# -------------------------------------------------------------------------------
def create_show_coverart(variants):
set_episode_date(input_date)
final_playlist = []
@ -640,10 +637,7 @@ def social_media_post():
''')
def create_animated_gif():
# filepaths
fp_in = "/home/rob/uho/html/episode/2/img/*.jpg".format(episode_number)
fp_out = "/home/rob/uho/html/episode/2/img/show_cover.gif"
@ -775,7 +769,6 @@ def create_podcast():
### ------------------------------------------------------------
def create_html_homepage_from_template():
# TODO "on this weeks show" variants fed to html from list here
set_episode_date(input_date)
@ -903,7 +896,6 @@ def parse_db_episode():
return output_from_parsed_template
def create_html_episode_from_template(episode_number, episode_duration):
set_episode_date(input_date)
output_from_parsed_template = parse_db_episode()
@ -1023,7 +1015,6 @@ def create_RSS_XML_from_template():
rss_page.write(output_from_parsed_template)
def main():
# playlist options
if args.playlist == "new":
@ -1077,4 +1068,3 @@ def main():
conn.close()
main()

View File

@ -72,7 +72,7 @@ episode_duration = 10
archive = []
# sqlite database connection
conn = sqlite3.connect("database/show.db")
conn = sqlite3.connect("database/uho_music.db")
fill_path = "archive/e/{0}/audio_fills".format(episode_number)
if not os.path.exists(fill_path):
@ -82,13 +82,59 @@ if not os.path.exists(fill_path):
#TODO scrape artist bio from bandcamp?
#TODO GET VARIATION PROMPT
def get_playlist_for_fill_recording(conn, episode_number, episode_duration):
def record_fill(episode_number):
cursor = conn.cursor()
cursor.execute('SELECT * FROM EPISODES WHERE EPISODE=? ORDER BY track_number ASC', [episode_number])
preview = cursor.fetchall()
num = input("Which TRACK # to record fill for: ")
for i in preview[int(num)-1:int(num)]:
print('''
POD TRACK#: {0}
TRACK: {2}
ARTIST: {3}
ALBUM: {1}
YEAR: {5}
LABEL: [{6}]
DURATION: {4}
GENRE: {8}
PATH:
{9}
COMMENT: {7}
'''\
.format('{:0>2}'.format(i[2]), i[4], i[5], i[6],\
i[7],i[9], i[11], i[12], i[8], i[10] ) )
in_or_out = input("hit 0 to record intro or 1 to record outro: ")
if in_or_out == "0":
the_file = "archive/e/{0}/audio_fills/{1}_in.wav".format(episode_number, num)
elif in_or_out == "1":
the_file = "archive/e/{0}/audio_fills/{1}_out.wav".format(episode_number, num)
else:
print("please select 0 or 1 (outro or intro).........")
print(the_file)
r = recorder(the_file)
p = player(the_file)
l = listener(r, p)
#os.system("clear")
print('............................Hold ctrl to record, press p to playback, press q to quit')
l.start() #keyboard listener is a thread so we start it here
l.join() #wait for the tread to terminate so the program doesn't instantly close
get_playlist_for_fill_recording(conn, episode_number)
def get_playlist_for_fill_recording(conn, episode_number):
cursor = conn.cursor()
cursor.execute('SELECT * FROM EPISODES WHERE EPISODE=? ORDER BY track_number ASC', [episode_number])
preview = cursor.fetchall()
cursor.execute('SELECT SUM(trackdur) FROM EPISODES WHERE EPISODE=? ', [episode_number])
episode_duration = cursor.fetchone()[0]
#episode_duration = cursor.fetchone()[0]
# os.system("clear")
print("\n>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>")
@ -100,74 +146,9 @@ def get_playlist_for_fill_recording(conn, episode_number, episode_duration):
print('| {0} | {3} ||| {2} ||| {1} ||| {5} ||| [{6}] ||| {4} |||\n'\
.format('{:0>2}'.format(i[2]), i[4], i[5], i[6],\
timedelta(seconds=round(i[7])), i[9], i[11] ) )
print(">> SELECT AN OPTION: >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>")
user_input = input('''
[l]isten to track
[r]ecord voice fill
>>>>>>>>>>>>>>>>>>>>>>>>>>> OR PRESS ENTER TO PROCEED................... : ''')
if user_input == 'l':
playlist_preview_track(conn, episode_number, episode_duration)
elif user_input == "r":
if fill == "out":
num = input("Which TRACK # to record OUTRO fill for : ")
the_file = "archive/e/{0}/audio_fills/{1}_out.wav".format(episode_number, num)
elif fill == "in":
num = input("Which TRACK # to record INTRO fill for : ")
the_file = "archive/e/{0}/audio_fills/{1}_in.wav".format(episode_number, num)
else:
print("must speficy in or out")
print(the_file)
r = recorder(the_file)
p = player(the_file)
l = listener(r, p)
#os.system("clear")
for i in preview[int(num)-1:int(num)]:
print('''
POD TRACK#: {0}
TRACK: {2}
ARTIST: {3}
ALBUM: {1}
YEAR: {5}
LABEL: [{6}]
DURATION: {4}
GENRE: {8}
PATH:
{9}
COMMENT: {7}
'''\
.format('{:0>2}'.format(i[2]), i[4], i[5], i[6],\
timedelta(seconds=round(i[7])), i[9], i[11], i[12], i[8], i[10] ) )
print('............................Hold ctrl to record, press p to playback, press q to quit')
l.start() #keyboard listener is a thread so we start it here
l.join() #wait for the tread to terminate so the program doesn't instantly close
record_fill(episode_number)
# todo implement a check box TUI showing track fills completed
get_playlist_for_fill_recording(conn, episode_number, 10)
else:
get_playlist_for_fill_recording(conn, episode_number, 10)
class player:
def __init__(self, wavfile):
self.wavfile = wavfile
@ -183,8 +164,8 @@ class player:
with wave.open(self.wavfile, 'rb') as wf:
p = pyaudio.PyAudio()
stream = p.open(format=p.get_format_from_width(wf.getsampwidth()),
input_device_index=4,
output_device_index=4,
input_device_index=13,
output_device_index=13,
channels=wf.getnchannels(),
rate=wf.getframerate(),
output=True)
@ -235,8 +216,8 @@ class recorder:
return (in_data, pyaudio.paContinue)
self.stream = self.p.open(format = self.dataformat,
input_device_index=4,
output_device_index=4,
input_device_index=13,
output_device_index=13,
channels = self.channels,
rate = self.rate,
input = True,
@ -254,6 +235,27 @@ class recorder:
self.recording = False
print('recording finished',end='')
def pause(self):
if self.recording:
self.stream.stop_stream()
#self.stream.close()
#self.wf.close()
#self.recording = False
print('recording paused',end='')
def resume(self):
if self.recording:
self.stream.start_stream()
#self.stream.close()
#self.wf.close()
#self.recording = False
print('recording paused',end='')
class listener(keyboard.Listener):
def __init__(self, recorder, player):
@ -266,12 +268,23 @@ class listener(keyboard.Listener):
pass
elif isinstance(key, keyboard.Key): #special key event
if key.ctrl and self.player.playing == 0:
#print("if ctrl")
self.recorder.start()
elif isinstance(key, keyboard.KeyCode): #alphanumeric key event
if key.char == 'o': #press p to puase
if self.recorder.recording:
self.recorder.pause()
if key.char == 'i': #press p to puaseif key.char == 'o': #press p to puase
if self.recorder.recording:
self.recorder.pause()
if self.recorder.recording:
self.recorder.resume()
if key.char == 'q': #press q to quit
if self.recorder.recording:
if self.recorder.recording:
self.recorder.stop()
return False #this is how you stop the listener thread
return False #this is how you stop the listener thread
if key.char == 'p' and not self.recorder.recording:
self.player.start()
@ -279,16 +292,16 @@ class listener(keyboard.Listener):
if key is None: #unknown event
pass
elif isinstance(key, keyboard.Key): #special key event
if key.ctrl:
self.recorder.stop()
elif isinstance(key, keyboard.KeyCode): #alphanumeric key event
pass
#if key.ctrl:
# self.recorder.pause()
elif isinstance(key, keyboard.KeyCode): #alphanumeric key event
if key.char == "z": # key z release stops recording
self.recorder.stop()
#pass
if __name__ == '__main__':
get_playlist_for_fill_recording(conn, episode_number, 10)
get_playlist_for_fill_recording(conn, episode_number)