Redesign UI with dropdown sound selection
Major UI Overhaul: - Replace individual buttons with dropdown selectors - New "Sound Assignment" card with 3 dropdowns: * Greeting Sound (plays on pickup) * Button Sound (plays when button pressed) * Recording Beep (plays before recording) - Rename "Greeting Messages" to "Available Sounds" - Show sound usage badges (⭐🔘📣) in sound list - Cleaner, more intuitive interface Benefits: - Easier to see which sound is assigned where - One click to change assignments - Less clutter with fewer buttons - Shows duration in dropdown options - Better visual hierarchy Template v1.5.0 - will auto-regenerate on restart 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -81,7 +81,7 @@ BACKUP_ON_WRITE = BACKUP_CONFIG.get('backup_on_write', True)
|
||||
WEB_PORT = SYS_CONFIG['web']['port']
|
||||
|
||||
# Template version - increment this when HTML template changes
|
||||
TEMPLATE_VERSION = "1.4.0" # Updated: Added recording beep sound feature
|
||||
TEMPLATE_VERSION = "1.5.0" # Updated: Redesigned sound selection with dropdowns
|
||||
|
||||
# Flask app
|
||||
app = Flask(__name__)
|
||||
@@ -1176,7 +1176,28 @@ def main():
|
||||
.upload-label:hover {
|
||||
background: #5568d3;
|
||||
}
|
||||
|
||||
|
||||
.sound-selector {
|
||||
width: 100%;
|
||||
padding: 12px;
|
||||
font-size: 1em;
|
||||
border: 2px solid #e5e7eb;
|
||||
border-radius: 8px;
|
||||
background: white;
|
||||
cursor: pointer;
|
||||
transition: border-color 0.3s;
|
||||
}
|
||||
|
||||
.sound-selector:hover {
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
.sound-selector:focus {
|
||||
outline: none;
|
||||
border-color: #667eea;
|
||||
box-shadow: 0 0 0 3px rgba(102, 126, 234, 0.1);
|
||||
}
|
||||
|
||||
.btn {
|
||||
padding: 10px 20px;
|
||||
border: none;
|
||||
@@ -1555,20 +1576,62 @@ def main():
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Greeting Messages Card -->
|
||||
<!-- Sound Assignment Card -->
|
||||
<div class="card">
|
||||
<h2>🎵 Greeting Messages</h2>
|
||||
<h2>🎵 Sound Assignment</h2>
|
||||
|
||||
<div class="alert alert-info">
|
||||
ℹ️ Active greeting: <strong>{{ active_greeting }}</strong>
|
||||
{% if extra_button_enabled %}
|
||||
<br>🔘 Extra button sound: <strong>{{ extra_button_sound }}</strong>
|
||||
{% endif %}
|
||||
<div style="padding: 20px; border-bottom: 1px solid #e5e7eb;">
|
||||
<h3 style="margin: 0 0 15px 0; font-size: 1.1em; color: #333;">⭐ Greeting Sound</h3>
|
||||
<p style="margin-bottom: 10px; color: #6b7280; font-size: 0.9em;">
|
||||
Plays when handset is picked up
|
||||
</p>
|
||||
<select id="greeting-selector" class="sound-selector" onchange="setActiveGreeting(this.value)">
|
||||
{% for greeting in greetings %}
|
||||
<option value="{{ greeting.filename }}" {% if greeting.is_active %}selected{% endif %}>
|
||||
{{ greeting.filename }} ({{ "%.1f"|format(greeting.duration) }}s)
|
||||
</option>
|
||||
{% endfor %}
|
||||
</select>
|
||||
</div>
|
||||
|
||||
{% if extra_button_enabled %}
|
||||
<div style="padding: 20px; border-bottom: 1px solid #e5e7eb;">
|
||||
<h3 style="margin: 0 0 15px 0; font-size: 1.1em; color: #333;">🔘 Button Sound</h3>
|
||||
<p style="margin-bottom: 10px; color: #6b7280; font-size: 0.9em;">
|
||||
Plays when extra button is pressed during recording
|
||||
</p>
|
||||
<select id="button-selector" class="sound-selector" onchange="setExtraButtonSound(this.value)">
|
||||
{% for greeting in greetings %}
|
||||
<option value="{{ greeting.filename }}" {% if greeting.is_button_sound %}selected{% endif %}>
|
||||
{{ greeting.filename }} ({{ "%.1f"|format(greeting.duration) }}s)
|
||||
</option>
|
||||
{% endfor %}
|
||||
</select>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<div style="padding: 20px;">
|
||||
<h3 style="margin: 0 0 15px 0; font-size: 1.1em; color: #333;">📣 Recording Beep</h3>
|
||||
<p style="margin-bottom: 10px; color: #6b7280; font-size: 0.9em;">
|
||||
Plays after greeting to signal recording start
|
||||
</p>
|
||||
<select id="beep-selector" class="sound-selector" onchange="setBeepSound(this.value)">
|
||||
{% for greeting in greetings %}
|
||||
<option value="{{ greeting.filename }}" {% if greeting.is_beep_sound %}selected{% endif %}>
|
||||
{{ greeting.filename }} ({{ "%.1f"|format(greeting.duration) }}s)
|
||||
</option>
|
||||
{% endfor %}
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Available Sounds Card -->
|
||||
<div class="card">
|
||||
<h2>🔊 Available Sounds</h2>
|
||||
|
||||
<div class="upload-section">
|
||||
<p style="margin-bottom: 15px; color: #6b7280;">
|
||||
Upload WAV files to play when the handset is picked up
|
||||
Upload WAV audio files for greetings, button sounds, and beeps
|
||||
</p>
|
||||
<form id="upload-form" enctype="multipart/form-data">
|
||||
<label for="soundfile" class="upload-label">
|
||||
@@ -1580,7 +1643,7 @@ def main():
|
||||
|
||||
<div class="button-group">
|
||||
<button class="btn btn-primary" onclick="uploadGreeting()" id="upload-btn" disabled>
|
||||
⬆️ Upload Greeting(s)
|
||||
⬆️ Upload Sound(s)
|
||||
</button>
|
||||
<button class="btn btn-secondary" onclick="restoreDefault()">
|
||||
🔄 Generate Default Dial Tone
|
||||
@@ -1588,60 +1651,32 @@ def main():
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Greetings List -->
|
||||
<!-- Sounds List -->
|
||||
{% if greetings %}
|
||||
<h3 style="margin-top: 30px; margin-bottom: 15px; color: #333;">Available Greetings</h3>
|
||||
<h3 style="margin-top: 30px; margin-bottom: 15px; color: #333;">Uploaded Sounds</h3>
|
||||
<div class="recordings-grid">
|
||||
{% for greeting in greetings %}
|
||||
<div class="recording-item {% if greeting.is_active %}active-greeting{% endif %}" id="greeting-{{ loop.index }}">
|
||||
<div class="recording-item" id="greeting-{{ loop.index }}">
|
||||
<div class="recording-info">
|
||||
<h3>
|
||||
{% if greeting.is_active %}⭐{% endif %}
|
||||
{% if greeting.is_button_sound and extra_button_enabled %}🔘{% endif %}
|
||||
{{ greeting.filename }}
|
||||
</h3>
|
||||
<h3>{{ greeting.filename }}</h3>
|
||||
<div class="recording-meta">
|
||||
📅 {{ greeting.date }} |
|
||||
⏱️ {{ "%.1f"|format(greeting.duration) }}s |
|
||||
💾 {{ "%.2f"|format(greeting.size_mb) }} MB
|
||||
</div>
|
||||
<div style="margin-top: 5px; font-size: 0.85em; color: #667eea;">
|
||||
{% if greeting.is_active %}⭐ Active Greeting{% endif %}
|
||||
{% if greeting.is_button_sound and extra_button_enabled %}{% if greeting.is_active %} | {% endif %}🔘 Button Sound{% endif %}
|
||||
{% if greeting.is_beep_sound %}{% if greeting.is_active or greeting.is_button_sound %} | {% endif %}📣 Beep Sound{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
<div class="recording-actions">
|
||||
<button class="btn btn-success" onclick="playAudio('greeting', '{{ greeting.filename }}')">
|
||||
▶️ Play
|
||||
</button>
|
||||
{% if not greeting.is_active %}
|
||||
<button class="btn btn-primary" onclick="setActiveGreeting('{{ greeting.filename }}')">
|
||||
⭐ Set Active
|
||||
</button>
|
||||
{% if extra_button_enabled and not greeting.is_button_sound %}
|
||||
<button class="btn btn-primary" onclick="setExtraButtonSound('{{ greeting.filename }}')">
|
||||
🔘 Set Button
|
||||
</button>
|
||||
{% endif %}
|
||||
{% if not greeting.is_beep_sound %}
|
||||
<button class="btn btn-primary" onclick="setBeepSound('{{ greeting.filename }}')">
|
||||
📣 Set Beep
|
||||
</button>
|
||||
{% endif %}
|
||||
<button class="btn btn-danger" onclick="deleteGreeting('{{ greeting.filename }}', {{ loop.index }})">
|
||||
🗑️ Delete
|
||||
</button>
|
||||
{% else %}
|
||||
<button class="btn btn-secondary" disabled>
|
||||
✓ Active
|
||||
</button>
|
||||
{% if extra_button_enabled and not greeting.is_button_sound %}
|
||||
<button class="btn btn-primary" onclick="setExtraButtonSound('{{ greeting.filename }}')">
|
||||
🔘 Set Button
|
||||
</button>
|
||||
{% endif %}
|
||||
{% if not greeting.is_beep_sound %}
|
||||
<button class="btn btn-primary" onclick="setBeepSound('{{ greeting.filename }}')">
|
||||
📣 Set Beep
|
||||
</button>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
@@ -1649,7 +1684,7 @@ def main():
|
||||
{% else %}
|
||||
<div class="no-recordings" style="margin-top: 20px;">
|
||||
<p style="font-size: 2em; margin-bottom: 10px;">🎵</p>
|
||||
<p>No greeting messages uploaded yet. Upload your first greeting!</p>
|
||||
<p>No sounds uploaded yet. Upload your first sound file!</p>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user