123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334 |
- <template>
- <div class="container">
- <div class="setters" :style="{width:cwidth}">
- <div class="minutes-set">
- <button
- data-setter="minutes-plus"
- @click="changeTime('minutes-plus')"
- :disabled="isStarted"
- :style="{ opacity: isStarted ? 0.5 : 1 }"
- >
- +
- </button>
- <button
- data-setter="minutes-minus"
- @click="changeTime('minutes-minus')"
- :disabled="isStarted"
- :style="{ opacity: isStarted ? 0.5 : 1 }"
- >
- -
- </button>
- </div>
- <div class="seconds-set">
- <button
- data-setter="seconds-plus"
- @click="changeTime('seconds-plus')"
- :disabled="isStarted"
- :style="{ opacity: isStarted ? 0.5 : 1 }"
- >
- +
- </button>
- <button
- data-setter="seconds-minus"
- @click="changeTime('seconds-minus')"
- :disabled="isStarted"
- :style="{ opacity: isStarted ? 0.5 : 1 }"
- >
- -
- </button>
- </div>
- </div>
- <div class="circle">
- <svg width="300" viewBox="0 0 220 220" xmlns="http://www.w3.org/2000/svg">
- <g transform="translate(110,110)">
- <circle r="100" class="e-c-base" />
- <g transform="rotate(-90)">
- <circle
- r="100"
- class="e-c-progress"
- :style="{ strokeDasharray: offset }"
- />
- <g id="e-pointer" :style="{ transform: pointerTransform }">
- <circle cx="100" cy="0" r="8" class="e-c-pointer" />
- </g>
- </g>
- </g>
- </svg>
- </div>
- <div class="controlls">
- <div class="display-remain-time">{{ displayString }}</div>
- <!-- <button
- :class="{ play: !play, pause: play }"
- id="pause"
- @click="pauseTimer"
- ></button> -->
- <el-button type="primary" @click="reset" class="reset_btn">重置</el-button>
- </div>
- </div>
- </template>
- <script>
- export default {
- props: ["preTime"],
- data() {
- return {
- length: Math.PI * 2 * 100,
- offset: 0,
- pointerTransform: "",
- play: false,
- intervalTimer: null,
- wholeTime: 0,
- timeLeft: "",
- isPaused: false,
- isStarted: false,
- displayString: "",
- isWhole:false,
- cwidth: '162px'
- };
- },
- methods: {
- changeWholeTime(seconds) {
- if (this.wholeTime + seconds >= 0) {
- this.wholeTime += seconds;
- this.update(this.wholeTime, this.wholeTime);
- }
- },
- changeTime(param) {
- switch (param) {
- case "minutes-plus":
- this.changeWholeTime(1 * 60);
- break;
- case "minutes-minus":
- this.changeWholeTime(-1 * 60);
- break;
- case "seconds-plus":
- this.changeWholeTime(1);
- break;
- case "seconds-minus":
- this.changeWholeTime(-1);
- break;
- }
- this.displayTimeLeft(this.wholeTime);
- },
- update(value, timePercent, type) {
- this.offset = -this.length - (this.length * value) / timePercent;
- if (value === 0 && type === 1) {
- this.pointerTransform = `rotate(${360}deg)`;
- } else {
- this.pointerTransform = `rotate(${(360 * value) / timePercent}deg)`;
- }
- },
- displayTimeLeft(timeLeft, type) {
- //displays time on the input
- let minutes = Math.floor(timeLeft / 60);
- let seconds = timeLeft % 60;
- this.displayString = `${minutes < 10 ? "0" : ""}${minutes}:${
- seconds < 10 ? "0" : ""
- }${seconds}`;
- // displayOutput.textContent = displayString;
- this.update(timeLeft, this.wholeTime, type);
- this.updateTimeNum();
- },
- timer(seconds) {
- //counts time, takes seconds
- let remainTime = Date.now() + seconds * 1000;
- this.displayTimeLeft(seconds);
- let _this = this;
- _this.intervalTimer = setInterval(function () {
- _this.timeLeft = Math.round((remainTime - Date.now()) / 1000);
- if (_this.timeLeft < 0) {
- clearInterval(_this.intervalTimer);
- _this.isStarted = false;
- _this.play = false;
- // setterBtns.forEach(function (btn) {
- // btn.disabled = false;
- // btn.style.opacity = 1;
- // });
- _this.displayTimeLeft(_this.wholeTime);
- _this.$message.success("时间到!!!");
- // pauseBtn.classList.remove("pause");
- // pauseBtn.classList.add("play");
- return;
- }
- _this.displayTimeLeft(_this.timeLeft);
- }, 1000);
- },
- pauseTimer() {
- if (!this.play && !this.isPaused) {
- this.play = true;
- this.isStarted = true;
- this.timer(this.wholeTime);
- } else if (this.isPaused) {
- this.play = true;
- this.timer(this.timeLeft);
- this.isStarted = true;
- this.isPaused = this.isPaused ? false : true;
- } else {
- this.play = false;
- this.isStarted = true;
- clearInterval(this.intervalTimer);
- this.isPaused = this.isPaused ? false : true;
- }
- console.log(1);
- },
- reset() {
- clearInterval(this.intervalTimer);
- this.play = false;
- this.isStarted = false;
- this.isPaused = false;
- this.wholeTime = 0;
- this.timeLeft = null;
- this.update(this.wholeTime, this.wholeTime, 1);
- this.displayTimeLeft(this.wholeTime, 1);
- },
- updateTimeNum() {
- this.$emit("updateTimeNum", this.wholeTime);
- },
- getValue() {
- this.wholeTime = this.preTime;
- this.update(this.wholeTime, this.wholeTime, 1);
- this.displayTimeLeft(this.wholeTime,1);
- // this.$forceUpdate();
- },
- },
- created() {
- this.offset = this.length;
- // this.update(this.wholeTime, this.wholeTime);
- // this.displayTimeLeft(this.wholeTime);
- this.getValue();
- this.$nextTick(()=>{
- setTimeout(() => {
- this.cwidth = document.querySelector(".controlls") ? (document.querySelector(".controlls").offsetWidth + 'px') : 'fit-content'
- }, 600);
- })
- },
- beforeDestroy() {
- clearInterval(this.intervalTimer);
- },
- };
- </script>
- <style scoped>
- button[data-setter] {
- outline: none;
- background: transparent;
- border: none;
- font-family: "Roboto";
- font-weight: 300;
- font-size: 36px;
- width: 32px;
- /* height: 30px; */
- color: #409eff;
- cursor: pointer;
- }
- button[data-setter]:hover {
- opacity: 0.5;
- }
- .container {
- position: relative;
- /* top: 30px; */
- width: 300px;
- margin: 0 auto;
- display: flex;
- flex-direction: column;
- justify-content: center;
- }
- .setters {
- position: absolute;
- left: 50%;
- top: 75px;
- transform: translateX(-50%);
- display: flex;
- justify-content: space-between;
- }
- .minutes-set {
- /* float: left; */
- /* margin-right: 28px; */
- /* margin-right: 20px; */
- }
- .seconds-set {
- /* float: right; */
- }
- .controlls {
- position: absolute;
- top: 105px;
- text-align: center;
- min-width: fit-content;
- width: fit-content;
- left: 50%;
- transform: translateX(-50%);
- }
- .display-remain-time {
- font-family: "Roboto";
- font-weight: 100;
- font-size: 66px;
- color: #409eff;
- display: flex;
- flex-wrap: nowrap;
- min-width: fit-content;
- justify-content: center;
- white-space: nowrap;
- }
- #pause {
- outline: none;
- background: transparent;
- border: none;
- margin-top: 10px;
- width: 50px;
- height: 50px;
- position: relative;
- }
- .play::before {
- display: block;
- content: "";
- position: absolute;
- top: 8px;
- left: 16px;
- border-top: 15px solid transparent;
- border-bottom: 15px solid transparent;
- border-left: 22px solid #77a4d3;
- }
- .pause::after {
- content: "";
- position: absolute;
- top: 8px;
- left: 12px;
- width: 15px;
- height: 30px;
- background-color: transparent;
- border-radius: 1px;
- border: 5px solid #77a4d3;
- border-top: none;
- border-bottom: none;
- }
- #pause:hover {
- opacity: 0.8;
- }
- .e-c-base {
- fill: none;
- stroke: #b6b6b6;
- stroke-width: 4px;
- }
- .e-c-progress {
- fill: none;
- stroke: #6eaded;
- stroke-width: 4px;
- transition: stroke-dashoffset 0.7s;
- }
- .e-c-pointer {
- fill: #fff;
- stroke: #6eaded;
- stroke-width: 2px;
- }
- #e-pointer {
- transition: transform 0.7s;
- }
- .reset_btn {
- width: 100px;
- margin: 15px auto 0px;
- background: #527aa3;
- border: none;
- }
- </style>
|