230 lines
6.9 KiB
Vue
230 lines
6.9 KiB
Vue
<script setup>
|
|
import { computed, ref } from 'vue';
|
|
import BigNumber from "bignumber.js";
|
|
|
|
/**
|
|
* @typedef {string} UnitNameStr
|
|
*/
|
|
|
|
/**
|
|
* @enum {UnitNameStr}
|
|
*/
|
|
const UnitName = Object.freeze({
|
|
KBYTE: "unit-k-byte",
|
|
MBYTE: "unit-m-byte",
|
|
GBYTE: "unit-g-byte",
|
|
TBYTE: "unit-t-byte",
|
|
KIBYTE: "unit-ki-byte",
|
|
MIBYTE: "unit-mi-byte",
|
|
GIBYTE: "unit-gi-byte",
|
|
TIBYTE: "unit-ti-byte",
|
|
BYTE: "unit-byte",
|
|
BIT: "unit-bit",
|
|
KBIT: "unit-k-bit",
|
|
MBIT: "unit-m-bit",
|
|
GBIT: "unit-g-bit",
|
|
TBIT: "unit-t-bit",
|
|
})
|
|
|
|
/**
|
|
* @enum {number}
|
|
*/
|
|
const UnitNameToSize = Object.freeze({
|
|
[UnitName.KBYTE]: 1000,
|
|
[UnitName.MBYTE]: 1000 * 1000,
|
|
[UnitName.GBYTE]: 1000 * 1000 * 1000,
|
|
[UnitName.TBYTE]: 1000 * 1000 * 1000 * 1000,
|
|
[UnitName.KIBYTE]: 1024,
|
|
[UnitName.MIBYTE]: 1024 * 1024,
|
|
[UnitName.GIBYTE]: 1024 * 1024 * 1024,
|
|
[UnitName.TIBYTE]: 1024 * 1024 * 1024 * 1024,
|
|
[UnitName.BYTE]: 1,
|
|
[UnitName.BIT]: 1 / 8,
|
|
[UnitName.KBIT]: 1000 / 8,
|
|
[UnitName.MBIT]: 1000000 / 8,
|
|
[UnitName.GBIT]: 1000000000 / 8,
|
|
[UnitName.TBIT]: 1000000000000 / 8,
|
|
});
|
|
|
|
const size = ref({
|
|
[UnitName.KBYTE]: '',
|
|
[UnitName.MBYTE]: '',
|
|
[UnitName.GBYTE]: '',
|
|
[UnitName.TBYTE]: '',
|
|
[UnitName.KIBYTE]: '',
|
|
[UnitName.MIBYTE]: '',
|
|
[UnitName.GIBYTE]: '',
|
|
[UnitName.TIBYTE]: '',
|
|
[UnitName.BYTE]: '',
|
|
[UnitName.BIT]: '',
|
|
[UnitName.KBIT]: '',
|
|
[UnitName.MBIT]: '',
|
|
[UnitName.GBIT]: '',
|
|
[UnitName.TBIT]: '',
|
|
});
|
|
|
|
/**
|
|
* Change ref variable when user inputs some characters.
|
|
* @param {UnitNameStr} unitName
|
|
* @returns {void}
|
|
*/
|
|
function sizeChanged(unitName) {
|
|
/**
|
|
* @type {object.<UnitNameStr, string>}
|
|
*/
|
|
let result = {};
|
|
// assign 0 to current input if nothing is passed
|
|
if (size.value[unitName].length === 0) result[unitName] = '0';
|
|
let inputedBytes = new BigNumber(UnitNameToSize[unitName]).multipliedBy(size.value[unitName]);
|
|
for (const key in UnitNameToSize) {
|
|
result[key] = inputedBytes.div(UnitNameToSize[key]).toString();
|
|
}
|
|
result[unitName] = size.value[unitName];
|
|
for (const key in UnitNameToSize) {
|
|
if (result[key] !== 'NaN') {
|
|
size.value[key] = result[key];
|
|
} else if (result[key] === 'NaN') {
|
|
size.value[key] = '';
|
|
}
|
|
}
|
|
}
|
|
|
|
const isMultipleOf4KiB = computed(() => {
|
|
let userInput = new BigNumber(size.value[UnitName.KIBYTE]);
|
|
if (userInput.toNumber() === 0) return false;
|
|
return userInput.mod(4).toNumber() === 0 ? true : false;
|
|
})
|
|
</script>
|
|
|
|
<template>
|
|
<h1>数据单位换算</h1>
|
|
<div class="unit-conversion-computation-area 1000-in-byte">
|
|
<p>1000 进制并以 Byte 计:</p>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.KBYTE" type="text" v-model="size[UnitName.KBYTE]"
|
|
@input="sizeChanged(UnitName.KBYTE)">
|
|
<span class="unit-name">KB</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.MBYTE" type="text" v-model="size[UnitName.MBYTE]"
|
|
@input="sizeChanged(UnitName.MBYTE)">
|
|
<span class="unit-name">MB</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.GBYTE" type="text" v-model="size[UnitName.GBYTE]"
|
|
@input="sizeChanged(UnitName.GBYTE)">
|
|
<span class="unit-name">GB</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.TBYTE" type="text" v-model="size[UnitName.TBYTE]"
|
|
@input="sizeChanged(UnitName.TBYTE)">
|
|
<span class="unit-name">TB</span>
|
|
</div>
|
|
</div>
|
|
<div class="unit-conversion-computation-area 1024-in-byte">
|
|
<p>1024 进制并以 Byte 计:</p>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.KIBYTE" type="text" v-model="size[UnitName.KIBYTE]"
|
|
@input="sizeChanged(UnitName.KIBYTE)">
|
|
<span class="unit-name">KiB</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.MIBYTE" type="text" v-model="size[UnitName.MIBYTE]"
|
|
@input="sizeChanged(UnitName.MIBYTE)">
|
|
<span class="unit-name">MiB</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.GIBYTE" type="text" v-model="size[UnitName.GIBYTE]"
|
|
@input="sizeChanged(UnitName.GIBYTE)">
|
|
<span class="unit-name">GiB</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.TIBYTE" type="text" v-model="size[UnitName.TIBYTE]"
|
|
@input="sizeChanged(UnitName.TIBYTE)">
|
|
<span class="unit-name">TiB</span>
|
|
</div>
|
|
</div>
|
|
<div class="unit-conversion-computation-area byte-bit">
|
|
<p>以 Byte (B) / bit (b) 计:</p>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.BYTE" type="text" v-model="size[UnitName.BYTE]"
|
|
@input="sizeChanged(UnitName.BYTE)">
|
|
<span class="unit-name">B</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.BIT" type="text" v-model="size[UnitName.BIT]"
|
|
@input="sizeChanged(UnitName.BIT)">
|
|
<span class="unit-name">b</span>
|
|
</div>
|
|
</div>
|
|
<div class="unit-conversion-computation-area 1000-in-bit">
|
|
<p>1000 进制并以 bit 计:</p>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.KBIT" type="text" v-model="size[UnitName.KBIT]"
|
|
@input="sizeChanged(UnitName.KBIT)">
|
|
<span class="unit-name">Kb</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.MBIT" type="text" v-model="size[UnitName.MBIT]"
|
|
@input="sizeChanged(UnitName.MBIT)">
|
|
<span class="unit-name">Mb</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.GBIT" type="text" v-model="size[UnitName.GBIT]"
|
|
@input="sizeChanged(UnitName.GBIT)">
|
|
<span class="unit-name">Gb</span>
|
|
</div>
|
|
<div class="unit-conversion-computation-node">
|
|
<input class="size-text" :id="UnitName.TBIT" type="text" v-model="size[UnitName.TBIT]"
|
|
@input="sizeChanged(UnitName.TBIT)">
|
|
<span class="unit-name">Tb</span>
|
|
</div>
|
|
</div>
|
|
<div class="unit-conversion-computation-result">
|
|
<p v-show="isMultipleOf4KiB">该结果值是 4 KiB 的倍数</p>
|
|
</div>
|
|
</template>
|
|
|
|
<style>
|
|
h1,
|
|
p {
|
|
margin: 0.5em 0;
|
|
}
|
|
|
|
.unit-conversion-computation-node {
|
|
margin: 0.5em 0;
|
|
}
|
|
|
|
.unit-conversion-computation-node {
|
|
float: left;
|
|
width: 170px;
|
|
margin: 0 8px 0 0;
|
|
}
|
|
|
|
.unit-conversion-computation-node .size-text {
|
|
margin: 0 6px 0 0;
|
|
width: 125px
|
|
}
|
|
|
|
@media screen and (max-width: 395px) {
|
|
.unit-conversion-computation-node {
|
|
width: 140px;
|
|
}
|
|
|
|
.unit-conversion-computation-node .size-text {
|
|
width: 95px;
|
|
}
|
|
}
|
|
|
|
.unit-conversion-computation-area::after {
|
|
content: '';
|
|
display: block;
|
|
clear: both;
|
|
}
|
|
|
|
.unit-conversion-computation-result {
|
|
margin: 0.5em 0 0.5em 0;
|
|
height: 1em;
|
|
}
|
|
</style>
|