Replace all emoji icons with Lucide SVGs, add accent color picker
- Replace all emoji characters across WebUI with inline Lucide SVG icons for cross-platform consistency (icon paths in icon-paths.js) - Add accent color picker popover with 9 preset colors + custom picker, persisted to localStorage, updates all CSS custom properties - Remove subtab separator line for cleaner look - Color badge icons with accent color for visual pop - Remove processing badge from target cards - Fix hardcoded #4CAF50 in FPS labels and active badges to use CSS vars - Replace CSS content emoji (▶) with pure CSS triangle Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -15,7 +15,12 @@ import { API_BASE, fetchWithAuth, escapeHtml } from '../core/api.js';
|
||||
import { t } from '../core/i18n.js';
|
||||
import { showToast, showConfirm } from '../core/ui.js';
|
||||
import { Modal } from '../core/modal.js';
|
||||
import { getValueSourceIcon, ICON_CLONE, ICON_EDIT, ICON_TEST } from '../core/icons.js';
|
||||
import {
|
||||
getValueSourceIcon,
|
||||
ICON_CLONE, ICON_EDIT, ICON_TEST,
|
||||
ICON_LED_PREVIEW, ICON_ACTIVITY, ICON_TIMER, ICON_MOVE_VERTICAL,
|
||||
ICON_MUSIC, ICON_TRENDING_UP, ICON_MAP_PIN, ICON_MONITOR, ICON_REFRESH,
|
||||
} from '../core/icons.js';
|
||||
import { loadPictureSources } from './streams.js';
|
||||
|
||||
export { getValueSourceIcon };
|
||||
@@ -58,7 +63,8 @@ export async function showValueSourceModal(editData) {
|
||||
const isEdit = !!editData;
|
||||
const titleKey = isEdit ? 'value_source.edit' : 'value_source.add';
|
||||
|
||||
document.getElementById('value-source-modal-title').textContent = t(titleKey);
|
||||
const titleIcon = isEdit ? getValueSourceIcon(editData.source_type) : getValueSourceIcon('static');
|
||||
document.getElementById('value-source-modal-title').innerHTML = `${titleIcon} ${t(titleKey)}`;
|
||||
document.getElementById('value-source-id').value = isEdit ? editData.id : '';
|
||||
document.getElementById('value-source-error').style.display = 'none';
|
||||
|
||||
@@ -471,13 +477,13 @@ export function createValueSourceCard(src) {
|
||||
|
||||
let propsHtml = '';
|
||||
if (src.source_type === 'static') {
|
||||
propsHtml = `<span class="stream-card-prop">📊 ${t('value_source.type.static')}: ${src.value ?? 1.0}</span>`;
|
||||
propsHtml = `<span class="stream-card-prop">${ICON_LED_PREVIEW} ${t('value_source.type.static')}: ${src.value ?? 1.0}</span>`;
|
||||
} else if (src.source_type === 'animated') {
|
||||
const waveLabel = src.waveform || 'sine';
|
||||
propsHtml = `
|
||||
<span class="stream-card-prop">〰️ ${escapeHtml(waveLabel)}</span>
|
||||
<span class="stream-card-prop">⏱️ ${src.speed ?? 10} cpm</span>
|
||||
<span class="stream-card-prop">↕️ ${src.min_value ?? 0}–${src.max_value ?? 1}</span>
|
||||
<span class="stream-card-prop">${ICON_ACTIVITY} ${escapeHtml(waveLabel)}</span>
|
||||
<span class="stream-card-prop">${ICON_TIMER} ${src.speed ?? 10} cpm</span>
|
||||
<span class="stream-card-prop">${ICON_MOVE_VERTICAL} ${src.min_value ?? 0}–${src.max_value ?? 1}</span>
|
||||
`;
|
||||
} else if (src.source_type === 'audio') {
|
||||
const audioSrc = _cachedAudioSources.find(a => a.id === src.audio_source_id);
|
||||
@@ -485,18 +491,18 @@ export function createValueSourceCard(src) {
|
||||
const audioSection = audioSrc ? (audioSrc.source_type === 'mono' ? 'audio-mono' : 'audio-multi') : 'audio-multi';
|
||||
const modeLabel = src.mode || 'rms';
|
||||
const audioBadge = audioSrc
|
||||
? `<span class="stream-card-prop stream-card-link" title="${escapeHtml(t('value_source.audio_source'))}" onclick="event.stopPropagation(); navigateToCard('streams','audio','${audioSection}','data-id','${src.audio_source_id}')">🎵 ${escapeHtml(audioName)}</span>`
|
||||
: `<span class="stream-card-prop" title="${escapeHtml(t('value_source.audio_source'))}">🎵 ${escapeHtml(audioName)}</span>`;
|
||||
? `<span class="stream-card-prop stream-card-link" title="${escapeHtml(t('value_source.audio_source'))}" onclick="event.stopPropagation(); navigateToCard('streams','audio','${audioSection}','data-id','${src.audio_source_id}')">${ICON_MUSIC} ${escapeHtml(audioName)}</span>`
|
||||
: `<span class="stream-card-prop" title="${escapeHtml(t('value_source.audio_source'))}">${ICON_MUSIC} ${escapeHtml(audioName)}</span>`;
|
||||
propsHtml = `
|
||||
${audioBadge}
|
||||
<span class="stream-card-prop">📈 ${modeLabel.toUpperCase()}</span>
|
||||
<span class="stream-card-prop">↕️ ${src.min_value ?? 0}–${src.max_value ?? 1}</span>
|
||||
<span class="stream-card-prop">${ICON_TRENDING_UP} ${modeLabel.toUpperCase()}</span>
|
||||
<span class="stream-card-prop">${ICON_MOVE_VERTICAL} ${src.min_value ?? 0}–${src.max_value ?? 1}</span>
|
||||
`;
|
||||
} else if (src.source_type === 'adaptive_time') {
|
||||
const pts = (src.schedule || []).length;
|
||||
propsHtml = `
|
||||
<span class="stream-card-prop">📍 ${pts} ${t('value_source.schedule.points')}</span>
|
||||
<span class="stream-card-prop">↕️ ${src.min_value ?? 0}–${src.max_value ?? 1}</span>
|
||||
<span class="stream-card-prop">${ICON_MAP_PIN} ${pts} ${t('value_source.schedule.points')}</span>
|
||||
<span class="stream-card-prop">${ICON_MOVE_VERTICAL} ${src.min_value ?? 0}–${src.max_value ?? 1}</span>
|
||||
`;
|
||||
} else if (src.source_type === 'adaptive_scene') {
|
||||
const ps = _cachedStreams.find(s => s.id === src.picture_source_id);
|
||||
@@ -507,11 +513,11 @@ export function createValueSourceCard(src) {
|
||||
else if (ps.stream_type === 'processed') { psSubTab = 'processed'; psSection = 'proc-streams'; }
|
||||
}
|
||||
const psBadge = ps
|
||||
? `<span class="stream-card-prop stream-card-link" onclick="event.stopPropagation(); navigateToCard('streams','${psSubTab}','${psSection}','data-stream-id','${src.picture_source_id}')" title="${escapeHtml(t('value_source.picture_source'))}">🖥️ ${escapeHtml(psName)}</span>`
|
||||
: `<span class="stream-card-prop">🖥️ ${escapeHtml(psName)}</span>`;
|
||||
? `<span class="stream-card-prop stream-card-link" onclick="event.stopPropagation(); navigateToCard('streams','${psSubTab}','${psSection}','data-stream-id','${src.picture_source_id}')" title="${escapeHtml(t('value_source.picture_source'))}">${ICON_MONITOR} ${escapeHtml(psName)}</span>`
|
||||
: `<span class="stream-card-prop">${ICON_MONITOR} ${escapeHtml(psName)}</span>`;
|
||||
propsHtml = `
|
||||
${psBadge}
|
||||
<span class="stream-card-prop">🔄 ${src.scene_behavior || 'complement'}</span>
|
||||
<span class="stream-card-prop">${ICON_REFRESH} ${src.scene_behavior || 'complement'}</span>
|
||||
`;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user