This commit is contained in:
huangjinming 2023-08-18 10:19:42 +08:00
parent 606a042025
commit 356ce606f1
112 changed files with 44778 additions and 1 deletions

4
.env.dev Normal file
View File

@ -0,0 +1,4 @@
VUE_APP_BASE_API='https://market.cebg.games'
VUE_APP_BASE_API2='https://invitation.counterfire.games'
//VUE_APP_BASE_API2='http://192.168.100.83:3000/'
VUE_APP_GPAL_API='https://gacha.counterfire.games'

2
.env.development Normal file
View File

@ -0,0 +1,2 @@
VUE_APP_BASE_API='https://market.cebg.games'
VUE_APP_GPAL_API='http://192.168.100.83:4000/sns'

3
.env.production Normal file
View File

@ -0,0 +1,3 @@
VUE_APP_BASE_API='https://market.cebg.games'
VUE_APP_BASE_API2='https://invitation.counterfire.games'
VUE_APP_GPAL_API='https://gacha.counterfire.games'

1
.evn.test Normal file
View File

@ -0,0 +1 @@
//VITE_API_BASE_URL=http://localhost:5000

15
.gitignore vendored Normal file
View File

@ -0,0 +1,15 @@
.DS_Store
node_modules/
/dist/
npm-debug.log*
yarn-debug.log*
yarn-error.log*
# Editor directories and files
.idea
.vscode
*.suo
*.ntvs*
*.njsproj
*.sln

View File

@ -1 +1,7 @@
planet
运行代码指令
npm run dev
yarn run dev

6
README.txt Normal file
View File

@ -0,0 +1,6 @@
build command:
export NODE_OPTIONS=--max_old_space_size=8192
npm run build:prod

58
index.html Normal file
View File

@ -0,0 +1,58 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<link rel="icon" href="/logo.png" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Planet</title>
<meta property="og:title" content="Gacha" />
<meta
property="og:description"
content="Gacha.counterFire.games | Gacha is blinking! Quest and Rewards.Join Counter Fire and Rise of Gacha. Get your gacha and rewards. A new evolution about Web3Gaming."
/>
<meta
name="description"
content="Gacha.counterFire.games | Gacha is blinking! Quest and Rewards.Join Counter Fire and Rise of Gacha. Get your gacha and rewards. A new evolution about Web3Gaming."
/>
<meta
name="keywords"
content="CounterFireCFGamefiWeb3web3gaming; Cf game;Cf mobile; CounterFire googleplay; CounterFire Appstore;
battle royale;token;airdrop;p2e; play to earn, free to play, blockchain game;Arbitrum game;Arbitrum. Cryptocurrency; Cryptoanime gameanime web3 gameTwo-dimensional gameshooting gameAnime shooting mobile game"
/>
<meta property="og:type" content="website" />
<meta property="og:url" content="https://gacha.counterfire.games/" />
<meta
property="og:image"
content="https://gacha.counterfire.games/images/counter.png"
/>
<!-- <meta property="og:site_name" content="Counter Fire" /> -->
<meta property="twitter:card" content="summary_large_image" />
<meta property="twitter:title" content="Gacha" />
<meta
property="twitter:image"
content="https://gacha.counterfire.games/images/counter.png"
/>
</head>
<script type="module">
import { Buffer } from "buffer";
window.Buffer = Buffer;
</script>
<body>
<div id="app"></div>
<script type="module" src="/src/main.js"></script>
<!-- Google tag (gtag.js) -->
<script
async
src="https://www.googletagmanager.com/gtag/js?id=G-9WFW3HQTR8"
></script>
<script>
window.dataLayer = window.dataLayer || [];
function gtag() {
dataLayer.push(arguments);
}
gtag("js", new Date());
gtag("config", "G-9WFW3HQTR8");
</script>
</body>
</html>

24957
package-lock.json generated Normal file

File diff suppressed because it is too large Load Diff

62
package.json Normal file
View File

@ -0,0 +1,62 @@
{
"name": "my-vue-app",
"private": true,
"version": "0.0.0",
"scripts": {
"dev": "vite --host --mode dev",
"build:dev": "vite build --mode dev",
"build:test": "vite build --mode test",
"build:prod": "vite build --mode production"
},
"dependencies": {
"@animxyz/core": "^0.6.6",
"@animxyz/vue3": "^0.6.7",
"@esbuild-plugins/node-globals-polyfill": "^0.2.3",
"@metamask/safe-event-emitter": "^2.0.0",
"@vue/runtime-dom": "^3.2.47",
"@vueuse/core": "^9.12.0",
"@walletconnect/web3-provider": "^1.8.0",
"animate.css": "^4.1.1",
"ant-design-vue": "^3.2.15",
"axios": "^1.3.3",
"buffer": "^6.0.3",
"gsap": "^3.11.5",
"js-cookie": "^3.0.1",
"normalize.css": "^8.0.1",
"pinia": "^2.0.30",
"postcss-px-to-viewport": "^1.1.1",
"prerender-spa-plugin-next": "^4.2.3",
"process": "^0.11.10",
"rollup-plugin-polyfill-node": "^0.12.0",
"stream-browserify": "^3.0.0",
"swiper": "8",
"util": "^0.12.5",
"uuid": "^9.0.0",
"video.js": "^8.0.4",
"videojs-flash": "^2.2.1",
"vite-plugin-pages": "^0.31.0",
"vite-plugin-ssr": "^0.4.132",
"vite-ssg": "^0.22.2",
"vue": "^3.2.45",
"vue-3d-loader": "^2.1.5",
"vue-router": "^4.1.6",
"vue3-autocounter": "^1.0.6",
"vue3-clipboard": "^1.0.0",
"web3": "^1.8.2",
"youtube-player": "^5.6.0"
},
"devDependencies": {
"@vitejs/plugin-vue": "^4.0.0",
"autoprefixer": "^10.4.14",
"eslint-config-prettier": "^8.6.0",
"eslint-plugin-prettier": "^4.2.1",
"postcss": "^8.4.21",
"prettier": "^2.8.4",
"sass": "^1.58.1",
"tailwindcss": "^3.3.1",
"terser": "^5.16.3",
"vite": "^4.1.0",
"vite-plugin-prerender": "^1.0.8",
"vite-plugin-require-transform": "^1.0.9"
}
}

24
postcss.config.cjs Normal file
View File

@ -0,0 +1,24 @@
module.exports = {
plugins: {
'postcss-px-to-viewport': {
unitToConvert: 'px', // 需要转换的单位,默认为"px"
viewportWidth: 1920, // 设计稿的视口宽度
unitPrecision: 5, // 单位转换后保留的精度
propList: ['*'], // 能转化为vw的属性列表
viewportUnit: 'vw', // 希望使用的视口单位
fontViewportUnit: 'vw', // 字体使用的视口单位
selectorBlackList: [], // 需要忽略的CSS选择器不会转为视口单位使用原有的px等单位。
minPixelValue: 1, // 设置最小的转换数值如果为1的话只有大于1的值会被转换
mediaQuery: false, // 媒体查询里的单位是否需要转换单位
replace: true, // 是否直接更换属性值,而不添加备用属性
exclude: undefined, // 忽略某些文件夹下的文件或特定文件,例如 'node_modules' 下的文件
include: undefined, // 如果设置了include那将只有匹配到的文件才会被转换
landscape: false, // 是否添加根据 landscapeWidth 生成的媒体查询条件 @media (orientation: landscape)
landscapeUnit: 'vw', // 横屏时使用的单位
landscapeWidth: 1920 // 横屏时使用的视口宽度
}
}
}

BIN
public/favicon.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.2 KiB

BIN
public/images/counter.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

BIN
public/logo.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 KiB

70
src/App.vue Normal file
View File

@ -0,0 +1,70 @@
<template>
<div id="app">
<Layout></Layout>
<Notification :position="'top-right'" :duration="3000" ref="notification" />
</div>
</template>
<script setup>
import { ref, onMounted, watch, reactive ,provide} from "vue";
import Layout from "@/components/layout/index.vue";
import Notification from './components/global/Notification.vue'
import { gsap } from "gsap";
import { ScrollTrigger } from "gsap/ScrollTrigger";
gsap.registerPlugin(ScrollTrigger);
const notification = ref(null);
// setup addNotification
provide('addNotification', (title, message) => {
notification.value.addNotification(title, message);
});
</script>
<style lang="scss">
body,
html {
padding: 0;
margin: 0;
height: 100%;
position: relative;
font-family: "ui-sans-serif", "system-ui", "-apple-system",
"BlinkMacSystemFont", "Segoe UI", "Roboto", "Helvetica Neue", "Arial",
"Noto Sans", "sans-serif", "Apple Color Emoji", "Segoe UI Emoji",
"Segoe UI Symbol", "Noto Color Emoji";
audio,
canvas,
embed,
iframe,
img,
object,
svg,
video {
display: block;
vertical-align: middle;
}
img,
video {
max-width: 100%;
height: auto;
}
}
.fade-enter-active,
.fade-leave-active {
transition: opacity 0.5s ease;
}
.fade-enter-from,
.fade-leave-to {
opacity: 0;
}
@font-face {
font-family: "MyFont";
src: url("/fonts/myfont.ttf") format("truetype");
}
#app{
height: 100%;
position: relative;
}
</style>

104
src/api/User.js Normal file
View File

@ -0,0 +1,104 @@
import request from '@/utils/request'
import request2 from '@/utils/requestduplicate'
const GPAL_URL = import.meta.env.VUE_APP_GPAL_API;
export const defaultUser = {
id: '',
username: '',
showname: '',
comment: '',
locked: false,
password: '',
avatar: '',
account: ''
}
/**
* @param data {account: string, token: string}
*/
export const getUserInfo = (data) =>
request({
url: '/webapp/index.php?c=BcUser&a=info',
method: 'get',
params: data
})
export const login = (data) =>
request({
url: '/webapp/index.php?c=Market&a=auth',
method: 'get',
params: data
})
export const logout = () =>
request({
url: '/api/user/logout',
method: 'post'
})
export const beginclaim = (data) => {
return request2({
url: '/aa2/beginClaim',
method: 'post',
data
})
}
export const Claim=(data)=>{
return request2({
url: '/aa2/claim',
method: 'post',
data
})
}
export const UserStatus=(data)=>{
return request2({
url: '/aa2/user_status',
method: 'post',
data
})
}
export const getLeaderboard=(data)=>{
return request2({
url: '/aa2/leaderboard',
method: 'post',
data
})
}
export const UserInfo=(data)=>{
return request2({
url: '/aa2/user_info',
method: 'post',
data
})
}
export const totalClaimed=(data)=>{
return request2({
url: '/aa2/totalClaimed',
method: 'post',
data
})
}
export const getJoin=(data)=>{
return request2({
url: '/aa2/join',
method: 'post',
data
})
}
//
// export const changePass = (params: any) =>
// request({
// url: '/api/user/passwd',
// method: 'post',
// data: params
// })
export const getNonce = (params) =>
request({
url: '/webapp/index.php?c=Market&a=getNonce',
method: 'get',
params: params
})

349
src/assets/css/normalize.css vendored Normal file
View File

@ -0,0 +1,349 @@
/*! normalize.css v8.0.1 | MIT License | github.com/necolas/normalize.css */
/* Document
========================================================================== */
/**
* 1. Correct the line height in all browsers.
* 2. Prevent adjustments of font size after orientation changes in iOS.
*/
html {
line-height: 1.15; /* 1 */
-webkit-text-size-adjust: 100%; /* 2 */
}
/* Sections
========================================================================== */
/**
* Remove the margin in all browsers.
*/
body {
margin: 0;
}
/**
* Render the `main` element consistently in IE.
*/
main {
display: block;
}
/**
* Correct the font size and margin on `h1` elements within `section` and
* `article` contexts in Chrome, Firefox, and Safari.
*/
h1 {
font-size: 2em;
margin: 0.67em 0;
}
/* Grouping content
========================================================================== */
/**
* 1. Add the correct box sizing in Firefox.
* 2. Show the overflow in Edge and IE.
*/
hr {
box-sizing: content-box; /* 1 */
height: 0; /* 1 */
overflow: visible; /* 2 */
}
/**
* 1. Correct the inheritance and scaling of font size in all browsers.
* 2. Correct the odd `em` font sizing in all browsers.
*/
pre {
font-family: monospace, monospace; /* 1 */
font-size: 1em; /* 2 */
}
/* Text-level semantics
========================================================================== */
/**
* Remove the gray background on active links in IE 10.
*/
a {
background-color: transparent;
}
/**
* 1. Remove the bottom border in Chrome 57-
* 2. Add the correct text decoration in Chrome, Edge, IE, Opera, and Safari.
*/
abbr[title] {
border-bottom: none; /* 1 */
text-decoration: underline; /* 2 */
text-decoration: underline dotted; /* 2 */
}
/**
* Add the correct font weight in Chrome, Edge, and Safari.
*/
b,
strong {
font-weight: bolder;
}
/**
* 1. Correct the inheritance and scaling of font size in all browsers.
* 2. Correct the odd `em` font sizing in all browsers.
*/
code,
kbd,
samp {
font-family: monospace, monospace; /* 1 */
font-size: 1em; /* 2 */
}
/**
* Add the correct font size in all browsers.
*/
small {
font-size: 80%;
}
/**
* Prevent `sub` and `sup` elements from affecting the line height in
* all browsers.
*/
sub,
sup {
font-size: 75%;
line-height: 0;
position: relative;
vertical-align: baseline;
}
sub {
bottom: -0.25em;
}
sup {
top: -0.5em;
}
/* Embedded content
========================================================================== */
/**
* Remove the border on images inside links in IE 10.
*/
img {
border-style: none;
}
/* Forms
========================================================================== */
/**
* 1. Change the font styles in all browsers.
* 2. Remove the margin in Firefox and Safari.
*/
button,
input,
optgroup,
select,
textarea {
font-family: inherit; /* 1 */
font-size: 100%; /* 1 */
line-height: 1.15; /* 1 */
margin: 0; /* 2 */
}
/**
* Show the overflow in IE.
* 1. Show the overflow in Edge.
*/
button,
input { /* 1 */
overflow: visible;
}
/**
* Remove the inheritance of text transform in Edge, Firefox, and IE.
* 1. Remove the inheritance of text transform in Firefox.
*/
button,
select { /* 1 */
text-transform: none;
}
/**
* Correct the inability to style clickable types in iOS and Safari.
*/
button,
[type="button"],
[type="reset"],
[type="submit"] {
-webkit-appearance: button;
}
/**
* Remove the inner border and padding in Firefox.
*/
button::-moz-focus-inner,
[type="button"]::-moz-focus-inner,
[type="reset"]::-moz-focus-inner,
[type="submit"]::-moz-focus-inner {
border-style: none;
padding: 0;
}
/**
* Restore the focus styles unset by the previous rule.
*/
button:-moz-focusring,
[type="button"]:-moz-focusring,
[type="reset"]:-moz-focusring,
[type="submit"]:-moz-focusring {
outline: 1px dotted ButtonText;
}
/**
* Correct the padding in Firefox.
*/
fieldset {
padding: 0.35em 0.75em 0.625em;
}
/**
* 1. Correct the text wrapping in Edge and IE.
* 2. Correct the color inheritance from `fieldset` elements in IE.
* 3. Remove the padding so developers are not caught out when they zero out
* `fieldset` elements in all browsers.
*/
legend {
box-sizing: border-box; /* 1 */
color: inherit; /* 2 */
display: table; /* 1 */
max-width: 100%; /* 1 */
padding: 0; /* 3 */
white-space: normal; /* 1 */
}
/**
* Add the correct vertical alignment in Chrome, Firefox, and Opera.
*/
progress {
vertical-align: baseline;
}
/**
* Remove the default vertical scrollbar in IE 10+.
*/
textarea {
overflow: auto;
}
/**
* 1. Add the correct box sizing in IE 10.
* 2. Remove the padding in IE 10.
*/
[type="checkbox"],
[type="radio"] {
box-sizing: border-box; /* 1 */
padding: 0; /* 2 */
}
/**
* Correct the cursor style of increment and decrement buttons in Chrome.
*/
[type="number"]::-webkit-inner-spin-button,
[type="number"]::-webkit-outer-spin-button {
height: auto;
}
/**
* 1. Correct the odd appearance in Chrome and Safari.
* 2. Correct the outline style in Safari.
*/
[type="search"] {
-webkit-appearance: textfield; /* 1 */
outline-offset: -2px; /* 2 */
}
/**
* Remove the inner padding in Chrome and Safari on macOS.
*/
[type="search"]::-webkit-search-decoration {
-webkit-appearance: none;
}
/**
* 1. Correct the inability to style clickable types in iOS and Safari.
* 2. Change font properties to `inherit` in Safari.
*/
::-webkit-file-upload-button {
-webkit-appearance: button; /* 1 */
font: inherit; /* 2 */
}
/* Interactive
========================================================================== */
/*
* Add the correct display in Edge, IE 10+, and Firefox.
*/
details {
display: block;
}
/*
* Add the correct display in all browsers.
*/
summary {
display: list-item;
}
/* Misc
========================================================================== */
/**
* Add the correct display in IE 10+.
*/
template {
display: none;
}
/**
* Add the correct display in IE 10.
*/
[hidden] {
display: none;
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 21 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 21 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 66 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 24 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 13 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 275 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 279 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 272 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 54 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.3 KiB

View File

@ -0,0 +1 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1677464048404" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="5219" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><path d="M911.020879 320.237361c-36.202548 0-66.192962 28.664228-66.192962 63.470791V630.54159c0 34.806563 28.966692 63.494057 66.192962 63.494057 36.179281 0 66.169695-28.687495 66.169695-63.517323V383.731418c-1.023722-34.806563-29.990414-63.470791-66.169695-63.47079z m-798.317365 0C76.547499 320.237361 46.533818 348.901589 46.533818 383.684885V630.54159c0 34.806563 28.943425 63.494057 66.169696 63.494057 37.22627 0 66.192962-28.687495 66.192961-63.517323V383.731418c0-34.806563-28.966692-63.470791-66.192961-63.47079z m106.513665 2.047445v451.601191c0 26.616783 22.754558 49.138677 51.697983 49.138677h58.957106v137.225338c0 34.829829 28.943425 63.494057 66.169695 63.494057 36.202548 0 66.192962-28.664228 66.192962-63.494057v-137.225338h103.395965v137.225338c0 34.829829 28.966692 63.494057 66.192962 63.494057C667.979867 1023.744069 697.993547 995.079841 697.993547 960.250012v-137.225338h58.933839c28.966692 0 51.721249-21.498171 51.72125-49.138677V322.26154H219.217179zM651.46071 88.783026L706.276393 15.051744c2.047445-5.118612 2.047445-11.260947-3.117701-13.308391-4.141423-3.071167-10.33029-1.023722-13.44799 3.071167l-55.839405 76.802449A363.142266 363.142266 0 0 0 511.862196 60.118798c-43.438404 0-84.78283 7.166057-122.009101 21.498171l-55.839405-76.779183c-3.1177-5.118612-9.306568-6.165601-13.44799-3.094433a9.655564 9.655564 0 0 0-2.093978 13.308391l54.815683 73.754548c-85.806553 37.87773-146.811103 109.561567-154.070226 193.530073h588.407734c-9.306568-83.991772-69.310662-155.652342-156.164203-193.553339zM387.782384 205.533916c-18.613135 0-32.061125-13.308392-32.061125-30.711673 0-17.426548 14.471713-30.711673 32.061125-30.711673 18.613135 0 32.037859 13.285125 32.037859 30.711673 0 17.403281-14.471713 30.711673-32.037859 30.711673z m252.301047 0c-18.613135 0-32.061125-13.308392-32.061125-30.711673 0-17.426548 14.494979-30.711673 32.061125-30.711673 18.613135 0 32.061125 13.285125 32.061125 30.711673 0 17.403281-14.471713 30.711673-32.061125 30.711673z" fill="#6E7580" p-id="5220"></path></svg>

After

Width:  |  Height:  |  Size: 2.3 KiB

1
src/assets/svg/apple.svg Normal file
View File

@ -0,0 +1 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1677464028670" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="4201" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><path d="M836.608 675.84q41.984 59.392 96.256 76.8-23.552 72.704-74.752 151.552-78.848 118.784-155.648 118.784-28.672 0-84.992-19.456-52.224-19.456-91.136-19.456t-86.016 20.48q-49.152 19.456-80.896 19.456-92.16 0-181.248-156.672-89.088-154.624-89.088-304.128 0-138.24 67.584-226.304 69.632-88.064 172.032-88.064 22.528 0 50.176 5.632t57.344 20.992q31.744 17.408 52.224 24.064t31.744 6.656q13.312 0 40.96-6.144t55.296-22.528q29.696-16.384 51.2-24.576t44.032-8.192q71.68 0 129.024 38.912 30.72 20.48 62.464 60.416-47.104 40.96-68.608 71.68-39.936 57.344-39.936 124.928 0 74.752 41.984 135.168zM630.784 197.632q-35.84 33.792-65.536 44.032-10.24 3.072-26.112 5.632t-36.352 4.608q1.024-90.112 47.104-155.648t151.552-90.112q2.048 10.24 3.072 14.336l0 11.264q0 36.864-17.408 82.944-18.432 45.056-56.32 82.944z" fill="#272636" p-id="4202"></path></svg>

After

Width:  |  Height:  |  Size: 1.1 KiB

11
src/assets/svg/btn.svg Normal file
View File

@ -0,0 +1,11 @@
<svg width="100" height="40">
<rect x="0" y="0" width="100" height="40" fill="#0080ff" />
<rect x="25" y="10" width="50" height="20" fill="#ff4d4d" opacity="0">
<animate attributeName="opacity" from="0" to="1" begin="mouseover" dur="0.2s" fill="freeze" />
<animate attributeName="width" from="0" to="50" begin="mouseover" dur="0.2s" fill="freeze" />
<animate attributeName="height" from="0" to="20" begin="mouseover" dur="0.2s" fill="freeze" />
<animate attributeName="x" from="50" to="25" begin="mouseover" dur="0.2s" fill="freeze" />
<animate attributeName="y" from="15" to="10" begin="mouseover" dur="0.2s" fill="freeze" />
</rect>
<text x="50" y="24" text-anchor="middle" fill="#fff" font-size="16">按钮</text>
</svg>

After

Width:  |  Height:  |  Size: 772 B

View File

@ -0,0 +1,19 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 29 28" style="enable-background:new 0 0 29 28;" xml:space="preserve">
<style type="text/css">
.st0{fill:#60FF00;}
.st1{fill:#030000;}
</style>
<g>
<g>
<path class="st0" d="M8.49,23.9L8.49,23.9c-0.59-0.59-0.59-1.54,0-2.12L26.17,4.1c0.59-0.59,1.54-0.59,2.12,0l0,0
c0.59,0.59,0.59,1.54,0,2.12L10.61,23.9C10.03,24.49,9.08,24.49,8.49,23.9z"/>
</g>
<g>
<path class="st0" d="M0.71,14L0.71,14c0.59-0.59,1.54-0.59,2.12,0l7.78,7.78c0.59,0.59,0.59,1.54,0,2.12l0,0
c-0.59,0.59-1.54,0.59-2.12,0l-7.78-7.78C0.13,15.54,0.13,14.59,0.71,14z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 836 B

View File

@ -0,0 +1,19 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 29 28" style="enable-background:new 0 0 29 28;" xml:space="preserve">
<style type="text/css">
.st0{fill:#60FF00;}
.st1{fill:#030000;}
</style>
<g>
<g>
<path class="st1" d="M8.49,23.9L8.49,23.9c-0.59-0.59-0.59-1.54,0-2.12L26.17,4.1c0.59-0.59,1.54-0.59,2.12,0l0,0
c0.59,0.59,0.59,1.54,0,2.12L10.61,23.9C10.03,24.49,9.08,24.49,8.49,23.9z"/>
</g>
<g>
<path class="st1" d="M0.71,14L0.71,14c0.59-0.59,1.54-0.59,2.12,0l7.78,7.78c0.59,0.59,0.59,1.54,0,2.12l0,0
c-0.59,0.59-1.54,0.59-2.12,0l-7.78-7.78C0.13,15.54,0.13,14.59,0.71,14z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 836 B

View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 48 48"><image width="46" height="45" xlink:href="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAC4AAAAtCAYAAADRLVmZAAAH1klEQVRogeXZeaweZRUG8F8FhBYI Q1WUCAKJKIgsslnAqhUomwRaEBSVAsHBDo0FyiYqCiotVNlKRxhZLYvKUhCXAmURRfaCytoihJKg INCBUmmKpf5xZvJNP+Zu7f3Pk3y5911m3ud955znPGdmCKzzjfEG2YbhVHwVr+A8XN7T5LLIB7zA qisIrDf7JC7ELlV7A1yGHXE8/jMYi7xnMG7SsCNxpw7opo3H7dhpMBYaLOBr4QL8HO/vZd4IzMY3 V3bBwQC+HW7F0S1jy6pf04bhZ8KdkhVddGWBH6798T+BWY327/Bo15yjcId4CgO2FQX+AVyES7FO 19iT+CJuwJDqNxNj8c+uuZ/CbUmaTRgogBUBvqM4zbRl7Hl8Cc9h3Ub/hlXfAXip65q1MC1JsyuS NHtff0EMFPh4EVzbtozNxR54vGo3gQ+r/t6L3cQmuu1Q3JmkWRsjvcv6C/yDuBY51m4Zn4PReLpq H4FJwq/n4lsYV409Jjb4tHfblsJ1Jg0G8JGCNQ7sYfyOCvTz1f2m4BK8iL2xD14VmfPH1Zx54uTv 9W7WGYqfJGk2I0mzHqm1L+Dfxh+wVQ/jz2ECloiMeQNOEgH6WRGMz1T/P4NTcJM42YXIqk202ddw d5Jmu7YNDqFVq6yP6RhTtZdilZbrF+FfWE0E2XD8WrjKoq65CX6BffFa9VsmJMHQHsATh3JqWeRn NjvbtMq+OAubNfr+holYrBN0y/Bf4a8nNeY+0gIaSuFW+1YbHF71T8LDWL0xd0G1ztnYAlOSNNse J5VF/izLn/gQfLf6vbdl12cKxddm++EKHU4vcFxjA6vjR8I1aoZ5FYfg1jZ1mKTZedX85uHOxcSy yGfVwNfDNBzUA7DabhLs8HrL2La4DptU7b8IWbtEuEjTV+cJvv8ry8vaJM2G45fYvQcMS/GDOjg3 7Qdo4mRvxHotY3OE28yp2jvjLtzTBfoe7FWDblqSZhuJAO8JNBFrJ9bAH8IZ/QAOn69u3gZ+ngjo P1XtjbBxY3yWyJ7/aAG9sQjsz/Wx/ss4uptVxgiX+XCf8COR7IdnW8bWxQzB4bXdLJ7q4pb5H8dv 8LE+1rwLR5VFPrebx2cK4XNLn7CDt2/H1i1jC0SWbdo07aB3EmzTF+ipZZGPKot8LstH7B4im52A PXE6vqP3JLWx2OyBOr5dW7c06FaRhC9fIfJGT/YCji6L/OYkzbbBYZheg9oK14ua8F58QlDffiKV 92abVOC7NflqXe3unLGnYI/eQM/GLhXocVV7Iq6qgS/R4dwRuF9UNL/FDoIGe7OPiGJhdKOv+0kN afw/VhzUcO22FKeURb47Xk7S7EqhdWrZ+2Z986fwBUFVdGrIAm9gf+E2S3sBv67YaE2rZdd47d+p 4Pth2u05jCqLfHKSZjvgzyIf1DYd+3ezyqr4qZChtT0qyqwHxOOdho/2soHFYqNv4Y9V39viSW6g 96c3ExPKIn8xSbNjRZytVY29hmPKIp/B8o9zFVGhTxRZ7dWqfxvBy6ng4Z0Ej/dkawg3OB3vVH1L Rcxc2st1x5VFPhYLkzS7XOiUGvQ9GFkW+YwkzTako1XWFm+bRuNkXCn89mLLZ7FrhO8vEOxzmt6V 3TLL+3abPY6sLPK7kzQbhfMF1dZ2dlnkkyBJswtErjmrBr6zjn/DOUIkweRqM7U9KSjpAVFkXChY aEVsRgX6zSTNjhFFSK0SXxGucVWSZptU69TB/3rtKk+KQKztWEGLm4liYoxOhb65cJ3jq78jRKoe iC3GMaLOXCNJs+vFYdWg78CICvTBQpLUoBfhezXwBSIAJ+oovxFC4R0hhNW2+H019l5MrdrDcLCo hN7oB+g54kmdJ8TWg4Iea5tSFvmumJ+k2bmC64c3rh1dFvm0VWCN7XaoL7pfuMwWQq8MFUlo/eoG VwvmGSl8d9Nq/An8SuiRkaK4brPLhH55UZRxRQPUfBxeFvkFSZptXt2ruaFLcFhZ5E/Tc+m2tuDx Qxt991XtWgGeKwKYoLvJ+D7WFFw7rnHtQuFy0yugF+uUhXAbjiyLfH6SZodUa9eV1hui8rmwCbAn HbKwWni8CBLCdR4WLyxn4tMiWxLp/VRRWA8XwXuQoM3LhTafLk77IcvXspPLIh+NV5I0uxRXNUA/ iN26QdPziTdtaxHRzXd8lwnfJ0q903QOYb6IlRu77nN6Nbemx3k6r563FG7YpMEcJ5dFvrANVH+A ExX6FBHAtT1YLfywOMmLdHT8O4KPLxFP4BShPmubJdzu36KuPENHPZY4oSzyi3sD1F/gtX1F0FYd fG8Jjj8fHxK+eUAv178tNM9UEUcFvtwYv0/w+iN9ARnou8NrMEpHgwzV+b6zSOjySUJtdttT4sXQ VHymAtkEPR279wf0igAnktVe4t1LbeNEwhopNMaeIgiJU75axMh9IiPP1sm2C/D1ssgnlEX+Zn9B DNRVuu1A4R6167wjTvxcwTRjhKqbLeKkEAKutruFGvz7QBde2S8S14nHf1vjfucIdbi+kAKzdZ5A E/RZImAHDJrB+Vw4V3yB+CFOrPrGYnvxBW5NkV3rUu4l4S5Xr8yig/Wdc4l4f/iQ8PENRFYd1zXv FiHOHlvZBQf7O+e1wnVu7epfJvLAPgYBNIMPnKgZ9xYvSV8Qpd84oVV6q1n/P+x/Y/QhtBsN+W0A AAAASUVORK5CYII=" transform="translate(1 1.5)" overflow="visible"/></svg>

After

Width:  |  Height:  |  Size: 2.9 KiB

View File

@ -0,0 +1,18 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 25.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 250 200" style="enable-background:new 0 0 250 200;" xml:space="preserve">
<style type="text/css">
.st0{fill:#EC2E5A;}
</style>
<path class="st0" d="M204.9,27.3c-0.1-0.1-0.2-0.2-0.3-0.3c-14.9-6.8-30.6-11.7-46.8-14.5c-0.3-0.1-0.6,0.1-0.8,0.4
c-2.1,3.9-4.1,7.9-5.8,12c-17.4-2.6-35.1-2.6-52.5,0c-1.7-4.1-3.7-8.1-5.9-12c-0.2-0.3-0.5-0.4-0.8-0.4C76,15.3,60.2,20.2,45.3,27
c-0.1,0.1-0.2,0.1-0.3,0.3C15.3,71.7,7.1,115.1,11.1,158c0,0.2,0.1,0.4,0.3,0.5c17.3,12.8,36.7,22.6,57.4,29c0.3,0.1,0.6,0,0.8-0.3
c4.4-6,8.4-12.4,11.7-19.1c0.2-0.4,0-0.8-0.3-1c0,0-0.1,0-0.1,0c-6.2-2.4-12.2-5.2-17.9-8.5c-0.4-0.2-0.5-0.7-0.3-1
c0-0.1,0.1-0.2,0.2-0.2c1.2-0.9,2.4-1.8,3.6-2.8c0.2-0.2,0.5-0.2,0.7-0.1c37.6,17.2,78.3,17.2,115.4,0c0.2-0.1,0.5-0.1,0.8,0.1
c1.2,1,2.4,1.9,3.6,2.8c0.3,0.2,0.4,0.7,0.1,1c-0.1,0.1-0.1,0.1-0.2,0.2c-5.7,3.3-11.7,6.2-17.9,8.5c-0.4,0.1-0.6,0.6-0.4,0.9
c0,0,0,0.1,0,0.1c3.4,6.6,7.4,13,11.7,19.1c0.2,0.3,0.5,0.4,0.8,0.3c20.7-6.3,40.1-16.1,57.4-29c0.2-0.1,0.3-0.3,0.3-0.5
C243.6,108.4,230.8,65.4,204.9,27.3L204.9,27.3z M86.9,131.9c-11.3,0-20.6-10.4-20.6-23.1s9.1-23.1,20.6-23.1
c11.6,0,20.8,10.5,20.6,23.1C107.6,121.5,98.4,131.9,86.9,131.9z M163.2,131.9c-11.3,0-20.6-10.4-20.6-23.1s9.1-23.1,20.6-23.1
c11.6,0,20.8,10.5,20.6,23.1C183.9,121.5,174.8,131.9,163.2,131.9z"/>
</svg>

After

Width:  |  Height:  |  Size: 1.5 KiB

View File

@ -0,0 +1 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1677464651966" class="icon" viewBox="0 0 1280 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="1126" xmlns:xlink="http://www.w3.org/1999/xlink" width="250" height="200"><path d="M1049.062 139.672a3 3 0 0 0-1.528-1.4A970.13 970.13 0 0 0 808.162 64.06a3.632 3.632 0 0 0-3.846 1.82 674.922 674.922 0 0 0-29.8 61.2 895.696 895.696 0 0 0-268.852 0 619.082 619.082 0 0 0-30.27-61.2 3.78 3.78 0 0 0-3.848-1.82 967.378 967.378 0 0 0-239.376 74.214 3.424 3.424 0 0 0-1.576 1.352C78.136 367.302 36.372 589.38 56.86 808.708a4.032 4.032 0 0 0 1.53 2.75 975.332 975.332 0 0 0 293.65 148.378 3.8 3.8 0 0 0 4.126-1.352A696.4 696.4 0 0 0 416.24 860.8a3.72 3.72 0 0 0-2.038-5.176 642.346 642.346 0 0 1-91.736-43.706 3.77 3.77 0 0 1-0.37-6.252 502.094 502.094 0 0 0 18.218-14.274 3.638 3.638 0 0 1 3.8-0.512c192.458 87.834 400.82 87.834 591 0a3.624 3.624 0 0 1 3.848 0.466 469.066 469.066 0 0 0 18.264 14.32 3.768 3.768 0 0 1-0.324 6.252 602.814 602.814 0 0 1-91.78 43.66 3.75 3.75 0 0 0-2 5.222 782.11 782.11 0 0 0 60.028 97.63 3.728 3.728 0 0 0 4.126 1.4A972.096 972.096 0 0 0 1221.4 811.458a3.764 3.764 0 0 0 1.53-2.704c24.528-253.566-41.064-473.824-173.868-669.082zM444.982 675.16c-57.944 0-105.688-53.174-105.688-118.478s46.818-118.482 105.688-118.482c59.33 0 106.612 53.64 105.686 118.478 0 65.308-46.82 118.482-105.686 118.482z m390.76 0c-57.942 0-105.686-53.174-105.686-118.478s46.818-118.482 105.686-118.482c59.334 0 106.614 53.64 105.688 118.478 0 65.308-46.354 118.482-105.688 118.482z" p-id="1127"></path></svg>

After

Width:  |  Height:  |  Size: 1.6 KiB

View File

@ -0,0 +1,11 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 25.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 200 200" style="enable-background:new 0 0 200 200;" xml:space="preserve">
<style type="text/css">
.st0{fill:#EC2E5A;}
</style>
<path class="st0" d="M127.1,91.5L40.9,5.1l109.7,63C150.5,68,127.1,91.5,127.1,91.5z M18.4,0c-5.1,2.7-8.5,7.5-8.5,13.8v172.4
c0,6.3,3.4,11.1,8.5,13.8l100.2-100L18.4,0z M184.5,88.1l-23-13.3L135.8,100l25.7,25.2l23.5-13.3C192,106.3,192,93.7,184.5,88.1
L184.5,88.1z M40.9,194.9l109.7-63l-23.5-23.5L40.9,194.9z"/>
</svg>

After

Width:  |  Height:  |  Size: 720 B

View File

@ -0,0 +1 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1677464090924" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="6760" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><path d="M650.6 468.6L209.2 26l561.6 322.4-120.2 120.2zM94 0C68 13.6 50.6 38.4 50.6 70.6v882.6c0 32.2 17.4 57 43.4 70.6l513.2-512L94 0z m850.4 451.2l-117.8-68.2-131.4 129 131.4 129 120.2-68.2c36-28.6 36-93-2.4-121.6zM209.2 998l561.6-322.4-120.2-120.2L209.2 998z" p-id="6761"></path></svg>

After

Width:  |  Height:  |  Size: 612 B

View File

@ -0,0 +1 @@
<svg version="1.1" id="prefix__图层_1" xmlns="http://www.w3.org/2000/svg" x="0" y="0" viewBox="0 0 48 48" xml:space="preserve"><style>.prefix__st2{fill:#0f6569} .prefix__st2:hover{fill:#f12c12}</style><path class="prefix__st2" d="M40.94 19.13l-1-1c0-7-4-16-14.41-16.47-7.4-.34-13.59.47-18.59 10.47s2 17 2 17c0-7 3-9 3-9 1.19 1.03.92.95 4 3 3 2 4 5 4 5v-3c0-.67-1-3-1-3s1 1 2 3c2.08 4.15 1.28 9.52 1.05 10 4.98-.07 8.95-10 8.95-10 1 5-1.78 7-1.78 7l-.22 3 4.89-1.33c4.89-2.33 6.11-13.67 6.11-13.67 1 1 3 0 3 0s-1 0-2-1z"/><path class="prefix__st2" d="M21.99 35.12h-.05c.01.07.03.05.05 0z"/><path class="prefix__st2" d="M27.94 33.13l-1 1s-.16 1.53 0 2c.53 1.59 3 6 3 6l-4 4h-5v-2s1.74-2.14 2-3c.07-.24.09-.77 0-1-.24-.66-1.31-1.86-2-2-.78-.16-3 1-3 1l-4-1-4-6v-1.04l3-2.96-1-5-1-1v6l-3 3 1 2 4 6 5 1s2.22-1.16 3-1c.35.07.89.66 1 1 .08.24.07.76 0 1-.26.86-2 3-2 3v3h6l5-5s-2.47-4.41-3-6c-.23-.71 0-3 0-3z"/></svg>

After

Width:  |  Height:  |  Size: 912 B

View File

@ -0,0 +1,37 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 228 72" style="enable-background:new 0 0 228 72;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#FFFFFF;}
.st2{fill:#D74458;}
.st3{fill:#90FEEA;}
.st4{fill:#122326;}
.st5{fill:#E83154;}
.st6{fill:#151E26;}
</style>
<path class="st0" d="M228,72H20C8.95,72,0,63.05,0,52V0h228V72z"/>
<g>
<polygon points="73,0 138.17,0 133.17,5 78,5 "/>
<polygon points="145,5 139,5 144,0 150,0 "/>
<polygon points="157.17,5 151.17,5 156.17,0 162.17,0 "/>
<polygon points="169.17,5 163.17,5 168.17,0 174.17,0 "/>
</g>
<g>
<polygon points="73,72 138.17,72 133.17,67 78,67 "/>
<polygon points="145,67 139,67 144,72 150,72 "/>
<polygon points="157.17,67 151.17,67 156.17,72 162.17,72 "/>
<polygon points="169.17,67 163.17,67 168.17,72 174.17,72 "/>
</g>
<g>
<g>
<polygon points="25,25.28 25,31.5 21,35.28 15,35.28 "/>
<polygon points="25,46.72 25,40.5 21,36.72 15,36.72 "/>
</g>
</g>
<g>
<polygon points="211,0 211,5 223,5 223,67 211,67 211,72 228,72 228,0 "/>
<path d="M17,66.48C10.1,64.7,5,58.45,5,51V5h12V0H0v52c0,10.02,7.38,18.3,17,19.75V66.48z"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

59
src/assets/svg/login.svg Normal file
View File

@ -0,0 +1,59 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 228 72" style="enable-background:new 0 0 228 72;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#D74458;}
.st2{fill:#90FEEA;}
.st3{fill:#122326;}
.st4{fill:#E83154;}
.st5{fill:#151E26;}
.st6{fill:#FFFFFF;}
</style>
<path d="M228,72H20C8.95,72,0,63.05,0,52V0h228V72z"/>
<g>
<g>
<g>
<polygon class="st0" points="73,0 138.17,0 133.17,5 78,5 "/>
</g>
<g>
<polygon class="st0" points="145,5 139,5 144,0 150,0 "/>
</g>
<g>
<polygon class="st0" points="157.17,5 151.17,5 156.17,0 162.17,0 "/>
</g>
<g>
<polygon class="st0" points="169.17,5 163.17,5 168.17,0 174.17,0 "/>
</g>
</g>
</g>
<g>
<g>
<g>
<polygon class="st0" points="73,72 138.17,72 133.17,67 78,67 "/>
</g>
<g>
<polygon class="st0" points="145,67 139,67 144,72 150,72 "/>
</g>
<g>
<polygon class="st0" points="157.17,67 151.17,67 156.17,72 162.17,72 "/>
</g>
<g>
<polygon class="st0" points="169.17,67 163.17,67 168.17,72 174.17,72 "/>
</g>
</g>
</g>
<g>
<g>
<polygon class="st0" points="25,25.28 25,31.5 21,35.28 15,35.28 "/>
<polygon class="st0" points="25,46.72 25,40.5 21,36.72 15,36.72 "/>
</g>
</g>
<g>
<g>
<polygon class="st0" points="211,0 211,5 223,5 223,67 211,67 211,72 228,72 228,0 "/>
<path class="st0" d="M17,66.48C10.1,64.7,5,58.45,5,51V5h12V0H0v52c0,10.02,7.38,18.3,17,19.75V66.48z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.6 KiB

View File

@ -0,0 +1,32 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#EC2E5B;}
.st2{fill:#9E9E9E;}
.st3{fill:#0F6569;}
.st4{fill:#CEC3C3;}
.st5{fill:#8AF4E1;}
</style>
<g>
<g>
<path class="st0" d="M46.09,17.49L24.1,1.57c-0.08-0.06-0.19-0.06-0.27,0L2.31,17.21c-0.36,0.26-0.36,0.81,0,1.07L23.2,33.41
c0.49,0.35,1.15,0.35,1.64,0l21.25-15.45C46.25,17.84,46.25,17.6,46.09,17.49z M24.96,7.12c0-0.24,0.28-0.37,0.47-0.22l7.68,6.15
c0.21,0.17,0.09,0.51-0.18,0.51H29.4c-0.07,0-0.13-0.02-0.18-0.06l-4.15-3.33c-0.07-0.05-0.11-0.14-0.11-0.22V7.12z M14.88,13.08
l7.68-6.15c0.19-0.15,0.47-0.02,0.47,0.22v2.82c0,0.09-0.04,0.17-0.11,0.22l-4.15,3.33c-0.05,0.04-0.11,0.06-0.18,0.06h-3.53
C14.79,13.59,14.67,13.24,14.88,13.08z M23.02,26.86c0,0.25-0.29,0.38-0.48,0.21L9.58,15.5C9.38,15.32,9.51,15,9.77,15h6.37
c0.07,0,0.13,0.02,0.18,0.06l6.59,5.3c0.07,0.05,0.11,0.14,0.11,0.22V26.86z M24.22,17.79c-0.11,0.11-0.29,0.11-0.41,0l-3.55-3.55
c-0.13-0.13-0.11-0.34,0.04-0.44l3.55-2.46c0.1-0.07,0.23-0.07,0.33,0l3.51,2.44c0.15,0.1,0.17,0.31,0.04,0.44L24.22,17.79z
M38.4,15.47L25.44,27.05c-0.18,0.16-0.48,0.03-0.48-0.21v-6.28c0-0.09,0.04-0.17,0.11-0.22l6.59-5.3
c0.05-0.04,0.11-0.06,0.18-0.06h6.37C38.48,14.97,38.6,15.3,38.4,15.47z"/>
<path class="st0" d="M45.27,21.49L24.9,35.38c-0.55,0.38-1.28,0.38-1.83,0L2.71,21.49c-0.31-0.21-0.72,0.01-0.72,0.38v2.9
c0,0.15,0.07,0.29,0.19,0.37l20.73,15.08c0.64,0.46,1.51,0.45,2.13-0.03l20.77-16.05c0.11-0.09,0.18-0.22,0.18-0.36v-1.9
C45.99,21.5,45.58,21.28,45.27,21.49z"/>
<path class="st0" d="M45.02,27.7L24.91,42.33c-0.55,0.4-1.29,0.4-1.83,0L2.96,27.7c-0.4-0.29-0.97-0.01-0.97,0.49v1.49
c0,0.2,0.09,0.38,0.25,0.49L23.02,45.3c0.58,0.42,1.36,0.42,1.94,0l20.78-15.11c0.16-0.11,0.25-0.3,0.25-0.49V28.2
C45.99,27.7,45.43,27.41,45.02,27.7z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 2.1 KiB

View File

@ -0,0 +1,32 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#EC2E5B;}
.st2{fill:#9E9E9E;}
.st3{fill:#0F6569;}
.st4{fill:#CEC3C3;}
.st5{fill:#8AF4E1;}
</style>
<g>
<g>
<path class="st0" d="M46.09,17.49L24.1,1.57c-0.08-0.06-0.19-0.06-0.27,0L2.31,17.21c-0.36,0.26-0.36,0.81,0,1.07L23.2,33.41
c0.49,0.35,1.15,0.35,1.64,0l21.25-15.45C46.25,17.84,46.25,17.6,46.09,17.49z M24.96,7.12c0-0.24,0.28-0.37,0.47-0.22l7.68,6.15
c0.21,0.17,0.09,0.51-0.18,0.51H29.4c-0.07,0-0.13-0.02-0.18-0.06l-4.15-3.33c-0.07-0.05-0.11-0.14-0.11-0.22V7.12z M14.88,13.08
l7.68-6.15c0.19-0.15,0.47-0.02,0.47,0.22v2.82c0,0.09-0.04,0.17-0.11,0.22l-4.15,3.33c-0.05,0.04-0.11,0.06-0.18,0.06h-3.53
C14.79,13.59,14.67,13.24,14.88,13.08z M23.02,26.86c0,0.25-0.29,0.38-0.48,0.21L9.58,15.5C9.38,15.32,9.51,15,9.77,15h6.37
c0.07,0,0.13,0.02,0.18,0.06l6.59,5.3c0.07,0.05,0.11,0.14,0.11,0.22V26.86z M24.22,17.79c-0.11,0.11-0.29,0.11-0.41,0l-3.55-3.55
c-0.13-0.13-0.11-0.34,0.04-0.44l3.55-2.46c0.1-0.07,0.23-0.07,0.33,0l3.51,2.44c0.15,0.1,0.17,0.31,0.04,0.44L24.22,17.79z
M38.4,15.47L25.44,27.05c-0.18,0.16-0.48,0.03-0.48-0.21v-6.28c0-0.09,0.04-0.17,0.11-0.22l6.59-5.3
c0.05-0.04,0.11-0.06,0.18-0.06h6.37C38.48,14.97,38.6,15.3,38.4,15.47z"/>
<path class="st0" d="M45.27,21.49L24.9,35.38c-0.55,0.38-1.28,0.38-1.83,0L2.71,21.49c-0.31-0.21-0.72,0.01-0.72,0.38v2.9
c0,0.15,0.07,0.29,0.19,0.37l20.73,15.08c0.64,0.46,1.51,0.45,2.13-0.03l20.77-16.05c0.11-0.09,0.18-0.22,0.18-0.36v-1.9
C45.99,21.5,45.58,21.28,45.27,21.49z"/>
<path class="st0" d="M45.02,27.7L24.91,42.33c-0.55,0.4-1.29,0.4-1.83,0L2.96,27.7c-0.4-0.29-0.97-0.01-0.97,0.49v1.49
c0,0.2,0.09,0.38,0.25,0.49L23.02,45.3c0.58,0.42,1.36,0.42,1.94,0l20.78-15.11c0.16-0.11,0.25-0.3,0.25-0.49V28.2
C45.99,27.7,45.43,27.41,45.02,27.7z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 2.1 KiB

View File

@ -0,0 +1,32 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#EC2E5B;}
.st2{fill:#9E9E9E;}
.st3{fill:#0F6569;}
.st4{fill:#CEC3C3;}
.st5{fill:#8AF4E1;}
</style>
<g>
<g>
<path class="st2" d="M46.03,17.62L24.04,1.7c-0.08-0.06-0.19-0.06-0.27,0L2.26,17.34c-0.36,0.26-0.36,0.81,0,1.07l20.89,15.12
c0.49,0.35,1.15,0.35,1.64,0l21.25-15.45C46.19,17.97,46.19,17.73,46.03,17.62z M24.91,7.25c0-0.24,0.28-0.37,0.47-0.22l7.68,6.15
c0.21,0.17,0.09,0.51-0.18,0.51h-3.53c-0.07,0-0.13-0.02-0.18-0.06l-4.15-3.33c-0.07-0.05-0.11-0.14-0.11-0.22V7.25z M14.82,13.2
l7.68-6.15c0.19-0.15,0.47-0.02,0.47,0.22v2.82c0,0.09-0.04,0.17-0.11,0.22l-4.15,3.33c-0.05,0.04-0.11,0.06-0.18,0.06H15
C14.73,13.71,14.61,13.37,14.82,13.2z M22.96,26.99c0,0.25-0.29,0.38-0.48,0.21L9.52,15.63c-0.2-0.18-0.07-0.5,0.19-0.5h6.37
c0.07,0,0.13,0.02,0.18,0.06l6.59,5.3c0.07,0.05,0.11,0.14,0.11,0.22V26.99z M24.17,17.92c-0.11,0.11-0.29,0.11-0.41,0l-3.55-3.55
c-0.13-0.13-0.11-0.34,0.04-0.44l3.55-2.46c0.1-0.07,0.23-0.07,0.33,0l3.51,2.44c0.15,0.1,0.17,0.31,0.04,0.44L24.17,17.92z
M38.35,15.6L25.38,27.17c-0.18,0.16-0.48,0.03-0.48-0.21v-6.28c0-0.09,0.04-0.17,0.11-0.22l6.59-5.3
c0.05-0.04,0.11-0.06,0.18-0.06h6.37C38.42,15.1,38.54,15.42,38.35,15.6z"/>
<path class="st2" d="M45.22,21.62L24.85,35.5c-0.55,0.38-1.28,0.38-1.83,0L2.65,21.62C2.35,21.41,1.94,21.63,1.94,22v2.9
c0,0.15,0.07,0.29,0.19,0.37l20.73,15.08c0.64,0.46,1.51,0.45,2.13-0.03l20.77-16.05c0.11-0.09,0.18-0.22,0.18-0.36V22
C45.94,21.63,45.52,21.41,45.22,21.62z"/>
<path class="st2" d="M44.97,27.83L24.85,42.46c-0.55,0.4-1.29,0.4-1.83,0L2.9,27.83c-0.4-0.29-0.97-0.01-0.97,0.49v1.49
c0,0.2,0.09,0.38,0.25,0.49l20.78,15.11c0.58,0.42,1.36,0.42,1.94,0l20.78-15.11c0.16-0.11,0.25-0.3,0.25-0.49v-1.49
C45.94,27.83,45.37,27.54,44.97,27.83z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 2.1 KiB

View File

@ -0,0 +1,24 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#EC2E5B;}
.st2{fill:#9E9E9E;}
.st3{fill:#0F6569;}
.st4{fill:#CEC3C3;}
.st5{fill:#8AF4E1;}
</style>
<g>
<g>
<path class="st0" d="M41,19c-0.25-0.25-1-1-1-1c0-7-4-16-14.41-16.47C18.19,1.19,12,2,7,12s2,17,2,17c0-7,3-9,3-9
c1.19,1.03,0.92,0.95,4,3c3,2,4,5,4,5s0-1.67,0-3c0-0.67-1-3-1-3s1,1,2,3c2.08,4.15,1.28,9.52,1.05,10C27.03,34.93,31,25,31,25
c1,5-1.78,7-1.78,7L29,35l4.89-1.33C38.78,31.34,40,20,40,20c1,1,3,0,3,0S42,20,41,19z"/>
<path class="st0" d="M22.05,35c-0.02,0-0.03,0-0.05,0C22.01,35.06,22.03,35.04,22.05,35z"/>
<path class="st0" d="M28,33l-1,1c0,0-0.16,1.53,0,2c0.53,1.59,3,6,3,6l-4,4h-5v-2c0,0,1.74-2.14,2-3c0.07-0.24,0.09-0.77,0-1
c-0.24-0.66-1.31-1.86-2-2c-0.78-0.16-3,1-3,1l-4-1l-4-6v-1.04L13,28l-1-5l-1-1v6l-3,3l1,2l4,6l5,1c0,0,2.22-1.16,3-1
c0.35,0.07,0.89,0.66,1,1c0.08,0.24,0.07,0.76,0,1c-0.26,0.86-2,3-2,3v3h6l5-5c0,0-2.47-4.41-3-6C27.76,35.29,28,33,28,33z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.3 KiB

View File

@ -0,0 +1,24 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#EC2E5B;}
.st2{fill:#9E9E9E;}
.st3{fill:#0F6569;}
.st4{fill:#CEC3C3;}
.st5{fill:#8AF4E1;}
</style>
<g>
<g>
<path class="st0" d="M41,19c-0.25-0.25-1-1-1-1c0-7-4-16-14.41-16.47C18.19,1.19,12,2,7,12s2,17,2,17c0-7,3-9,3-9
c1.19,1.03,0.92,0.95,4,3c3,2,4,5,4,5s0-1.67,0-3c0-0.67-1-3-1-3s1,1,2,3c2.08,4.15,1.28,9.52,1.05,10C27.03,34.93,31,25,31,25
c1,5-1.78,7-1.78,7L29,35l4.89-1.33C38.78,31.34,40,20,40,20c1,1,3,0,3,0S42,20,41,19z"/>
<path class="st0" d="M22.05,35c-0.02,0-0.03,0-0.05,0C22.01,35.06,22.03,35.04,22.05,35z"/>
<path class="st0" d="M28,33l-1,1c0,0-0.16,1.53,0,2c0.53,1.59,3,6,3,6l-4,4h-5v-2c0,0,1.74-2.14,2-3c0.07-0.24,0.09-0.77,0-1
c-0.24-0.66-1.31-1.86-2-2c-0.78-0.16-3,1-3,1l-4-1l-4-6v-1.04L13,28l-1-5l-1-1v6l-3,3l1,2l4,6l5,1c0,0,2.22-1.16,3-1
c0.35,0.07,0.89,0.66,1,1c0.08,0.24,0.07,0.76,0,1c-0.26,0.86-2,3-2,3v3h6l5-5c0,0-2.47-4.41-3-6C27.76,35.29,28,33,28,33z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.3 KiB

View File

@ -0,0 +1,26 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#EC2E5B;}
.st2{fill:#9E9E9E;}
.st3{fill:#0F6569;}
.st4{fill:#CEC3C3;}
.st5{fill:#8AF4E1;}
</style>
<g>
<g>
<path class="st2" d="M40.94,19.13c-0.25-0.25-1-1-1-1c0-7-4-16-14.41-16.47c-7.4-0.34-13.59,0.47-18.59,10.47s2,17,2,17
c0-7,3-9,3-9c1.19,1.03,0.92,0.95,4,3c3,2,4,5,4,5s0-1.67,0-3c0-0.67-1-3-1-3s1,1,2,3c2.08,4.15,1.28,9.52,1.05,10
c4.98-0.07,8.95-10,8.95-10c1,5-1.78,7-1.78,7l-0.22,3l4.89-1.33c4.89-2.33,6.11-13.67,6.11-13.67c1,1,3,0,3,0
S41.94,20.13,40.94,19.13z"/>
<path class="st2" d="M21.99,35.12c-0.02,0-0.03,0-0.05,0C21.95,35.19,21.97,35.17,21.99,35.12z"/>
<path class="st2" d="M27.94,33.13l-1,1c0,0-0.16,1.53,0,2c0.53,1.59,3,6,3,6l-4,4h-5v-2c0,0,1.74-2.14,2-3
c0.07-0.24,0.09-0.77,0-1c-0.24-0.66-1.31-1.86-2-2c-0.78-0.16-3,1-3,1l-4-1l-4-6v-1.04l3-2.96l-1-5l-1-1v6l-3,3l1,2l4,6l5,1
c0,0,2.22-1.16,3-1c0.35,0.07,0.89,0.66,1,1c0.08,0.24,0.07,0.76,0,1c-0.26,0.86-2,3-2,3v3h6l5-5c0,0-2.47-4.41-3-6
C27.71,35.42,27.94,33.13,27.94,33.13z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

View File

@ -0,0 +1,25 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#EC2E5B;}
.st2{fill:#9E9E9E;}
.st3{fill:#0F6569;}
.st4{fill:#CEC3C3;}
.st5{fill:#8AF4E1;}
</style>
<g>
<g>
<path class="st0" d="M6.2,12.44h3.98V13H11c3.1-4.32,7.78-6.6,13.5-6.6s10.78,2.82,13.88,7.14h1.37l1.05-1.05h2.14
C39.19,6.21,32.34,2,24.5,2C15.81,2,8.34,6.17,4.95,13.59H6.2V12.44z"/>
<path class="st0" d="M7.2,26.12v-3.15l-1.1-1.1H3.18C3.07,22.74,3,22.61,3,23.5c0,2.54,0.47,4.98,1.28,7.24L7.2,26.12z"/>
<path class="st0" d="M41.52,21.93c0.05,0.52,0.08,1.04,0.08,1.57c0,9.45-7.66,17.1-17.1,17.1c-3.85,0-7.39-1.29-10.24-3.43
l-2,3.99C15.73,43.58,19.95,45,24.5,45C36.37,45,46,35.37,46,23.5c0-0.53-0.04-1.05-0.08-1.57H41.52z"/>
<path class="st0" d="M44.48,14l-1-1h-2l-1,1H9v-1H7v1H4.48v5h-1v2h3l2,2v3L1.11,37.67V42h9.37l8-15c2.52,2,6,1.93,6,1.93
c7,0,7.37-7.93,7.37-7.93h13.63l1-1.3v-2.11h1V14H44.48z M28.48,26c-1.04,1.65-5.48,2-7.81,0c-0.84-0.72-2.41-3.16,1.7-4.08
c0,0,0.03,1.15,0.41,2.2c0.3,0.84,0.81,1.61,1.7,1.69c0,0-0.81-2.05-0.48-2.81c0.16-0.37,1-1,2-1S31,22,28.48,26z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

View File

@ -0,0 +1,25 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#EC2E5B;}
.st2{fill:#9E9E9E;}
.st3{fill:#0F6569;}
.st4{fill:#CEC3C3;}
.st5{fill:#8AF4E1;}
</style>
<g>
<g>
<path class="st0" d="M6.2,12.44h3.98V13H11c3.1-4.32,7.78-6.6,13.5-6.6s10.78,2.82,13.88,7.14h1.37l1.05-1.05h2.14
C39.19,6.21,32.34,2,24.5,2C15.81,2,8.34,6.17,4.95,13.59H6.2V12.44z"/>
<path class="st0" d="M7.2,26.12v-3.15l-1.1-1.1H3.18C3.07,22.74,3,22.61,3,23.5c0,2.54,0.47,4.98,1.28,7.24L7.2,26.12z"/>
<path class="st0" d="M41.52,21.93c0.05,0.52,0.08,1.04,0.08,1.57c0,9.45-7.66,17.1-17.1,17.1c-3.85,0-7.39-1.29-10.24-3.43
l-2,3.99C15.73,43.58,19.95,45,24.5,45C36.37,45,46,35.37,46,23.5c0-0.53-0.04-1.05-0.08-1.57H41.52z"/>
<path class="st0" d="M44.48,14l-1-1h-2l-1,1H9v-1H7v1H4.48v5h-1v2h3l2,2v3L1.11,37.67V42h9.37l8-15c2.52,2,6,1.93,6,1.93
c7,0,7.37-7.93,7.37-7.93h13.63l1-1.3v-2.11h1V14H44.48z M28.48,26c-1.04,1.65-5.48,2-7.81,0c-0.84-0.72-2.41-3.16,1.7-4.08
c0,0,0.03,1.15,0.41,2.2c0.3,0.84,0.81,1.61,1.7,1.69c0,0-0.81-2.05-0.48-2.81c0.16-0.37,1-1,2-1S31,22,28.48,26z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

View File

@ -0,0 +1,25 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 26.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFBA00;}
.st1{fill:#EC2E5B;}
.st2{fill:#9E9E9E;}
.st3{fill:#0F6569;}
.st4{fill:#CEC3C3;}
.st5{fill:#8AF4E1;}
</style>
<g>
<g>
<path class="st2" d="M6.14,12.57h3.98v0.56h0.82c3.1-4.32,7.78-6.6,13.5-6.6s10.78,2.82,13.88,7.14h1.37l1.05-1.05h2.14
C39.13,6.34,32.29,2.13,24.44,2.13c-8.69,0-16.16,4.17-19.55,11.59h1.24V12.57z"/>
<path class="st2" d="M7.14,26.25V23.1L6.04,22H3.12c-0.1,0.86-0.18,0.73-0.18,1.62c0,2.54,0.47,4.98,1.28,7.24L7.14,26.25z"/>
<path class="st2" d="M41.47,22.05c0.05,0.52,0.08,1.04,0.08,1.57c0,9.45-7.66,17.1-17.1,17.1c-3.85,0-7.39-1.29-10.24-3.43
l-2,3.99c3.48,2.41,7.69,3.84,12.24,3.84c11.87,0,21.5-9.63,21.5-21.5c0-0.53-0.04-1.05-0.08-1.57H41.47z"/>
<path class="st2" d="M44.43,14.13l-1-1h-2l-1,1H8.94v-1h-2v1H4.43v5h-1v2h3l2,2v3L1.06,37.79v4.33h9.37l8-15c2.52,2,6,1.93,6,1.93
c7,0,7.37-7.93,7.37-7.93h13.63l1-1.3v-2.11h1v-3.59H44.43z M28.43,26.13c-1.04,1.65-5.48,2-7.81,0c-0.84-0.72-2.41-3.16,1.7-4.08
c0,0,0.03,1.15,0.41,2.2c0.3,0.84,0.81,1.61,1.7,1.69c0,0-0.81-2.05-0.48-2.81c0.16-0.37,1-1,2-1S30.94,22.13,28.43,26.13z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

View File

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 25.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 200 200" style="enable-background:new 0 0 200 200;" xml:space="preserve">
<style type="text/css">
.st0{fill:#EC2E5A;}
</style>
<path class="st0" d="M81.5,155.4l2.3-35.2l64-57.7c2.8-2.6-0.6-3.8-4.3-1.6l-79,49.9L30.3,100c-7.3-2.1-7.4-7.2,1.7-10.8l133.1-51.3
c6.1-2.8,11.9,1.5,9.6,10.8L152,155.4c-1.6,7.6-6.2,9.4-12.5,5.9L105,135.8l-16.6,16.1C86.5,153.8,84.9,155.4,81.5,155.4z"/>
</svg>

After

Width:  |  Height:  |  Size: 662 B

View File

@ -0,0 +1 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1677464753225" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="2113" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><path d="M417.28 795.733333l11.946667-180.48 327.68-295.253333c14.506667-13.226667-2.986667-19.626667-22.186667-8.106667L330.24 567.466667 155.306667 512c-37.546667-10.666667-37.973333-36.693333 8.533333-55.466667l681.386667-262.826666c31.146667-14.08 61.013333 7.68 49.066666 55.466666l-116.053333 546.56c-8.106667 38.826667-31.573333 48.213333-64 30.293334L537.6 695.466667l-84.906667 82.346666c-9.813333 9.813333-17.92 17.92-35.413333 17.92z" fill="" p-id="2114"></path></svg>

After

Width:  |  Height:  |  Size: 803 B

View File

@ -0,0 +1,13 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 25.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 200 200" style="enable-background:new 0 0 200 200;" xml:space="preserve">
<style type="text/css">
.st0{fill:#EC2E5A;}
</style>
<path class="st0" d="M200,38c-7.5,3.3-15.5,5.5-23.6,6.5c8.6-5.1,15-13.2,18-22.7c-8.1,4.8-16.9,8.2-26.1,10
c-15.6-16.5-41.5-17.2-58-1.6c-8.2,7.8-12.9,18.5-12.8,29.8c0,3.1,0.4,6.3,1.1,9.3c-33-1.7-63.8-17.3-84.6-43
c-3.7,6.2-5.6,13.4-5.6,20.6C8,60.5,14.6,73.3,25.8,81C19,80.8,6.3,79,6.3,75.9v0.5c0.5,19.6,14.6,36.2,33.8,40
c-3.3,0.9-6.6,1.4-10,1.4c-2.5,0-5-0.2-7.5-0.7c5.4,16.7,20.8,28.2,38.4,28.5c-14.5,11.5-32.5,17.8-51,17.8c-3.3,0-6.7-0.2-10-0.6
c18.8,12,40.6,18.4,62.9,18.4c64,0.7,116.4-50.7,117.1-114.7c0-0.7,0-1.3,0-2v-5.3C187.9,53.4,194.6,46.2,200,38z"/>
</svg>

After

Width:  |  Height:  |  Size: 974 B

View File

@ -0,0 +1 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1677463959719" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="3002" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><path d="M1024 194.56a420.352 420.352 0 0 1-120.832 33.28 210.432 210.432 0 0 0 92.16-116.224 422.4 422.4 0 0 1-133.632 51.2A209.92 209.92 0 0 0 499.2 307.2a211.968 211.968 0 0 0 5.632 47.616 596.48 596.48 0 0 1-433.152-220.16 208.896 208.896 0 0 0-28.672 105.472A204.8 204.8 0 0 0 132.096 414.72C97.28 413.696 32.256 404.48 32.256 388.608v2.56a214.528 214.528 0 0 0 173.056 204.8 193.024 193.024 0 0 1-51.2 7.168 199.68 199.68 0 0 1-38.4-3.584 210.944 210.944 0 0 0 196.608 145.92A420.864 420.864 0 0 1 51.2 836.608a438.784 438.784 0 0 1-51.2-3.072 594.944 594.944 0 0 0 322.048 94.208A593.408 593.408 0 0 0 921.6 330.24v-27.136a427.008 427.008 0 0 0 102.4-108.544z m0 0" fill="#000" p-id="3003"></path></svg>

After

Width:  |  Height:  |  Size: 1.0 KiB

View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 48 48"><image width="46" height="45" xlink:href="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAC4AAAAtCAYAAADRLVmZAAAFrklEQVRogeXZe4xcVR0H8M8Oy1IK 2qFsRdP6iNgaIiGIGKlPqv0D4yPBWB8hgP7BmI4SlRqNUeOjaiIJxmgzMaMBQdFoFBLQ+mqxCBSQ gKDx0aTUB21VoO1g6Xa7Xbr+8Tu3vZ2dO3PvsMlq/CYnd+7J75zznd859/c6/I9iZGZmZqBQvdEc JHISnoU6lmIxFmIKB7Abj2NfelZCp92a1TdadZIuvAIXYDVejjP6yD6FP+B2bMZv8I9hFx6W+CV4 O95cYY4TcE5qV+JPuBVtPFyVQFXiq/BJvL7qQj1wVmrvwo34LA6VHVwrKTeG9bjF3JDO43n4OO7E a8sOGqjxeqN5Oq7HmwaI/gv/TG03JtL8dTwXS9JzQcH484ViPozrnhbxeqO5NE12XoHINH4uPraf iXNbhGfg1bgIb8BLesgswrU4DV8eini90VyWCK0oELleaOb2fgvksB8/TW0J3okP4cwestcIpXy1 aLKeZ7zeaJ6aiK1IE+TxF2FN3lOBdDcewwZciNlGOvAVnF00wSwHVG80F+ILwoHciBGsFF/9L3EZ 9g5JuAiXYl36vQBb8QnhwE7GTKfd2jWI+JlYK7S5Ho+K83Y+bsAjafKRAhJHCvpHCsYcTmNOyslN YkYclfcL5/VBfFMc75lCl19vNNfgB+l1C3ZiPA0sIi0t0ot8TTihXphJLU98kfDKJ6b+fbgn/cFH jyOeTN9avEicv+f3ITif2N9tVZ6JJp4zD2SqYKLbqkwIR/LfjN24rpt4DafMA5kquAufOko8mcH1 WD5vlMphDKN5jT8bF88TmSo4EbUa1BvNV+J9gvi78at5JDYIu3Awsyp1fBSjnXZrXb3R3CiCppUV J30KD4lQdRy/xSZh118gFDOWZA+KSPKACCt6hR+TIkav4VT8HRs67dZMRjx7XlVvNMeFSbxWOIB+ zqab9MfwbeGwRsTubcvJfF3s7H34HLYLSzZdsM5CYSwyz/pwp93amyc8lhO+DH8WmppyzBUPwoMi qsuwX2xrHjcl4j9ObRA+gnckHmO4r95oruu0W5MZ8e6U6QzhcqukdvuS/LQI0q7CMqGEDFPpOVFy zleJJDzDkdSOnqsDXQN+h5cpji164TxxtIiocpXjScPb0nObcuhe/2+ddmuKYxrdg38Ll79b5H9f Ks8ZUUv5vojjHxOaP0Uo57DIeC7Hbfh1yTnHu96PljMy4juxA+fiavFRvK4C6a24H28RiW8vHBLl iCvxRIk5XyisUx5/zX6MQqfd2lNvNHeIaPAb+KLI+8rgEawRO3U1Xiz+OGFpsjD3cWEey+I1oiqW 4aAwtceIJ9yPX4gtXVthgZsSaWLndlYY2w9v7Hrfhruzlzzxa8QZv8Xx5rEfDoosf65xDt7a1be1 025NZi9HvVWn3TokbOwFyuOPIlqba3xA5JoZpvCdvEA+OjxblAuq4CfCGs0lVuOKrr7bOu3W3fmO LMg6QdQET6+wwBOC+FxiqTAOeRzGZ7oFM42vEq61CjarZiUG4TR8VwRjeWzotFv3dgvX6o3mArxX +WAqwyahjbnAuPC23UXPh0T4MAs1Ucu7qOJCu0QpbS7wUmw02/xlxmJPr0E14e0WV1xss5wXGxJL hJfd6vhAiggX1mDWEckw2mPQIBzBt0RlaRW+hx8KD1kGy0XofLHeFdv9oiR3a79JRlWzJERMMy1K Y8vFjn0aD4jgbLsocTwp8sPFIrw9V2RUZymu22wXXnvTIBLD3AHdLLSVVQNqjl2LXCLSraweOJLW GCux1o9E+rijDIlRfF5c9T2pv2UZS6S2iBJwERYovnXohQfxNZEqlsaw95wXCru/2nB1mCPCKm0U hCf7Cc/lPeeW1JaJj3tlaivE7nVjShyB3+MOkSzfM+TaePoXtFkYe7OILBeJMsLJIiafFvnlhIhp 9pp9w/H/hf8AsHdjd0huR7YAAAAASUVORK5CYII=" transform="translate(1 1.5)" overflow="visible"/></svg>

After

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

BIN
src/assets/text/arial.ttf Normal file

Binary file not shown.

BIN
src/assets/text/arialbd.ttf Normal file

Binary file not shown.

BIN
src/assets/text/ariblk.ttf Normal file

Binary file not shown.

Binary file not shown.

33
src/assets/text/text.css Normal file
View File

@ -0,0 +1,33 @@
@font-face {
font-family: "Big John";
src: url('./big-john-woff2-2.ttf');
font-weight: normal;
font-style: normal;
}
@font-face {
font-family: "Arial";
src: url('./arial.ttf');
font-weight: normal;
font-style: normal;
}
@font-face {
font-family: 'Poppins';
font-style: normal;
font-weight: 600;
src: url('./Poppins-SemiBold.ttf') format('truetype');
}
@font-face {
font-family: 'MEurostile';
font-style: normal;
font-weight: 600;
src: url('./MEUROSTILE.TTF') format('truetype');
}
@font-face {
font-family: 'GemunuExtraBold';
font-style: normal;
font-weight: 600;
src: url('./GEMUNULIBRE-EXTRABOLD.TTF') format('truetype');
}

1
src/assets/vue.svg Normal file
View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" aria-hidden="true" role="img" class="iconify iconify--logos" width="37.07" height="36" preserveAspectRatio="xMidYMid meet" viewBox="0 0 256 198"><path fill="#41B883" d="M204.8 0H256L128 220.8L0 0h97.92L128 51.2L157.44 0h47.36Z"></path><path fill="#41B883" d="m0 0l128 220.8L256 0h-51.2L128 132.48L50.56 0H0Z"></path><path fill="#35495E" d="M50.56 0L128 133.12L204.8 0h-47.36L128 51.2L97.92 0H50.56Z"></path></svg>

After

Width:  |  Height:  |  Size: 496 B

21
src/bus/event.js Normal file
View File

@ -0,0 +1,21 @@
export const PRESALE_BEGIN = 'presale_begin'
export const PRESALE_ORDER_GET = 'presale_order_get'
export const PRESALE_SUCCESS = 'presale_success'
export const PRESALE_ERROR = 'presale_error'
export const NEED_LOGIN = 'need_login'
export const NEED_NONCE = 'need_nonce'
export const ACCOUNT_CHANGE = 'account_change'
export const SHOW_CHAIN_MODAL = 'show_chain_modal'
export const NEED_CHANGE_CHAIN = 'need_change_chain'
export const WALLET_SELECTED = 'wallet_selected'
export const CHAIN_SELECTED = 'chain_selected'

48
src/chain/Chain.ts Normal file
View File

@ -0,0 +1,48 @@
import Web3 from 'web3'
import { useAppStore } from '@/store/app'
import { ERC20ABI } from '@/configs/contracts'
import pinia from '@/store';
const AppModule = useAppStore(pinia);
export class Chain {
private web3: Web3
constructor(provider: any) {
this.web3 = new Web3(provider)
}
public async initInstance({ abi, address, account }: {abi: any, address: string, account: string}) {
return new this.web3.eth.Contract(
abi,
address,
{ from: account }
)
}
public async initContractInstance(address: string, abi: any = ERC20ABI) {
return this.initInstance({
abi,
address,
account: AppModule.accountId
})
}
public async sendCmd({ method, params, from }: any) {
return new Promise((resolve, reject) => {
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
this.web3.currentProvider.send({
method,
params,
from
}, async function(err: any, result: any) {
if (err) {
reject && reject(err)
return
}
resolve && resolve(result)
})
})
}
}

276
src/chain/ChainManager.ts Normal file
View File

@ -0,0 +1,276 @@
import { Blockchain } from "@/chain/blockchain";
import { getNonce } from "@/api/User";
import pinia from "@/store";
import { useAppStore } from "@/store/app";
import { useUserStore } from "@/store/user";
import { message } from "ant-design-vue";
import { Chain } from "@/chain/Chain";
import { AVAILABLE_CHAINS } from "@/configs/configchain";
import { AllChains } from "@/configs/allchain";
import {
ACTIVATE_PROXY_ABI,
MYSTERY_BOX_ABI,
MYSTERY_PROXY_ABI
} from "@/configs/contracts";
const AppModule = useAppStore(pinia);
const UserModule = useUserStore();
export default class ChainManager {
bc: Blockchain;
instanceMap: Map<string, any>;
public chainMap: Map<number, any> = new Map();
private _availableChains: Map<number, any> = new Map();
constructor() {
this.bc = new Blockchain();
this.instanceMap = new Map();
for (const data of AllChains) {
this.chainMap.set(data.id, data);
}
}
get availableChains() {
if (this._availableChains.size === 0) {
for (const id of AVAILABLE_CHAINS) {
const d = this.chainMap.get(id);
if (d) {
this._availableChains.set(id, d);
}
}
}
return this._availableChains;
}
public async init() {
if (this.bc.isWalletConnect) {
try {
await this.bc.connect();
} catch (err) {
console.log("connect chain error: ", err);
}
}
}
get isLogined() {
return !!UserModule.token && !!AppModule.step;
}
public async logout() {
await this.bc.disconnect();
}
public get currentChain() {
return this.bc.currentChain;
}
public async login() {
if (!AppModule.step) {
try {
await this.bc.connect(true);
await this.checkNance();
} catch (err) {
message.error(err.message, 5);
await this.bc.disconnect();
await Promise.reject(err);
}
}
}
public async checkNance() {
try {
const preRequest: any = await getNonce();
let nonce = preRequest.nonce + "";
const tips = preRequest.data?.tips;
AppModule.updateNonce(nonce);
await UserModule.Login({
bcInstance: this.bc,
account: AppModule.accountId,
chainId: AppModule.chainId,
nonce,
tips,
});
AppModule.updateStep(1);
} catch (err) {
console.log(err);
await Promise.reject(err);
}
}
public async getInstance(address: string, chainId: number, abi?: any) {
const key = `${chainId}_${address}`;
if (!this.instanceMap.has(key)) {
const chain = new Chain(this.chainMap.get(chainId)!.rpc);
const coinInstance = await chain.initContractInstance(address, abi);
this.instanceMap.set(key, coinInstance);
}
return this.instanceMap.get(key);
}
public async getBalance(address: string, chainId: number) {
const coinInstance = await this.getInstance(address, chainId);
const balance = await coinInstance.methods
.balanceOf(AppModule.accountId)
.call();
console.log("balance: ", balance);
return balance;
}
/**
* get amount of mystery boxes
* this method can get amount of general erc721 also
* @param {string} address
* @param {number} chainId
* @return {Promise<any>}
*/
public async getNftBalance(address: string, chainId: number) {
const coinInstance = await this.getInstance(
address,
chainId,
MYSTERY_BOX_ABI
);
const balance = await coinInstance.methods
.balanceOf(AppModule.accountId)
.call();
console.log("nft balance: ", balance);
return balance;
}
/**
* Get NFT list of current user
* @param {string} address NFT address
* @param {number} chainId chain id
* @param {number} start
* @param {number} page
*/
public async getNftList(
address: string,
chainId: number,
start = 0,
page = 8
) {
const nftInstance = await this.getInstance(
address,
chainId,
MYSTERY_BOX_ABI
);
return nftInstance.methods
.userTokens(AppModule.accountId, start, page)
.call();
}
/**
* Get NFT of current user with index
* @param {string} address
* @param {number} chainId
* @param {number} index
* @return {Promise<any>}
*/
public async getNftIdOfIndex(
address: string,
chainId: number,
index: number
) {
const nftInstance = await this.getInstance(
address,
chainId,
MYSTERY_BOX_ABI
);
const nftId = await nftInstance.methods
.tokenOfOwnerByIndex(AppModule.accountId, index)
.call();
console.log(
`address: ${address}, chainId: ${chainId}, index: ${index}, token: ${nftId}`
);
return nftId;
}
/**
* Open one mystery box
* @param {string} address address of mystery box contract on current chain
* @param {string} boxId nftid of mystery box
* @param {number[]} tokenIds
* @param {string} nonce
* @param {string} signature
* @return {Promise<any>}
*/
public async openMysteryBox(
address: string,
boxId: string,
tokenIds: number[],
nonce: string,
signature: string
) {
const proxyInstance = await this.bc.getContractInstance(
address,
MYSTERY_PROXY_ABI
);
// get transactionHash and upload to server for verify
return proxyInstance.methods
.openBox(boxId, tokenIds, nonce, signature)
.send({ gas: 1000000 });
}
/**
* activate one nft with 18 digital id
* @param {string} address
* @param {string} nftOld
* @param {string} nftNew
* @param {number} nftType
* @param {string} nonce
* @param {string} signature
* @return {Promise<any>}
*/
public async activateOneNft(
address: string,
nftOld: string,
nftNew: string,
nftType: number,
nonce: string,
signature: string
) {
const nftProxyInstance = await this.bc.getContractInstance(
address,
ACTIVATE_PROXY_ABI
);
const gas = await nftProxyInstance.methods
.activateOne(nftOld, nftNew, nftType, nonce, signature)
.estimateGas({ gas: 1000000 });
console.log("nftProxyInstance activateOne need gas: ", gas);
return nftProxyInstance.methods
.activateOne(nftOld, nftNew, nftType, nonce, signature)
.send({ gas: (gas * 1.1) | 0 });
}
public async transferToAccount({
to,
amount,
chainId,
address,
}: {
to: string;
amount: number;
chainId: number;
address: string;
}) {
const self = this;
if (chainId !== this.bc.currentChain) {
return new Promise((resolve, reject) => {
this.bc.switchEthereumChain(chainId, function () {
self.bc
.transferToAccount(to, amount, address)
.then((res) => {
resolve && resolve(res);
})
.catch((err) => {
reject && reject(err);
});
});
});
} else {
return this.bc.transferToAccount(to, amount, address);
}
}
}

577
src/chain/blockchain.ts Normal file
View File

@ -0,0 +1,577 @@
import WalletConnectProvider from "@walletconnect/web3-provider";
import { useAppStore } from "@/store/app";
import Web3 from "web3";
import { AVAILABLE_CHAINS, CONTRACT_ADDRESS } from "@/configs/configchain";
import { useUserStore } from "@/store/user";
import { isMobile } from "@/utils/resize";
import { hasMetamask, toHexChainId } from "@/utils/chain.util";
import { AllChains } from "@/configs/allchain";
import { ERC20ABI,CLAIM_ABI} from "@/configs/contracts";
import { TransactionReceipt } from "web3-core";
import { useEventBus } from "@vueuse/core";
import { Global } from "@/configs/global";
import * as bus_event from "@/bus/event";
import pinia from "@/store";
const EIP721_DOMAIN_DATA = [
{ name: "name", type: "string" },
{ name: "version", type: "string" },
{ name: "chainId", type: "uint256" },
{ name: "verifyingContract", type: "address" },
];
const CACHE_KEY = "cebg_chain_cache_key";
const busShowChainModal = useEventBus(bus_event.SHOW_CHAIN_MODAL);
const busNeedChangeChain = useEventBus(bus_event.NEED_CHANGE_CHAIN);
const busNeedLogin = useEventBus(bus_event.NEED_LOGIN);
const busNeedNonce = useEventBus(bus_event.NEED_NONCE);
const AppModule = useAppStore(pinia);
const UserModule = useUserStore(pinia);
export class Blockchain {
provider: any;
web3: Web3;
currentChain = 0;
// 0: null, 1: metamask, 2: walletconnect
walletType = 0;
dataCached = false;
instanceCacheMap: Map<string, any>;
public chainMap: Map<number, any> = new Map();
public rpc: any = {};
constructor() {
const allChainMap: Map<number, any> = new Map();
for (const d of AllChains) {
const id = d.id;
this.rpc[id] = d.rpc;
allChainMap.set(id, d);
}
for (const id of AVAILABLE_CHAINS) {
this.chainMap.set(id, allChainMap.get(id)!);
}
this.loadCachedProvider();
this.instanceCacheMap = new Map();
// AppModule.updateChainID(chainId)
busNeedLogin.on(this.connect.bind(this));
}
get isWalletConnect() {
return !!this.walletType && !!this.currentChain;
}
get mallAddress() {
return CONTRACT_ADDRESS[this.currentChain]?.mall;
}
public get hexChainId() {
return toHexChainId(this.currentChain);
}
public async chainSelected(id: number) {
if (!this.chainMap.has(id)) {
return;
}
this.currentChain = id;
if (this.provider) {
await this.switchEthereumChain();
} else {
await this.connectWallet(true);
}
}
public async connectWallet(isManual: boolean) {
console.log(
"begin connect to wallet: ",
this.walletType,
this.currentChain
);
if (this.walletType === 1) {
this.provider = await this.connectMetaMask();
} else if (this.walletType === 2) {
this.provider = await this.connectWalletConnect();
}
if (!this.provider) {
return;
}
this.web3 = new Web3(this.provider);
const chainId = await this.web3.eth.getChainId();
await this.checkChain(chainId);
this.subscribeToEvents();
const accounts = await this.web3.eth.getAccounts();
if (accounts && accounts.length > 0) {
AppModule.updateAccount(accounts[0]);
}
if (!this.currentChain) this.currentChain = chainId;
this.saveProvider();
AppModule.updateChainID(chainId);
AppModule.updateWalletStatus(true);
console.log("current login chain: ", chainId);
console.log("accountsLogin: ", accounts, AppModule.accountId);
if (isManual) {
busNeedNonce.emit(busNeedNonce);
} else {
AppModule.updateStep(1);
}
return { account: accounts[0], chainId };
}
/**
* check whether special chainId is supported by config
* show chain picker when chainId is not supported and current wallet is meatmask
* show message box when chainId is not supported and current wallet is wallet connect
* @param {number} chainId
* @return {Promise<void>}
* @private
*/
private async checkChain(chainId: number) {
if (chainId !== AVAILABLE_CHAINS[0]) {
// if (this.walletType === 1) {
try {
await this.selectChain();
} catch (err) {
await this.disconnect();
}
// } else if (this.walletType === 2) {
// await this.disconnect()
// this.walletType = 2
// await MessageBox.alert(
// 'You need to connect to supported network',
// 'Wrong Network',
// {
// confirmButtonText: 'Confirm'
// })
// await this.connectWallet(true)
// }
}
}
public async connect(isManual = false) {
// if (isMobile()) {
// if (hasMetamask()) {
// this.walletType = 1;
// } else {
// this.walletType = 2;
// }
// } else {
// if (hasMetamask()) {
// if (isManual && !this.walletType) {
// this.walletType = await this.selectWallet();
// }
// } else {
// this.walletType = 2;
// }
// }
this.walletType = 1;
if (isManual || this.isWalletConnect) {
await this.connectWallet(isManual);
}
}
/**
* show wallet picker
* @return {Promise<number>}
* @private
*/
private selectWallet(): Promise<number> {
return new Promise((resolve, reject) => {
busShowChainModal.emit({
confirm: (id: number) => {
console.log("select wallet: ", id);
resolve && resolve(id);
},
cancel: (reason: any) => {
console.log("cancel select wallet: ", reason);
reject && reject(reason);
},
});
});
}
/**
* show chain picker
* @return {Promise<number>}
* @private
*/
private selectChain(): Promise<number> {
return new Promise((resolve, reject) => {
this.switchEthereumChain(AVAILABLE_CHAINS[0], (res: any)=>{
if (res.err) {
reject && reject(res.err)
return
}
resolve && resolve(res.chain)
});
});
}
public async connectMetaMask() {
let provider = null;
if (typeof window.ethereum !== "undefined") {
provider = window.ethereum;
try {
await provider.request({ method: "eth_requestAccounts" });
} catch (error: any) {
if (error.code === -32002) {
// const hexChainId = toHexChainId(this.currentChain)
// await provider.request({
// method: 'wallet_switchEthereumChain',
// params: [{ chainId: hexChainId }]
// })
throw new Error("MeatMask not login, Open MeatMask and login first");
} else {
throw new Error("User Rejected");
}
}
} else if (window.web3) {
provider = window.web3.currentProvider;
} else if (window.celo) {
provider = window.celo;
} else {
throw new Error("Cannot find Metamask");
}
return provider;
}
public async connectWalletConnect() {
const provider = new WalletConnectProvider({
infuraId: import.meta.env.VUE_APP_WALLET_INFURAID,
rpc: this.rpc,
});
try {
await provider.enable();
} catch (err) {
console.log("connect to wallet connect error: ", err);
await Promise.reject(err);
}
return provider;
}
public async getContractInstance(address: string, abi: any = ERC20ABI) {
if (!this.web3) {
this.connectWallet(true)
// throw new Error(
// "Web3 instance is not initialized. Please call `initWeb3` method after user login."
// );
}
if (!this.instanceCacheMap.has(address)) {
const instance = new this.web3.eth.Contract(abi, address, {
from: AppModule.accountId,
});
this.instanceCacheMap.set(address, instance);
}
return this.instanceCacheMap.get(address);
}
public clearCachedProvider() {
console.log("clear cached provider");
localStorage.removeItem(CACHE_KEY);
}
public loadCachedProvider() {
const dataStr = localStorage.getItem(CACHE_KEY);
if (dataStr) {
try {
const data = JSON.parse(dataStr);
this.walletType = data.walletType;
if (this.chainMap.has(data.chainId)) {
this.currentChain = data.chainId;
}
} catch (err) {
console.log("err parse cached json");
this.clearCachedProvider();
}
}
}
public saveProvider() {
const data = {
walletType: this.walletType,
chainId: this.currentChain,
};
localStorage.setItem(CACHE_KEY, JSON.stringify(data));
}
public async disconnect() {
try {
await UserModule.Logout();
await this.provider?.disconnect();
} catch (err) {}
this.currentChain = 0;
this.walletType = 0;
this.instanceCacheMap.clear();
this.clearCachedProvider();
AppModule.updateStep(0);
AppModule.updateChainID(0);
AppModule.updateNonce("");
AppModule.updateAccount("");
AppModule.updateWalletStatus(false);
}
public subscribeToEvents = () => {
// Subscribe to accounts change
this.provider.on("accountsChanged", async (accounts: string[]) => {
console.log("accountsChanged: ", accounts);
if (accounts && accounts.length > 0) {
if (AppModule.accountId !== accounts[0]) {
await UserModule.Logout();
this.currentChain = 0;
this.walletType = 0;
this.instanceCacheMap.clear();
this.clearCachedProvider();
AppModule.updateStep(0);
AppModule.updateChainID(0);
AppModule.updateNonce("");
AppModule.updateAccount("");
AppModule.updateWalletStatus(false);
localStorage.removeItem("totalSupply");
localStorage.removeItem("supplyLimit");
localStorage.removeItem("mintableCount");
location.reload();
}
}
});
// Subscribe to chainId change
this.provider.on("chainChanged", async (chainId: string) => {
const chainIdNum = parseInt(chainId);
console.log("chainChanged", chainId, chainIdNum);
await this.checkChain(chainIdNum);
this.currentChain = chainIdNum;
this.saveProvider();
AppModule.updateChainID(this.currentChain);
});
// Subscribe to session disconnection
this.provider.on("disconnect", (err: any) => {
console.log("disconnect", err);
});
};
/**
* change chain of metamask
* @param {number} chainId
* @param {() => void} cb
* @return {Promise<void>}
*/
async switchEthereumChain(chainId?: number, cb?: (res: any) => void) {
chainId = chainId || AVAILABLE_CHAINS[0];
const hexChainId = toHexChainId(chainId);
const onChainChange = (chainId: string) => {
console.log("switchEthereumChain: ", chainId);
this.provider.removeListener("chainChanged", onChainChange);
cb && cb({chain: chainId});
};
this.provider.on("chainChanged", onChainChange);
try {
const data = this.chainMap.get(chainId)!;
await this.provider.request({
method: "wallet_addEthereumChain",
params: [
{
chainId: hexChainId,
chainName: data.name,
nativeCurrency: {
name: data.symbol,
symbol: data.symbol,
decimals: data.decimals || 18,
},
blockExplorerUrls: [data.explorerurl],
rpcUrls: [data.rpc],
},
],
});
console.log("add chain success");
} catch (addError) {
console.error("add chain error: ", addError);
this.provider.removeListener("chainChanged", onChainChange);
cb && cb({err: addError})
}
}
public async getTransactionReceipt(txHash: string) {
return this.web3.eth.getTransactionReceipt(txHash);
}
public async getTxConfirms(txhash: string) {
const receipt: TransactionReceipt = await this.getTransactionReceipt(
txhash
);
const latest = await this.web3.eth.getBlockNumber();
return latest - receipt.blockNumber + 1;
}
public async signPresale({
type,
paymentTokenAddress,
price,
buyerAddress,
netId,
}: {
type: number | string;
paymentTokenAddress: string;
price: any;
buyerAddress: string;
netId?: any;
}) {
const nonce = (Math.random() * 100000) | 0;
const signMsg = {
item: type,
token: paymentTokenAddress,
price: price,
salt: nonce,
};
netId = netId || (await this.web3.eth.getChainId());
const signObj = {
types: {
EIP712Domain: EIP721_DOMAIN_DATA,
set: [
{ name: "item", type: "uint256" },
{ name: "token", type: "address" },
{ name: "price", type: "uint256" },
{ name: "salt", type: "uint256" },
],
},
primaryType: "set",
domain: {
name: "BEBoxMall",
version: "1",
chainId: netId,
verifyingContract: this.mallAddress,
},
message: signMsg,
};
const signature = await this.signData(signObj, buyerAddress);
return { nonce, signature };
}
public async increaseAllowance(address: string, price: string) {
const coinInstance: any = await this.getContractInstance(address);
const res = await coinInstance.methods
.increaseAllowance(this.mallAddress, price)
.send({ gas: 1000000 });
console.log("increaseAllowance: ", res);
}
public async claimReward(address: string,startTime:string,saltNonce:string,signature:string) {
const coinInstance: any = await this.getContractInstance(
Global.LIMIT_ABI_Address,
CLAIM_ABI
);
let gas = await coinInstance.methods.claim(address,startTime,saltNonce,signature).estimateGas()
gas = gas * 1.1 | 0
console.log('gas:: ' , gas)
let gasPrice = await this.web3.eth.getGasPrice()
const res = await coinInstance.methods.claim(address,startTime,saltNonce,signature).send({gas, gasPrice});
console.log("claimReward: ", res);
return res
}
public async getBalances( account: string ) {
account = account || AppModule.accountId
const coinInstance: any = await this.getContractInstance(
Global.LIMIT_ABI_Address,
CLAIM_ABI
);
return await coinInstance.methods.claimHistory(account).call()
}
// public async totalSupply(address: string) {
// const coinInstance: any = await this.getContractInstance(
// Global.LIMIT_ABI_Address,
// LIMIT_ABI
// );
// const res = await coinInstance.methods.totalSupply().call();
// console.log("totalSupply: ", res);
// return res
// }
// // 获取当前用户可mint的数量
// public async getMintableCount(address?: string) {
// // address = address || //TODO: current address
// const coinInstance: any = await this.getContractInstance(
// Global.MEDAL_REWARDS_Address,
// MEDAL_REWARDS_ABI
// );
// const res = await coinInstance.methods
// .getMintableCount(AppModule.accountId)
// .call();
// console.log("getMintableCount: ", res);
// return res
// }
// // 获取当前用户的mint总数
// public async supplyLimit(address: string) {
// const coinInstance: any = await this.getContractInstance(
// Global.LIMIT_ABI_Address,
// LIMIT_ABI
// );
// const res = await coinInstance.methods.supplyLimit().call();
// console.log("supplyLimit: ", res);
// return res
// }
/**
* @param {string} address
* @param {string | null} account
* @return {Promise<any>}
*/
// public async getBalance(address: string, account: string | null) {
// account = account || AppModule.accountId;
// const coinInstance: any = await this.getContractInstance(address);
// return await coinInstance.methods.balanceOf(account).call();
// }
public async getBalance(address: string, account: string | null) {
account = account || AppModule.accountId
const coinInstance: any = await this.getContractInstance(address)
return await coinInstance.methods.claimHistory(account).call()
}
public async transferToAccount(
account: string,
amount: number,
address: string
) {
const amountBN = this.web3.utils.toBN(this.web3.utils.toWei(amount + ""));
const coinInstance: any = await this.getContractInstance(address);
return coinInstance.methods
.transfer(account, amountBN)
.send({ gas: 1000000 });
}
public async signData(signObj: any, signer: string) {
const msgParams = JSON.stringify(signObj);
const from = signer;
console.log("clicked, sending personal sign req", "from", from, msgParams);
const params = [from, msgParams];
const result: any = await this.sendCmd({
method: "eth_signTypedData_v4",
params,
from,
});
console.log(result);
return result.result;
}
public async sendCmd({ method, params, from }: any) {
return new Promise((resolve, reject) => {
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
this.web3.currentProvider.sendAsync(
{
method,
params,
from,
},
async function (err: any, result: any) {
if (err) {
reject && reject(err);
return;
}
resolve && resolve(result);
}
);
});
}
}

View File

@ -0,0 +1,119 @@
<template>
<transition-group name="slide" tag="div">
<div
v-for="(notification, index) in notifications"
:key="notification.id"
class="notification"
:class="position"
>
<span>{{ notification.message }}</span>
</div>
</transition-group>
</template>
<script setup>
import { ref, reactive, onMounted, watchEffect } from "vue";
let id = 0;
const props = defineProps({
position: {
type: String,
default: "top-right",
validator: (value) =>
["top-right", "top-left", "bottom-right", "bottom-left"].includes(value),
},
duration: {
type: Number,
default: 3000,
},
});
const notifications = reactive([]);
const addNotification = (message) => {
const notification = {
id: id++,
message,
};
notifications.push(notification);
setTimeout(() => {
closeNotification(notifications.indexOf(notification));
}, props.duration);
};
const closeNotification = (index) => {
if (index !== -1) {
notifications.splice(index, 1);
}
};
defineExpose({
addNotification,
closeNotification,
});
</script>
<style lang="scss" scoped>
.slide-enter-active,
.slide-leave-active {
transition: transform 0.3s ease-out, opacity 0.3s ease-out;
}
.slide-enter-from,
.slide-leave-to {
transform: translateX(100%);
opacity: 0;
}
.slide-enter-to,
.slide-leave-from {
transform: translateX(0);
opacity: 1;
}
.notification {
position: fixed;
padding: 0.8em;
background: url('../../assets/img/task/msg-bg.png') no-repeat;
background-size: 100% 100%;
color: #721c24;
/* border: solid 1px #f5c6cb; */
border-radius: 0.25rem;
min-width: 304px;
min-height: 80px; /* set minimum height */
display: flex;
font-size: 14px;
font-family: Arial;
font-weight: 400;
color: #ffffff;
align-items: center;
justify-content: center;
text-align: center;
white-space: normal;
word-wrap: break-word;
}
.notification.top-right {
right: 50px;
top: 80px;
}
.notification.top-left {
left: 0;
top: 0;
}
.notification.bottom-right {
right: 0;
bottom: 0;
}
.notification.bottom-left {
left: 0;
bottom: 0;
}
</style>

View File

@ -0,0 +1,213 @@
<template>
<div class="chain-modal" v-if="modalShow" :class="{ mobile: 'mobile' }">
<div class="modal-bg" @click="cancelSelect"></div>
<div class="modal-content" :class="{ mobile: 'mobile' }">
<div class="modal-title">You need to connect to supported network</div>
<div
class="chain-modal-card"
v-for="data in currentDatas"
:key="data.name"
@click="cardClicked(data.id)"
>
<div class="icon">
<img :src="data.logo" :alt="data.name" />
</div>
<div class="name">{{ data.name }}</div>
<div class="desc">{{ data.desc }}</div>
</div>
</div>
</div>
</template>
<script setup>
import { ref, computed, onMounted, onUnmounted } from "vue";
import { ALL_PROVIDERS } from "@/configs/configchain";
import { useChainStore } from "@/store/chain";
import { useEventBus } from "@vueuse/core";
import * as bus_event from "@/bus/event";
const busShowChainModal = useEventBus(bus_event.SHOW_CHAIN_MODAL);
const busNeedChangeChain = useEventBus(bus_event.NEED_CHANGE_CHAIN);
const chain = useChainStore();
const modalShow = ref(false);
const dataType = ref(1);
const chainDatas = computed(() => {
// console.log([...chain.chainManager.availableChains.values()]);
return [...chain.chainManager.availableChains.values()];
});
// const currentDatas = computed(()=> {
// if (dataType.value===0) {
// //console.log({ALL_PROVIDERS});
// return ALL_PROVIDERS;
// } else if (dataType.value===1) {
// //console.log({chainDatas});
// return chainDatas.value;
// } else {
// //console.log("error=====");
// return [];
// }
// });
const currentDatas = computed(() => {
return (
{
0: ALL_PROVIDERS,
1: chainDatas.value,
}[dataType.value] || []
);
});
let confirmFun = (id) => {};
let cancelFun = (reason) => {};
onMounted(() => {
busShowChainModal.on(showSelectWallet);
busNeedChangeChain.on(showChangeChain);
});
onUnmounted(() => {
busShowChainModal.off(showSelectWallet);
busNeedChangeChain.off(showChangeChain);
});
function showSelectWallet({ confirm, cancel }) {
confirmFun = confirm;
cancelFun = cancel;
showModal(0);
}
function showChangeChain({ confirm, cancel }) {
confirmFun = confirm;
cancelFun = cancel;
// showModal(0);
cancelSelect();
}
function cardClicked(id) {
console.log("card clicked:", id);
confirmFun && confirmFun(id);
hideModal();
}
function cancelSelect() {
cancelFun();
hideModal();
}
function showModal(type) {
dataType.value = type;
modalShow.value = true;
}
function hideModal() {
modalShow.value = false;
// confirmFun = (id) => {
// console.log(id);
// };
// cancelFun = (reason) => {
// console.log(reason);
// };
}
</script>
<style lang="scss" scoped>
.chain-modal {
position: fixed;
top: 0;
right: 0;
bottom: 0;
left: 0;
overflow: auto;
margin: 0;
z-index: 10;
.modal-bg {
position: absolute;
top: 0;
right: 0;
bottom: 0;
left: 0;
overflow: auto;
margin: 0;
background-color: #000000a3;
}
.modal-content {
width: 500px;
max-height: 400px;
position: absolute;
top: 0;
right: 0;
bottom: 0;
left: 0;
margin: auto;
display: flex;
flex-direction: column;
.mobile {
width: 100vw;
}
.modal-title {
background-color: rgb(255, 255, 255);
color: black;
border-radius: 12px 12px 0 0;
padding: 15px 20px;
border-bottom: 1px solid rgba(195, 195, 195, 0.14);
}
.chain-modal-card {
background-color: rgb(255, 255, 255);
transition: background-color 0.2s ease-in-out 0s;
display: flex;
flex-direction: column;
-webkit-box-pack: center;
justify-content: center;
-webkit-box-align: center;
align-items: center;
padding: 24px 16px;
text-align: center;
cursor: pointer;
&:first-child {
border-radius: 12px 12px 0 0;
}
&:not(:first-child) {
border-top: 1px solid rgba(195, 195, 195, 0.14);
}
&:last-child {
border-radius: 0 0 12px 12px;
}
.icon {
width: 45px;
height: 45px;
display: flex;
border-radius: 50%;
overflow: visible;
box-shadow: none;
-webkit-box-pack: center;
justify-content: center;
-webkit-box-align: center;
align-items: center;
img {
width: 100%;
height: 100%;
}
.icon-svg {
width: 100%;
height: 100%;
fill: currentColor;
color: unset;
stroke: none;
}
}
.name {
width: 100%;
font-size: 24px;
font-weight: 700;
margin-top: 0.5em;
color: rgb(12, 12, 13);
}
.desc {
width: 100%;
font-size: 18px;
margin: 0.333em 0px;
color: rgb(169, 169, 188);
}
}
}
}
</style>

View File

@ -0,0 +1,603 @@
<template>
<div>
<div class="header header-top">
<div class="header-left">
<div class="header-logo">
<a href="/"
><img src="../../assets/img/planet/header-logo.png" alt=""
/></a>
</div>
<div class="nav">
<a
class="nav-item duration-200"
v-for="(nav, i) in navList"
:class="getNavItemClass(i, nav)"
:key="i"
@click="handNavCurent(nav)"
>
<span> {{ nav.name }}</span>
<div class="dropdown">
<ul>
<li v-for="(item, index) in nav.submenu" :key="index">
<div
class="link-content"
v-if="i !== 2"
@click="openThirdPartyLink(item.link)"
>
<div>
<a
class="link-name"
:href="item.link"
target="_blank"
rel="noopener noreferrer"
>{{ item.label }}</a
>
</div>
<div>
<a
:href="item.link"
target="_blank"
rel="noopener noreferrer"
>
<img
class="link-img"
src="../../assets/img/home/link-icon.png"
alt=""
/>
</a>
</div>
</div>
<div v-else class="link-label">{{ item.label }}</div>
</li>
</ul>
</div>
</a>
</div>
</div>
<div class="header-right">
<div class="community-btn">Community</div>
<div class="metaMask-login">
<div class="metaMask-logo">
<img src="../../assets/img/planet/wallet_icon.png" alt="" />
</div>
<div class="matamask">
<div>Connect</div>
<div>wallet</div>
</div>
</div>
<!-- <div
v-if="!chain.logined"
class="login-btn login-btn-active"
@click="login"
>
LOGIN
</div>
<div v-else class="avatar" @click="showMenu = !showMenu">
<img
class="avatar-img"
src="../../assets/img/home/avatar.png"
alt="用户头像"
/>
<div class="menu" v-show="showMenu">
<div class="menu-item-top">
<div class="title">{{ formatAddress }}</div>
<div @click="handleCopy">
<img src="../../assets/img/home/copy.png" alt="" />
</div>
</div>
<div class="menu-item" @click="logout">Logout</div>
</div>
</div> -->
</div>
</div>
<ChainModel></ChainModel>
</div>
</template>
<script setup>
import { ref, reactive, onMounted, computed, watchEffect } from "vue";
import { useChainStore } from "@/store/chain";
import { useAppStore } from "@/store/app";
import { useRouter, useRoute } from "vue-router";
import ChainModel from "@/components/home/ChainModel.vue";
import { useCopyToClipboard } from "./../../hooks/useCopyToClipboard";
const AppModule = useAppStore();
const router = useRouter();
const route = useRoute();
const chain = useChainStore();
const app = useAppStore();
function click(event) {
router.push(event.key);
}
//const { copied, copyToClipboard } = useCopyToClipboard(AppModule.accountId);
const { copied, error, reset, copyToClipboard } = useCopyToClipboard();
const message = copied.value
? "Text copied!"
: "Click the button to copy text.";
const formatAddress = computed(() => {
const accountId = AppModule.accountId;
if (!accountId) return "-";
if (accountId.length >= 10) {
return `${accountId.substring(0, 6)}......${accountId.slice(-4)}`;
}
return accountId;
});
const getNavItemClass = (index, nav) => {
if (index === activeIndex.value) {
return "active-nav-item";
} else if (index === 5) {
return "badge-nav-item";
} else if (index === 6) {
return "task-nav-item"; // Add the desired class for index 6
} else {
return "";
}
};
async function login(event) {
if (!chain.logined) {
//
await chain.chainManager.login();
// console.log("logined:", chain.chainManager.isLogined);
chain.logined = chain.chainManager.isLogined;
}
}
const logout = async () => {
await chain.chainManager.logout();
window.location.reload();
// console.log("logined:", chain.chainManager.isLogined);
chain.logined = chain.chainManager.isLogined;
window.location.reload();
};
const avatarUrl = ref("https://example.com/avatar.jpg");
const showMenu = ref(false);
const showNavMenu = ref(false);
const activeIndex = ref(0);
const navList = reactive([
{ id: 0, name: "MAP", path: "/" },
{ id: 1, name: "TEH GAME", path: "/about" },
{
id: 2,
name: "STAKE",
path: "/marketpalce",
submenu: [{ label: "Coming soon", link: "/products/1" }],
},
{
id: 3,
name: "MORE",
path: "/contact",
submenu: [
{ label: "Twitter", link: "https://twitter.com/CEBG_GAME" },
{
label: "Youtube",
link: "https://youtube.com/c/CryptoElitesBattlegrounds",
},
{
label: "Facebook",
link: "https://www.facebook.com/profile.php?id=100090965821157&mibextid=LQQJ4d",
},
{ label: "Medium", link: "https://medium.com/@CEBG-BATTLEGROUNDS" },
{ label: "Telegram", link: "https://t.me/CEBG_Rally" },
{ label: "Discord", link: "https://discord.com/invite/fNSn2NHUvf" },
],
},
// { id: 4, name: "BETA TEST II", path: "/" },
// { id: 5, name: "BADGE", path: "https://badge.kingsome.cn" },
// { id: 6, name: "TASK", path: "/task" },
]);
//{ id: 5, name: "BADGE", path: "https://badge.kingsome.cn" },
function handNavCurent(nav) {
activeIndex.value = nav.id;
if (nav.id === 0 || nav.id === 1 || (nav.id === 4) | (nav.id === 6)) {
router.push(nav.path);
} else if (nav.id === 5) {
window.location.href = nav.path;
//window.open(nav.path, "_blank");
}
}
function openThirdPartyLink(url) {
window.open(url, "_blank");
}
const handleCopy = () => {
const accountId = AppModule.accountId;
reset();
copyToClipboard(accountId).then(() => {
// if (copied.value) {
// message.success("Copy successful!");
// }
});
};
watchEffect(() => {
const index = navList.findIndex(
(navItem) => route.path.slice(0, 5) === navItem.path.slice(0, 5)
);
activeIndex.value = index !== -1 ? index : 0;
});
</script>
<style lang="scss" scoped>
.header {
position: fixed;
z-index: 19;
top: 0;
left: 0;
background-color: #0e0e0e;
width: 100%;
height: 84px;
display: flex;
align-items: center;
padding-right: 11px;
justify-content: space-between;
box-shadow: 0 4px 6px -1px rgba(0, 0, 0, 0.1),
0 2px 4px -2px rgba(0, 0, 0, 0.1);
.header-left{
display: flex;
align-items: center;
}
.header-logo {
margin-left: 64px;
width: 194px;
height: 64px;
}
.nav {
padding-left: 83px;
display: flex;
justify-content: space-between;
// width: 830px;
a {
padding-top: 29px;
padding-bottom: 29px;
}
.nav-item {
font-size: 16px;
position: relative;
font-weight: 800;
padding-left: 64px;
padding-right: 64px;
transition-property: color;
transition-duration: 0.15s;
transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
font-family: "Big John";
font-size: 18px;
color: #cccccc;
.dropdown {
position: absolute;
top: 84px;
left: 50%;
width: 100%;
background: rgba(0, 0, 0, 0.84);
border-radius: 0px 0px 12px 12px;
z-index: 1;
opacity: 0;
transform: translate(-50%, 0%);
visibility: hidden;
transition: all 0.3s ease-out;
}
.dropdown ul {
list-style: none;
margin: 0;
padding: 0;
}
.dropdown li {
padding-top: 10px;
padding-bottom: 10px;
padding-left: 20px;
padding-right: 20px;
cursor: pointer;
}
.link-content {
display: flex;
// width: 150px;
align-items: center;
justify-content: space-between;
}
.link-label {
font-size: 16px;
font-family: Arial;
font-weight: 400;
text-align: center;
color: #ffffff;
}
.dropdown li a {
font-size: 16px;
font-family: Arial;
font-weight: 400;
color: #ffffff;
}
.dropdown li span {
font-size: 15px;
font-family: Arial;
font-weight: 400;
color: #ffffff;
}
}
.duration-200 {
transition-duration: 0.2s;
}
.nav-item:hover {
transition-property: color;
transition-duration: 0.15s;
transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
font-family: "Big John";
background-color: #2dadb2;
color: rgba(12, 12, 12, 1);
}
.nav-item:hover .dropdown {
opacity: 1;
visibility: visible;
}
// .nav-item::after {
// content: "";
// height: 7px;
// overflow: hidden;
// display: block;
// left: 0;
// bottom: 0;
// position: absolute;
// width: 100%;
// // background: #1fc8ff;
// background: url("@/assets/img/home/nav-boder.png") no-repeat;
// background-size: 100% 100%;
// transform: scaleX(0);
// transition: all 0.3s;
// }
// .nav-item:hover::after {
// transform: scaleX(1);
// }
.active-nav-item {
font-size: 16px;
font-family: "Big John";
position: relative;
font-weight: 800;
background-color: #2dadb2;
transition-property: color;
transition-duration: 0.3s;
transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
color: rgba(12, 12, 12, 1);
}
// .active-nav-item::after {
// content: "";
// height: 8px;
// overflow: hidden;
// display: block;
// left: -7%;
// bottom: 0;
// position: absolute;
// width: 120%;
// // background: #1fc8ff;
// background: url("@/assets/img/home/nav-boder.png") no-repeat;
// background-size: 100% 100%;
// transform: scaleX(0);
// transition: all 0.3s;
// }
// .active-nav-item::after {
// transform: scaleX(1);
// }
}
}
.header-right {
// width: 228px;
// position: absolute;
display: flex;
justify-content: center;
align-items: center;
// right: 11px;
.community-btn {
width: 218px;
height: 68px;
background: #2a2b3e;
margin-right: 10px;
text-align: center;
line-height: 68px;
cursor: pointer;
color: #fff;
font-size: 20px;
font-family: "Poppins";
font-weight: 400;
color: #eeecff;
border-radius: 10px;
}
.metaMask-login {
width: 218px;
height: 68px;
display: flex;
justify-content: center;
align-items: center;
color: #fff;
cursor: pointer;
background: #2a2b3e;
font-size: 20px;
font-family: "Poppins";
font-weight: 400;
color: #eeecff;
border-radius: 10px;
}
.menu {
position: absolute;
top: 111%;
right: -35px;
width: 180px;
z-index: 1;
padding: 10px 0;
background-color: #000000;
border-radius: 5px;
box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
list-style: none;
transition: all 0.3s ease-out;
}
li {
margin: 5px 0;
}
.menu-item-top {
padding: 10px 15px;
color: #f5f5f5;
display: flex;
align-items: center;
position: relative;
padding-bottom: 15px;
.title {
margin-right: 20px;
}
}
.menu-item-top:before {
position: absolute;
top: 100%;
left: 15px;
content: "";
width: 140px;
height: 1px;
background: #676767;
}
.menu-item {
padding: 5px 15px;
color: #f5f5f5;
display: flex;
padding-top: 10px;
align-items: center;
.title {
margin-right: 10px;
}
}
a:hover {
background-color: #f5f5f5;
}
}
.login-btn {
position: relative;
width: 228px;
height: 65px;
font-size: 26px;
line-height: 65px;
font-size: 22px;
font-family: "Big John";
color: #122326;
text-align: center;
cursor: pointer;
background: url("@/assets/svg/login-active.svg") no-repeat;
background-size: 100% 100%;
z-index: 0;
transition: background-image 1s;
// transition:background-image 1s linear;
// transform: scaleX(1);
// transition: all 0.15s;
// transition-property: background;
// transition-duration: 0.15s;
// transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
}
.login-btn::after {
content: "";
position: absolute;
left: 0;
right: 0;
top: 0;
bottom: 0;
opacity: 1;
// transition: 0.5s;
background: url("@/assets/svg/login.svg") no-repeat;
background-size: 100% 100%;
transform: scaleX(1, 1);
clip-path: polygon(50% 50%, 50% 50%, 50% 50%, 50% 50%);
transition: all 0.3s ease-in-out;
z-index: -1;
// transition:background-image 1s linear;
// transform: scaleX(0.98);
}
.login-btn:hover {
color: #ffba00;
}
.login-btn:hover:after {
opacity: 1;
clip-path: polygon(
calc(50% + 0px) calc(50% + 150px),
calc(50% + 150px) calc(50% + 0px),
calc(50% + 0px) calc(50% - 150px),
calc(50% - 150px) calc(50% - 0px)
);
color: #ffba00;
transition: all 0.3s ease-in-out;
transform: scaleX(1, 1);
}
.login-btn:active:after {
opacity: 1;
color: #ffba00;
transform: scaleX(1);
}
.avatar {
position: relative;
display: flex;
justify-content: center;
align-items: center;
cursor: pointer;
}
.avatar-img {
width: 54px;
height: 54px;
margin-top: 5px;
margin-right: 30px;
border: 2px solid #ffba00;
border-radius: 50%;
}
.link-name {
position: relative;
.link-img {
position: absolute;
top: 24px;
right: -18px;
}
}
@media (max-width: 1440px) {
.header {
.header-logo {
margin-left: 20px;
}
.nav {
padding-left: 40px;
.nav-item {
padding-left: 30px;
padding-right: 30px;
.dropdown {
top: 63px;
}
}
}
.header-right {
width: 200px;
right: -20px;
.menu {
right: -20px;
}
}
.login-btn {
width: 200px;
}
}
}
.header-btn {
width: 181px;
height: 51px;
border: 1px solid #ffffff;
clip-path: polygon(
10% 0,
/* 左上角缺角的位置 */ 100% 0,
100% 90%,
/* 右下角缺角的位置 */ 0 100%,
0 0
);
background-color: transparent;
}
</style>

View File

@ -0,0 +1,50 @@
<template>
<div class="layout">
<NavBar></NavBar>
<router-view> </router-view>
</div>
</template>
<script setup>
import { ref } from "vue";
import { useRouter, useRoute } from "vue-router";
import NavBar from "./NavBar.vue";
const currentRoute = useRoute();
const showLoading = ref(false);
const startLoading = () => {
showLoading.value = true;
};
const stopLoading = () => {
showLoading.value = false;
};
</script>
<style lang="scss" scoped>
.layout{
width: 100%;
height: 100%;
}
.fade-enter-from,
.fade-leave-to {
/*定义进入开始和离开结束的透明度为0*/
opacity: 0;
}
.fade-leave-to {
transform: translateX(20px);
}
.fade-enter-to {
transform: translateX(-20px);
}
.fade-enter-to,
.fade-leave-from {
/*定义进入结束和离开开始的透明度为1*/
opacity: 1;
}
.fade-leave-active,
.fade-enter-active {
transition: all 0.32s ease-out;
}
</style>

View File

@ -0,0 +1,229 @@
<template>
<div class="naber">
<div class="content">
<div class="logo" @click="handTaskHome">
<a ><img src="@/assets/img/task/logo.png" alt="" /></a>
</div>
<div class="header-right">
<div class="twitter">
<a
href="https://twitter.com/_CounterFire"
target="_blank"
rel="noopener noreferrer"
>
<img src="@/assets/img/task/TW.png" alt=""
/></a>
</div>
<div class="discode">
<a
href="https://discord.com/invite/fNSn2NHUvf"
target="_blank"
rel="noopener noreferrer"
><img src="@/assets/img/task/DC.png" alt=""
/></a>
</div>
<div v-if="!chain.logined" class="login-btn" @click="login">
Connect Wallet
</div>
<div v-else class="login-btn-active" @click="showMenu = !showMenu">
{{ formatAddress }}
<div class="menu" v-show="showMenu">
<div class="menu-item" @click="logout">Disconnect</div>
</div>
</div>
</div>
</div>
</div>
</template>
<script setup>
import { ref, reactive, onMounted, computed, watchEffect } from "vue";
import { useChainStore } from "@/store/chain";
import { useAppStore } from "@/store/app";
import { useRouter, useRoute } from "vue-router";
import { UserStatus } from "@/api/User";
import ChainModel from "@/components/home/ChainModel.vue";
import { useCopyToClipboard } from "./../../hooks/useCopyToClipboard";
import { hasMetamask } from "@/utils/chain.util";
const AppModule = useAppStore();
const router = useRouter();
const route = useRoute();
const showMenu = ref(false);
const chain = useChainStore();
const app = useAppStore();
const { copied, error, reset, copyToClipboard } = useCopyToClipboard();
const emit = defineEmits(["login-success"]);
const formatAddress = computed(() => {
const accountId = AppModule.accountId;
if (!accountId) return "-";
if (accountId.length >= 10) {
return `${accountId.substring(0, 6)}......${accountId.slice(-4)}`;
}
return accountId;
});
async function login(event) {
var next = window.location.href;
if (!hasMetamask()) {
var url = `https://metamask.app.link/dapp/${next}`;
location.href = url;
} else {
if (!chain.logined) {
//
await chain.chainManager.login();
// console.log("logined:", chain.chainManager.isLogined);
chain.logined = chain.chainManager.isLogined;
const resq = await UserStatus({
account: AppModule.accountId,
invite_code: route.query.code,
});
emit("login-success");
}
}
}
const logout = async () => {
await chain.chainManager.logout();
window.location.reload();
// console.log("logined:", chain.chainManager.isLogined);
chain.logined = chain.chainManager.isLogined;
window.location.reload();
};
const handTaskHome = () => {
//router.push("/quest");
const code = route.query.code;
if (code) {
router.push({ path: "/quest", query: { code: code } });
} else {
router.push("/quest");
}
};
const handleCopy = () => {
const accountId = AppModule.accountId;
reset();
copyToClipboard(accountId).then(() => {
// if (copied.value) {
// message.success("Copy successful!");
// }
});
};
</script>
<style lang="scss" scoped>
.naber {
// position: fixed;
// z-index: 20;
// top: 0;
// left: 0;
// background-color: rgb(15, 15, 15);
width: 100%;
height: 75px;
padding-top: 10px;
display: flex;
//padding-right: 360px;
justify-content: center;
align-items: center;
.content {
width: 1200px;
display: flex;
justify-content: space-between;
}
.login-btn {
width: 180px;
height: 50px;
color: #fff;
cursor: pointer;
text-align: center;
line-height: 50px;
//border: 1px solid #ffffff;
background: url("@/assets/img/task/login-btn.png") no-repeat;
background-size: 100% 100%;
}
.login-btn:hover {
background: url("@/assets/img/task/login-btn-active.png") no-repeat;
background-size: 100% 100%;
color: #000000;
}
.login-btn-active {
width: 180px;
height: 50px;
cursor: pointer;
color: #fff;
text-align: center;
line-height: 50px;
// border: 1px solid #ffffff;
background: url("@/assets/img/task/login-btn.png") no-repeat;
background-size: 100% 100%;
position: relative;
.menu {
position: absolute;
top: 100%;
right: 0; //update this line to right: 0;
width: 180px;
z-index: 1;
// padding: 10px 0;
// background-color: #bdb8b8;
border-radius: 5px;
box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
list-style: none;
transition: all 0.3s ease-out;
}
li {
margin: 5px 0;
}
.menu-item-top {
padding: 10px 15px;
color: #f5f5f5;
display: flex;
align-items: center;
position: relative;
padding-bottom: 15px;
.title {
margin-right: 20px;
}
}
.menu-item-top:before {
position: absolute;
top: 100%;
left: 15px;
content: "";
width: 140px;
height: 1px;
background: #676767;
}
.menu-item {
// padding: 5px 15px;
color: #f5f5f5;
display: flex;
//border: 1px solid #ccc;
background-color: #161515;
justify-content: center;
text-align: center;
// padding-top: 10px;
align-items: center;
.title {
margin-right: 10px;
}
}
}
.login-btn-active:hover {
background: url("@/assets/img/task/login-btn-active.png") no-repeat;
background-size: 100% 100%;
color: #000000;
}
.header-right {
// width: 228px;
display: flex;
align-items: center;
.discode {
padding-left: 28px;
padding-right: 39px;
}
.twitter {
// padding-left: 28px;
//padding-right: 39px;
}
}
}
</style>

View File

@ -0,0 +1,189 @@
<template>
<div class="counterfire-container">
<div class="header"></div>
<div class="container-conter">
<div class="content">
<div>
<div class="counterfire-img"><img src="../../assets/img/planet/logo.png" alt="" /></div>
<div class="humanity-text">
<div>
As humanity delves into the mysteries of the cosmos, it marks a
new era where Pluto serves as a vital jumpgate. This colossal leap
allows humanity to venture into uncharted star systems, opening
doors to unexplored realms of discovery and daring.
</div>
<div>
In the expanse of the universe, humanity encounters novel races
and untapped energy sources. Amid the quest for the precious
universal resource known as Crystals, brace yourself to etch your
legend across this cosmos teeming with adventure and challenge.
</div>
</div>
<div class="download-btn">
<a href="https://apps.apple.com/app/counter%20fire/id6444462915" target="_blank" class="download-item">
<img src="../../assets/img/planet/AppStore_icon.png" alt=""
/></a>
<a class="https://play.google.com/store/apps/details?id=com.cege.games.release" target="_blank" href="http://"
><img src="../../assets/img/planet/GooglePlay_icon.png" alt=""
/></a>
</div>
</div>
</div>
<div class="bg">
<img src="../../assets/img/planet/CFunivers_bg.png" alt="" />
</div>
</div>
<div class="footer">
<div class="footer-content">
<div class="footer-left">
<div class="footer-logo">
<a href="/"
><img src="../../assets/img/planet/footer-logo.png" alt=""
/></a>
</div>
<div class="copyright">Copyright © 2023</div>
</div>
<div class="footer-right">
<a href="https://discord.com/invite/fNSn2NHUvf" class="discord-icon"
><img src="../../assets/img/planet/com_Discord_icon.png" alt=""
/></a>
<a class="twitter-icon" href="https://twitter.com/_CounterFire"
><img src="../../assets/img/planet/com_Twitter_icon.png" alt=""
/></a>
<a class="youtube-icon" href="https://www.youtube.com/c/CryptoElitesBattlegrounds"
><img src="../../assets/img/planet/com_Youtube_icon.png" alt=""
/></a>
</div>
<!-- <div class="logo"></div> -->
</div>
</div>
</div>
</template>
<script setup></script>
<style lang="scss" scoped>
.counterfire-container {
height: 100%;
width: 100%;
}
.header {
height: 84px;
}
.container-conter {
position: relative;
height: calc(100% - 168px);
width: 100%;
.content {
width: 1764px;
margin: 0 auto;
display: flex;
padding-top: 58px;
justify-content: flex-end;
.counterfire-img{
// width: 992px;
// height: 152px;
}
}
.humanity-text {
text-align: left;
width: 992px;
font-size: 24px;
font-family: "Poppins";
font-weight: 400;
color: #110d1c;
}
.bg {
position: absolute;
height: 100%;
width: 100%;
left: 0;
top: 0px;
right: 0;
z-index: -1;
bottom: 0;
color: transparent;
img {
position: absolute;
height: 100%;
width: 100%;
left: 0;
top: 0px;
right: 0;
// object-fit: cover;
bottom: 0;
z-index: 0;
color: transparent;
}
}
}
.footer {
height: 84px;
background-color: #0e0f22;
.footer-content {
width: 1764px;
margin: 0 auto;
display: flex;
align-items: center;
justify-content: space-between;
}
.copyright {
font-size: 20px;
font-family: "Poppins";
font-weight: 400;
color: #686a8f;
}
.footer-logo {
width: 194px;
height: 62px;
img {
width: 194px;
height: 62px;
}
}
.footer-right {
display: flex;
.discord-icon {
width: 64px;
height: 48px;
img {
width: 64px;
height: 48px;
}
}
.twitter-icon {
width: 60px;
height: 48px;
margin-right: 34px;
margin-left: 42px;
img {
width: 60px;
height: 48px;
}
}
.youtube-icon {
width: 60px;
height: 42px;
img {
width: 60px;
height: 42px;
}
}
}
}
.download-btn {
display: flex;
margin-top: 38px;
justify-content: space-between;
width: 100%;
.download-item{
width: 413px;
height: 112px;
}
}
</style>

View File

@ -0,0 +1,139 @@
<template>
<div class="planet-container">
<div class="herder"></div>
<div class="banner">
<div class="banner-content">
<div class="banner-left">
<div class="banner-left-top">
<div class="title">
<img src="../../assets/img/planet/planet_title.png" alt="" />
</div>
<div class="banner-slogan">
Secure Your Stellar Investment with Exclusive Planets! Embark on
an interstellar journey and claim planets that are truly
exceptional. Stake for success and unlock rewards that are out of
this world.
</div>
<div class="each">Each one is a unique masterpiece.</div>
<div class="buy-btn">Buy our token</div>
</div>
<div class="investors">
<img src="../../assets/img/planet/investors.png" alt="" />
</div>
</div>
<div class="banner-right">
<div class="planet_card">
<div class="planet_card01">
<img src="../../assets/img/planet/planet_card01.png" alt="" />
</div>
<div class="planet_card02">
<img src="../../assets/img/planet/planet_card02.png" alt="" />
</div>
<div class="planet_card03">
<img src="../../assets/img/planet/planet_card03.png" alt="" />
</div>
</div>
</div>
</div>
<div class="bg">
<img src="../../assets/img/planet/planet_banner.png" alt="" />
</div>
</div>
</div>
</template>
<script setup>
import { ref, reactive, onMounted } from "vue";
</script>
<style lang="scss" scoped>
.planet-container {
width: 100%;
height: 100%;
.header {
height: 84px;
}
// padding-bottom: 232px;
.banner {
position: relative;
width: 100%;
top: 84px;
height: 100%;
.banner-content {
width: 1764px;
margin: 0 auto;
display: flex;
padding-top: 83px;
.banner-left {
width: 776px;
display: flex;
height: 100%;
flex-direction: column;
justify-content: space-between;
.banner-slogan {
font-size: 24px;
font-family: "Poppins";
font-weight: 400;
text-align: left;
margin-top: 24px;
color: #f3f0ff;
}
.each {
font-size: 28px;
font-family: "Poppins";
font-weight: 400;
text-align: left;
margin-top: 24px;
color: #f3f0ff;
}
.buy-btn {
width: 369px;
height: 87px;
font-size: 36px;
font-family: "Poppins";
font-weight: bold;
text-align: center;
cursor: pointer;
margin-top: 45px;
line-height: 87px;
color: #ffffff;
background: url("../../assets/img/planet/planet_btnBg.png");
}
.investors {
margin-top: 103px;
}
}
}
}
.bg {
position: absolute;
height: 100%;
width: 100%;
left: 0;
top: 0;
right: 0;
z-index: -1;
bottom: 0;
color: transparent;
img {
position: absolute;
height: 100%;
width: 100%;
left: 0;
top: 0;
right: 0;
object-fit: cover;
bottom: 0;
z-index: 0;
color: transparent;
}
}
}
.banner-right{
.planet_card{
display: flex;
margin-top: 190px;
}
}
</style>

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,889 @@
<template>
<div class="task-two">
<div class="task-two-header">
<NavBar></NavBar>
</div>
<div class="content">
<div class="center">
<div class="header">
<div class="return">
<div class="return-icon" @click="handTaskHome">
<img src="@/assets/img/task/return.png" alt="" />
</div>
<div class="invite-quest">
<a
href="https://medium.com/@CounterFire/rise-of-gacha-4d5fac449d95"
target="_blank"
rel="noopener noreferrer"
>
VIEW YOUR QUEST</a
>
</div>
</div>
<div class="complete">
<!-- Complete the Sailors Quest to unlock the invite quest -->
</div>
</div>
<div class="content-conter">
<div class="content-left">
<div class="leaderboard">Leaderboard</div>
<div class="address-header">
<div class="address-header-item">#</div>
<div class="address-header-item-address">Address</div>
<div class="address-header-item-points">Points</div>
<!-- <div>Points</div> -->
</div>
<div class="scroll-content">
<a-list
item-layout="vertical"
class="value-list"
:data-source="formattedData"
:bordered="false"
:split="false"
>
<template #renderItem="{ item }">
<a-list-item>
<div class="assress-item">
<div class="assress-item-id">{{ item.id }}</div>
<div>{{ item.account }}</div>
<div class="code">
<!-- <NumberCounter :duration="10000" :targetNumber="item.code"></NumberCounter> -->
{{ item.point }}
<!-- <Vue3autocounter
ref="counter"
:startAmount="0"
:endAmount="Number(item.point)"
:duration="0.4"
prefix=""
suffix=""
separator=","
decimalSeparator="."
:decimals="0"
:autoinit="true"
>
</Vue3autocounter> -->
</div>
<!-- <div>{{ item.targetCode }}</div> -->
</div>
</a-list-item>
</template>
</a-list>
</div>
</div>
<div class="content-right" v-if="isStatus">
<!-- <div class="link-title">Invite Link</div> -->
<div class="boder-left"></div>
<div class="link-btn">
<div>
<div>Invite Link</div>
<div>{{ inviteLink }}</div>
</div>
<div class="copy" @click="handleCopy">
<img src="@/assets/img/task/copy-icon.png" alt="" />
</div>
</div>
<div class="you">
<div class="you-title">
You Invited
<span class="you-title-number">{{
userInfo.direct_clan ? userInfo.direct_clan : "0"
}}</span>
</div>
<div class="you-input">
<div v-if="userInfo.regular && userInfo.regular.length > 0">
<div class="you-input-item">
Points
<span class="item-number">
{{ userInfo.point - totalRegularPoints }}
</span>
<a-tooltip placement="bottom" overlayClassName="my-tooltip">
<template #title>
<div class="tooltip-text">
<span v-html="typesInRegular"></span><br />
</div>
</template>
<span class="item-number-right">
+ {{ totalRegularPoints }}</span
>
</a-tooltip>
</div>
</div>
<div class="you-input-item" v-else>
Points
<span class="item-number">{{
userInfo.point ? userInfo.point : "0"
}}</span>
</div>
<!-- <a-tooltip placement="bottomLeft">
<template #title>
<span>10 points for each successful invite.</span>
</template> -->
<div class="you-input-item">
Rank
<span class="item-number">{{
userInfo.rank ? userInfo.rank : "0"
}}</span>
</div>
<!-- <div class="you-input-item">
Top
<span class="item-number"
>{{ userInfo.top > 30 ? "+30" : userInfo.top }}%</span
>
</div> -->
<!-- </a-tooltip> -->
<a-tooltip placement="bottom" overlayClassName="my-tooltip">
<template #title>
<div class="tooltip-text">
<div>
Top 10% points holder share 40% of the prize pool
</div>
<div>
Top 10%-30% points holder share 40% of the prize pool
</div>
<div>
Top 30%-50% points holder share 20% of the prize pool
</div>
</div>
</template>
<div class="you-input-item">
Top
<span class="item-number">
{{ userInfo.top != null ? userInfo.top : "0" }}%
</span>
</div>
</a-tooltip>
</div>
<div class="invitation">
<div class="invitation-img">
<img src="@/assets/img/task/currency.png" alt="" />
</div>
<div class="invitation-title">
10 points for each successful invite,<br />
Points will be used to get Token rewards and other.
</div>
</div>
<div class="points-ticket">
<div class="points-item">
<a-tooltip
placement="bottomLeft"
overlayClassName="my-tooltip"
>
<template #title>
<span class="tooltip-text"
>Every 20 points will earn you 1 Yoyo.</span
>
</template>
<div>
Your Yoyo
<span class="points-item-number">{{
userInfo.tickets ? userInfo.tickets : "0"
}}</span>
</div>
</a-tooltip>
</div>
</div>
<div class="candy-dispenser">
<div class="candy-img-content">
<img src="@/assets/img/task/candy-dispenser.png" alt="" />
<a-tooltip placement="bottom" overlayClassName="my-tooltip">
<template #title>
<div>
<div class="tooltip-text">
The Yoyo Machine event will be introduced after this
event ends.
</div>
<div class="tooltip-text">
You can then collect your Yoyo and participate in a
4-week-long lottery. Rewards may include
ARB\ETH\CEC\NFTs
</div>
</div>
</template>
<div class="img-tips"></div>
</a-tooltip>
</div>
<!-- <div>
<img src="@/assets/img/task/candy-dispenser.png" alt="" />
</div> -->
</div>
<!-- <div class="tip">
<div class="tip-item">10 points for each successful invite</div>
<div class="tip-item">1 ticket for every 20 points</div>
</div> -->
</div>
</div>
<div class="content-right-not-login" v-else>
<!-- <div class="complete">
Complete the Gacha Quest to unlock the invite quest
</div> -->
<div v-if="!isStatus && chain.logined" class="the-event" >The event has ended</div>
<div v-else>
<div class="quest-content">
<div class="quest-left">
<div class="currency-img">
<img src="@/assets/img/task/currency.png" alt="" />
</div>
</div>
<div class="quest-right">
<div class="candy-dispenser-img">
<img src="@/assets/img/task/candy-dispenser.png" alt="" />
</div>
</div>
</div>
<div class="token-btns">
<div class="token-btn">Token Rewards</div>
<div class="token-btn">Yoyo Event</div>
</div>
<div class="gacha-quest" @click="login">Connect and check</div>
</div>
</div>
</div>
</div>
</div>
<div class="bg">
<img src="@/assets/img/task/one-bg.png" alt="" />
</div>
</div>
</template>
<script setup>
import { useRouter, useRoute } from "vue-router";
import Vue3autocounter from "vue3-autocounter";
import NavBar from "../layout/navber.vue";
import { useCopyToClipboard } from "../../hooks/useCopyToClipboard";
import { getLeaderboard, UserInfo, UserStatus, getJoin } from "@/api/User";
import { useChainStore } from "@/store/chain";
import { useAppStore } from "@/store/app";
import { hasMetamask } from "@/utils/chain.util";
import { ref, reactive, watchEffect, onMounted, watch, computed } from "vue";
import { message } from "ant-design-vue";
const chain = useChainStore();
const AppModule = useAppStore();
const loginLoading = ref(false);
const router = useRouter();
const route = useRoute();
const invited = ref(0);
const rank = ref(0);
const top = ref(0);
const points = ref(0);
const ticket = ref(0);
const counter = ref(null);
const isStatus = ref(false);
const data = reactive([]);
const userInfo = reactive({});
const formattedData = computed(() => {
return data
.map((item) => ({
...item,
account: item.account.slice(0, 6) + "..." + item.account.slice(-6),
}))
.reduce((acc, current) => {
const x = acc.find((item) => item.account === current.account);
if (!x) {
return acc.concat([current]);
} else {
return acc;
}
}, []);
});
const typesInRegular = computed(() =>
userInfo.regular.map((item) => item.type).join("<br/>")
);
async function login(event) {
var next = window.location.href;
if (!hasMetamask()) {
var url = `https://metamask.app.link/dapp/${next}`;
location.href = url;
} else {
if (!chain.logined) {
//
loginLoading.value = true;
try {
await chain.chainManager.login();
chain.logined = chain.chainManager.isLogined;
currentTask.value = 2;
loginLoading.value = false;
} catch (err) {
loginLoading.value = false;
}
// console.log("logined:", chain.chainManager.isLogined);
}
}
}
const assign = (source, target) => {
if (target === undefined || target === null) {
throw new TypeError("Cannot convert undefined or null to object");
}
for (let key in target) {
source[key] = target[key];
}
};
const totalRegularPoints = computed(() =>
userInfo.regular.reduce((total, item) => total + item.point, 0)
);
const handTaskHome = () => {
const code = route.query.code;
if (code) {
router.push({ path: "/quest", query: { code: code } });
} else {
router.push("/quest");
}
};
const handTaskOne = () => {
const code = route.query.code;
if (code) {
router.push({ path: "/taskTwo", query: { code: code } });
} else {
router.push("/taskTwo");
}
console.log(router, "-=-=-");
};
watchEffect(() => {
console.log(data); //
});
const inviteLink = ref(
`${import.meta.env.VUE_APP_GPAL_API}/?code=${userInfo.invite_code}`
);
const { copied, error, reset, copyToClipboard } = useCopyToClipboard();
const handleCopy = () => {
reset();
copyToClipboard(inviteLink.value).then(() => {
if (copied.value) {
message.success("Copy successful!");
}
});
};
watch(
() => chain.logined,
async (newValue, oldValue) => {
// console.log("logined changed from", oldValue, "to", newValue);
const res = await getLeaderboard({ offset: 0, limit: 100 });
console.log(res);
if (res) {
data.value = res.data;
res.data.forEach((e) => {
data.push(e);
});
console.log(res.data, "res.data.data");
console.log(data.value, "ff");
}
const userStatus = await UserStatus({ account: AppModule.accountId });
if (
userStatus &&
userStatus.claim &&
Number(userStatus.claim) !== 0 &&
userStatus.status.every((status) => status == 1)
) {
isStatus.value = true;
const resjoin = await getJoin({
account: AppModule.accountId,
invite_code: route.query.code,
});
}
const resq = await UserInfo({ account: AppModule.accountId });
if (resq) {
// userInfo.value = resq
assign(userInfo, resq);
inviteLink.value = `${import.meta.env.VUE_APP_GPAL_API}/?code=${
userInfo.invite_code
}`;
}
console.log(resq, "dsdsdsdsd");
console.log(userInfo.value);
}
);
onMounted(async () => {
const res = await getLeaderboard({ offset: 0, limit: 100 });
console.log(res);
if (res) {
data.value = res.data;
res.data.forEach((e) => {
data.push(e);
});
console.log(res.data, "res.data.data");
console.log(data.value, "ff");
}
const resStatus = await UserStatus({ account: AppModule.accountId });
if (
resStatus &&
resStatus.claim &&
Number(resStatus.claim) !== 0 &&
resStatus.status.every((status) => status == 1)
) {
isStatus.value = true;
}
const resq = await UserInfo({ account: AppModule.accountId });
if (resq) {
// userInfo.value = resq
assign(userInfo, resq);
inviteLink.value = `${import.meta.env.VUE_APP_GPAL_API}/?code=${
userInfo.invite_code
}`;
}
console.log(res);
//console.log(formattedData);
});
</script>
<style lang="scss" scoped>
.task-two-header {
// height: 65px;
}
.the-event{
padding-left: 100px;
padding-right: 100px;
color: #fff;
font-size: 28px;
}
.task-two {
position: relative;
width: 100%;
height: 100%;
// height: calc(100vh - 65px);
// padding-bottom: 100px;
.bg {
position: absolute;
height: 100%;
width: 100%;
left: 0;
top: 0;
right: 0;
z-index: -1;
bottom: 0;
color: transparent;
img {
position: absolute;
height: 100%;
width: 100%;
left: 0;
top: 0;
right: 0;
bottom: 0;
object-fit: cover;
z-index: 0;
color: transparent;
}
}
.content {
max-width: 1200px;
margin: 0 auto;
display: flex;
height: calc(100% - 85px);
justify-content: center;
align-items: center;
.header {
// padding-top: 47px;
display: flex;
justify-content: space-between;
.complete {
// width: 48%;
font-size: 18px;
font-family: "MEurostile";
font-weight: 400;
color: #959595;
}
.return {
font-size: 50px;
font-family: "GemunuExtraBold";
font-weight: 400;
display: flex;
color: #ffffff;
cursor: pointer;
align-items: center;
.return-icon {
margin-right: 28px;
}
}
}
.content-conter {
width: 100%;
display: flex;
//justify-content: space-between;
}
.content-left {
// padding-top: 190px;
// margin-top: 58px;
width: 540px;
padding-right: 33px;
height: 600px;
overflow: hidden;
position: relative;
//border-right: 1px solid #ffffff;
}
.content-right {
// padding-top: 51px;
border-left: 1px solid #5d5548;
padding-left: 66px;
// width: 100%;
position: relative;
.boder-left {
position: absolute;
top: 50px;
left: 0;
// height: 550px;
width: 1px;
background-color: #ffffff;
}
.link-title {
font-size: 32px;
font-family: "GemunuExtraBold";
font-weight: 400;
color: #ffffff;
// margin-left: 180px;
// margin-top: 19px;
// margin-right: 28px;
}
.link-btn {
width: 581px;
height: 61px;
border: 1px solid #8f7440;
border-radius: 12px;
font-size: 18px;
line-height: 20px;
font-family: "MEurostile";
font-weight: 400;
color: #96763a;
display: flex;
background: rgba(40, 33, 20, 0.6);
justify-content: space-between;
align-items: center;
padding-left: 31px;
padding-right: 31px;
margin-bottom: 24px;
// padding-top: 5px;
}
.you-input {
width: 100%;
// height: 51px;
// padding-left: 31px;
// padding-right: 31px;
display: flex;
align-items: center;
line-height: 20px;
margin-bottom: 26px;
// background: rgba(40, 33, 20, 0.6);
// border: 1px solid #ffffff;
justify-content: space-between;
border-radius: 12px;
.you-input-item {
font-size: 32px;
font-family: "GemunuExtraBold";
font-weight: 400;
color: #ffffff;
}
}
.item-number {
font-size: 32px;
font-family: "GemunuExtraBold";
font-weight: 400;
color: #5ce501;
}
.item-number-right {
font-size: 22px;
font-family: "GemunuExtraBold";
font-weight: 400;
position: relative;
color: #5ce501;
}
.item-number-right::after {
content: ""; /* 伪元素需要内容才能显示,这里我们不需要实际的内容,所以设置为空 */
position: absolute; /* 使用绝对定位来放置红点 */
top: 0px; /* 红点在右上角,所以 top 和 right 都设置为 0 */
right: -6px;
width: 6px; /* 可以根据需要调整红点的大小 */
height: 6px;
background-color: #f50123; /* 红点的颜色 */
border-radius: 50%; /* 使红点成为一个圆形 */
}
.points-item {
width: 100%;
display: flex;
// height: 51px;
// text-align: center;
line-height: 21px;
// background: rgba(40, 33, 20, 0.6);
// border: 1px solid #ffffff;
// opacity: 0.6;
font-size: 22px;
font-family: "GemunuExtraBold";
font-weight: 400;
color: #ffffff;
// padding-left: 31px;
border-radius: 12px;
.points-item-number {
color: #5ce501;
}
}
.points-ticket {
display: flex;
justify-content: space-between;
margin-top: 49px;
}
.tip {
display: flex;
justify-content: space-between;
color: #ffffff;
font-size: 14px;
font-family: "MEurostile";
font-weight: 400;
color: #afa07d;
.tip-item {
width: 281px;
// height: 51px;
}
}
.candy-dispenser {
display: flex;
justify-content: center;
}
}
}
}
.candy-img-content {
position: relative;
.img-tips {
width: 166px;
height: 100px;
// background-color: #5ce501;
position: absolute;
left: 0;
bottom: 30px;
}
}
// .points-title {
// max-width: 250px; /* */
// word-wrap: break-word; /* */
// }
.tooltip-text {
font-size: 16px;
font-family: "Arial";
font-weight: 400;
color: #96763a;
}
.copy {
cursor: pointer;
}
.scroll-content {
height: 540px;
overflow: auto;
scrollbar-width: thin; /* Firefox */
scrollbar-color: transparent transparent; /* Firefox */
}
.scroll-content::-webkit-scrollbar {
width: 0;
height: 0;
}
.assress-item {
display: flex;
font-size: 18px;
font-family: "MEurostile";
font-weight: 400;
color: #ffffff;
justify-content: space-between;
.assress-item-id {
width: 40px;
}
}
.address-header {
display: flex;
justify-content: space-between;
font-size: 18px;
font-family: "MEurostile";
font-weight: 400;
color: #898989;
.address-header-item {
width: 40px;
}
.address-header-item-address {
width: 124px;
}
.address-header-item-points {
width: 89px;
text-align: center;
}
}
.code {
width: 89px;
text-align: center;
color: #5ce501;
transition: all 0.3s ease-out;
}
.leaderboard {
color: #ffffff;
font-size: 32px;
font-family: "GemunuExtraBold";
font-weight: 400;
color: #ffffff;
}
.you-title {
font-size: 22px;
font-family: "GemunuExtraBold";
font-weight: 400;
color: #ffffff;
// text-align: center;
margin-bottom: 20px;
.you-title-number {
color: #5ce501;
}
}
.invite-quest {
position: relative;
line-height: 43px;
a {
color: #fff;
}
border-bottom: 2px solid transparent;
&:hover {
border-bottom: 2px solid #ccc;
}
}
.invite-quest::after {
content: "";
display: inline-block;
position: absolute;
width: 25px; /* Adjust according to your needs */
height: 24px; /* Adjust according to your needs */
background-image: url("@/assets/img/task/arrow.png");
background-size: cover;
background-repeat: no-repeat;
opacity: 0;
right: -30px; /* Or adjust as per your needs */
top: 20%; /* Or adjust as per your needs */
//transform: translateY(-50%); /* To vertically center the image */
transition: all 0.3s ease;
}
.invite-quest:hover::after {
// right: -34px;
// top: 48%; //
opacity: 1;
transform: translate(3px, -3px);
}
.invitation {
display: flex;
padding-bottom: 10px;
align-items: center;
border-bottom: 1px solid #5d5548;
.invitation-title {
margin-left: 24px;
font-size: 16px;
font-family: "Arial";
font-weight: 400;
color: #d3d3d3;
}
}
.content-right-not-login {
padding-left: 135px;
.quest-content {
display: flex;
width: 85%;
margin: 0 auto;
margin-top: 42px;
justify-content: space-between;
align-items: center;
margin-bottom: 22px;
}
.token-btns {
width: 100%;
cursor: pointer;
margin: 0 auto;
display: flex;
justify-content: space-between;
}
.gacha-quest {
width: 409px;
height: 58px;
margin: 0 auto;
cursor: pointer;
margin-top: 47px;
margin-bottom: 71px;
text-align: center;
line-height: 58px;
background: url("@/assets/img/task/gacha-quest-bg.png") no-repeat;
background-size: contain;
}
.token-btn {
width: 215px;
height: 53px;
text-align: center;
line-height: 53px;
background: url("@/assets/img/task/token-btn-bg.png") no-repeat;
background-size: contain;
font-size: 18px;
font-family: Arial;
font-weight: 400;
color: #96763a;
}
.currency-img {
width: 117px;
height: 95px;
}
.candy-dispenser-img {
width: 124px;
height: 124px;
}
.complete {
// width: 90%;
margin: 0 auto;
margin-bottom: 17px;
text-align: center;
font-size: 22px;
margin-top: 60px;
font-family: "MEurostile";
font-weight: 400;
color: #c2c2c2;
}
}
@media screen and (min-width: 1441px) {
/* 在此处插入你希望在屏幕宽度大于1440px时应用的样式 */
.header {
margin-bottom: 60px;
}
/* 更多的样式代码 */
}
@media (min-width: 1200px) and (max-width: 1439px) {
/* 在这里写你的样式规则 */
.center {
height: 85%;
display: flex;
flex-direction: column;
justify-content: space-between;
}
}
</style>
<style lang="scss">
.my-tooltip {
&.ant-tooltip {
//sass
max-width: 600px;
}
}
</style>

286
src/configs/allchain.ts Normal file
View File

@ -0,0 +1,286 @@
export const AllChains = [
{
name: 'Ethereum Mainnet RPC',
type: 'Mainnet',
rpc: 'https://rpc.ankr.com/eth',
id: 1,
symbol: 'ETH',
explorerurl: 'https://etherscan.io'
},
{
name: 'Ethereum Ropsten Testnet RPC',
type: 'Testnet',
rpc: 'https://ropsten.infura.io/v3/9aa3d95b3bc440fa88ea12eaa4456161',
id: 3,
symbol: 'ETH',
explorerurl: 'https://ropsten.etherscan.io'
},
{
name: 'Ethereum Rinkeby Testnet RPC',
type: 'Testnet',
rpc: 'https://rinkey.infura.io/v3/9aa3d95b3bc440fa88ea12eaa4456161',
id: 4,
symbol: 'ETH',
explorerurl: 'https://rinkey.etherscan.io'
},
{
name: 'Ethereum Goerli Testnet RPC',
type: 'Testnet',
rpc: 'https://goerli.infura.io/v3/9aa3d95b3bc440fa88ea12eaa4456161',
id: 5,
symbol: 'ETH',
explorerurl: 'https://goerli.etherscan.io'
},
{
name: 'Ethereum Kovan Testnet RPC',
type: 'Testnet',
rpc: 'https://kovan.infura.io/v3/9aa3d95b3bc440fa88ea12eaa4456161',
id: 6,
symbol: 'ETH',
explorerurl: 'https://kovan.etherscan.io'
},
{
name: 'Ubiq Mainnet RPC',
type: 'Mainnet',
rpc: 'https://rpc.octano.dev/',
id: 8,
symbol: 'UBQ',
explorerurl: 'https://ubiqscan.io/'
},
{
name: 'Elastos ETH Mainnet RPC',
type: 'Mainnet',
rpc: 'https://api.elastos.io/eth',
id: 20,
symbol: 'ELA',
explorerurl: 'https://explorer.elaeth.io/'
},
{
name: 'Cronos Mainnet RPC',
type: 'Mainnet',
rpc: 'https://evm-cronos.crypto.org',
id: 25,
symbol: 'CRO',
explorerurl: 'https://cronos.crypto.org/explorer/'
},
{
name: 'Telos EVM Mainnet RPC',
type: 'Mainnet',
rpc: 'https://mainnet.telos.net/evm',
id: 40,
symbol: 'TLOS',
explorerurl: 'https://telos.net/'
},
{
name: 'Binance Smart Chain',
type: 'Mainnet',
rpc: 'https://rpc.ankr.com/bsc',
logo: 'data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNTAwIiBoZWlnaHQ9IjI1MDAiIHZpZXdCb3g9IjAgMCAyMDAwIDIwMDAiPjxnIGZpbGw9IiNmM2JhMmYiPjxwYXRoIGQ9Ik02MTEuNTkgODQwLjQybDM4OC40LTM4OC4zOSAzODguNiAzODguNTkgMjI2LTIyNkw5OTkuOTkgMCAzODUuNiA2MTQuNDJsMjI1Ljk5IDIyNk0uMDA2IDk5OS45NjlsMjI2LjAwNy0yMjYuMDA3IDIyNS45OTIgMjI1Ljk5M0wyMjYgMTIyNS45NnpNNjExLjU5IDExNTkuNThsMzg4LjQgMzg4LjM5IDM4OC41OS0zODguNTggMjI2LjEyIDIyNS44OC0uMTEuMTJMOTk5Ljk5IDIwMDBsLTYxNC40MS02MTQuNC0uMzItLjMyIDIyNi4zMy0yMjUuN00xNTQ4LjAxMyAxMDAwLjA5M2wyMjYuMDA3LTIyNi4wMDYgMjI1Ljk5MiAyMjUuOTkyLTIyNi4wMDYgMjI2LjAwN3oiLz48cGF0aCBkPSJNMTIyOS4yMiA5OTkuODhoLjFMOTk5Ljk5IDc3MC41NSA4MzAuNTEgOTQwLjAzaC0uMDFsLTE5LjQ3IDE5LjQ4LTQwLjE2IDQwLjE3LS4zMi4zMS4zMi4zMyAyMjkuMTIgMjI5LjEzIDIyOS4zMy0yMjkuMzMuMTEtLjEzLS4yMS0uMTEiLz48L2c+PC9zdmc+',
id: 56,
symbol: 'BNB',
explorerurl: 'https://bscscan.com'
},
{
name: 'OKExChain Mainnet RPC',
type: 'Mainnet',
rpc: 'https://exchainrpc.okex.org',
id: 66,
symbol: 'OKT',
explorerurl: 'https://www.oklink.com/okexchain'
},
{
name: 'Hoo Mainnet RPC',
type: 'Mainnet',
rpc: 'https://http-mainnet.hoosmartchain.com',
id: 70,
symbol: 'HOO',
explorerurl: 'https://hooscan.com'
},
{
name: 'Binance Smart Chain Testnet RPC',
type: 'Testnet',
rpc: 'https://data-seed-prebsc-1-s1.binance.org:8545/',
id: 97,
logo: 'data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNTAwIiBoZWlnaHQ9IjI1MDAiIHZpZXdCb3g9IjAgMCAyMDAwIDIwMDAiPjxnIGZpbGw9IiNmM2JhMmYiPjxwYXRoIGQ9Ik02MTEuNTkgODQwLjQybDM4OC40LTM4OC4zOSAzODguNiAzODguNTkgMjI2LTIyNkw5OTkuOTkgMCAzODUuNiA2MTQuNDJsMjI1Ljk5IDIyNk0uMDA2IDk5OS45NjlsMjI2LjAwNy0yMjYuMDA3IDIyNS45OTIgMjI1Ljk5M0wyMjYgMTIyNS45NnpNNjExLjU5IDExNTkuNThsMzg4LjQgMzg4LjM5IDM4OC41OS0zODguNTggMjI2LjEyIDIyNS44OC0uMTEuMTJMOTk5Ljk5IDIwMDBsLTYxNC40MS02MTQuNC0uMzItLjMyIDIyNi4zMy0yMjUuN00xNTQ4LjAxMyAxMDAwLjA5M2wyMjYuMDA3LTIyNi4wMDYgMjI1Ljk5MiAyMjUuOTkyLTIyNi4wMDYgMjI2LjAwN3oiLz48cGF0aCBkPSJNMTIyOS4yMiA5OTkuODhoLjFMOTk5Ljk5IDc3MC41NSA4MzAuNTEgOTQwLjAzaC0uMDFsLTE5LjQ3IDE5LjQ4LTQwLjE2IDQwLjE3LS4zMi4zMS4zMi4zMyAyMjkuMTIgMjI5LjEzIDIyOS4zMy0yMjkuMzMuMTEtLjEzLS4yMS0uMTEiLz48L2c+PC9zdmc+',
symbol: 'BNB',
explorerurl: 'https://testnet.bscscan.com'
},
{
name: 'xDai Mainnet RPC',
type: 'Mainnet',
rpc: 'https://rpc.xdaichain.com/',
id: 100,
symbol: 'XDAI',
explorerurl: 'https://blockscout.com/xdai/mainnet/'
},
{
name: 'Fuse Mainnet RPC',
type: 'Mainnet',
rpc: 'https://rpc.fuse.io',
id: 122,
symbol: 'FUSE',
explorerurl: 'https://explorer.fuse.io/'
},
{
name: 'HECO Mainnet RPC',
type: 'Mainnet',
rpc: 'https://http-mainnet-node.huobichain.com/',
id: 128,
symbol: 'HT',
explorerurl: 'https://hecoinfo.com/'
},
{
name: 'Matic Mainnet RPC',
type: 'Mainnet',
rpc: 'https://polygon-rpc.com',
id: 137,
symbol: 'MATIC',
explorerurl: 'https://explorer.matic.network/'
},
{
name: 'Fantom Opera Mainnet RPC',
type: 'Mainnet',
rpc: 'https://rpc.ftm.tools/',
id: 250,
symbol: 'FTM',
explorerurl: 'https://ftmscan.com'
},
{
name: 'HECO Testnet RPC',
type: 'Testnet',
rpc: 'https://http-testnet.hecochain.com',
id: 256,
symbol: 'HT',
explorerurl: 'https://testnet.hecoinfo.com/'
},
{
name: 'KCC Mainnet',
type: 'Mainnet',
rpc: 'https://rpc-mainnet.kcc.network',
id: 321,
logo: 'data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0idXRmLTgiPz4KPCEtLSBHZW5lcmF0b3I6IEFkb2JlIElsbHVzdHJhdG9yIDI0LjAuMCwgU1ZHIEV4cG9ydCBQbHVnLUluIC4gU1ZHIFZlcnNpb246IDYuMDAgQnVpbGQgMCkgIC0tPgo8c3ZnIHZlcnNpb249IjEuMSIgaWQ9IkxheWVyXzEiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiIHg9IjBweCIgeT0iMHB4IgoJIHZpZXdCb3g9IjAgMCAzMiAzMiIgc3R5bGU9ImVuYWJsZS1iYWNrZ3JvdW5kOm5ldyAwIDAgMzIgMzI7IiB4bWw6c3BhY2U9InByZXNlcnZlIj4KPHN0eWxlIHR5cGU9InRleHQvY3NzIj4KCS5zdDB7ZmlsbC1ydWxlOmV2ZW5vZGQ7Y2xpcC1ydWxlOmV2ZW5vZGQ7ZmlsbDojMDA5M0REO30KCS5zdDF7ZmlsbC1ydWxlOmV2ZW5vZGQ7Y2xpcC1ydWxlOmV2ZW5vZGQ7ZmlsbDojRkZGRkZGO30KPC9zdHlsZT4KPGc+Cgk8Y2lyY2xlIGNsYXNzPSJzdDAiIGN4PSIxNiIgY3k9IjE2IiByPSIxNiIvPgoJPHBhdGggY2xhc3M9InN0MSIgZD0iTTEzLjUsMTZsNS4yLDUuM0wyMiwxOGMwLjYtMC42LDEuNS0wLjYsMiwwYzAsMCwwLDAsMCwwYzAuNiwwLjYsMC42LDEuNiwwLDIuMmwtNC4zLDQuNAoJCWMtMC42LDAuNi0xLjUsMC42LTIuMSwwYzAsMCwwLDAsMCwwbC02LjItNi40VjIyYzAsMC44LTAuNywxLjUtMS41LDEuNWMtMC44LDAtMS41LTAuNy0xLjUtMS41VjEwYzAtMC44LDAuNy0xLjUsMS41LTEuNQoJCWMwLjgsMCwxLjUsMC43LDEuNSwxLjV2My44bDYuMi02LjRjMC42LTAuNiwxLjUtMC42LDIuMSwwYzAsMCwwLDAsMCwwbDQuMyw0LjRjMC42LDAuNiwwLjYsMS42LDAsMi4yYy0wLjYsMC42LTEuNSwwLjYtMiwwCgkJYzAsMCwwLDAsMCwwbC0zLjMtMy40TDEzLjUsMTZ6IE0xOC43LDE0LjVjMC44LDAsMS41LDAuNywxLjUsMS41cy0wLjcsMS41LTEuNSwxLjVzLTEuNS0wLjctMS41LTEuNQoJCUMxNy4yLDE1LjIsMTcuOSwxNC41LDE4LjcsMTQuNXoiLz4KPC9nPgo8L3N2Zz4K',
symbol: 'KCS',
explorerurl: 'https://scan.kcc.network'
},
{
name: 'KCC Testnet',
type: 'Testnet',
logo: 'data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0idXRmLTgiPz4KPCEtLSBHZW5lcmF0b3I6IEFkb2JlIElsbHVzdHJhdG9yIDI0LjAuMCwgU1ZHIEV4cG9ydCBQbHVnLUluIC4gU1ZHIFZlcnNpb246IDYuMDAgQnVpbGQgMCkgIC0tPgo8c3ZnIHZlcnNpb249IjEuMSIgaWQ9IkxheWVyXzEiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiIHg9IjBweCIgeT0iMHB4IgoJIHZpZXdCb3g9IjAgMCAzMiAzMiIgc3R5bGU9ImVuYWJsZS1iYWNrZ3JvdW5kOm5ldyAwIDAgMzIgMzI7IiB4bWw6c3BhY2U9InByZXNlcnZlIj4KPHN0eWxlIHR5cGU9InRleHQvY3NzIj4KCS5zdDB7ZmlsbC1ydWxlOmV2ZW5vZGQ7Y2xpcC1ydWxlOmV2ZW5vZGQ7ZmlsbDojMDA5M0REO30KCS5zdDF7ZmlsbC1ydWxlOmV2ZW5vZGQ7Y2xpcC1ydWxlOmV2ZW5vZGQ7ZmlsbDojRkZGRkZGO30KPC9zdHlsZT4KPGc+Cgk8Y2lyY2xlIGNsYXNzPSJzdDAiIGN4PSIxNiIgY3k9IjE2IiByPSIxNiIvPgoJPHBhdGggY2xhc3M9InN0MSIgZD0iTTEzLjUsMTZsNS4yLDUuM0wyMiwxOGMwLjYtMC42LDEuNS0wLjYsMiwwYzAsMCwwLDAsMCwwYzAuNiwwLjYsMC42LDEuNiwwLDIuMmwtNC4zLDQuNAoJCWMtMC42LDAuNi0xLjUsMC42LTIuMSwwYzAsMCwwLDAsMCwwbC02LjItNi40VjIyYzAsMC44LTAuNywxLjUtMS41LDEuNWMtMC44LDAtMS41LTAuNy0xLjUtMS41VjEwYzAtMC44LDAuNy0xLjUsMS41LTEuNQoJCWMwLjgsMCwxLjUsMC43LDEuNSwxLjV2My44bDYuMi02LjRjMC42LTAuNiwxLjUtMC42LDIuMSwwYzAsMCwwLDAsMCwwbDQuMyw0LjRjMC42LDAuNiwwLjYsMS42LDAsMi4yYy0wLjYsMC42LTEuNSwwLjYtMiwwCgkJYzAsMCwwLDAsMCwwbC0zLjMtMy40TDEzLjUsMTZ6IE0xOC43LDE0LjVjMC44LDAsMS41LDAuNywxLjUsMS41cy0wLjcsMS41LTEuNSwxLjVzLTEuNS0wLjctMS41LTEuNQoJCUMxNy4yLDE1LjIsMTcuOSwxNC41LDE4LjcsMTQuNXoiLz4KPC9nPgo8L3N2Zz4K',
rpc: 'https://rpc-testnet.kcc.network',
id: 322,
symbol: 'tKCS',
explorerurl: 'https://scan-testnet.kcc.network'
},
{
name: 'Moonriver Mainnet RPC',
type: 'Mainnet',
rpc: 'https://rpc.moonriver.moonbeam.network',
id: 1285,
symbol: 'MOVR',
explorerurl: 'https://blockscout.moonriver.moonbeam.network/'
},
{
name: 'Fantom Testnet RPC',
type: 'Testnet',
rpc: 'https://rpc.testnet.fantom.network/',
id: 4002,
symbol: 'FTM',
explorerurl: 'https://testnet.ftmscan.com'
},
{
name: 'IoTeX Mainnet RPC',
type: 'Mainnet',
rpc: 'https://babel-api.mainnet.iotex.io',
id: 4689,
symbol: 'IOTEX',
explorerurl: 'https://iotexscan.io/'
},
{
name: 'Nahmii Mainnet RPC',
type: 'Mainnet',
rpc: 'https://l2.nahmii.io/',
id: 5551,
symbol: 'ETH',
explorerurl: 'https://explorer.nahmii.io/'
},
{
name: 'Nahmii Testnet RPC',
type: 'Testnet',
rpc: 'https://l2.testnet.nahmii.io/',
id: 5553,
symbol: 'ETH',
explorerurl: 'https://explorer.testnet.nahmii.io/'
},
{
name: 'Arbitrum One',
type: 'Mainnet',
rpc: 'https://arbitrum-one.public.blastapi.io',
id: 42161,
symbol: 'ETH',
explorerurl: 'https://explorer.arbitrum.io'
},
{
name: 'Arbitrum Goerli',
type: 'Testnet',
rpc: 'https://arbitrum-goerli.public.blastapi.io',
id: 421613,
symbol: 'AGOR',
explorerurl: 'https://goerli-rollup-explorer.arbitrum.io'
},
{
name: 'Celo Mainnet RPC',
type: 'Mainnet',
rpc: 'https://rpc.ankr.com/celo',
id: 42220,
symbol: 'CELO',
explorerurl: 'https://celoscan.com'
},
{
name: 'Avalanche C Chain Local RPC',
type: 'Testnet',
rpc: 'https://localhost:9650/ext/bc/C/rpc',
id: 43112,
symbol: 'AVAX',
explorerurl: 'https://snowtrace.io'
},
{
name: 'Avalanche FUJI Testnet RPC',
type: 'Testnet',
rpc: 'https://api.avax-test.network/ext/bc/C/rpc',
id: 43113,
symbol: 'AVAX',
explorerurl: 'https://testnet.explorer.avax.network/'
},
{
name: 'Avalanche C Chain Mainnet RPC',
type: 'Mainnet',
rpc: 'https://rpc.ankr.com/avalanche',
id: 43114,
symbol: 'AVAX',
explorerurl: 'https://snowtrace.io'
},
{
name: 'Matic Testnet RPC',
type: 'Testnet',
rpc: 'https://rpc-mumbai.maticvigil.com',
id: 80001,
symbol: 'MATIC',
explorerurl: 'https://mumbai.polygonscan.com/'
},
{
name: 'Harmony Mainnet RPC',
type: 'Mainnet',
rpc: 'https://api.harmony.one/',
id: 1666600000,
symbol: 'ONE',
explorerurl: 'https://explorer.harmony.one'
},
{
name: 'Harmony Testnet RPC',
type: 'Testnet',
rpc: 'https://api.s0.b.hmny.io/',
id: 1666700000,
symbol: 'ONE',
explorerurl: 'https://explorer.harmony.one'
}
]

File diff suppressed because one or more lines are too long

3398
src/configs/contracts.ts Normal file

File diff suppressed because it is too large Load Diff

4
src/configs/global.ts Normal file
View File

@ -0,0 +1,4 @@
export namespace Global {
export const MEDAL_REWARDS_Address: string = "0x54f6e2B13d9F754f7676494d3F53426C594D65b3"; // 分发地址
export const LIMIT_ABI_Address: string = "0x8E2ab40CA9dc6871131AacC1F82bf73B28DB75F9"; // 徽章地址
}

View File

@ -0,0 +1,75 @@
export const HeroList = [
{
id: 1,
img: new URL("@/assets/img/home/hero/001.png", import.meta.url).href,
name: "midif",
slogan:
"Coming from the Black Forest region on the West Coast, Aoi is rumored to be a descendant of the Grand Druid. Because of her fondness for candy, she often seals her cure magics in lollipops.",
},
{
id: 2,
img: new URL("@/assets/img/home/hero/002.png", import.meta.url).href,
name: "ChipCard",
slogan:
"Canoe, the Priest of the Church of Fallen Angels, is a master summoner of hordes of mechs. Her greatest pleasure is fueled by her opponents' desperation.",
},
{
id: 3,
img: new URL("@/assets/img/home/hero/003.png", import.meta.url).href,
name: "ChipCard",
slogan:
"Mariana was originally a fur trapper in the Beast Valley of the South. After accidentally touching the blood of Beshimus, Mariana gained the powerful shape-shifting ability.",
},
{
id: 4,
img: new URL("@/assets/img/home/hero/004.png", import.meta.url).href,
name: "ChipCard",
slogan:
"The Fox Clan of Hill has been there for a long time. They are good charmers. The prettier they are, the greater their strength. And Hill is at the top of her craft.",
},
{
id: 5,
img: new URL("@/assets/img/home/hero/005.png", import.meta.url).href,
name: "ChipCard",
slogan:
"Raised by a group of assassins after losing her parents at an early age, Astral grows into an agile and skilled assassin.",
},
{
id: 6,
img: new URL("@/assets/img/home/hero/006.png", import.meta.url).href,
name: "ChipCard",
slogan:
"Miffy likes to play hide-and-seek with people and observe them in the dark. No one knows why. Maybe she's just timid and wants to play with everyone.",
},
{
id: 7,
img: new URL("@/assets/img/home/hero/007.png", import.meta.url).href,
name: "ChipCard",
slogan:
"Yamato is a gifted scholar who can easily build the most powerful bombs yet often forgets the trifles of life.",
},
{
id: 8,
img: new URL("@/assets/img/home/hero/008.png", import.meta.url).href,
name: "ChipCard",
slogan:
"Dragonscale's origin is obscure. It is said that he came here from a mysterious land in the East in search of an ancient artifact that would relieve his people of their misery.",
},
{
id: 9,
img: new URL("@/assets/img/home/hero/009.png", import.meta.url).href,
name: "ChipCard",
slogan:
"Kurosawa is the youngest of the king's guards in Shata, with a resolute and steady personality unlike his peers. Imbued with royal protocol, he also has an amazing flair for food and tasting.",
},
{
id: 10,
img: new URL("@/assets/img/home/hero/010.png", import.meta.url).href,
name: "ChipCard",
slogan:
"Lazer was born in the Exile Street, where he grew up poor and often fought in underground boxing matches for a living. He takes the law of the jungle as his creed and shows no mercy to enemies.",
},
];
export default {
HeroList,
};

View File

@ -0,0 +1,25 @@
import { ref } from "vue";
export function useCopyToClipboard() {
const copied = ref(false);
const error = ref(null);
const reset = () => {
copied.value = false;
error.value = null;
};
const copyToClipboard = async (text) => {
try {
if (!navigator.clipboard) {
throw new Error("Clipboard API not available");
}
await navigator.clipboard.writeText(text);
copied.value = true;
} catch (err) {
error.value = err;
//console.error("Failed to copy text: ", err);
}
};
return { copied, error, reset, copyToClipboard };
}

17
src/hooks/useDebounce.js Normal file
View File

@ -0,0 +1,17 @@
import { ref } from 'vue'
function useDebounce(value, delay = 500) {
const debouncedValue = ref(value)
let timer
const debounce = () => {
clearTimeout(timer)
timer = setTimeout(() => {
debouncedValue.value = value.value
}, delay)
}
debounce()
return debouncedValue
}

3
src/index.css Normal file
View File

@ -0,0 +1,3 @@
@tailwind base;
@tailwind components;
@tailwind utilities;

36
src/main.js Normal file
View File

@ -0,0 +1,36 @@
import { createApp } from "vue";
// import './style.css'
import "./style/rest.css";
import "normalize.css";
import "@/assets/text/text.css";
import "./index.css"; // 导入 Tailwind CSS 样式
import Antd from "ant-design-vue";
import "ant-design-vue/dist/antd.css";
import pinia from "@/store";
import router from "./router/index";
import VueAnimXyz from "@animxyz/vue3";
import "@animxyz/core"; // Import css here if you haven't elsewhere
import App from "./App.vue";
import vue3dLoader from "vue-3d-loader";
import VueClipboard from "vue3-clipboard";
import Vue3Autocounter from 'vue3-autocounter';
import { notification } from 'ant-design-vue';
notification.config({
placement: 'topRight',
top: '90px',
duration: 100,
rtl: true,
});
const app = createApp(App);
app.config.globalProperties.$log = console.log.bind(console);
app
.use(pinia)
.use(VueClipboard)
.use(VueAnimXyz)
.use(vue3dLoader)
.use(Antd)
.use(router)
.mount("#app");

107
src/router/index.js Normal file
View File

@ -0,0 +1,107 @@
import { createRouter, createWebHistory } from "vue-router";
const routes = [
{
path: "/",
name: "index1",
component: () =>
import(/* webpackChunkName "index1" */ "@/views/MapView.vue"),
meta: {
title: "Planet",
canonical: "https://gacha.counterfire.games",
alternate: "https://m.gacha.counterfire.games",
},
},
{
path: "/quest",
name: "QUEST",
meta: {
title: "Planet Quest",
canonical: "https://gacha.counterfire.games/quest",
alternate: "https://m.gacha.counterfire.games/quest",
},
component: () =>
import(/* webpackChunkName "marketplace" */ "@/views/TaskView.vue"),
},
{
path: "/index.html",
name: "index",
component: () =>
import(/* webpackChunkName "index" */ "@/views/TaskView.vue"),
meta: {
title: "Gacha index",
canonical: "https://gacha.counterfire.games/index.html",
alternate: "https://m.gacha.counterfire.games/index.html",
},
},
{
path: "/undertest",
name: "TaskOne",
meta: {
title: "Gacha Undertest",
canonical: "https://gacha.counterfire.games/undertest",
alternate: "https://m.gacha.counterfire.games/undertest",
},
component: () =>
import(/* webpackChunkName "TaskOne" */ "@/components/task/TaskOne.vue"),
},
{
path: "/taskTwo",
name: "TaskTwo",
meta: {
title: "Gacha TaskTwo",
canonical: "https://gacha.counterfire.games/taskTwo",
alternate: "https://m.gacha.counterfire.games/taskTwo",
},
component: () =>
import(/* webpackChunkName "TaskTwo" */ "@/components/task/TaskTwo.vue"),
},
];
const router = createRouter({
history: createWebHistory(),
routes,
scrollBehavior(to, from, savedPosition) {
return { top: 0 };
},
});
function isMobileDevice(userAgent) {
return /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(
userAgent
);
}
router.beforeEach((to, from, next) => {
const isMobile = isMobileDevice(window.navigator.userAgent);
// 对于 PC 端官网项目:
if (!isMobile) {
if (to.meta.title) {
document.title = to.meta.title;
}
let link = document.querySelector("link[rel='canonical']");
if (!link) {
link = document.createElement("link");
link.rel = "canonical";
document.head.appendChild(link);
}
link.href = to.meta.canonical;
let alternateLink = document.querySelector("link[rel='alternate']");
if (!alternateLink) {
alternateLink = document.createElement("link");
alternateLink.rel = "alternate";
alternateLink.media = "only screen and (max-width: 640px)";
document.head.appendChild(alternateLink);
}
alternateLink.href = to.meta.alternate;
next(); // 如果是 PC 设备,继续导航
} else {
window.location.href = `https://m.gacha.counterfire.games${ to.query.code ? '?code=' + to.query.code : ""
}`;
}
});
export default router;

55
src/store/app.js Normal file
View File

@ -0,0 +1,55 @@
import { defineStore } from 'pinia';
import { ref } from 'vue';
export const useAppStore = defineStore('app', () => {
const list = ref([
{userId: "1", headpic: "/images/1667520250923113.webp"},
{userId: "2", headpic: "/images/16555781459976085.webp"},
{userId: "3", headpic: "/images/16595363622946259.webp"},
{userId: "4", headpic: "/images/16620693455819353.webp"},
]);
function get(userId) {
return list.value.find(i=>i.userId==userId);
}
const walletConnected = ref(false);
const accountId = ref('');
const chainId = ref(0);
const presaleStatus = ref(0);
const step = ref(0);
const nonce = ref('');
const token = ref('');
function updateWalletStatus(_connected) {
walletConnected.value = _connected;
}
function updateAccount(_accountId) {
accountId.value = _accountId;
}
function updateChainID(_chainId) {
chainId.value = _chainId;
}
function updateStep(_step) {
step.value = _step;
}
function updateNonce(_nonce) {
nonce.value = _nonce;
}
function updateToken(_token) {
token.value = _token;
}
return { list, get,
accountId, updateAccount,
chainId, updateChainID,
walletConnected, updateWalletStatus,
step, updateStep,
nonce, updateNonce,
token, updateToken,
}
})

16
src/store/chain.js Normal file
View File

@ -0,0 +1,16 @@
import ChainManager from '@/chain/ChainManager';
import { defineStore } from 'pinia';
import { ref } from 'vue';
export const useChainStore = defineStore('chain', ()=> {
const logined = ref(false);
const chainManager = ref(new ChainManager());
chainManager.value.init().then(()=> {
// console.log("chain init:", {chainManager})
logined.value = chainManager.value.isLogined;
});
return { chainManager, logined }
})

3
src/store/index.js Normal file
View File

@ -0,0 +1,3 @@
import { createPinia } from "pinia";
const pinia = createPinia();
export default pinia;

95
src/store/user.js Normal file
View File

@ -0,0 +1,95 @@
import { defineStore } from "pinia";
import { ref } from "vue";
import {
getToken,
setToken,
removeToken,
getAccountId,
setAccountId,
removeAccountId,
} from "@/utils/cookies";
import glodata from "./user_global";
import pinia from "@/store";
import { useAppStore } from "@/store/app";
const AppModule = useAppStore(pinia);
glodata.token = getToken();
glodata.accountId = AppModule.accountId.value;
glodata.chainId = AppModule.chainId.value;
import { login } from "@/api/User";
export const useUserStore = defineStore("user", () => {
const EIP721_DOMAIN_DATA = [
{ name: "name", type: "string" },
{ name: "version", type: "string" },
];
const token = ref(getToken());
const accountId = ref(getAccountId());
AppModule.updateAccount(accountId.value);
if (token.value && accountId.value) {
AppModule.updateStep(1);
}
async function Login({ bcInstance, account, chainId, nonce }) {
nonce += "";
const tips =
"Hi!Welcome to Counter Fire.\nPlease sign to verify wallet ownership.\nSigning is gas-less and non-transactional.";
const signMsg = {
tips,
nonce,
};
const signObj = {
types: {
EIP712Domain: EIP721_DOMAIN_DATA,
set: [
{ name: "tips", type: "string" },
{ name: "nonce", type: "string" },
],
},
primaryType: "set",
domain: {
name: "Auth",
version: "1",
},
message: signMsg,
};
const signature = await bcInstance.signData(signObj, account);
const authData = {
account,
nonce,
signature,
tips,
net_id: chainId,
};
const res = await login(authData);
if (!res.errcode && res.token) {
accountId.value = account;
setToken(res.token);
setAccountId(account);
AppModule.updateAccount(account);
AppModule.updateToken(res.token);
token.value = res.token;
}
}
function Logout() {
if (token === "") {
return;
}
removeAccountId();
removeToken();
token.value = "";
accountId.value = "";
AppModule.updateAccount("");
}
return {
token,
Login,
Logout,
};
});

5
src/store/user_global.js Normal file
View File

@ -0,0 +1,5 @@
export default {
token:"",
accountId:"",
chainId:0,
}

237
src/style/rest.css Normal file
View File

@ -0,0 +1,237 @@
html,
body,
div,
span,
applet,
object,
iframe,
h1,
h2,
h3,
h4,
h5,
h6,
p,
blockquote,
pre,
a,
abbr,
acronym,
address,
big,
cite,
code,
del,
dfn,
em,
font,
img,
ins,
kbd,
q,
s,
samp,
small,
strike,
strong,
sub,
sup,
tt,
var,
b,
u,
i,
center,
dl,
dt,
dd,
ol,
ul,
li,
fieldset,
form,
label,
legend,
caption {
margin: 0;
padding: 0;
border: 0;
outline: 0;
font-size: 100%;
vertical-align: baseline;
background: transparent;
}
table,
tbody,
tfoot,
thead,
tr,
th,
td {
margin: 0;
padding: 0;
outline: 0;
font-size: 100%;
vertical-align: baseline;
background: transparent;
}
button,
input,
textarea {
margin: 0;
padding: 0;
}
/* form elements 表单元素 */
body,
button,
input,
select,
textarea {
font: normal 12px/1.5 '\5FAE\8F6F\96C5\9ED1', tahoma, arial;
}
/*设置的字体,行高*/
h1,
h2,
h3,
h4,
h5,
h6,
th {
font-size: 100%;
font-weight: normal;
}
/*重置标题*/
address,
cite,
dfn,
var {
font-style: normal;
}
/* 将斜体扶正 */
code,
kbd,
pre,
samp {
font-family: 'courier new', courier, monospace;
}
/* 统一等宽字体 */
small {
font-size: 12px;
}
/* 小于 12px 的中文很难阅读,让 small 正常化 */
ul,
ol {
list-style: none;
}
/* 重置列表元素 */
button,
input[type="submit"],
input[type="button"] {
cursor: pointer;
}
input[type="radio"],
input[type="checkbox"],
input[type="submit"],
input[type="reset"] {
vertical-align: middle;
cursor: pointer;
border: none;
}
/** 重置文本格式元素 **/
a {
text-decoration: none;
}
a:hover {
text-decoration: none;
}
a:focus {
outline: 0;
}
sup {
vertical-align: text-top;
}
/* 重置,减少对行高的影响 */
sub {
vertical-align: text-bottom;
}
/** 重置表单元素 **/
legend {
color: #000;
}
/* for ie6 */
fieldset,
img {
border: 0;
}
/* img 搭车:让链接里的 img 无边框 */
button,
input,
select,
textarea {
background: transparent;
font-size: 100%;
outline: 0;
}
/* 使得表单元素在 ie 下能继承字体大小 */
/* 注optgroup 无法扶正 */
table {
border-collapse: collapse;
border-spacing: 0;
}
td,
th {
vertical-align: middle;
}
/** 重置表格元素 **/
/* 重置 HTML5 元素 */
article,
aside,
details,
figcaption,
figure,
footer,
header,
hgroup,
menu,
nav,
section,
summary,
time,
mark,
audio,
video {
display: block;
margin: 0;
padding: 0;
}
/*回复标签重置*/
blockquote,
q {
quotes: none;
}
blockquote:before,
blockquote:after,
q:before,
q:after {
content: '';
display: none;
}

Some files were not shown because too many files have changed in this diff Show More