ва поисковых поля (Google и Яндекс) с логотипами, адаптивные, крупный шрифт, занимают всю ширину
This commit is contained in:
parent
a4f6dd4d93
commit
c3b0c19758
@ -12,6 +12,7 @@
|
|||||||
- Поддержка настройки времени кэширования погоды через weather.cache_ttl (минуты, по умолчанию 60)
|
- Поддержка настройки времени кэширования погоды через weather.cache_ttl (минуты, по умолчанию 60)
|
||||||
- В шапке вместо приветствия теперь крупно текущее время, дата на русском
|
- В шапке вместо приветствия теперь крупно текущее время, дата на русском
|
||||||
- Дата и время теперь на одной строке, одинакового размера и цвета, хорошо видны на тёмном фоне
|
- Дата и время теперь на одной строке, одинакового размера и цвета, хорошо видны на тёмном фоне
|
||||||
|
- Два поисковых поля (Google и Яндекс) с логотипами, адаптивные, крупный шрифт, занимают всю ширину
|
||||||
|
|
||||||
## [init] Стартовая инициализация структуры Flask-приложения
|
## [init] Стартовая инициализация структуры Flask-приложения
|
||||||
- Создана структура каталогов: templates/, static/
|
- Создана структура каталогов: templates/, static/
|
||||||
|
|||||||
@ -14,15 +14,30 @@
|
|||||||
<body style="--color-primary: #FFFDEA; --color-accent: #5c5c5c; --color-background: #1a1a1a;">
|
<body style="--color-primary: #FFFDEA; --color-accent: #5c5c5c; --color-background: #1a1a1a;">
|
||||||
<div id="root">
|
<div id="root">
|
||||||
<div class="Layout_Container__HIHX7">
|
<div class="Layout_Container__HIHX7">
|
||||||
<div><input type="text" class="SearchBar_SearchBar__MQiwu" placeholder="Поиск..."></div>
|
<div style="display:flex; flex-direction:row; align-items:center; gap:18px; margin-bottom:12px; width:100%;">
|
||||||
|
<form id="google-search" style="display:flex; align-items:center; gap:6px; flex:1 1 0;" onsubmit="event.preventDefault(); window.open('https://www.google.com/search?q='+encodeURIComponent(this.elements.q.value),'_blank');">
|
||||||
|
<img src="https://www.google.com/favicon.ico" alt="Google" width="24" height="24"/>
|
||||||
|
<input type="text" name="q" class="SearchBar_SearchBar__MQiwu" placeholder="Поиск Google..." autocomplete="off" style="width:100%; min-width:0; font-size:1.2em;"/>
|
||||||
|
</form>
|
||||||
|
<form id="yandex-search" style="display:flex; align-items:center; gap:6px; flex:1 1 0;" onsubmit="event.preventDefault(); window.open('https://yandex.ru/search/?text='+encodeURIComponent(this.elements.q.value),'_blank');">
|
||||||
|
<img src="https://yandex.ru/favicon.ico" alt="Yandex" width="24" height="24"/>
|
||||||
|
<input type="text" name="q" class="SearchBar_SearchBar__MQiwu" placeholder="Поиск Яндекс..." autocomplete="off" style="width:100%; min-width:0; font-size:1.2em;"/>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
<header class="Header_Header__GCJdR">
|
<header class="Header_Header__GCJdR">
|
||||||
<span class="Header_HeaderMain__oLoBB">
|
<span class="Header_HeaderMain__oLoBB">
|
||||||
<div style="display:flex; flex-direction:row; align-items:center; gap:12px;">
|
<div style="display:flex; flex-direction:row; align-items:center; gap:12px;">
|
||||||
<span style="font-size:1.1em; color: var(--color-primary);">{{ current_time }}</span>
|
<span style="font-size:1.6em; color: var(--color-primary);">{{ current_time }}</span>
|
||||||
<span style="font-size:1.1em; color: var(--color-primary);">{{ now }}</span>
|
<span style="font-size:1.6em; color: var(--color-primary);">{{ now }}</span>
|
||||||
</div>
|
</div>
|
||||||
<div class="WeatherWidget_WeatherWidget__3XlYt">
|
<div class="WeatherWidget_WeatherWidget__3XlYt" id="weather-area" style="cursor:pointer;">
|
||||||
<div><canvas id="weather-icon" width="50" height="50"></canvas></div>
|
<div>
|
||||||
|
{% if weather and weather.icon %}
|
||||||
|
<img src="{{ weather.icon if not weather.icon.startswith('//') else 'https:' + weather.icon }}" width="50" height="50" alt="icon"/>
|
||||||
|
{% else %}
|
||||||
|
<canvas id="weather-icon" width="50" height="50"></canvas>
|
||||||
|
{% endif %}
|
||||||
|
</div>
|
||||||
<div class="WeatherWidget_WeatherDetails__1y3CA">
|
<div class="WeatherWidget_WeatherDetails__1y3CA">
|
||||||
{% if weather %}
|
{% if weather %}
|
||||||
<span>{{ weather.temp }}°C</span>
|
<span>{{ weather.temp }}°C</span>
|
||||||
@ -85,6 +100,13 @@
|
|||||||
<div id="config-error" style="color:red;"></div>
|
<div id="config-error" style="color:red;"></div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div id="forecast-modal" style="display:none; position:fixed; z-index:2000; left:0; top:0; width:100vw; height:100vh; background:rgba(0,0,0,0.7); align-items:center; justify-content:center;">
|
||||||
|
<div style="background:#fff; color:#222; padding:24px; border-radius:8px; min-width:320px; max-width:90vw; max-height:90vh; display:flex; flex-direction:column; gap:12px;">
|
||||||
|
<h2 id="forecast-title">Прогноз</h2>
|
||||||
|
<div id="forecast-content" style="overflow-y:auto; max-height:60vh;"></div>
|
||||||
|
<button id="close-forecast-btn" style="padding:10px 24px; font-size:1.1em; align-self:flex-end;">Закрыть</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
<div class="NotificationCenter_NotificationCenter__Tfgzh" style="height: 0px;"></div>
|
<div class="NotificationCenter_NotificationCenter__Tfgzh" style="height: 0px;"></div>
|
||||||
</div>
|
</div>
|
||||||
<script src="https://cdn.jsdelivr.net/npm/monaco-editor@0.44.0/min/vs/loader.js"></script>
|
<script src="https://cdn.jsdelivr.net/npm/monaco-editor@0.44.0/min/vs/loader.js"></script>
|
||||||
@ -166,6 +188,39 @@ let resizeObserver = new ResizeObserver(() => {
|
|||||||
resizeMonaco();
|
resizeMonaco();
|
||||||
});
|
});
|
||||||
resizeObserver.observe(document.getElementById('config-modal-content'));
|
resizeObserver.observe(document.getElementById('config-modal-content'));
|
||||||
|
|
||||||
|
const weatherArea = document.getElementById('weather-area');
|
||||||
|
const forecastModal = document.getElementById('forecast-modal');
|
||||||
|
const forecastContent = document.getElementById('forecast-content');
|
||||||
|
const closeForecastBtn = document.getElementById('close-forecast-btn');
|
||||||
|
const forecastTitle = document.getElementById('forecast-title');
|
||||||
|
|
||||||
|
weatherArea.onclick = function() {
|
||||||
|
forecastContent.innerHTML = 'Загрузка...';
|
||||||
|
forecastModal.style.display = 'flex';
|
||||||
|
fetch('/api/weather-forecast').then(r => r.json()).then(data => {
|
||||||
|
if(data.error) {
|
||||||
|
forecastContent.innerHTML = '<span style="color:red;">'+data.error+'</span>';
|
||||||
|
forecastTitle.textContent = 'Прогноз';
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
let days = data.forecast.length;
|
||||||
|
forecastTitle.textContent = `Прогноз на ${days} ${days === 1 ? 'день' : (days < 5 ? 'дня' : 'дней')}`;
|
||||||
|
let html = '<table style="width:100%; border-collapse:collapse;">';
|
||||||
|
html += '<tr><th style="text-align:left; padding:4px;">Дата</th><th style="text-align:left; padding:4px;">Температура</th><th style="text-align:left; padding:4px;">Облачность</th><th style="text-align:left; padding:4px;">Состояние</th><th></th></tr>';
|
||||||
|
for(const day of data.forecast) {
|
||||||
|
html += `<tr><td style="padding:4px;">${day.date}</td><td style="padding:4px;">${day.temp}°C</td><td style="padding:4px;">${day.cloud}%</td><td style="padding:4px;">${day.text||''}</td><td>${day.icon ? `<img src='${day.icon.startsWith('//') ? 'https:' + day.icon : day.icon}' width='32' height='32'/>` : ''}</td></tr>`;
|
||||||
|
}
|
||||||
|
html += '</table>';
|
||||||
|
forecastContent.innerHTML = html;
|
||||||
|
}).catch(() => {
|
||||||
|
forecastContent.innerHTML = '<span style="color:red;">Ошибка загрузки прогноза</span>';
|
||||||
|
forecastTitle.textContent = 'Прогноз';
|
||||||
|
});
|
||||||
|
};
|
||||||
|
closeForecastBtn.onclick = function() {
|
||||||
|
forecastModal.style.display = 'none';
|
||||||
|
};
|
||||||
</script>
|
</script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
Loading…
x
Reference in New Issue
Block a user