mirror of
https://github.com/VickScarlet/lifeRestart.git
synced 2025-07-16 09:03:55 +08:00
add view
This commit is contained in:
1
.gitignore
vendored
1
.gitignore
vendored
@@ -103,5 +103,4 @@ dist
|
||||
# TernJS port file
|
||||
.tern-port
|
||||
|
||||
view/
|
||||
utils/xlsxTransform-*
|
2
.vscode/launch.json
vendored
2
.vscode/launch.json
vendored
@@ -8,7 +8,7 @@
|
||||
"type": "node",
|
||||
"request": "launch",
|
||||
"name": "test",
|
||||
"program": "${workspaceFolder}/test.js",
|
||||
"program": "${workspaceFolder}/test",
|
||||
"skipFiles": [
|
||||
"<node_internals>/**"
|
||||
]
|
||||
|
1002
data/age.json
1002
data/age.json
File diff suppressed because it is too large
Load Diff
BIN
data/age.xlsx
BIN
data/age.xlsx
Binary file not shown.
1024
data/events.json
1024
data/events.json
File diff suppressed because it is too large
Load Diff
BIN
data/events.xlsx
BIN
data/events.xlsx
Binary file not shown.
@@ -3,37 +3,37 @@
|
||||
"id": "1001",
|
||||
"name": "随身玉佩",
|
||||
"description": "2岁时不会死",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1002": {
|
||||
"id": "1002",
|
||||
"name": "红肚兜",
|
||||
"description": "3岁时不会死",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1003": {
|
||||
"id": "1003",
|
||||
"name": "生而为男",
|
||||
"description": "性别一定为男",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1004": {
|
||||
"id": "1004",
|
||||
"name": "生而为女",
|
||||
"description": "性别一定为女",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1005": {
|
||||
"id": "1005",
|
||||
"name": "动漫高手",
|
||||
"description": "入宅的可能性翻6倍",
|
||||
"rare": "2"
|
||||
"grade": "2"
|
||||
},
|
||||
"1006": {
|
||||
"id": "1006",
|
||||
"name": "乐天派",
|
||||
"description": "快乐+1",
|
||||
"rare": "0",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"SPR": "1"
|
||||
}
|
||||
@@ -42,14 +42,14 @@
|
||||
"id": "1007",
|
||||
"name": "天赋异禀",
|
||||
"description": "初始可用属性点+2",
|
||||
"rare": "1",
|
||||
"grade": "1",
|
||||
"status": "2"
|
||||
},
|
||||
"1008": {
|
||||
"id": "1008",
|
||||
"name": "天生抑郁",
|
||||
"description": "快乐-3",
|
||||
"rare": "0",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"SPR": "-3"
|
||||
}
|
||||
@@ -58,7 +58,7 @@
|
||||
"id": "1009",
|
||||
"name": "网络巨魔",
|
||||
"description": "快乐+2",
|
||||
"rare": "1",
|
||||
"grade": "1",
|
||||
"effect": {
|
||||
"SPR": "2"
|
||||
}
|
||||
@@ -67,31 +67,31 @@
|
||||
"id": "1010",
|
||||
"name": "天龙人",
|
||||
"description": "你拥有北京户口",
|
||||
"rare": "2"
|
||||
"grade": "2"
|
||||
},
|
||||
"1011": {
|
||||
"id": "1011",
|
||||
"name": "独生子女",
|
||||
"description": "你没有兄弟姐妹",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1012": {
|
||||
"id": "1012",
|
||||
"name": "乡间微风",
|
||||
"description": "你出生在农村",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1013": {
|
||||
"id": "1013",
|
||||
"name": "城中高楼",
|
||||
"description": "你出生在城市",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1014": {
|
||||
"id": "1014",
|
||||
"name": "美籍华人",
|
||||
"description": "你有美国国籍",
|
||||
"rare": "2",
|
||||
"grade": "2",
|
||||
"effect": {
|
||||
"MNY": "3"
|
||||
}
|
||||
@@ -100,25 +100,25 @@
|
||||
"id": "1015",
|
||||
"name": "家中老大",
|
||||
"description": "你最受父母宠爱",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1016": {
|
||||
"id": "1016",
|
||||
"name": "水性良好",
|
||||
"description": "不会被淹死",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1017": {
|
||||
"id": "1017",
|
||||
"name": "先天免疫",
|
||||
"description": "你不会得艾滋病",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1018": {
|
||||
"id": "1018",
|
||||
"name": "天选之人",
|
||||
"name": "人类进化",
|
||||
"description": "所有属性+1",
|
||||
"rare": "2",
|
||||
"grade": "2",
|
||||
"effect": {
|
||||
"SPR": "1"
|
||||
},
|
||||
@@ -130,32 +130,32 @@
|
||||
"1019": {
|
||||
"id": "1019",
|
||||
"name": "超凡",
|
||||
"description": "初始可用属性点+3",
|
||||
"rare": "2"
|
||||
"description": "初始可用属性点+4",
|
||||
"grade": "2"
|
||||
},
|
||||
"1020": {
|
||||
"id": "1020",
|
||||
"name": "父母美貌",
|
||||
"description": "颜值+2",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1021": {
|
||||
"id": "1021",
|
||||
"name": "红颜薄命",
|
||||
"description": "颜值+2,体质-2",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1022": {
|
||||
"id": "1022",
|
||||
"name": "属蛇",
|
||||
"description": "不会被蛇咬死",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1023": {
|
||||
"id": "1023",
|
||||
"name": "半神",
|
||||
"description": "所有属性+2",
|
||||
"rare": "3",
|
||||
"grade": "3",
|
||||
"effect": {
|
||||
"SPR": "2"
|
||||
},
|
||||
@@ -168,49 +168,49 @@
|
||||
"id": "1024",
|
||||
"name": "人中龙凤",
|
||||
"description": "天生双重性别",
|
||||
"rare": "2"
|
||||
"grade": "2"
|
||||
},
|
||||
"1025": {
|
||||
"id": "1025",
|
||||
"name": "阴阳之外",
|
||||
"description": "天生无性别",
|
||||
"rare": "2"
|
||||
"grade": "2"
|
||||
},
|
||||
"1026": {
|
||||
"id": "1026",
|
||||
"name": "彩虹之下",
|
||||
"description": "可能和同性交往",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1027": {
|
||||
"id": "1027",
|
||||
"name": "斩情证道",
|
||||
"description": "终生不恋爱结婚",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1028": {
|
||||
"id": "1028",
|
||||
"name": "桃花连连",
|
||||
"description": "恋爱机会提升",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1029": {
|
||||
"id": "1029",
|
||||
"name": "平安童年",
|
||||
"description": "12岁前父母都健在",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1030": {
|
||||
"id": "1030",
|
||||
"name": "宠物大师",
|
||||
"description": "宠物不会意外死亡",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1031": {
|
||||
"id": "1031",
|
||||
"name": "天生残疾",
|
||||
"description": "体质-2",
|
||||
"rare": "0",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"STR": "-2"
|
||||
}
|
||||
@@ -219,7 +219,7 @@
|
||||
"id": "1032",
|
||||
"name": "早产儿",
|
||||
"description": "所有属性-1",
|
||||
"rare": "0",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"SPR": "-1"
|
||||
},
|
||||
@@ -232,163 +232,308 @@
|
||||
"id": "1033",
|
||||
"name": "十死无生",
|
||||
"description": "体质-10",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1034": {
|
||||
"id": "1034",
|
||||
"name": "家运不顺",
|
||||
"description": "家境-2",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1035": {
|
||||
"id": "1035",
|
||||
"name": "头着地",
|
||||
"description": "智力-2",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1036": {
|
||||
"id": "1036",
|
||||
"name": "胎教",
|
||||
"description": "智力+1",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1037": {
|
||||
"id": "1037",
|
||||
"name": "班中红人",
|
||||
"description": "和同学容易处好关系",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1038": {
|
||||
"id": "1038",
|
||||
"name": "骑士",
|
||||
"description": "能轻松学会骑车",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1039": {
|
||||
"id": "1039",
|
||||
"name": "永远的神",
|
||||
"description": "电竞天才",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1040": {
|
||||
"id": "1040",
|
||||
"name": "黄帝",
|
||||
"description": "赌毒不沾",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1041": {
|
||||
"id": "1041",
|
||||
"name": "丁克",
|
||||
"description": "不生孩子",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1042": {
|
||||
"id": "1042",
|
||||
"name": "少数民族",
|
||||
"description": "高考+5分",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1043": {
|
||||
"id": "1043",
|
||||
"name": "老司机",
|
||||
"description": "你的家人不会发生车祸",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1044": {
|
||||
"id": "1044",
|
||||
"name": "低压",
|
||||
"description": "你的家人不会心脏病",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1045": {
|
||||
"id": "1045",
|
||||
"name": "战功",
|
||||
"description": "你退伍后会当官",
|
||||
"rare": "0"
|
||||
"grade": "0"
|
||||
},
|
||||
"1046": {
|
||||
"id": "1046",
|
||||
"name": "不孕不育",
|
||||
"description": "你生不出孩子",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1047": {
|
||||
"id": "1047",
|
||||
"name": "白头偕老",
|
||||
"description": "爱人至少能活到70岁",
|
||||
"rare": "1"
|
||||
"grade": "1"
|
||||
},
|
||||
"1048": {
|
||||
"id": "1048",
|
||||
"name": "一个小盒子",
|
||||
"name": "神秘的小盒子",
|
||||
"description": "100岁时才能开启",
|
||||
"rare": "3"
|
||||
"grade": "3"
|
||||
},
|
||||
"1049": {
|
||||
"id": "1049"
|
||||
"id": "1049",
|
||||
"name": "三十而立",
|
||||
"description": "30岁时家境+2",
|
||||
"condition": "age?[30]",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"MNY": "2"
|
||||
}
|
||||
},
|
||||
"1050": {
|
||||
"id": "1050"
|
||||
"id": "1050",
|
||||
"name": "四十不惑",
|
||||
"description": "40岁时智力+2",
|
||||
"condition": "age?[40]",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"INT": "2"
|
||||
}
|
||||
},
|
||||
"1051": {
|
||||
"id": "1051"
|
||||
"id": "1051",
|
||||
"name": "知天命",
|
||||
"description": "50岁时智力、快乐+1",
|
||||
"condition": "age?[50]",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"SPR": "1"
|
||||
},
|
||||
"INT": "1"
|
||||
},
|
||||
"1052": {
|
||||
"id": "1052"
|
||||
"id": "1052",
|
||||
"name": "耳顺",
|
||||
"description": "60岁时快乐+2",
|
||||
"condition": "age?[60]",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"SPR": "2"
|
||||
}
|
||||
},
|
||||
"1053": {
|
||||
"id": "1053"
|
||||
"id": "1053",
|
||||
"name": "从心所欲",
|
||||
"description": "70岁时快乐+3",
|
||||
"condition": "age?[70]",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"SPR": "3"
|
||||
}
|
||||
},
|
||||
"1054": {
|
||||
"id": "1054"
|
||||
"id": "1054",
|
||||
"name": "老当益壮",
|
||||
"description": "60岁时体质+2",
|
||||
"condition": "age?[60]",
|
||||
"grade": "1",
|
||||
"effect": {
|
||||
"STR": "2"
|
||||
}
|
||||
},
|
||||
"1055": {
|
||||
"id": "1055"
|
||||
"id": "1055",
|
||||
"name": "鹤发童颜",
|
||||
"description": "70岁时颜值+3",
|
||||
"condition": "age?[70]",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"CHR": "3"
|
||||
}
|
||||
},
|
||||
"1056": {
|
||||
"id": "1056"
|
||||
"id": "1056",
|
||||
"name": "学前启蒙",
|
||||
"description": "5岁时智力+2",
|
||||
"condition": "age?[5]",
|
||||
"grade": "1",
|
||||
"effect": {
|
||||
"INT": "2"
|
||||
}
|
||||
},
|
||||
"1057": {
|
||||
"id": "1057"
|
||||
"id": "1057",
|
||||
"name": "十八变",
|
||||
"description": "18岁时颜值+2",
|
||||
"condition": "age?[18]",
|
||||
"grade": "1",
|
||||
"effect": {
|
||||
"CHR": "2"
|
||||
}
|
||||
},
|
||||
"1058": {
|
||||
"id": "1058"
|
||||
"id": "1058",
|
||||
"name": "迟来之财",
|
||||
"description": "90岁时家境+4",
|
||||
"condition": "age?[90]",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"MNY": "4"
|
||||
}
|
||||
},
|
||||
"1059": {
|
||||
"id": "1059"
|
||||
"id": "1059",
|
||||
"name": "理财达人",
|
||||
"description": "30、40、50岁时家境+1",
|
||||
"condition": "age?[30,40,50]",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"MNY": "1"
|
||||
}
|
||||
},
|
||||
"1060": {
|
||||
"id": "1060"
|
||||
"id": "1060",
|
||||
"name": "成熟",
|
||||
"description": "12、18岁时智力+1",
|
||||
"condition": "age?[12,18]",
|
||||
"grade": "1",
|
||||
"effect": {
|
||||
"INT": "1"
|
||||
}
|
||||
},
|
||||
"1061": {
|
||||
"id": "1061"
|
||||
"id": "1061",
|
||||
"name": "形象管理",
|
||||
"description": "16、24岁时颜值+1",
|
||||
"condition": "age?[16,24]",
|
||||
"grade": "1",
|
||||
"effect": {
|
||||
"CHR": "1"
|
||||
}
|
||||
},
|
||||
"1062": {
|
||||
"id": "1062"
|
||||
"id": "1062",
|
||||
"name": "成年礼",
|
||||
"description": "18岁时快乐+1",
|
||||
"condition": "age?[18]",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"SPR": "1"
|
||||
}
|
||||
},
|
||||
"1063": {
|
||||
"id": "1063"
|
||||
"id": "1063",
|
||||
"name": "开光之胎",
|
||||
"description": "初始可用属性点+1",
|
||||
"grade": "0",
|
||||
"status": "1"
|
||||
},
|
||||
"1064": {
|
||||
"id": "1064"
|
||||
"id": "1064",
|
||||
"name": "天命",
|
||||
"description": "初始可用属性点+8",
|
||||
"grade": "3",
|
||||
"status": "8"
|
||||
},
|
||||
"1065": {
|
||||
"id": "1065"
|
||||
"id": "1065",
|
||||
"name": "祖传药丸",
|
||||
"description": "功能不明",
|
||||
"grade": "1"
|
||||
},
|
||||
"1066": {
|
||||
"id": "1066"
|
||||
"id": "1066",
|
||||
"name": "贵人相助",
|
||||
"description": "家境为0时家境+1",
|
||||
"condition": "MNY<1",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"MNY": "1"
|
||||
}
|
||||
},
|
||||
"1067": {
|
||||
"id": "1067"
|
||||
"id": "1067",
|
||||
"name": "乐天派",
|
||||
"description": "快乐为0时快乐+1",
|
||||
"condition": "SPR<1",
|
||||
"grade": "1",
|
||||
"effect": {
|
||||
"SPR": "1"
|
||||
}
|
||||
},
|
||||
"1068": {
|
||||
"id": "1068"
|
||||
"id": "1068",
|
||||
"name": "命悬一线",
|
||||
"description": "体质为0时体质+1",
|
||||
"condition": "STR<1",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"STR": "1"
|
||||
}
|
||||
},
|
||||
"1069": {
|
||||
"id": "1069"
|
||||
"id": "1069",
|
||||
"name": "智可生财",
|
||||
"description": "若20岁时智力>8,家境+2",
|
||||
"condition": "(age?[20])&(INT>8)",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"MNY": "2"
|
||||
}
|
||||
},
|
||||
"1070": {
|
||||
"id": "1070"
|
||||
"id": "1070",
|
||||
"name": "舔狗甚多",
|
||||
"description": "若20岁时颜值>8,快乐+2",
|
||||
"condition": "(age?[20])&(CHR>8)",
|
||||
"grade": "0",
|
||||
"effect": {
|
||||
"SPR": "2"
|
||||
}
|
||||
},
|
||||
"1071": {
|
||||
"id": "1071"
|
||||
|
Binary file not shown.
362
src/app.js
Normal file
362
src/app.js
Normal file
@@ -0,0 +1,362 @@
|
||||
import Life from './life.js'
|
||||
class App{
|
||||
constructor(){
|
||||
this.#life = new Life();
|
||||
}
|
||||
|
||||
#life;
|
||||
#pages;
|
||||
#talentSelected = new Set();
|
||||
#totalMax=20;
|
||||
#isEnd = false;
|
||||
|
||||
async initial() {
|
||||
this.initPages();
|
||||
this.switch('loading');
|
||||
await this.#life.initial();
|
||||
this.switch('index');
|
||||
}
|
||||
|
||||
initPages() {
|
||||
|
||||
// Loading
|
||||
const loadingPage = $(`
|
||||
<div id="main">
|
||||
<div id="title">
|
||||
人生重开模拟器<br>
|
||||
<div style="font-size:1.5rem; font-weight:normal;">加载中...</div>
|
||||
</div>
|
||||
</div>
|
||||
`);
|
||||
|
||||
// Index
|
||||
const indexPage = $(`
|
||||
<div id="main">
|
||||
<div id="cnt" class="head">已重开1次</div>
|
||||
<button id="rank">排行榜</button>
|
||||
<div id="title">
|
||||
人生重开模拟器<br>
|
||||
<div style="font-size:1.5rem; font-weight:normal;">这垃圾人生一秒也不想呆了</div>
|
||||
</div>
|
||||
<button id="restart" class="mainbtn"><span class="iconfont"></span>立即重开</button>
|
||||
<div class="hint">别卷了!没有排行榜</div>
|
||||
</div>
|
||||
`);
|
||||
|
||||
indexPage
|
||||
.find('#restart')
|
||||
.click(()=>this.switch('talent'));
|
||||
|
||||
const talentPage = $(`
|
||||
<div id="main">
|
||||
<div class="head" style="font-size: 1.6rem">天赋抽卡</div>
|
||||
<button id="random" class="mainbtn" style="top: 50%;">10连抽!</button>
|
||||
<ul id="talents" class="selectlist"></ul>
|
||||
<button id="next" class="mainbtn" style="top:auto; bottom:0.1em">请选择3个</button>
|
||||
</div>
|
||||
`);
|
||||
|
||||
// Talent
|
||||
const createTalent = ({ grade, name, description }) => {
|
||||
const element = $(`<li>${name}(${description})</li>`)
|
||||
switch(grade) {
|
||||
case 1:
|
||||
element.addClass('sprcial_blue');
|
||||
break;
|
||||
case 2:
|
||||
element.addClass('sprcial_purple');
|
||||
break;
|
||||
case 3:
|
||||
element.addClass('sprcial_orange');
|
||||
break;
|
||||
default: break;
|
||||
}
|
||||
return element;
|
||||
};
|
||||
|
||||
talentPage
|
||||
.find('#random')
|
||||
.click(()=>{
|
||||
talentPage.find('#random').hide();
|
||||
const ul = talentPage.find('#talents');
|
||||
this.#life.talentRandom()
|
||||
.forEach(talent=>{
|
||||
const li = createTalent(talent);
|
||||
ul.append(li);
|
||||
li.click(()=>{
|
||||
if(li.hasClass('selected')) {
|
||||
li.removeClass('selected')
|
||||
this.#talentSelected.delete(talent.id);
|
||||
} else {
|
||||
if(this.#talentSelected.size==3) {
|
||||
this.hint('只能选3个天赋');
|
||||
return;
|
||||
}
|
||||
li.addClass('selected');
|
||||
this.#talentSelected.add(talent.id);
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
talentPage
|
||||
.find('#next')
|
||||
.click(()=>{
|
||||
if(this.#talentSelected.size!=3) {
|
||||
this.hint('请选择3个天赋');
|
||||
return;
|
||||
}
|
||||
this.#totalMax = 20 + this.#life.getTalentAllocationAddition(Array.from(this.#talentSelected));
|
||||
this.switch('property');
|
||||
})
|
||||
|
||||
// Property
|
||||
const propertyPage = $(`
|
||||
<div id="main">
|
||||
<div class="head" style="font-size: 1.6rem">
|
||||
调整初始属性<br>
|
||||
<div id="total" style="font-size:1rem; font-weight:normal;">可用属性点:0</div>
|
||||
</div>
|
||||
<ul id="propertyAllocation" class="propinitial"></ul>
|
||||
<button id="random" class="mainbtn" style="top:auto; bottom:7rem">随机分配</button>
|
||||
<button id="start" class="mainbtn" style="top:auto; bottom:0.1rem">开始新人生</button>
|
||||
</div>
|
||||
`);
|
||||
|
||||
const groups = {};
|
||||
const total = ()=>{
|
||||
let t = 0;
|
||||
for(const type in groups)
|
||||
t += groups[type].get();
|
||||
return t;
|
||||
}
|
||||
const freshTotal = ()=>{
|
||||
propertyPage.find('#total').text(`可用属性点:${this.#totalMax - total()}`);
|
||||
}
|
||||
const getBtnGroups = (name, min, max)=>{
|
||||
const group = $(`<li>${name} </li>`);
|
||||
const btnSub = $(`<span class="iconfont propbtn"></span>`);
|
||||
const inputBox = $(`<input value="0">`);
|
||||
const btnAdd = $(`<span class="iconfont propbtn"></span>`);
|
||||
group.append(btnSub);
|
||||
group.append(inputBox);
|
||||
group.append(btnAdd);
|
||||
|
||||
const limit = v=>{
|
||||
v = Number(v)||0;
|
||||
v = Math.round(v);
|
||||
return v < min ? min : (
|
||||
v > max ? max : v
|
||||
)
|
||||
}
|
||||
const get = ()=>Number(inputBox.val());
|
||||
const set = v=>{
|
||||
inputBox.val(limit(v));
|
||||
freshTotal();
|
||||
}
|
||||
btnAdd.click(()=>{
|
||||
if(total() == this.#totalMax) {
|
||||
this.hint('没用可分配的点数了');
|
||||
return;
|
||||
}
|
||||
set(get()+1);
|
||||
});
|
||||
btnSub.click(()=>set(get()-1));
|
||||
return {group, get, set};
|
||||
}
|
||||
|
||||
groups.CHR = getBtnGroups("颜值", 0, 10); // 颜值 charm CHR
|
||||
groups.INT = getBtnGroups("智力", 0, 10); // 智力 intelligence INT
|
||||
groups.STR = getBtnGroups("体质", 0, 10); // 体质 strength STR
|
||||
groups.MNY = getBtnGroups("家境", 0, 10); // 家境 money MNY
|
||||
|
||||
const ul = propertyPage.find('#propertyAllocation');
|
||||
|
||||
for(const type in groups) {
|
||||
ul.append(groups[type].group);
|
||||
}
|
||||
|
||||
propertyPage.find('#random')
|
||||
.click(()=>{
|
||||
let t = this.#totalMax;
|
||||
const arr = [10, 10, 10, 10];
|
||||
while(t>0) {
|
||||
const sub = Math.round(Math.random() * (Math.min(t, 10) - 1)) + 1;
|
||||
while(true) {
|
||||
const select = Math.floor(Math.random() * 4) % 4;
|
||||
if(arr[select] - sub <0) continue;
|
||||
arr[select] -= sub;
|
||||
break;
|
||||
}
|
||||
t -= sub;
|
||||
}
|
||||
groups.CHR.set(arr[0]);
|
||||
groups.INT.set(arr[1]);
|
||||
groups.STR.set(arr[2]);
|
||||
groups.MNY.set(arr[3]);
|
||||
});
|
||||
|
||||
propertyPage.find('#start')
|
||||
.click(()=>{
|
||||
this.#life.restart({
|
||||
CHR: groups.CHR.get(),
|
||||
INT: groups.INT.get(),
|
||||
STR: groups.STR.get(),
|
||||
MNY: groups.MNY.get(),
|
||||
TLT: Array.from(this.#talentSelected),
|
||||
});
|
||||
this.switch('trajectory');
|
||||
this.#pages.trajectory.born();
|
||||
});
|
||||
|
||||
// Trajectory
|
||||
const trajectoryPage = $(`
|
||||
<div id="main">
|
||||
<ul id="lifeTrajectory" class="lifeTrajectory"></ul>
|
||||
<button id="summary" class="mainbtn" style="top:auto; bottom:0.1rem">人生总结</button>
|
||||
</div>
|
||||
`);
|
||||
|
||||
trajectoryPage.find('#lifeTrajectory')
|
||||
.click(()=>{
|
||||
if(this.#isEnd) return;
|
||||
const trajectory = this.#life.next();
|
||||
const { age, content, isEnd } = trajectory;
|
||||
|
||||
const li = $(`<li><span>${age}岁:</span>${
|
||||
content.map(
|
||||
({type, description, grade, name, postEvent}) => {
|
||||
switch(type) {
|
||||
case 'TLT':
|
||||
return `天赋【${name}】发动:${description}`;
|
||||
case 'EVT':
|
||||
return description + (postEvent?`<br>${postEvent}`:'');
|
||||
}
|
||||
}
|
||||
).join('<br>')
|
||||
}</li>`);
|
||||
li.appendTo('#lifeTrajectory');
|
||||
if(isEnd) {
|
||||
this.#isEnd = true;
|
||||
trajectoryPage.find('#summary').show();
|
||||
}
|
||||
});
|
||||
|
||||
this.#pages = {
|
||||
loading: {
|
||||
page: loadingPage,
|
||||
clear: ()=>{},
|
||||
},
|
||||
index: {
|
||||
page: indexPage,
|
||||
btnRank: indexPage.find('#rank'),
|
||||
btnRestart: indexPage.find('#restart'),
|
||||
hint: indexPage.find('.hint'),
|
||||
cnt: indexPage.find('.cnt'),
|
||||
clear: ()=>{
|
||||
indexPage.find('.hint').hide();
|
||||
|
||||
const times = this.times;
|
||||
const btnRank = indexPage.find('#rank');
|
||||
const cnt = indexPage.find('.cnt');
|
||||
if(times < 0) {
|
||||
btnRank.hide();
|
||||
cnt.hide();
|
||||
return;
|
||||
}
|
||||
|
||||
btnRank.show();
|
||||
cnt.show();
|
||||
cnt.text(`已重开${times}次`);
|
||||
},
|
||||
},
|
||||
talent: {
|
||||
page: talentPage,
|
||||
clear: ()=>{
|
||||
talentPage.find('ul.selectlist').children().remove();
|
||||
talentPage.find('#random').show();
|
||||
this.#totalMax = 20;
|
||||
},
|
||||
},
|
||||
property: {
|
||||
page: propertyPage,
|
||||
clear: ()=>{
|
||||
freshTotal();
|
||||
},
|
||||
},
|
||||
trajectory: {
|
||||
page: trajectoryPage,
|
||||
clear: ()=>{
|
||||
trajectoryPage.find('#lifeTrajectory').children().remove();
|
||||
trajectoryPage.find('#summary').hide();
|
||||
this.#isEnd = false;
|
||||
},
|
||||
born: ()=>{
|
||||
trajectoryPage.find('#lifeTrajectory').trigger("click");
|
||||
}
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
switch(page) {
|
||||
const p = this.#pages[page];
|
||||
if(!p) return;
|
||||
$('#main').remove();
|
||||
p.clear();
|
||||
p.page.appendTo('body');
|
||||
}
|
||||
|
||||
hint(str) {
|
||||
alert(str);
|
||||
}
|
||||
|
||||
test() {
|
||||
this.#life.restart({
|
||||
CHR: 5, // 颜值 charm CHR
|
||||
INT: 5, // 智力 intelligence INT
|
||||
STR: 5, // 体质 strength STR
|
||||
MNY: 5, // 家境 money MNY
|
||||
SPR: 5, // 快乐 spirit SPR
|
||||
TLT: [1004, 1005, 1009], // 天赋 talent TLT
|
||||
});
|
||||
const lifeTrajectory = [];
|
||||
let trajectory;
|
||||
do{
|
||||
try{
|
||||
trajectory = this.#life.next();
|
||||
} catch(e) {
|
||||
console.error(e);
|
||||
// debugger
|
||||
throw e;
|
||||
}
|
||||
lifeTrajectory.push(lifeTrajectory);
|
||||
const { age, content } = trajectory;
|
||||
console.debug(
|
||||
`---------------------------------`,
|
||||
`\n-- ${age} 岁\n `,
|
||||
content.map(
|
||||
({type, description, grade, name, postEvent}) => {
|
||||
switch(type) {
|
||||
case 'TLT':
|
||||
return `天赋【${name}】发动:${description}`;
|
||||
case 'EVT':
|
||||
return description + (postEvent?`\n ${postEvent}`:'');
|
||||
}
|
||||
}
|
||||
).join('\n ')
|
||||
);
|
||||
} while(!trajectory.isEnd)
|
||||
return lifeTrajectory;
|
||||
}
|
||||
|
||||
main() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
get times() {return localStorage.times || 0;}
|
||||
set times(v) {localStorage.times = parseInt(v) || 0};
|
||||
|
||||
}
|
||||
|
||||
export default App;
|
18
src/life.js
18
src/life.js
@@ -15,9 +15,9 @@ class Life {
|
||||
#triggerTalents;
|
||||
|
||||
async initial() {
|
||||
const age = JSON.parse(await json('data/age.json'));
|
||||
const talents = JSON.parse(await json('data/talents.json'));
|
||||
const events = JSON.parse(await json('data/events.json'));
|
||||
const age = await json('age');
|
||||
const talents = await json('talents');
|
||||
const events = await json('events');
|
||||
|
||||
this.#property.initial({age});
|
||||
this.#talent.initial({talents});
|
||||
@@ -30,6 +30,10 @@ class Life {
|
||||
this.doTalent();
|
||||
}
|
||||
|
||||
getTalentAllocationAddition(talents) {
|
||||
return this.#talent.allocationAddition(talents);
|
||||
}
|
||||
|
||||
next() {
|
||||
const {age, event, talent} = this.#property.ageNext();
|
||||
|
||||
@@ -56,7 +60,7 @@ class Life {
|
||||
contents.push({
|
||||
type: this.#property.TYPES.TLT,
|
||||
name,
|
||||
rate,
|
||||
grade,
|
||||
desctiption,
|
||||
})
|
||||
if(!result.effect) continue;
|
||||
@@ -91,6 +95,12 @@ class Life {
|
||||
return eventId;
|
||||
return events[events.length-1];
|
||||
}
|
||||
|
||||
talentRandom() {
|
||||
return this.#talent.talentRandom();
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
export default Life;
|
||||
|
||||
|
@@ -27,6 +27,7 @@ class Property {
|
||||
if(value.length==1) value.push(1);
|
||||
return value;
|
||||
});
|
||||
age[a].talent = age[a].talent?.split(',').map(v=>Number(v));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -114,7 +115,7 @@ class Property {
|
||||
}
|
||||
|
||||
isEnd() {
|
||||
return !this.get(this.TYPES.LIF);
|
||||
return this.get(this.TYPES.LIF) < 1;
|
||||
}
|
||||
|
||||
ageNext() {
|
||||
|
@@ -6,6 +6,11 @@ class Talent {
|
||||
|
||||
initial({talents}) {
|
||||
this.#talents = talents;
|
||||
for(const id in talents) {
|
||||
const talent = talents[id];
|
||||
talent.id= Number(id);
|
||||
talent.grade = Number(talent.grade);
|
||||
}
|
||||
}
|
||||
|
||||
check(talentId) {
|
||||
@@ -20,16 +25,53 @@ class Talent {
|
||||
}
|
||||
|
||||
information(talentId) {
|
||||
const { rate, name, description } = this.get(talentId)
|
||||
return { rate, name, description };
|
||||
const { grade, name, description } = this.get(talentId)
|
||||
return { grade, name, description };
|
||||
}
|
||||
|
||||
talentRandom() {
|
||||
// 1000, 100, 10, 1
|
||||
const talentList = {};
|
||||
for(const talentId in this.#talents) {
|
||||
const { id, grade, name, description } = this.#talents[talentId];
|
||||
if(!talentList[grade]) talentList[grade] = [{ grade, name, description, id }];
|
||||
else talentList[grade].push({ grade, name, description, id });
|
||||
}
|
||||
|
||||
return new Array(10)
|
||||
.fill(1).map(()=>{
|
||||
const gradeRandom = Math.random();
|
||||
let grade;
|
||||
if(gradeRandom>=0.111) grade = 0;
|
||||
else if(gradeRandom>=0.011) grade = 1;
|
||||
else if(gradeRandom>=0.001) grade = 2;
|
||||
else grade = 3;
|
||||
|
||||
while(talentList[grade].length == 0) grade--;
|
||||
|
||||
const length = talentList[grade].length;
|
||||
|
||||
const random = Math.floor(Math.random()*length) % length;
|
||||
return talentList[grade].splice(random,1)[0];
|
||||
});
|
||||
}
|
||||
|
||||
allocationAddition(talents) {
|
||||
if(Array.isArray(talents)) {
|
||||
let addition = 0;
|
||||
for(const talent of talents)
|
||||
addition += this.allocationAddition(talent);
|
||||
return addition;
|
||||
}
|
||||
return this.get(talents).status || 0;
|
||||
}
|
||||
|
||||
do(talentId) {
|
||||
const { effect, condition, initiative, rate, name, description } = this.get(talentId);
|
||||
const { effect, condition, initiative, grade, name, description } = this.get(talentId);
|
||||
if(!initiative) return null;
|
||||
if(condition && !checkCondition(condition))
|
||||
return null;
|
||||
return { effect, rate, name, description };
|
||||
return { effect, grade, name, description };
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -1,7 +1,7 @@
|
||||
import { readFile } from 'fs/promises';
|
||||
import Life from '../src/life.js'
|
||||
|
||||
global.json = filePath => readFile(filePath);
|
||||
global.json = async fileName => JSON.parse(await readFile(`data/${fileName}.json`));
|
||||
|
||||
async function debug() {
|
||||
|
||||
@@ -28,9 +28,9 @@ async function debug() {
|
||||
}
|
||||
lifeTrajectory.push(lifeTrajectory);
|
||||
const { age, content } = trajectory;
|
||||
console.debug(`---------------------------------`);
|
||||
console.debug(`-- ${age} 岁`);
|
||||
console.debug(' ',
|
||||
console.debug(
|
||||
`---------------------------------`,
|
||||
`\n-- ${age} 岁\n `,
|
||||
content.map(
|
||||
({type, description, rate, name, postEvent}) => {
|
||||
switch(type) {
|
||||
|
180
view/condition_test.html
Normal file
180
view/condition_test.html
Normal file
@@ -0,0 +1,180 @@
|
||||
颜值: <input class="prop" name="CHR" style="width:300px;" value="5" >(CHR)<br/>
|
||||
智力: <input class="prop" name="INT" style="width:300px;" value="5" >(INT)<br/>
|
||||
体质: <input class="prop" name="STR" style="width:300px;" value="5" >(STR)<br/>
|
||||
家境: <input class="prop" name="MNY" style="width:300px;" value="5" >(MNY)<br/>
|
||||
快乐: <input class="prop" name="SPR" style="width:300px;" value="5" >(SPR)<br/>
|
||||
生命: <input class="prop" name="LIF" style="width:300px;" value="5" >(LIF)<br/>
|
||||
天赋: <input class="prop" name="TLT" style="width:300px;" value="[5]" >(TLT)<br/>
|
||||
事件: <input class="prop" name="EVT" style="width:300px;" value="[5]" >(EVT)<br/>
|
||||
<br/><br/>
|
||||
表达式:<input id="conditions" style="width:500px;"><br/><br/>
|
||||
结果:<span id="result" style="color:red;"></span><br/><br/>
|
||||
<button id="submit"> 测 试 </button><br/>
|
||||
|
||||
<script>
|
||||
const DEFAULT_PROP = {
|
||||
CHR: 5, // 颜值 charm CHR
|
||||
INT: 5, // 智力 intelligence INT
|
||||
STR: 5, // 体质 strength STR
|
||||
MNY: 5, // 家境 money MNY
|
||||
SPR: 5, // 快乐 spirit SPR
|
||||
LIF: 5, // 生命 life LIF
|
||||
TLT: [5], // 天赋 talent TLT
|
||||
EVT: [5], // 事件 event EVT
|
||||
};
|
||||
document.querySelector("#submit").onclick = function() {
|
||||
document.querySelectorAll('.prop').forEach(({name, value})=>DEFAULT_PROP[name] = JSON.parse(value));
|
||||
conditions = document.querySelector("#conditions").value;
|
||||
const result = check(conditions);
|
||||
document.querySelector("#result").textContent = result;
|
||||
}
|
||||
|
||||
function getProp(prop) {
|
||||
switch(prop) {
|
||||
case 'CHR':
|
||||
case 'INT':
|
||||
case 'STR':
|
||||
case 'MNY':
|
||||
case 'SPR':
|
||||
case 'LIF':
|
||||
case 'TLT':
|
||||
case 'EVT': return DEFAULT_PROP[prop];
|
||||
default: return null;
|
||||
}
|
||||
}
|
||||
|
||||
function check(condition) {
|
||||
const conditions = parseCondition(condition);
|
||||
return checkParsedCondition(conditions);
|
||||
}
|
||||
|
||||
function checkParsedCondition(conditions) {
|
||||
if(!Array.isArray(conditions)) return checkLogic(conditions);
|
||||
if(conditions.length == 0) return true;
|
||||
if(conditions.length == 1) return checkParsedCondition(conditions[0]);
|
||||
|
||||
let ret = checkParsedCondition(conditions[0]);
|
||||
for(let i=1; i<conditions.length; i+=2) {
|
||||
switch(conditions[i]) {
|
||||
case '&':
|
||||
if(ret) ret = checkParsedCondition(conditions[i+1]);
|
||||
break;
|
||||
case '|':
|
||||
if(ret) return true;
|
||||
ret = checkParsedCondition(conditions[i+1]);
|
||||
break;
|
||||
default: return false;
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
|
||||
}
|
||||
|
||||
function checkLogic(condition) {
|
||||
const length = condition.length;
|
||||
let i = condition.search(/[><\!\?=]/);
|
||||
|
||||
const prop = condition.substring(0,i);
|
||||
const symbol = condition.substring(i, i+=(condition[i+1]=='='?2:1));
|
||||
const d = condition.substring(i, length);
|
||||
|
||||
const propData = getProp(prop);
|
||||
const conditionData = d[0]=='['? JSON.parse(d): Number(d);
|
||||
|
||||
switch(symbol) {
|
||||
case '>': return propData > conditionData;
|
||||
case '<': return propData < conditionData;
|
||||
case '>=': return propData >= conditionData;
|
||||
case '<=': return propData <= conditionData;
|
||||
case '=':
|
||||
if(Array.isArray(propData))
|
||||
return propData.includes(conditionData);
|
||||
return propData == conditionData;
|
||||
case '!=':
|
||||
if(Array.isArray(propData))
|
||||
return !propData.includes(conditionData);
|
||||
return propData == conditionData;
|
||||
case '?':
|
||||
if(Array.isArray(propData)) {
|
||||
for(const p of propData)
|
||||
if(conditionData.includes(p)) return true;
|
||||
return false;
|
||||
}
|
||||
return conditionData.includes(propData);
|
||||
case '!':
|
||||
if(Array.isArray(propData)) {
|
||||
for(const p of propData)
|
||||
if(conditionData.includes(p)) return false;
|
||||
return true;
|
||||
}
|
||||
return !conditionData.includes(propData);
|
||||
|
||||
default: return false;
|
||||
}
|
||||
}
|
||||
|
||||
function parseCondition(condition) {
|
||||
const conditions = [];
|
||||
const length = condition.length;
|
||||
const stack = [];
|
||||
stack.unshift(conditions);
|
||||
let cursor = 0;
|
||||
const catchString = i => {
|
||||
const str = condition.substring(cursor, i).trim();
|
||||
cursor = i;
|
||||
if(str) stack[0].push(str);
|
||||
};
|
||||
|
||||
for(let i=0; i<length; i++) {
|
||||
switch(condition[i]) {
|
||||
case ' ': continue;
|
||||
|
||||
case '(':
|
||||
catchString(i);
|
||||
cursor ++;
|
||||
const sub = [];
|
||||
stack[0].push(sub);
|
||||
stack.unshift(sub);
|
||||
break;
|
||||
|
||||
case ')':
|
||||
catchString(i);
|
||||
cursor ++;
|
||||
stack.shift();
|
||||
break;
|
||||
|
||||
case '|':
|
||||
case '&':
|
||||
catchString(i);
|
||||
catchString(i+1);
|
||||
break;
|
||||
default: continue;
|
||||
}
|
||||
}
|
||||
|
||||
catchString(length);
|
||||
|
||||
return conditions;
|
||||
}
|
||||
|
||||
// function debug(...conditions) {
|
||||
// for(const condition of conditions)
|
||||
// console.debug(check(condition), '\t', condition);
|
||||
// }
|
||||
//
|
||||
// debug(
|
||||
// '(STR<2&MNY>3)|(MNY<2&CHR<2)',
|
||||
// '(STR<2&MNY>3)',
|
||||
// '(STR>2&MNY>3)',
|
||||
// '((((STR>2&MNY>2))))',
|
||||
// '((((STR>2&MNY>2)|(MNY<2&CHR<2))))',
|
||||
// '((((STR>2&MNY>2)|(MNY<2&CHR<2)&(STR>2&MNY>3))))',
|
||||
// '((((STR>2&MNY>2)|(MNY<2&CHR<2))&(STR>2&MNY>3)))',
|
||||
// 'EVT![1,2,3]',
|
||||
// 'EVT![1,2]',
|
||||
// 'EVT?[1,2,3]',
|
||||
// 'EVT?[1,2]',
|
||||
// );
|
||||
</script>
|
||||
|
||||
|
BIN
view/iconfont.ttf
Normal file
BIN
view/iconfont.ttf
Normal file
Binary file not shown.
BIN
view/iconfont.woff
Normal file
BIN
view/iconfont.woff
Normal file
Binary file not shown.
BIN
view/iconfont.woff2
Normal file
BIN
view/iconfont.woff2
Normal file
Binary file not shown.
21
view/index.html
Normal file
21
view/index.html
Normal file
@@ -0,0 +1,21 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<link rel="stylesheet" href="style.css">
|
||||
<script src="https://cdn.jsdelivr.net/npm/jquery@3.6.0/dist/jquery.min.js"></script>
|
||||
<script src="https://cdn.jsdelivr.net/npm/axios/dist/axios.min.js"></script>
|
||||
<script>window.json = async fileName=>(await axios(`../data/${fileName}.json`)).data;</script>
|
||||
<title>Document</title>
|
||||
</head>
|
||||
<body style="margin: 0; height: 100%"></body>
|
||||
<script type="module">
|
||||
import App from '../src/app.js';
|
||||
const app = new App();
|
||||
app
|
||||
.initial()
|
||||
.then(()=>app.main());
|
||||
</script>
|
||||
</html>
|
238
view/style.css
Normal file
238
view/style.css
Normal file
@@ -0,0 +1,238 @@
|
||||
@media (min-width:640px){html{font-size:24px;}}
|
||||
@media (min-width:631px) and (max-width:639px){html{font-size:23.66px;}}
|
||||
@media (min-width:622px) and (max-width:630px){html{font-size:23.33px;}}
|
||||
@media (min-width:613px) and (max-width:621px){html{font-size:23px;}}
|
||||
@media (min-width:604px) and (max-width:612px){html{font-size:22.66px;}}
|
||||
@media (min-width:595px) and (max-width:603px){html{font-size:22.33px;}}
|
||||
@media (min-width:586px) and (max-width:594px){html{font-size:22px;}}
|
||||
@media (min-width:577px) and (max-width:585px){html{font-size:21.66px;}}
|
||||
@media (min-width:568px) and (max-width:576px){html{font-size:21.33px;}}
|
||||
@media (min-width:559px) and (max-width:567px){html{font-size:21px;}}
|
||||
@media (min-width:550px) and (max-width:558px){html{font-size:20.66px;}}
|
||||
@media (min-width:541px) and (max-width:549px){html{font-size:20.33px;}}
|
||||
@media (min-width:533px) and (max-width:540px){html{font-size:20px;}}
|
||||
@media (min-width:524px) and (max-width:532px){html{font-size:19.66px;}}
|
||||
@media (min-width:515px) and (max-width:523px){html{font-size:19.33px;}}
|
||||
@media (min-width:506px) and (max-width:514px){html{font-size:19px;}}
|
||||
@media (min-width:497px) and (max-width:505px){html{font-size:18.66px;}}
|
||||
@media (min-width:488px) and (max-width:496px){html{font-size:18.33px;}}
|
||||
@media (min-width:480px) and (max-width:487px){html{font-size:18px;}}
|
||||
@media (min-width:471px) and (max-width:479px){html{font-size:17.66px;}}
|
||||
@media (min-width:462px) and (max-width:470px){html{font-size:17.33px;}}
|
||||
@media (min-width:453px) and (max-width:461px){html{font-size:17px;}}
|
||||
@media (min-width:444px) and (max-width:452px){html{font-size:17.12px;}}
|
||||
@media (min-width:435px) and (max-width:443px){html{font-size:16.33px;}}
|
||||
@media (min-width:426px) and (max-width:434px){html{font-size:16px;}}
|
||||
@media (min-width:417px) and (max-width:425px){html{font-size:15.66px;}}
|
||||
@media (min-width:408px) and (max-width:416px){html{font-size:15.33px;}}
|
||||
@media (min-width:400px) and (max-width:407px){html{font-size:15px;}}
|
||||
@media (min-width:391px) and (max-width:399px){html{font-size:14.66px;}}
|
||||
@media (min-width:382px) and (max-width:390px){html{font-size:14.33px;}}
|
||||
@media (min-width:374px) and (max-width:381px){html{font-size:14px;}}
|
||||
@media (min-width:365px) and (max-width:373px){html{font-size:13.66px;}}
|
||||
@media (min-width:356px) and (max-width:364px){html{font-size:13.33px;}}
|
||||
@media (min-width:347px) and (max-width:355px){html{font-size:13px;}}
|
||||
@media (min-width:338px) and (max-width:346px){html{font-size:12.66px;}}
|
||||
@media (min-width:329px) and (max-width:337px){html{font-size:12.44px;}}
|
||||
@media (max-width:328px){html{font-size:12px;}}
|
||||
|
||||
@font-face {
|
||||
font-family: 'iconfont';
|
||||
src: url('iconfont.woff2?t=1628944689555') format('woff2'),
|
||||
url('iconfont.woff?t=1628944689555') format('woff'),
|
||||
url('iconfont.ttf?t=1628944689555') format('truetype');
|
||||
}
|
||||
|
||||
html {
|
||||
font-family: PingFangSC, 'Noto Sans CJK SC', 'MS Yahei';
|
||||
}
|
||||
|
||||
#main {
|
||||
align-content: center;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
#title {
|
||||
position: fixed;
|
||||
font-size: 3rem;
|
||||
font-weight: 700;
|
||||
top: 35%;
|
||||
left: 50%;
|
||||
white-space: nowrap;
|
||||
transform: translate(-50%,-50%);
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.mainbtn {
|
||||
position: fixed;
|
||||
top: 65%;
|
||||
left: 50%;
|
||||
padding: 0.8rem 1rem;
|
||||
border: 1px #ccc solid;
|
||||
border-radius: 0.2rem;
|
||||
background-color:white;
|
||||
font-size: 1.6rem;
|
||||
white-space: nowrap;
|
||||
transform: translate(-50%,-50%);
|
||||
cursor: pointer;
|
||||
z-index:2;
|
||||
}
|
||||
|
||||
.iconfont {
|
||||
font-family: "iconfont" !important;
|
||||
font-style: normal;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
}
|
||||
|
||||
#rank {
|
||||
position: fixed;
|
||||
top: 1rem;
|
||||
right: 1rem;
|
||||
padding: 0.1rem 1rem;
|
||||
border: none;
|
||||
border-radius: 0.2rem;
|
||||
background-color:lightsteelblue;
|
||||
font-size: 1.4rem;
|
||||
color: white;
|
||||
cursor: pointer;
|
||||
z-index:2;
|
||||
}
|
||||
|
||||
.hint {
|
||||
position: fixed;
|
||||
bottom: 2rem;
|
||||
left: 50%;
|
||||
padding: 0.3rem 2rem;
|
||||
border: none;
|
||||
border-radius: 0.2rem;
|
||||
background-color:gray;
|
||||
font-size: 1.4rem;
|
||||
color: white;
|
||||
white-space: nowrap;
|
||||
transform: translateX(-50%);
|
||||
}
|
||||
|
||||
.head {
|
||||
position: fixed;
|
||||
font-size: 1.4rem;
|
||||
top: 1.1rem;
|
||||
left: 50%;
|
||||
white-space: nowrap;
|
||||
transform: translateX(-50%);
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.lifeTrajectory,
|
||||
.propinitial,
|
||||
.selectlist {
|
||||
position: fixed;
|
||||
list-style-type: none;
|
||||
left: 50%;
|
||||
top: 5rem;
|
||||
bottom: 8.5rem;
|
||||
width: 30rem;
|
||||
max-width: calc(100% - 2rem);
|
||||
margin: auto;
|
||||
padding: 0;
|
||||
overflow: auto;
|
||||
transform: translateX(-50%);
|
||||
}
|
||||
|
||||
.selectlist > li {
|
||||
position: relative;
|
||||
border: 1px #ccc solid;
|
||||
display: inline-block;
|
||||
width: 95%;
|
||||
margin: 0.1rem auto;
|
||||
font-size: 1.4rem;
|
||||
text-align: center;
|
||||
border-radius: 0.2rem;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.selectlist > li::before {
|
||||
position: absolute;
|
||||
display: inline-block;
|
||||
left: 0;
|
||||
top: 0;
|
||||
border-radius: 0.2rem 0 0 0.2rem;
|
||||
margin: -1px;
|
||||
padding: 1px;
|
||||
height: 100%;
|
||||
width: 1.5rem;
|
||||
content: " ";
|
||||
}
|
||||
|
||||
.sprcial_blue::before {
|
||||
background-color: rgb(116, 191, 255);
|
||||
}
|
||||
|
||||
.sprcial_purple::before {
|
||||
background-color: rgb(226, 167, 255);
|
||||
}
|
||||
|
||||
.sprcial_orange::before {
|
||||
background-color: lightsalmon;
|
||||
}
|
||||
|
||||
.selected {
|
||||
background-color: gray;
|
||||
color: white;
|
||||
}
|
||||
|
||||
.propinitial {
|
||||
top: 6rem;
|
||||
bottom: 14rem;
|
||||
}
|
||||
|
||||
.propinitial > li {
|
||||
position: relative;
|
||||
display: inline-block;
|
||||
width: 95%;
|
||||
margin: 0.1rem auto;
|
||||
font-size: 1.4rem;
|
||||
text-align: center;
|
||||
border-radius: 0.2rem;
|
||||
padding: 0.2rem;
|
||||
}
|
||||
|
||||
.propinitial > li > input {
|
||||
height: 2.2rem;
|
||||
width: 2.2rem;
|
||||
margin: 0 0.5rem;
|
||||
padding: 0;
|
||||
text-align: center;
|
||||
font-size: 2rem;
|
||||
border: 0.1rem #ccc solid;
|
||||
}
|
||||
|
||||
.propbtn {
|
||||
position: relative;
|
||||
cursor: pointer;
|
||||
font-size: 2rem;
|
||||
}
|
||||
|
||||
.lifeTrajectory {
|
||||
border: 1px lightblue solid;
|
||||
background-color: aliceblue;
|
||||
}
|
||||
|
||||
.lifeTrajectory > li {
|
||||
position: relative;
|
||||
width: calc(100% - 7rem);
|
||||
margin: 0.5rem 0;
|
||||
padding: 0.5rem 1rem 0.5rem 6rem;
|
||||
font-size: 1.4rem;
|
||||
background-color: white;
|
||||
box-shadow: lightblue 0 0 0.4rem;
|
||||
}
|
||||
|
||||
.lifeTrajectory > li > span {
|
||||
position: absolute;
|
||||
left: 0;
|
||||
width: 6rem;
|
||||
text-align: right;
|
||||
}
|
31
view/test.html
Normal file
31
view/test.html
Normal file
@@ -0,0 +1,31 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<link rel="stylesheet" href="style.css">
|
||||
<script src="https://cdn.jsdelivr.net/npm/jquery@3.6.0/dist/jquery.min.js"></script>
|
||||
<script src="https://cdn.jsdelivr.net/npm/axios/dist/axios.min.js"></script>
|
||||
<script>window.json = async fileName=>(await axios(`../data/${fileName}.json`)).data;</script>
|
||||
<title>Document</title>
|
||||
</head>
|
||||
<body style="margin: 0; height: 100%">
|
||||
<div id="main">
|
||||
<ul id="lifeTrajectory" class="lifeTrajectory">
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
<li><span>0岁:</span>你出生了你出生了你出生了你出生了你出生了你出生了你出生了你出生了你出生了你出生了你出生了你出生了你出生了</li>
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
<li><span>0岁:</span>你出生了,你是女孩</li>
|
||||
</ul>
|
||||
<button id="summary" class="mainbtn" style="top:auto; bottom:0.1rem">人生总结</button>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
Reference in New Issue
Block a user