想给网站加一个倒数日卡片
但是主题里没有相关配置
因为对网站之类的完全零基础,看了一圈感觉自己想要的效果跟网站上已有的”座右铭”卡片的实现很像
准备学习借用一下~
motto.ejs(座右铭卡片)
1 2 3 4 5 6 7 8 9 10
| <% if (theme.motto.on && page.current === 1) { %> <div class="motto"> <h3 class="motto-title"><%= theme.motto.title %></h3> <div class="motto-content"> <p> <%= theme.motto.content %> </p> </div> </div> <% } %>
|
theme.motto.on?感觉好像懂了什么
主题配置文件新增:
刚刚还在想卡片的样式是在哪里定义的,然后想起来还有ccs
motto.styl
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
| .motto { width: 100%; margin-bottom: 16px; background: #fff; box-shadow: 0 1px 20px -6px rgba(0, 0, 0, 0.5); padding: 20px; border-radius: 10px; box-sizing: border-box; transition: all 0.3s; position: relative; background: convert(hexo-config('motto.background'));
.motto-title { text-align: center; }
.motto-content { text-align: center; padding: 15px 20%; color: #34495e; } }
@media (max-width: 551px) { .motto { .motto-content { padding: 15px 10%; } } }
|
感觉设置多个平行内容跟公告有点像,看看去
主题配置文件
1
| list: # list相当于数组对象,[{title:'xx',date: 'xx', url: 'xxx', color: 'red'}]根据自己实际情况,增加或者删除
|
我也储存一下
countdown.ejs新增:
1 2 3 4 5 6 7 8 9 10 11 12
| <script> let listData = [ { title: "计算机二级", targetDate: "2024-03-23", }, { title: "蓝桥杯省赛", targetDate: "2024-04-13", } ]; </script>
|
countdown.ejs新增倒数日函数:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
| <script> function countdown(targetDate, callback) { const targetTime = new Date(targetDate).getTime(); const currentTime = new Date().getTime();
const remainingTime = targetTime - currentTime;
if (remainingTime <= 0) { return '倒计时结束'; }
const days = Math.floor(remainingTime / (1000 * 60 * 60 * 24)); const hours = Math.floor( (remainingTime % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60) ); const minutes = Math.floor( (remainingTime % (1000 * 60 * 60)) / (1000 * 60) ); const seconds = Math.floor((remainingTime % (1000 * 60)) / 1000);
return `${days}天 ${hours}小时 ${minutes}分钟 ${seconds}秒`; } </script>
|
现在countdown.ejs是这样的:
countdown.ejs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59
| <%if (theme.countdown.on && page.current === 1) { listData.forEach(function(item) { %> <div class="index-notice" id="appIndexNotice"> <h3> <i class="fas fa-bullhorn index-notice-icon"></i><%= item.title %> </h3> <div class="index-notice-content"> <% item.listData.forEach(function(data) { %> <div class="countdown-card"> <h4><%= data.title %></h4> <p>目标日期: <%= data.targetDate %></p> <p>剩余时间: <%= countdown(data.targetDate) %></p> </div> <% }); %> </div> </div> <% }); }%> <script> function countdown(targetDate) { const targetTime = new Date(targetDate).getTime(); const currentTime = new Date().getTime();
const remainingTime = targetTime - currentTime;
if (remainingTime <= 0) { return '倒计时结束'; }
const days = Math.floor(remainingTime / (1000 * 60 * 60 * 24)); const hours = Math.floor( (remainingTime % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60) ); const minutes = Math.floor( (remainingTime % (1000 * 60 * 60)) / (1000 * 60) ); const seconds = Math.floor((remainingTime % (1000 * 60)) / 1000);
return `${days}天 ${hours}小时 ${minutes}分钟 ${seconds}秒`; } </script> <script> let listData = [ { title: "计算机二级", targetDate: "2024-03-23", }, { title: "蓝桥杯省赛", targetDate: "2024-04-13", } ]; </script>
|
现在新建countdown.styl
(我现在还不太清楚要不要定义卡片放在页面哪个位置,到最后再说吧)
找到一个东西:
motto.ejs:
1 2 3 4 5 6 7
| @media (max-width: 551px) { .motto { .motto-content { padding: 15px 10%; } } }
|
感觉是卡片排列的底层逻辑,由于这里是屏幕宽度小于等于 551px 时,于是要找一个总的默认的.styl文件看一看
找到一个感觉很像的:
home.styl:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
| .widget { margin-bottom: 16px; background: #fff; border-radius: 10px; box-shadow: 0 1px 20px -6px rgba(0, 0, 0, 0.5);
.content { padding: 8px 16px; } }
@media screen and (max-width: 1200px) { & { width: 80%; } }
@media screen and (max-width: 992px) { & { width: 95%; } }
@media screen and (max-width: 992px) { & { width: 95%; flex-direction: column;
.l_content { width: 100%; margin: 0 auto; } } }
|
刚刚发现.styl文件里还要一个这个属性
motto.styl:
总之总之卡片/组件位置应该不用我准确定义了
主题配置文件新增:
1 2 3 4
| # 首页倒数日 countdown: on: true background: blue
|
最后的countdown.styl(太晚了,具体的没细改,主打的一个出现了就是最好的!)
countdown.styl:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34
| .index-notice { width: 100%; margin-bottom: 16px; background: #fff; box-shadow: 0 1px 20px -6px rgba(0, 0, 0, 0.5); padding: 20px; border-radius: 10px; box-sizing: border-box; transition: all 0.3s; position: relative; background: convert(hexo-config('countdown.background'));
.index-notice-icon { text-align: center; }
.index-notice-content{ margin-top: 10px; }
.countdown-card { text-align: center; padding: 15px 20%; color: #34495e; } }
@media (max-width: 551px) { .motto { .motto-content { padding: 15px 10%; } } }
|
countdown.ejs和countdown.styl都备份好了,开始第一次测试~
发现没成功,但是我又发现了一个需要配置的文件:
index.ejs:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
| <% if(theme.swiper.on ) { %> <%- partial('_partial/swiper') %> <% } %>
<div id="l_main"> <div class="l_content"> <%- partial('_partial/home_widget') %> <%- partial('_partial/motto') %> <%- partial('_partial/notice') %> <%- partial('_partial/topArticle', {page: page}) %>
<div class="bg-floor" id="home-bg-floor" style="position: fixed;left: 0;top: 0;width: 100%;height: 100%;z-index: -2;"></div> <%- partial('_partial/card/post') %> <%- partial('_partial/paginator') %> </div>
<%- partial('_partial/side') %> </div>
<%- partial('_partial/scripts/falling') %>
<%- partial('_partial/lantern') %>
|
然后照葫芦画瓢:
index.ejs新增:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
| <% if(theme.swiper.on ) { %> <%- partial('_partial/swiper') %> <% } %>
<div id="l_main"> <div class="l_content"> <%- partial('_partial/home_widget') %> <%- partial('_partial/countdown') %> <%- partial('_partial/motto') %> <%- partial('_partial/notice') %> <%- partial('_partial/topArticle', {page: page}) %>
<div class="bg-floor" id="home-bg-floor" style="position: fixed;left: 0;top: 0;width: 100%;height: 100%;z-index: -2;"></div> <%- partial('_partial/card/post') %> <%- partial('_partial/paginator') %> </div>
<%- partial('_partial/side') %> </div>
<%- partial('_partial/scripts/falling') %>
<%- partial('_partial/lantern') %>
|
第二次测试~
私密马赛,报bug了:
bug:
1 2 3 4 5 6 7
| D:\github_code\blog\themes\hexo-theme-bamboo\layout\_partial\countdown.ejs:1 >> 1| <%if (theme.countdown.on && page.current === 1) { 2| listData.forEach(function(item) { %> 3| <div class="index-notice" id="appIndexNotice"> 4| <h3>
listData is not defined
|
修改了一下countdown.ejs:
index.ejs新增:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70
| <%if (theme.countdown.on && page.current === 1) { let listData = [ { title: "计算机二级", targetDate: "2024-03-23", }, { title: "蓝桥杯省赛", targetDate: "2024-04-13", } ];
listData.forEach(function(item) { %> <div class="index-notice" id="appIndexNotice"> <h3> <i class="fas fa-bullhorn index-notice-icon"></i><%= item.title %> </h3> <div class="index-notice-content"> <% item.listData.forEach(function(data) { %> <div class="countdown-card"> <h4><%= data.title %></h4> <p>目标日期: <%= data.targetDate %></p> <p>剩余时间: <%= countdown(data.targetDate) %></p> </div> <% }); %> </div> </div> <% }); }%> <script> let listData = [ { title: "计算机二级", targetDate: "2024-03-23", }, { title: "蓝桥杯省赛", targetDate: "2024-04-13", } ]; </script> <script> function countdown(targetDate) { const targetTime = new Date(targetDate).getTime(); const currentTime = new Date().getTime();
const remainingTime = targetTime - currentTime;
if (remainingTime <= 0) { return '倒计时结束'; }
const days = Math.floor(remainingTime / (1000 * 60 * 60 * 24)); const hours = Math.floor( (remainingTime % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60) ); const minutes = Math.floor( (remainingTime % (1000 * 60 * 60)) / (1000 * 60) ); const seconds = Math.floor((remainingTime % (1000 * 60)) / 1000);
return `${days}天 ${hours}小时 ${minutes}分钟 ${seconds}秒`; } </script>
|
变量名错了/(ㄒoㄒ)/~~再改一下:
countdown.ejs新增:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68
| <%if (theme.countdown.on && page.current === 1) { let listData = [ { title: "计算机二级", targetDate: "2024-03-23", }, { title: "蓝桥杯省赛", targetDate: "2024-04-13", } ];
listData.forEach(function(item) { %> <div class="index-notice" id="appIndexNotice"> <h3> <i class="fas fa-bullhorn index-notice-icon"></i><%= item.title %> </h3> <div class="index-notice-content"> <div class="countdown-card"> <h4><%= item.title %></h4> <p>目标日期: <%= item.targetDate %></p> <p>剩余时间: <%= countdown(item.targetDate) %></p> </div> </div> </div> <% }); }%> <script> let listData = [ { title: "计算机二级", targetDate: "2024-03-23", }, { title: "蓝桥杯省赛", targetDate: "2024-04-13", } ]; </script> <script> function countdown(targetDate) { const targetTime = new Date(targetDate).getTime(); const currentTime = new Date().getTime();
const remainingTime = targetTime - currentTime;
if (remainingTime <= 0) { return '倒计时结束'; }
const days = Math.floor(remainingTime / (1000 * 60 * 60 * 24)); const hours = Math.floor( (remainingTime % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60) ); const minutes = Math.floor( (remainingTime % (1000 * 60 * 60)) / (1000 * 60) ); const seconds = Math.floor((remainingTime % (1000 * 60)) / 1000);
return `${days}天 ${hours}小时 ${minutes}分钟 ${seconds}秒`; } </script>
|
又报错啦被自己蠢笑啦
countdown.ejs:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53
| <%if (theme.countdown.on && page.current === 1) { let listData = [ { title: "计算机二级", targetDate: "2024-03-23", }, { title: "蓝桥杯省赛", targetDate: "2024-04-13", } ];
function countdown(targetDate) { const targetTime = new Date(targetDate).getTime(); const currentTime = new Date().getTime();
const remainingTime = targetTime - currentTime;
if (remainingTime <= 0) { return '倒计时结束'; }
const days = Math.floor(remainingTime / (1000 * 60 * 60 * 24)); const hours = Math.floor( (remainingTime % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60) ); const minutes = Math.floor( (remainingTime % (1000 * 60 * 60)) / (1000 * 60) ); const seconds = Math.floor((remainingTime % (1000 * 60)) / 1000);
return `${days}天 ${hours}小时 ${minutes}分钟 ${seconds}秒`; }
listData.forEach(function (item) { %> <div class="index-notice" id="appIndexNotice"> <h3> <i class="fas fa-bullhorn index-notice-icon"></i><%= item.title %> </h3> <div class="index-notice-content"> <div class="countdown-card"> <h4><%= item.title %></h4> <p>目标日期: <%= item.targetDate %></p> <p>剩余时间: <%= countdown(item.targetDate) %></p> </div> </div> </div> <% }); }%>
|
第三次测试~(给代码磕个头/(ㄒoㄒ)/~~)
成功了!!!!!!
等会。。。。/(ㄒoㄒ)/~~
两个bug:
1.看起来用的不是我现在的时间呀,像是我上传的时间,因为怎么样他都不变
2.我公告栏怎么不滚动了????Orz
第一个bug,突然想起来这个网站是静态,请教了GPT老师:
GPT老师
是的,这段代码获取的是客户端的当前日期和时间,而不是服务器的日期和时间。如果你的网站是静态的,即没有与服务器进行交互更新页面内容的能力,那么 new Date().getTime()
获取的时间将始终是用户打开网页时的时间,不会实时更新。
如果你想要在静态网站中实现实时倒计时功能,你可以考虑使用 JavaScript 配合客户端的时区偏移来获取当前时间。以下是一个示例实现:
1 2 3 4 5 6 7 8 9
| function getCurrentTime() { var date = new Date(); var offset = date.getTimezoneOffset() * 60 * 1000; var currentTime = date.getTime() - offset; return currentTime; }
var targetTime = new Date(targetDate).getTime(); var currentTime = getCurrentTime();
|
在这个示例中,getCurrentTime
函数通过获取客户端的时区偏移,将客户端时间与服务器时间进行同步。这样就能在静态网站中实现实时的倒计时功能。请注意,这种方法仍然依赖于客户端的时间,因此可能会受到用户设备时间不准确或篡改的影响。
然后又加了实时滚动功能:
countdown.ejs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87
| <!DOCTYPE html> <html> <head> <title>实时倒计时</title> <style> .countdown-card { font-size: 20px; text-align: center; } </style> </head> <body> <div id="countdown-container"> <% let listData = [ { title: "计算机二级", targetDate: "2024-03-23", // 目标日期 }, { title: "蓝桥杯省赛", targetDate: "2024-04-13", // 目标日期 } ];
listData.forEach(function(item) { %> <div class="index-notice"> <h3> <i class="fas fa-bullhorn index-notice-icon"></i> <%= item.title %> </h3> <div class="index-notice-content"> <div class="countdown-card"> <h4><%= item.title %></h4> <p>目标日期: <%= item.targetDate %></p> <p>剩余时间: <span id="countdown-<%= item.title %>">0</span></p> </div> </div> </div> <% }) %> </div>
<script> function getCurrentTime() { var date = new Date(); var offset = date.getTimezoneOffset() * 60 * 1000; var currentTime = date.getTime() - offset; return currentTime; }
function updateCountdown(id, remainingTime) { var obj = document.getElementById(id); var days = Math.floor(remainingTime / (1000 * 60 * 60 * 24)); var hours = Math.floor((remainingTime % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60)); var minutes = Math.floor((remainingTime % (1000 * 60 * 60)) / (1000 * 60)); var seconds = Math.floor((remainingTime % (1000 * 60)) / 1000);
obj.textContent = `${days}天 ${hours}小时 ${minutes}分钟 ${seconds}秒`;
if (remainingTime <= 0) { clearInterval(timer); obj.textContent = '倒计时结束'; } }
function countdown(targetDate, id) { var targetTime = new Date(targetDate).getTime(); var currentTime = getCurrentTime(); var remainingTime = targetTime - currentTime; if (remainingTime <= 0) { document.getElementById(id).textContent = '倒计时结束'; return; }
var timer = setInterval(function() { remainingTime -= 1000; updateCountdown(id, remainingTime); }, 1000); }
window.addEventListener('DOMContentLoaded', (event) => { <% listData.forEach(function(item) { %> countdown("<%= item.targetDate %>", 'countdown-<%= item.title %>'); <% }) %> }); </script> </body> </html>
|
02:37了。我去睡觉了~(第二个bug自己好了。。。)