diff --git a/app/static/css/book.css b/app/static/css/book.css index bab522e..404249a 100644 --- a/app/static/css/book.css +++ b/app/static/css/book.css @@ -21,6 +21,13 @@ z-index: 0; } +.category-filter-dropdown, +.sort-dropdown, +.order-dropdown { + z-index: 9999; +} + + @keyframes bubble { 0% { transform: translateY(100%) scale(0); @@ -181,30 +188,188 @@ max-width: 800px; } +/* 现代化下拉列表样式 */ +.filter-section .custom-select-container { + position: relative; + width: 100%; +} + +.filter-section .filter-header { + display: flex; + justify-content: space-between; + align-items: center; + background-color: #f8f9fa; + border-radius: 12px; + padding: 12px 16px; + cursor: pointer; + user-select: none; + box-shadow: 0 2px 6px rgba(0, 0, 0, 0.05); + border: 2px solid #f9c0d0; + transition: all 0.3s ease; + background-color: rgba(255, 255, 255, 0.95); + color: #666; + font-weight: 500; +} + +.filter-section .filter-header:hover { + border-color: #e67e9f; + box-shadow: 0 0 0 3px rgba(230, 126, 159, 0.1); + background-color: #fff; + transform: translateY(-2px); +} + +.filter-section .filter-header .filter-title { + display: flex; + align-items: center; + gap: 10px; +} + +.filter-section .filter-header .filter-title i { + color: #e67e9f; + font-size: 16px; +} + +.filter-section .filter-header .icon-arrow { + transition: transform 0.3s ease; +} + +.filter-section .filter-header.open .icon-arrow { + transform: rotate(180deg); +} + +.filter-section .dropdown-options { + position: absolute; + top: calc(100% + 8px); + left: 0; + right: 0; + max-height: 300px; + overflow-y: auto; + background-color: white; + border-radius: 12px; + box-shadow: 0 6px 16px rgba(0, 0, 0, 0.1); + z-index: 9999; + padding: 8px 0; + display: none; + animation: dropdownFadeIn 0.3s ease; + border: 1px solid rgba(233, 152, 174, 0.3); +} + +.filter-section .dropdown-options.show { + display: block; +} + +@keyframes dropdownFadeIn { + from { + opacity: 0; + transform: translateY(-10px); + } + to { + opacity: 1; + transform: translateY(0); + } +} + +.filter-section .option-item { + padding: 10px 16px; + color: #666; + display: flex; + align-items: center; + gap: 10px; + cursor: pointer; + transition: all 0.2s ease; +} + +.filter-section .option-item:hover { + background: linear-gradient(135deg, #ffeef2, #ffd9e2); + color: #d23f6e; +} + +.filter-section .option-item.selected { + background: linear-gradient(135deg, #ffeef2, #ffd9e2); + color: #d23f6e; + font-weight: 500; +} + +.filter-section .option-item i { + font-size: 16px; + width: 20px; + text-align: center; +} + +.filter-section .option-item.all-option { + background-color: #f0f7ff; + margin: 0 8px 8px 8px; + border-radius: 8px; +} + +.filter-section .option-item.all-option i { + color: #4a73c7; +} + +/* 全局类别和选项图标 */ +.filter-section .icon-all { + color: #4a73c7; +} + +.filter-section .icon-literature { + color: #e67e9f; +} + +.filter-section .icon-novel { + color: #f0ad4e; +} + +.filter-section .icon-essay { + color: #56c596; +} + +.filter-section .icon-computer { + color: #5bc0de; +} + +.filter-section .icon-programming { + color: #9c27b0; +} + +.filter-section .icon-sort { + color: #5c88da; +} + +.filter-section .icon-order { + color: #e67e9f; +} + +/* 使搜索框和下拉列表样式保持一致 */ .search-group .form-control { - border: 1px solid #f9c0d0; + border: 2px solid #f9c0d0; + height: 46px; + font-weight: 500; + color: #666; + transition: all 0.3s ease; border-right: none; - border-radius: 25px 0 0 25px; + border-radius: 12px 0 0 12px; padding: 10px 20px; - height: 42px; - font-size: 0.95rem; - background-color: rgba(255, 255, 255, 0.9); - box-shadow: inset 0 1px 3px rgba(0, 0, 0, 0.05); - transition: all 0.3s; + background-color: rgba(255, 255, 255, 0.95); + box-shadow: 0 2px 6px rgba(0, 0, 0, 0.05); flex: 1; } -.search-group .form-control:focus { - outline: none; +.search-group .form-control:hover { border-color: #e67e9f; - box-shadow: inset 0 1px 3px rgba(0, 0, 0, 0.05), 0 0 0 3px rgba(230, 126, 159, 0.2); + box-shadow: 0 0 0 3px rgba(230, 126, 159, 0.1); +} + +.search-group .form-control:focus { + border-color: #d23f6e; + box-shadow: 0 0 0 3px rgba(230, 126, 159, 0.2); + color: #333; } .search-group .btn { - border-radius: 50%; - width: 42px; - height: 42px; - min-width: 42px; + border-radius: 0 12px 12px 0; + width: 46px; + height: 46px; + min-width: 46px; padding: 0; background: linear-gradient(135deg, #e67e9f 60%, #ffd3e1 100%); color: white; @@ -232,28 +397,7 @@ .filter-group { flex: 1; - min-width: 130px; -} - -.filter-section .form-control { - border: 1px solid #f9c0d0; - border-radius: 25px; - height: 42px; - padding: 10px 20px; - background-color: rgba(255, 255, 255, 0.9); - appearance: none; - background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='12' viewBox='0 0 12 12'%3E%3Cpath fill='%23e67e9f' d='M6 8.825L1.175 4 2.238 2.938 6 6.7 9.763 2.937 10.825 4z'/%3E%3C/svg%3E"); - background-repeat: no-repeat; - background-position: right 15px center; - background-size: 12px; - box-shadow: inset 0 1px 3px rgba(0, 0, 0, 0.05); - width: 100%; -} - -.filter-section .form-control:focus { - outline: none; - border-color: #e67e9f; - box-shadow: inset 0 1px 3px rgba(0, 0, 0, 0.05), 0 0 0 3px rgba(230, 126, 159, 0.2); + min-width: 180px; } /* 图书网格布局 */ @@ -263,7 +407,7 @@ gap: 24px; margin-bottom: 30px; position: relative; - z-index: 2; + /*z-index: 2;*/ } /* 图书卡片样式 */ @@ -685,9 +829,17 @@ } .filter-section { - padding: 15px; + margin-bottom: 25px; + padding: 18px; + background-color: rgba(255, 255, 255, 0.8); + border-radius: 16px; + box-shadow: 0 4px 15px rgba(0, 0, 0, 0.05); + position: relative; + z-index: 100; /* Higher than books-grid but lower than dropdown-options */ + backdrop-filter: blur(5px); } + .search-form { flex-direction: column; gap: 12px; @@ -702,7 +854,12 @@ } .books-grid { - grid-template-columns: 1fr; + display: grid; + grid-template-columns: repeat(auto-fill, minmax(320px, 1fr)); + gap: 24px; + margin-bottom: 30px; + position: relative; + z-index: 10; /* Lower than filter-section */ } .book-actions { diff --git a/app/static/js/book-list.js b/app/static/js/book-list.js index 605dda9..d9a01b4 100644 --- a/app/static/js/book-list.js +++ b/app/static/js/book-list.js @@ -1,41 +1,81 @@ // 图书列表页面脚本 $(document).ready(function() { - // 处理分类筛选 - function setFilter(button, categoryId) { - // 移除所有按钮的活跃状态 - $('.filter-btn').removeClass('active'); - // 为当前点击的按钮添加活跃状态 - $(button).addClass('active'); - // 设置隐藏的分类ID输入值 - $('#category_id').val(categoryId); - // 提交表单 - $(button).closest('form').submit(); - } + // 自定义下拉列表处理 + const filterHeaders = document.querySelectorAll('.filter-header'); - // 处理排序方向切换 - function toggleSortDirection(button) { - const $button = $(button); - const isAsc = $button.hasClass('asc'); + filterHeaders.forEach(header => { + header.addEventListener('click', function() { + // 切换当前下拉列表 + const dropdown = this.nextElementSibling; + const isOpen = dropdown.classList.contains('show'); - // 切换方向类 - $button.toggleClass('asc desc'); + // 关闭所有下拉列表 + document.querySelectorAll('.dropdown-options').forEach(el => { + el.classList.remove('show'); + }); + document.querySelectorAll('.filter-header').forEach(el => { + el.classList.remove('open'); + }); - // 更新图标 - if (isAsc) { - $button.find('i').removeClass('fa-sort-amount-up').addClass('fa-sort-amount-down'); - $('#sort_order').val('desc'); - } else { - $button.find('i').removeClass('fa-sort-amount-down').addClass('fa-sort-amount-up'); - $('#sort_order').val('asc'); + // 如果当前不是打开状态,则打开它 + if(!isOpen) { + dropdown.classList.add('show'); + this.classList.add('open'); + } + }); + }); + + // 点击选项时更新并提交表单 + const optionItems = document.querySelectorAll('.option-item'); + optionItems.forEach(item => { + item.addEventListener('click', function() { + const container = this.closest('.custom-select-container'); + const header = container.querySelector('.filter-header .filter-title'); + const dropdown = this.closest('.dropdown-options'); + const hiddenInput = container.querySelector('input[type="hidden"]'); + + // 移除之前的选中项 + dropdown.querySelectorAll('.option-item').forEach(opt => { + opt.classList.remove('selected'); + }); + + // 设置新的选中项 + this.classList.add('selected'); + + // 更新隐藏输入值 + const value = this.getAttribute('data-value'); + hiddenInput.value = value; + + // 更新显示的文本和图标 + const icon = this.querySelector('i').cloneNode(true); + const text = this.querySelector('span').textContent; + + header.innerHTML = ''; + header.appendChild(icon); + const span = document.createElement('span'); + span.textContent = text; + header.appendChild(span); + + // 关闭下拉列表 + dropdown.classList.remove('show'); + container.querySelector('.filter-header').classList.remove('open'); + + // 提交表单 + document.getElementById('filter-form').submit(); + }); + }); + + // 点击页面其他地方关闭下拉列表 + document.addEventListener('click', function(e) { + if(!e.target.closest('.custom-select-container')) { + document.querySelectorAll('.dropdown-options').forEach(el => { + el.classList.remove('show'); + }); + document.querySelectorAll('.filter-header').forEach(el => { + el.classList.remove('open'); + }); } - - // 提交表单 - $button.closest('form').submit(); - } - - // 将函数暴露到全局作用域 - window.setFilter = setFilter; - window.toggleSortDirection = toggleSortDirection; + }); // 处理删除图书 let bookIdToDelete = null; @@ -278,16 +318,18 @@ $(document).ready(function() { $(window).on('resize', adjustCardHeights); // 为封面图片添加加载错误处理 - $('.book-cover').on('error', function() { + $('.book-cover img').on('error', function() { const $this = $(this); - const title = $this.attr('alt') || '图书'; + const bookTitle = $this.attr('alt') || '图书'; + const $cover = $this.closest('.book-cover'); - // 替换为默认封面 - $this.replaceWith(` -
+ // 替换为无封面显示 + $cover.html(` +
- ${title.charAt(0)} + 无封面
+
${bookTitle}
`); }); diff --git a/app/templates/book/list.html b/app/templates/book/list.html index a8bb77d..ba65446 100644 --- a/app/templates/book/list.html +++ b/app/templates/book/list.html @@ -8,6 +8,10 @@ {% block content %}
+ + {% for i in range(15) %} +
+ {% endfor %}
-
+
@@ -41,29 +45,89 @@
-
- +
+
+
+
+ + {% if category_id %}{% for category in categories %}{% if category.id == category_id %}{{ category.name }}{% endif %}{% endfor %}{% else %}全部分类{% endif %} +
+ +
+ + +
-
- + +
+
+
+
+ + + {% if sort == 'id' %}默认排序 + {% elif sort == 'created_at' %}入库时间 + {% elif sort == 'title' %}书名 + {% elif sort == 'stock' %}库存 + {% else %}默认排序{% endif %} + +
+ +
+ + +
-
- + +
+
+
+
+ + {% if order == 'asc' %}升序{% else %}降序{% endif %} +
+ +
+ + +
@@ -205,4 +269,3 @@ {{ super() }} {% endblock %} -