Tomato Clock use web storage to save the history data
A Pen by Mandy Chien on CodePen.
<head> | |
<link href="https://fonts.googleapis.com/icon?family=Material+Icons" | |
rel="stylesheet"> | |
</head> | |
<body> | |
<div class = "container"> | |
<div id = "panel"> | |
<transition name = "fade"> | |
<div class = "panel" v-if = "showPanel"> | |
<div class = "panel-header-rect" v-bind:class="{ right: tabIsRight }"></div> | |
<div class = "panel-header-button" v-on:click = "changeTab('to_do_list')" v-bind:class="{ active: tabIsLeft }"> | |
To-do list | |
</div> | |
<div class = "panel-header-button right" v-on:click = "changeTab('dashboard')" v-bind:class="{ active: tabIsRight }"> | |
Dashboard | |
</div> | |
<div id = "panel-to-do" class = "panel-content" v-show = "showTODOLIST"> | |
<div class = "panel-week-content"> | |
<div class = "panel-date-button" v-on:click = "changeActiveDate(0)" v-bind:class="{ active: activeDay == '0'}" > | |
<div class = "button-content"> | |
{{historyData[0].date}}<br>SUN | |
</div> | |
</div> | |
<div class = "panel-date-button" v-on:click = "changeActiveDate(1)" v-bind:class="{ active: activeDay == '1'}"> | |
<div class = "button-content"> | |
{{historyData[1].date}}<br>MON | |
</div> | |
</div> | |
<div class = "panel-date-button" v-on:click = "changeActiveDate(2)" v-bind:class="{ active: activeDay == '2'}"> | |
<div class = "button-content"> | |
{{historyData[2].date}}<br>TUE | |
</div> | |
</div> | |
<div class = "panel-date-button" v-on:click = "changeActiveDate(3)" v-bind:class="{ active: activeDay == '3'}"> | |
<div class = "button-content"> | |
{{historyData[3].date}}<br>WED | |
</div> | |
</div> | |
<div class = "panel-date-button" v-on:click = "changeActiveDate(4)" v-bind:class="{ active: activeDay == '4'}"> | |
<div class = "button-content"> | |
{{historyData[4].date}}<br>THU | |
</div> | |
</div> | |
<div class = "panel-date-button" v-on:click = "changeActiveDate(5)" v-bind:class="{ active: activeDay == '5'}"> | |
<div class = "button-content"> | |
{{historyData[5].date}}<br>FRI | |
</div> | |
</div> | |
<div class = "panel-date-button" v-on:click = "changeActiveDate(6)" v-bind:class="{ active: activeDay == '6'}"> | |
<div class = "button-content"> | |
{{historyData[6].date}}<br>SAT | |
</div> | |
</div> | |
</div> | |
<div class = "panel-todo-content"> | |
<ul> | |
<li v-for="item in historyData[activeDay].task" v-bind:class="{ active: isSelected == item}" @click = "isSelected = item"> | |
<button v-bind:class="{ active: item.complete }" @click = "changeTaskStatus(item.taskName)"></button> | |
<a v-if = "item.complete" class = "line-through">{{ item.taskName }}</a> | |
<a v-else>{{ item.taskName }}</a> | |
</li> | |
<li><button class = "add">+</button><input type = "text" placeholder = "Add new task" v-model="taskName" v-on:keyup.enter = "addTask"></input></li> | |
</ul> | |
</div> | |
</div> | |
<div id = "panel-dash-board" class = "panel-content" v-show = "showDASHBOARD"> | |
<div class = "panel-calculate-content"> | |
<div class = "left"> | |
<div class = "font-bold up" v-cloak>{{tomatoSum[activeDay]}}</div> | |
<div class = "down">TODAY</div> | |
</div> | |
<div class = "right"> | |
<div class = "font-bold up" v-cloak>{{weekTomatoSum}}</div> | |
<div class = "down" v-cloak>{{historyData[0].date}}~{{historyData[6].date}}</div> | |
</div> | |
</div> | |
<div class = "panel-statistic-content"> | |
<div id = "day1" class = "statistic-flex"> | |
<transition name="up"> | |
<div v-show = "tabIsRight" class = "straight"> | |
<div class = "font-bold" v-bind:style="{ height: 31 + 150 -tomatoSum[0]*180/15+ 'px'}" v-cloak>{{tomatoSum[0]}}</div> | |
</div> | |
</transition> | |
</div> | |
<div id = "day2" class = "statistic-flex"> | |
<transition name="up"> | |
<div v-show = "tabIsRight" class = "straight"> | |
<div class = "font-bold" v-bind:style="{ height: 31 + 150 -tomatoSum[1]*180/15+ 'px'}" v-cloak>{{tomatoSum[1]}}</div> | |
</div> | |
</transition> | |
</div> | |
<div id = "day3" class = "statistic-flex"> | |
<transition name="up"> | |
<div v-show = "tabIsRight" class = "straight"> | |
<div class = "font-bold" v-bind:style="{ height: 31 + 150 -tomatoSum[2]*180/15+ 'px'}" v-cloak>{{tomatoSum[2]}}</div> | |
</div> | |
</transition> | |
</div> | |
<div id = "day4" class = "statistic-flex"> | |
<transition name="up"> | |
<div v-show = "tabIsRight" class = "straight"> | |
<div class = "font-bold" v-bind:style="{ height: 31 + 150 -tomatoSum[3]*180/15+ 'px'}" v-cloak>{{tomatoSum[3]}}</div> | |
</div> | |
</transition> | |
</div> | |
<div id = "day5" class = "statistic-flex"> | |
<transition name="up"> | |
<div v-show = "tabIsRight" class = "straight"> | |
<div class = "font-bold" v-bind:style="{ height: 31 + 150 -tomatoSum[4]*180/15+ 'px'}" v-cloak>{{tomatoSum[4]}}</div> | |
</div> | |
</transition> | |
</div> | |
<div id = "day6" class = "statistic-flex"> | |
<transition name="up"> | |
<div v-show = "tabIsRight" class = "straight"> | |
<div class = "font-bold" v-bind:style="{ height: 31 + 150 -tomatoSum[5]*180/15+ 'px'}" v-cloak>{{tomatoSum[5]}}</div> | |
</div> | |
</transition> | |
</div> | |
<div id = "day7" class = "statistic-flex"> | |
<transition name="up"> | |
<div v-show = "tabIsRight" class = "straight"> | |
<div class = "font-bold" v-bind:style="{ height: 31 + 150 -tomatoSum[6]*180/15+ 'px'}" v-cloak>{{tomatoSum[6]}}</div> | |
</div> | |
</transition> | |
</div> | |
</div> | |
<div class = "panel-statistic-date"> | |
<div class = "panel-statistic-date-detail"> | |
<div v-cloak>{{historyData[0].date}}</div> | |
<div>MON</div> | |
</div> | |
<div class = "panel-statistic-date-detail"> | |
<div v-cloak>{{historyData[1].date}}</div> | |
<div>TUE</div> | |
</div> | |
<div class = "panel-statistic-date-detail"> | |
<div v-cloak>{{historyData[2].date}}</div> | |
<div>WED</div> | |
</div> | |
<div class = "panel-statistic-date-detail"> | |
<div v-cloak>{{historyData[3].date}}</div> | |
<div>THU</div> | |
</div> | |
<div class = "panel-statistic-date-detail"> | |
<div v-cloak>{{historyData[4].date}}</div> | |
<div>FRI</div> | |
</div> | |
<div class = "panel-statistic-date-detail"> | |
<div v-cloak>{{historyData[5].date}}</div> | |
<div>SAT</div> | |
</div> | |
<div class = "panel-statistic-date-detail"> | |
<div v-cloak>{{historyData[6].date}}</div> | |
<div>SUN</div> | |
</div> | |
</div> | |
</div> | |
<div class = "finish-text">Finished</div> | |
<div class = "finish-area"> | |
<i v-for = "n in tomatoSum[activeDay]" class="material-icons">favorite</i> | |
</div> | |
</div> | |
</transition> | |
</div> | |
<div id = "clock"> | |
<div class = "circle"> | |
<div class = "timer" v-cloak>{{countMinutes}}:{{countSeconds}}</div> | |
</div> | |
<button class = "button above-circle" @click = "changeAlarmStatus"> | |
<i class="material-icons" v-cloak>{{alarm}}</i> | |
</button> | |
<button v-if = "isPlaying == true" class = "button left-circle" v-on:click = "stopCounDown"> | |
<i class="material-icons">pause</i> | |
</button> | |
<button v-else class = "button left-circle" v-on:click = "timeCountDown"> | |
<i class="material-icons">play_arrow</i> | |
</button> | |
<button class = "button under-circle" v-on:click = "reset"> | |
<i class="material-icons">replay</i> | |
</button> | |
<transition name = "rotate"> | |
<div v-if = "showClock" class = "minute-rect"> | |
<div class = "line-rect minute-30" @click = "changeTargetMinutes('30')"> | |
<div class = "minute" v-bind:class="{ active: targetMinutes == '30' }">30</div> | |
<div class = "line"></div> | |
</div> | |
<div class = "line-rect minute-25" @click = "changeTargetMinutes('25')"> | |
<div class = "minute" v-bind:class="{ active: targetMinutes == '25' }">25</div> | |
<div class = "line"></div> | |
</div> | |
<div class = "line-rect minute-20" @click = "changeTargetMinutes('20')"> | |
<div class = "minute" v-bind:class="{ active: targetMinutes == '20' }">20</div> | |
<div class = "line"></div> | |
</div> | |
<div class = "line-rect minute-15" @click = "changeTargetMinutes('15')"> | |
<div class = "minute" v-bind:class="{ active: targetMinutes == '15' }">15</div> | |
<div class = "line"></div> | |
</div> | |
<div class = "line-rect minute-10" @click = "changeTargetMinutes('10')"> | |
<div class = "minute" v-bind:class="{ active: targetMinutes == '10' }">10</div> | |
<div class = "line"></div> | |
</div> | |
<div class = "line-rect minute-5" @click = "changeTargetMinutes('05')"> | |
<div class = "minute" v-bind:class="{ active: targetMinutes == '05' }">5</div> | |
<div class = "line"></div> | |
</div> | |
<div class = "line-rect minute-0" @click = "changeTargetMinutes('00')"> | |
<div class = "minute" v-bind:class="{ active: targetMinutes == '00' }">0</div> | |
<div class = "line"></div> | |
</div> | |
</div> | |
</transition> | |
</div> | |
<div class = "license">UI Designed By | |
<a href="https://challenge.thef2e.com/user/1875?schedule=2512#works-2512">杯杯</a> | |
</div> | |
</div> | |
</body> |
Tomato Clock use web storage to save the history data
A Pen by Mandy Chien on CodePen.
var vuePanel = new Vue({ | |
el: '#panel', | |
data: { | |
showTODOLIST : true, | |
showDASHBOARD : false, | |
showPanel: false, | |
tabIsRight: false, | |
tabIsLeft: true, | |
isSelected: '', | |
activeDay : '', | |
currentDay: '', | |
currentDate: '', | |
currentMonthe: '', | |
currentYear: '', | |
taskName:'', | |
tomatoSum: [], | |
weekTomatoSum: 0, | |
historyData: [] | |
}, | |
mounted:function(){ | |
this.showPanel = true; | |
var today = new Date(); | |
this.currentYear = today.getFullYear(); | |
this.currentMonth = today.getMonth()+1; | |
this.currentDate = today.getDate(); | |
this.currentDay = today.getDay(); | |
this.activeDay = this.currentDay; | |
//get the date og the first day of this week | |
var date = new Date(); | |
date.setDate(date.getDate() - this.currentDay); //get the date of Sunday of current week | |
var startDay = date.getDate(); | |
var startMonth = date.getMonth()+1; | |
backup = JSON.parse(localStorage.getItem('historyData')); | |
if (backup != null && backup[0].date == startMonth +'/' + startDay){ | |
this.historyData = JSON.parse(JSON.stringify(backup)); | |
} | |
else{ | |
for (var i = 0; i < 7; i++) { | |
var tempMonth = date.getMonth()+1; | |
var tempDate = date.getDate(); | |
this.historyData.push({date: tempMonth +'/' + tempDate, task: []}); | |
date.setDate(date.getDate() + 1); | |
} | |
} | |
this.updateTomatoSum(); | |
}, | |
methods:{ | |
changeTab: function(pTarget){ | |
if (pTarget == "to_do_list"){ | |
this.showTODOLIST = true; | |
this.showDASHBOARD = false; | |
this.tabIsRight = false; | |
this.tabIsLeft = true; | |
} | |
else{ | |
this.showTODOLIST = false; | |
this.showDASHBOARD = true; | |
this.tabIsRight = true; | |
this.tabIsLeft = false; | |
} | |
}, | |
changeActiveDate: function(pDate){ | |
this.isSelected = ''; | |
this.activeDay = pDate; | |
this.updateTomatoSum(); | |
}, | |
updateTomatoSum(){ | |
let weekSum = 0 | |
for(var i = 0; i < 7; i++){ | |
this.tomatoSum[i] = this.historyData[i].task.reduce(function(sum,element){ | |
if ("tomatoNum" in element){ | |
return sum + element.tomatoNum | |
} | |
else{ | |
return sum; | |
} | |
},0); | |
weekSum += this.tomatoSum[i]; | |
} | |
this.weekTomatoSum = weekSum; | |
}, | |
addTask(){ | |
this.historyData[this.activeDay].task.push({taskName: this.taskName, complete: false, tomatoNum: 0}); | |
localStorage.setItem('historyData', JSON.stringify(this.historyData)); | |
this.taskName = ''; | |
}, | |
changeTaskStatus: function(pTaskName){ | |
var selectedIndex = this.historyData[this.activeDay].task.map(function(e) { return e.taskName; }).indexOf(pTaskName); | |
if (this.historyData[this.activeDay].task[selectedIndex].complete == true){ | |
this.historyData[this.activeDay].task[selectedIndex].complete = false; | |
} | |
else{ | |
this.historyData[this.activeDay].task[selectedIndex].complete = true; | |
} | |
localStorage.setItem('historyData', JSON.stringify(this.historyData)); | |
} | |
} | |
}); | |
var vueClock = new Vue({ | |
el: '#clock', | |
data:{ | |
showClock: false, | |
targetMinutes: '15', | |
countMinutes: '15', | |
countSeconds: '00', | |
isPlaying: false, | |
alarm: 'notifications', | |
timer: null, | |
}, | |
mounted:function(){ | |
this.showClock = true; | |
}, | |
methods:{ | |
changeAlarmStatus(){ | |
this.alarm == 'notifications'?this.alarm = 'notifications_off':this.alarm = 'notifications'; | |
}, | |
changeTargetMinutes: function(pTargetMinutes){ | |
this.targetMinutes = pTargetMinutes; | |
this.countMinutes = pTargetMinutes; | |
this.countSeconds = '00'; | |
}, | |
reset(){ | |
this.countMinutes = this.targetMinutes; | |
this.countSeconds = '00'; | |
}, | |
timeCountDown(){ | |
if (vuePanel.isSelected != ''){ | |
let my = this; | |
this.isPlaying = true; | |
this.timer = setInterval(function() { | |
var m = Number(my.countMinutes); | |
var s = Number(my.countSeconds); | |
var snd = new Audio("https://www.freespecialeffects.co.uk/soundfx/various/forest.wav"); | |
if (m != 0 && s == 0){ | |
m--; | |
s = 59; | |
} | |
else if (m == 0 && s==0){ | |
my.stopCounDown(); | |
if (this.alarm == 'notifications'){ | |
snd.play(); | |
} | |
else{ | |
alert('Stop timing'); | |
} | |
var selectedIndex = vuePanel.historyData[vuePanel.activeDay].task.map(function(e) { return e.taskName; }).indexOf(vuePanel.isSelected.taskName); | |
vuePanel.historyData[vuePanel.activeDay].task[selectedIndex].tomatoNum += 1 | |
localStorage.setItem('historyData', JSON.stringify(vuePanel.historyData)); | |
vuePanel.updateTomatoSum(); | |
} | |
else{ | |
s--; | |
} | |
m < 10 ? my.countMinutes = '0' + m : my.countMinutes = '' + m; | |
s < 10 ? my.countSeconds = '0' + s : my.countSeconds = '' + s; | |
},1000); | |
} | |
else{ | |
alert('Please choose the task'); | |
} | |
}, | |
stopCounDown(){ | |
clearInterval(this.timer); | |
this.isPlaying = false; | |
} | |
} | |
}) |
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.6.10/vue.min.js"></script> |
$main-color: #FFF3F0; | |
$main-color-2: #FFD8CC; | |
$font-color: #9B9B9B; | |
$shadow-color: #bbbbbb; | |
$focus-color: #FF764C; | |
$font: Seravek; | |
@function pow($number, $exp) { | |
$value: 1; | |
@if $exp > 0 { | |
@for $i from 1 through $exp { | |
$value: $value * $number; | |
} | |
} | |
@else if $exp < 0 { | |
@for $i from 1 through -$exp { | |
$value: $value / $number; | |
} | |
} | |
@return $value; | |
} | |
@function fact($number) { | |
$value: 1; | |
@if $number > 0 { | |
@for $i from 1 through $number { | |
$value: $value * $i; | |
} | |
} | |
@return $value; | |
} | |
@function pi() { | |
@return 3.14159265359; | |
} | |
@function rad($angle) { | |
$unit: unit($angle); | |
$unitless: $angle / ($angle * 0 + 1); | |
// If the angle has 'deg' as unit, convert to radians. | |
@if $unit == deg { | |
$unitless: $unitless / 180 * pi(); | |
} | |
@return $unitless; | |
} | |
@function sin($angle) { | |
$sin: 0; | |
$angle: rad($angle); | |
// Iterate a bunch of times. | |
@for $i from 0 through 10 { | |
$sin: $sin + pow(-1, $i) * pow($angle, (2 * $i + 1)) / fact(2 * $i + 1); | |
} | |
@return $sin; | |
} | |
@function cos($angle) { | |
$cos: 0; | |
$angle: rad($angle); | |
// Iterate a bunch of times. | |
@for $i from 0 through 10 { | |
$cos: $cos + pow(-1, $i) * pow($angle, 2 * $i) / fact(2 * $i); | |
} | |
@return $cos; | |
} | |
@function tan($angle) { | |
@return sin($angle) / cos($angle); | |
} | |
*{ | |
font-family: Seravek; | |
} | |
.material-icons { | |
color: $focus-color; | |
cursor: pointer; | |
} | |
body{ | |
background-color: $main-color; | |
} | |
.container { | |
position: relative; | |
} | |
.panel { | |
position: absolute; | |
top: 63px; | |
left: 122px; | |
width: 504px; | |
height: 421px; | |
} | |
.panel-header-rect{ | |
position:absolute; | |
border-radius: 10px 10px 0px 0px; | |
height: 55px; | |
width: 252px; | |
background-color: $main-color; | |
-webkit-box-shadow: 0 0 10px $shadow-color; | |
-moz-box-shadow: 0 0 10px $shadow-color; | |
box-shadow: 0 0 10px $shadow-color; | |
z-index: 1; | |
&.right{ | |
left: 252px; | |
} | |
} | |
.panel-header-button{ | |
position:absolute; | |
border-radius: 10px 10px 0px 0px; | |
height: 55px; | |
width: 252px; | |
padding-top: 16px; | |
text-align: center; | |
font-size: 20px; | |
color: #4A4A4A; | |
background-color: $main-color-2; | |
letter-spacing: 1.25px; | |
cursor: pointer; | |
&.right{ | |
left: 252px; | |
z-index: 0; | |
} | |
&.active{ | |
background-color: $main-color; | |
z-index: 3; | |
} | |
} | |
.panel-content{ | |
position:absolute; | |
top: 55px; | |
height: 366px; | |
width: 504px; | |
background-color: $main-color; | |
border-radius: 0px 0px 10px 10px; | |
text-align: center; | |
-webkit-box-shadow: 0 0 10px $shadow-color; | |
-moz-box-shadow: 0 0 10px $shadow-color; | |
box-shadow: 0 0 10px $shadow-color; | |
z-index:2; | |
} | |
.panel-week-content{ | |
display:flex; | |
justify-content: center; | |
margin: 19px 8px 16px 8px; | |
background-color: $main-color; | |
} | |
.panel-date-button{ | |
height: 56px; | |
width: 56px; | |
margin: 0px 5px; | |
border: solid 1px; | |
border-radius: 5px; | |
border-color: rgba(151,151,151,0.2); | |
cursor: pointer; | |
&:active, &:hover, &:focus{ | |
background-color: $main-color-2; | |
} | |
&.active{ | |
border-color: $main-color-2; | |
background-color: $main-color-2; | |
.button-content{ | |
color: black; | |
} | |
} | |
} | |
.button-content{ | |
margin: 10px; | |
color: $font-color; | |
font-size: 16px; | |
letter-spacing: 1px; | |
text-align: center; | |
cursor: pointer; | |
} | |
.panel-todo-content{ | |
height: 255px; | |
width: 464px; | |
margin:0px auto; | |
background-color: white; | |
border-radius: 5px; | |
text-align: left; | |
overflow:auto; | |
ul{ | |
margin: 16px 16px 16px 16px; | |
padding: 0px; | |
list-style-type: none; | |
li{ | |
margin-top: 10px; | |
line-height: 35px; | |
border-radius: 5px; | |
letter-spacing: 1.27px; | |
cursor: pointer; | |
&.active{ | |
background-color: $focus-color; | |
color: white; | |
} | |
button{ | |
width: 20px; | |
height: 20px; | |
margin-right: 16px; | |
margin-left: 5px; | |
padding-left: 1px; | |
border-radius: 50%; | |
border: solid 3px white; | |
vertical-align:middle; | |
background-color: white; | |
color: $focus-color; | |
font-size: 19px; | |
line-height: 15px; | |
cursor: pointer; | |
-webkit-box-shadow: 0 0 10px $shadow-color; | |
-moz-box-shadow: 0 0 10px $shadow-color; | |
box-shadow: 0 0 10px $shadow-color; | |
&.active{ | |
background-color: $focus-color; | |
} | |
} | |
.line-through{ | |
text-decoration:line-through; | |
} | |
input{ | |
line-height: 24px; | |
width: 360px; | |
font-size: 14px; | |
letter-spacing: 1.27px; | |
border-top:solid 0px; | |
border-right: solid 0px; | |
border-left: solid 0px; | |
border-bottom: solid 1px #D8D8D8; | |
} | |
} | |
} | |
} | |
.panel-calculate-content{ | |
position: absolute; | |
width: 464px; | |
height: 70px; | |
left: 20px; | |
top: 24px; | |
background-color: white; | |
border-radius: 5px; | |
.left{ | |
width:232px; | |
height: 70px; | |
left: 0px; | |
} | |
.right{ | |
position: absolute; | |
width:232px; | |
height: 70px; | |
left: 232px; | |
top: 0px; | |
} | |
} | |
.up{ | |
margin-top: 7px; | |
color: #4A4A4A; | |
font-size: 30px; | |
} | |
.down{ | |
font-size: 16px; | |
letter-spacing: 1px; | |
color: #4A4A4A; | |
} | |
.font-bold{ | |
color: $focus-color; | |
} | |
.panel-statistic-content{ | |
display: flex; | |
position:absolute; | |
width: 464px; | |
height: 181px; | |
left: 20px; | |
top: 118px; | |
align-items:flex-start; | |
background-color: white; | |
border-radius: 5px; | |
} | |
.panel-statistic-date{ | |
display: flex; | |
position: absolute; | |
width: 464px; | |
height: 50px; | |
top: 307px; | |
left: 20px; | |
} | |
.panel-statistic-date-detail{ | |
width: 464px; | |
font-size: 12px; | |
letter-spacing: 0.75px; | |
} | |
.straight{ | |
width: 12px; | |
height: 181px; | |
background-color: #FFBBA6; | |
transition-duration: 0.5s; | |
.up{ | |
margin-top: 0px; | |
background-color: white; | |
border: solid 1px black; | |
} | |
} | |
.statistic-flex{ | |
margin-left: 47.5px; | |
.font-bold{ | |
display: flex; | |
align-items:flex-end; | |
font-size: 24px; | |
background-color: white; | |
} | |
} | |
.circle{ | |
position: absolute; | |
top: 262px; | |
left: 953px; | |
height: 123px; | |
width: 123px; | |
text-align: center; | |
border-radius: 50%; | |
border: 15px solid #FF9D80; | |
} | |
.button{ | |
position: absolute; | |
display: block; | |
border-radius: 50%; | |
background-color: white; | |
height: 40px; | |
width: 40px; | |
cursor: pointer; | |
z-index: 1; | |
&:active, &:hover{ | |
background-color: $main-color-2; | |
} | |
&.inside-circle{ | |
margin-left: 41.5px; | |
margin-top: 41.5px; | |
} | |
&.above-circle{ | |
top: 262px - 23px - 35px; | |
left: 953px + 41.5px + 15px; | |
} | |
&.left-circle{ | |
top: 262px + 41.5px + 15px; | |
left: 953px - 41.5px - 15px; | |
} | |
&.under-circle{ | |
top: 262px + 83px + 30px + 35px + 23px; | |
left: 953px + 41.5px + 15px; | |
} | |
} | |
.minute-rect{ | |
position:absolute; | |
width: 700px; | |
height:700px; | |
left:680px; | |
z-index: 0; | |
} | |
.line-rect{ | |
$half-long: (89.9px + 90px) /2 ; | |
position: absolute; | |
height: 89.9px + 90px; | |
width: 50px; | |
top: 262px - 33.4px + $half-long - 65px; | |
left: 322px;//953px + 41.5px + 15px + 18.9px - 25px; | |
cursor: pointer; | |
.line{ | |
margin: 0px auto; | |
height: 89.9px; | |
width: 0px; | |
border: solid 1px #9B9B9B; | |
} | |
.minute{ | |
font-size: 32px; | |
text-align: center; | |
color: #9B9B9B; | |
letter-spacing: 2px; | |
margin-bottom: 10px; | |
transform: rotate(90deg); | |
&.active, &:hover{ | |
font-size: 32px; | |
color: #000000; | |
font-weight:bold; | |
transition-duration: 0.5s; | |
} | |
} | |
&.minute-30{ | |
transform: translateY(-160px - $half-long + 40px); | |
} | |
&.minute-25{ | |
$cos: cos(30deg) * -205px; | |
$sin: sin(30deg) * -205px; | |
transform: translate($sin, $cos) rotate(330deg); | |
} | |
&.minute-20{ | |
$cos: cos(60deg) * -205px; | |
$sin: sin(60deg) * -205px; | |
transform: translate($sin, $cos) rotate(300deg); | |
} | |
&.minute-15{ | |
$cos: cos(90deg) * -205px; | |
$sin: sin(90deg) * -205px; | |
transform: translate($sin, $cos) rotate(270deg); | |
} | |
&.minute-10{ | |
$cos: cos(120deg) * -205px; | |
$sin: sin(120deg) * -205px; | |
transform: translate($sin, $cos) rotate(240deg); | |
} | |
&.minute-5{ | |
$cos: cos(150deg) * -205px; | |
$sin: sin(150deg) * -205px; | |
transform: translate($sin, $cos) rotate(210deg); | |
} | |
&.minute-0{ | |
$cos: cos(180deg) * -205px; | |
$sin: sin(180deg) * -205px; | |
transform: translate($sin, $cos) rotate(180deg); | |
} | |
} | |
.timer{ | |
line-height: 123px; | |
font-size: 26px; | |
letter-spacing: 1.25px; | |
} | |
.finish-text{ | |
position: absolute; | |
top: 450px; | |
opacity: 0.5; | |
font-size: 20px; | |
color: #000000; | |
letter-spacing: 1.25px; | |
text-align: center; | |
} | |
.finish-area{ | |
position: absolute; | |
top: 450px + 30px; | |
} | |
.license{ | |
letter-spacing: 1.25px; | |
opacity: 0.5; | |
} | |
button:focus { | |
outline: none; | |
} | |
/***Hide vue instance***/ | |
[v-cloak] { | |
display: none; | |
} | |
/***transition***/ | |
.up-enter-active, .up-leave-active { | |
transition: all .3s ease; | |
} | |
.up-enter, .up-leave-to /* .fade-leave-active below version 2.1.8 */ { | |
transform: translateY(10px); | |
opacity: 0; | |
} | |
.rotate-enter-active, .rotate-leave-active { | |
transition: all 1s ease; | |
//transform: rotate(-30deg); | |
} | |
.rotate-enter, .rotate-leave-to /* .fade-leave-active below version 2.1.8 */ { | |
transform: rotate(30deg) translateX(30px); | |
opacity: 0; | |
} | |
.fade-enter-active, .fade-leave-active { | |
transition: opacity 3s; | |
} | |
.fade-enter, .fade-leave-to /* .fade-leave-active below version 2.1.8 */ { | |
opacity: 0; | |
} |