mps_school.html 50 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203
  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <meta charset="UTF-8">
  5. <meta http-equiv="Content-Type" content="text/html;charset=utf-8">
  6. <title>学校信息管理</title>
  7. <link href="https://kylx365-1253256735.file.myqcloud.com/js/jquery.tagit.css" rel="stylesheet" type="text/css">
  8. <link href="https://kylx365-1253256735.file.myqcloud.com/js/tagit.ui-zendesk.css" rel="stylesheet" type="text/css">
  9. <script src="https://kylx365-1253256735.file.myqcloud.com/js/jquery-1.10.2.min.js"></script>
  10. <script src="https://kylx365-1253256735.file.myqcloud.com/js/jquery-ui.min.js"></script>
  11. <script src="https://kylx365-1253256735.file.myqcloud.com/js/vue.min.js"></script>
  12. <link rel="stylesheet" href="./mg/common.css">
  13. <style>
  14. .main00 {
  15. width: 100%;
  16. height: 100vh;
  17. min-height: 600px;
  18. background: white;
  19. display: flex;
  20. flex-direction: column;
  21. overflow: hidden; /* 防止出现滚动条 */
  22. }
  23. .ListTop {
  24. width: 100%;
  25. height: 60px;
  26. background: white;
  27. border-bottom: 1px solid #EEEEEE;
  28. justify-content: flex-start;
  29. flex-shrink: 0; /* 防止头部被压缩 */
  30. }
  31. .ListTop3 {
  32. margin-left: 40px;
  33. height: 50px;
  34. align-items: center;
  35. }
  36. .ListTop4 {
  37. margin-left: 40px;
  38. height: 100%;
  39. }
  40. .title {
  41. font-size: 24px;
  42. color: #333333;
  43. font-weight: bold;
  44. }
  45. .btnNavigation {
  46. padding: 0 15px;
  47. height: 100%;
  48. font-size: 14px;
  49. color: #666666;
  50. border-bottom: 2px solid transparent;
  51. }
  52. .btnNavigation:hover {
  53. color: #4A90E2;
  54. }
  55. .btnSaveSelect {
  56. color: #4A90E2;
  57. border-bottom: 2px solid #4A90E2;
  58. }
  59. .main0 {
  60. width: 100%;
  61. background: white;
  62. flex: 1; /* 使用flex: 1代替固定高度 */
  63. min-height: 0; /* 确保flex子项可以收缩 */
  64. overflow: hidden;
  65. display: flex;
  66. position: relative;
  67. align-items: flex-start;
  68. }
  69. .school-list {
  70. width: 400px;
  71. border-right: 1px solid #EEEEEE;
  72. background: #F9F9F9;
  73. display: flex;
  74. flex-direction: column;
  75. height: 100%;
  76. position: relative;
  77. flex-shrink: 0;
  78. }
  79. .school-list-scrollable {
  80. flex: 1;
  81. overflow-y: auto;
  82. width: 100%;
  83. min-height: 0; /* 确保flex子项可以收缩 */
  84. display: flex;
  85. flex-direction: column;
  86. }
  87. .search-box {
  88. flex-shrink: 0; /* 防止搜索框被压缩 */
  89. }
  90. .school-detail {
  91. width: calc(100% - 400px);
  92. padding: 20px;
  93. overflow-y: auto;
  94. margin-top: 50px;
  95. }
  96. .search-box {
  97. padding: 15px;
  98. border-bottom: 1px solid #EEEEEE;
  99. background: white;
  100. width: 100%;
  101. justify-content: center;
  102. }
  103. .search-input {
  104. width: 200px;
  105. height: 32px;
  106. padding: 0 32px 0 12px;
  107. border: 1px solid #DDDDDD;
  108. border-radius: 4px;
  109. font-size: 14px;
  110. color: #333333;
  111. }
  112. .search-input:focus {
  113. border-color: #4A90E2;
  114. outline: none;
  115. }
  116. .btn33 {
  117. width: 32px;
  118. height: 32px;
  119. margin-left: 8px;
  120. border-radius: 4px;
  121. background: #F5F5F5;
  122. }
  123. .btn33:hover {
  124. background: #EEEEEE;
  125. }
  126. .district-list {
  127. padding: 0;
  128. width: 100%;
  129. align-self: flex-start;
  130. }
  131. .district-item {
  132. margin: 0;
  133. border-bottom: 1px solid #EEEEEE;
  134. }
  135. .district-name {
  136. font-weight: 500;
  137. cursor: pointer;
  138. padding: 12px 15px;
  139. font-size: 14px;
  140. color: #333333;
  141. background: white;
  142. }
  143. .district-name:hover {
  144. background: #F5F5F5;
  145. }
  146. .school-item {
  147. padding: 10px 15px 10px 30px;
  148. cursor: pointer;
  149. font-size: 14px;
  150. color: #666666;
  151. background: #F9F9F9;
  152. width: 100%;
  153. box-sizing: border-box;
  154. }
  155. .school-id {
  156. display: inline-block;
  157. font-size: 12px;
  158. color: #666;
  159. background-color: #f8f8f8;
  160. padding: 2px 6px;
  161. border-radius: 3px;
  162. margin-right: 8px;
  163. font-family: "Consolas", monospace;
  164. min-width: 40px;
  165. text-align: center;
  166. }
  167. .school-items {
  168. width: 100%;
  169. }
  170. .school-category {
  171. width: 100%;
  172. }
  173. .category-title {
  174. padding: 10px 15px 10px 30px;
  175. font-size: 14px;
  176. color: #333333;
  177. background: #F5F5F5;
  178. border-bottom: 1px solid #EEEEEE;
  179. border-left: 3px solid #4A90E2;
  180. font-weight: 600;
  181. margin-top: 4px;
  182. }
  183. .category-schools:empty::before {
  184. content: '暂无数据';
  185. display: block;
  186. padding: 10px 15px 10px 30px;
  187. color: #999;
  188. font-size: 14px;
  189. text-align: left;
  190. width: 100%;
  191. box-sizing: border-box;
  192. background: #F9F9F9;
  193. }
  194. .school-items:empty::before {
  195. content: '暂无数据';
  196. display: block;
  197. padding: 15px;
  198. color: #999;
  199. font-size: 14px;
  200. text-align: left;
  201. width: 100%;
  202. box-sizing: border-box;
  203. background: #F9F9F9;
  204. }
  205. .school-item:hover {
  206. background: #F5F5F5;
  207. color: #333333;
  208. }
  209. .school-item.active {
  210. background: #E6F3FF;
  211. color: #4A90E2;
  212. }
  213. .form-group {
  214. margin-bottom: 20px;
  215. }
  216. .form-label {
  217. display: block;
  218. margin-bottom: 8px;
  219. font-weight: 500;
  220. font-size: 14px;
  221. color: #333333;
  222. }
  223. .form-input {
  224. width: 100%;
  225. height: 36px;
  226. padding: 0 12px;
  227. border: 1px solid #DDDDDD;
  228. border-radius: 4px;
  229. font-size: 14px;
  230. color: #333333;
  231. transition: all 0.3s;
  232. }
  233. .form-input:focus {
  234. border-color: #4A90E2;
  235. outline: none;
  236. box-shadow: 0 0 0 2px rgba(74, 144, 226, 0.1);
  237. }
  238. .form-select {
  239. width: 100%;
  240. height: 36px;
  241. padding: 0 12px;
  242. border: 1px solid #DDDDDD;
  243. border-radius: 4px;
  244. font-size: 14px;
  245. color: #333333;
  246. background: white;
  247. cursor: pointer;
  248. transition: all 0.3s;
  249. }
  250. .form-select:focus {
  251. border-color: #4A90E2;
  252. outline: none;
  253. box-shadow: 0 0 0 2px rgba(74, 144, 226, 0.1);
  254. }
  255. .form-textarea {
  256. width: 100%;
  257. padding: 12px;
  258. border: 1px solid #DDDDDD;
  259. border-radius: 4px;
  260. min-height: 120px;
  261. resize: vertical;
  262. font-size: 14px;
  263. color: #333333;
  264. transition: all 0.3s;
  265. }
  266. .form-textarea:focus {
  267. border-color: #4A90E2;
  268. outline: none;
  269. box-shadow: 0 0 0 2px rgba(74, 144, 226, 0.1);
  270. }
  271. .btn-group {
  272. margin-top: 24px;
  273. text-align: right;
  274. padding: 0 20px 20px;
  275. }
  276. .btn {
  277. min-width: 30px;
  278. height: 36px;
  279. padding: 0 16px;
  280. margin-left: 12px;
  281. border: none;
  282. border-radius: 4px;
  283. cursor: pointer;
  284. font-size: 14px;
  285. transition: all 0.3s;
  286. }
  287. .btn-primary {
  288. background: #4A90E2;
  289. color: white;
  290. }
  291. .btn-primary:hover {
  292. background: #357ABD;
  293. }
  294. .btn-default {
  295. background: white;
  296. border: 1px solid #DDDDDD;
  297. color: #666666;
  298. }
  299. .btn-default:hover {
  300. background: #F5F5F5;
  301. border-color: #CCCCCC;
  302. }
  303. .form-sections {
  304. display: flex;
  305. flex-direction: row;
  306. width: 100%;
  307. align-items: flex-start;
  308. }
  309. .form-column {
  310. min-width: 0;
  311. /* 防止flex子项溢出 */
  312. }
  313. .form-section {
  314. border: 1px solid #EEEEEE;
  315. border-radius: 4px;
  316. padding: 20px;
  317. margin-bottom: 24px;
  318. background: white;
  319. }
  320. .form-section-title {
  321. font-size: 16px;
  322. font-weight: 500;
  323. margin-bottom: 20px;
  324. padding-bottom: 12px;
  325. border-bottom: 1px solid #EEEEEE;
  326. color: #333333;
  327. }
  328. .form-row {
  329. display: flex;
  330. margin: 0 -8px;
  331. flex-wrap: wrap;
  332. }
  333. .form-col {
  334. flex: 0 0 32%;
  335. padding: 0 8px;
  336. box-sizing: border-box;
  337. }
  338. .form-col-2 {
  339. flex: 0 0 63%;
  340. padding: 0 8px;
  341. box-sizing: border-box;
  342. }
  343. .form-col-3 {
  344. flex: 0 0 94%;
  345. padding: 0 8px;
  346. box-sizing: border-box;
  347. }
  348. .form-col-4 {
  349. flex: 0 0 48%;
  350. padding: 0 8px;
  351. box-sizing: border-box;
  352. }
  353. .toast {
  354. position: fixed;
  355. top: 20px;
  356. left: 50%;
  357. transform: translateX(-50%);
  358. padding: 12px 24px;
  359. background: rgba(0, 0, 0, 0.7);
  360. color: white;
  361. border-radius: 4px;
  362. z-index: 9999;
  363. opacity: 0;
  364. transition: opacity 0.3s;
  365. }
  366. .toast.show {
  367. opacity: 1;
  368. }
  369. .toast.success {
  370. background: #4CAF50;
  371. }
  372. .toast.error {
  373. background: #F44336;
  374. }
  375. .toast.info {
  376. background: #2196F3;
  377. }
  378. /* 清空按钮样式 */
  379. .clear-btn {
  380. position: absolute;
  381. right: 12px;
  382. top: 50%;
  383. transform: translateY(-50%);
  384. width: 16px;
  385. height: 16px;
  386. background-color: #999;
  387. border-radius: 50%;
  388. display: flex;
  389. align-items: center;
  390. justify-content: center;
  391. cursor: pointer;
  392. transition: background-color 0.2s;
  393. }
  394. .clear-btn:hover {
  395. background-color: #666;
  396. }
  397. .clear-x {
  398. position: relative;
  399. width: 8px;
  400. height: 8px;
  401. }
  402. .clear-x:before, .clear-x:after {
  403. content: '';
  404. position: absolute;
  405. width: 8px;
  406. height: 2px;
  407. background-color: white;
  408. top: 3px;
  409. left: 0;
  410. }
  411. .clear-x:before {
  412. transform: rotate(45deg);
  413. }
  414. .clear-x:after {
  415. transform: rotate(-45deg);
  416. }
  417. </style>
  418. </head>
  419. <body class="container FlexRow">
  420. <div id="app" class="main00 FlexColumn">
  421. <div class="ListTop FlexRow">
  422. <div class="ListTop3 FlexRow">
  423. <div class="title CursorPointer">学校信息管理</div>
  424. </div>
  425. </div>
  426. <div class="main0 FlexRow" style="height: calc(100% - 60px);">
  427. <!-- 左侧学校列表 -->
  428. <div class="school-list FlexColumn">
  429. <div class="search-box FlexRow">
  430. <div style="position: relative;">
  431. <input type="text" class="search-input" v-model="searchText" @input="debounceSearch"
  432. @keyup.enter="searchSchools" placeholder="输入学校名称搜索...">
  433. <div class="clear-btn" v-show="searchText" @click="clearSearch">
  434. <span class="clear-x"></span>
  435. </div>
  436. </div>
  437. <div class="btn33 btn31 btn FlexRow" @click="searchSchools">
  438. <img title="搜索" alt="搜索"
  439. src="https://kylx365-1253256735.file.myqcloud.com/web/universalpic_search_gray_30x30.png"
  440. style="width: 20px; height: 20px;" />
  441. </div>
  442. </div>
  443. <div class="school-list-scrollable">
  444. <div class="district-list">
  445. <div class="district-item" v-for="district in districts">
  446. <div class="district-name FlexRow" @click="toggleDistrict(district)">
  447. <div class="flex-1">{{ district.id }} {{ district.name }} <template v-if="district.count">({{
  448. district.count
  449. }})</template></div>
  450. <div class="district-icon">
  451. </div>
  452. </div>
  453. <transition name="slide">
  454. <div v-show="district.isOpen" class="school-items">
  455. <!-- 高中部分 -->
  456. <div class="school-category"
  457. v-if="district.highSchools && district.highSchools.length > 0">
  458. <div class="category-title">高中</div>
  459. <div class="category-schools">
  460. <div class="school-item" v-for="school in district.highSchools"
  461. :class="{ active: selectedSchool && selectedSchool.ID === school.ID }"
  462. @click="selectSchool(school)">
  463. <span class="school-id">{{ school.ID }}</span>
  464. {{ school.SchoolFullName }}
  465. </div>
  466. </div>
  467. </div>
  468. <!-- 初中部分 -->
  469. <div class="school-category"
  470. v-if="district.middleSchools && district.middleSchools.length > 0">
  471. <div class="category-title">初中</div>
  472. <div class="category-schools">
  473. <div class="school-item" v-for="school in district.middleSchools"
  474. :class="{ active: selectedSchool && selectedSchool.ID === school.ID }"
  475. @click="selectSchool(school)">
  476. <span class="school-id">{{ school.ID }}</span>
  477. {{ school.SchoolFullName }}
  478. </div>
  479. </div>
  480. </div>
  481. </div>
  482. </transition>
  483. </div>
  484. </div>
  485. </div>
  486. </div>
  487. <!-- 右侧学校详情 -->
  488. <div class="school-detail FlexColumn" v-if="!selectedSchool">
  489. <div style="font-size:36px;margin-top: 340px;">欢迎使用学校信息管理平台</div>
  490. </div>
  491. <div class="school-detail FlexColumn" v-if="selectedSchool">
  492. <form @submit.prevent="saveSchool">
  493. <!-- 基本信息 -->
  494. <div class="form-sections FlexRow" style="margin: 0 -12px;">
  495. <!-- 第一列 -->
  496. <div class="form-column" style="flex: 1; padding: 0 12px;">
  497. <div class="form-section">
  498. <div class="form-section-title">基本信息</div>
  499. <div class="form-row">
  500. <div class="form-col">
  501. <div class="form-group">
  502. <label class="form-label">学校ID</label>
  503. <input type="text" class="form-input" v-model="selectedSchool.ID" readonly>
  504. </div>
  505. </div>
  506. <div class="form-col-2">
  507. <div class="form-group">
  508. <label class="form-label">学校全称</label>
  509. <input type="text" class="form-input"
  510. v-model="selectedSchool.SchoolFullName">
  511. </div>
  512. </div>
  513. </div>
  514. <div class="form-row">
  515. <div class="form-col">
  516. <div class="form-group">
  517. <label class="form-label">学校简称</label>
  518. <input type="text" class="form-input"
  519. v-model="selectedSchool.SchoolShortName">
  520. </div>
  521. </div>
  522. <div class="form-col">
  523. <div class="form-group">
  524. <label class="form-label">其他名称</label>
  525. <input type="text" class="form-input"
  526. v-model="selectedSchool.SchoolOtherName">
  527. </div>
  528. </div>
  529. <div class="form-col">
  530. <div class="form-group">
  531. <label class="form-label">招生代码</label>
  532. <input type="text" class="form-input" v-model="selectedSchool.SchoolNumber">
  533. </div>
  534. </div>
  535. </div>
  536. <div class="form-row">
  537. <div class="form-col">
  538. <div class="form-group">
  539. <label class="form-label">拼音首字母</label>
  540. <input type="text" class="form-input" v-model="selectedSchool.Pinyin">
  541. </div>
  542. </div>
  543. <div class="form-col-2">
  544. <div class="form-group">
  545. <label class="form-label">有初高中同名(对应ID)</label>
  546. <input type="text" class="form-input" v-model="selectedSchool.HasSameName">
  547. </div>
  548. </div>
  549. </div>
  550. <div class="form-row">
  551. <div class="form-col">
  552. <div class="form-group">
  553. <label class="form-label">住宿情况</label>
  554. <select class="form-select" v-model="selectedSchool.Accommodation">
  555. <option value="">未知</option>
  556. <option value="全部寄宿">全部寄宿</option>
  557. <option value="部分寄宿">部分寄宿</option>
  558. <option value="无寄宿">无寄宿</option>
  559. </select>
  560. </div>
  561. </div>
  562. <div class="form-col-2">
  563. <div class="form-group">
  564. <label class="form-label">住宿情况说明</label>
  565. <input type="text" class="form-input"
  566. v-model="selectedSchool.AccommodationRemark">
  567. </div>
  568. </div>
  569. </div>
  570. <div class="form-row">
  571. <div class="form-col-3">
  572. <div class="form-group">
  573. <label class="form-label">收费标准</label>
  574. <textarea class="form-textarea" v-model="selectedSchool.Fees"></textarea>
  575. </div>
  576. </div>
  577. </div>
  578. <div class="form-row">
  579. <div class="form-col">
  580. <div class="form-group">
  581. <label class="form-label">学校类型</label>
  582. <input type="text" class="form-input" v-model="selectedSchool.SchoolType1"
  583. readonly>
  584. </div>
  585. </div>
  586. <div class="form-col">
  587. <div class="form-group">
  588. <label class="form-label">学校性质</label>
  589. <select class="form-select" v-model="selectedSchool.PublicOrPrivate">
  590. <option value="">未知</option>
  591. <option value="公办">公办</option>
  592. <option value="民办">民办</option>
  593. <option value="中外合作">中外合作</option>
  594. </select>
  595. </div>
  596. </div>
  597. <div class="form-col">
  598. <div class="form-group">
  599. <label class="form-label">详细类型</label>
  600. <input type="text" class="form-input" v-model="selectedSchool.SchoolType2"
  601. readonly>
  602. </div>
  603. </div>
  604. </div>
  605. </div>
  606. </div>
  607. <!-- 第二列 -->
  608. <div class="form-column" style="flex: 1; padding: 0 12px;">
  609. <!-- 地理信息 -->
  610. <div class="form-section">
  611. <div class="form-section-title">地理信息</div>
  612. <div class="form-row">
  613. <div class="form-col">
  614. <div class="form-group">
  615. <label class="form-label">所属区</label>
  616. <input type="text" class="form-input" v-model="selectedSchool.District"
  617. readonly>
  618. </div>
  619. </div>
  620. <div class="form-col-2">
  621. <div class="form-group">
  622. <label class="form-label">经纬度坐标</label>
  623. <input type="text" class="form-input" v-model="selectedSchool.Coordinates">
  624. </div>
  625. </div>
  626. </div>
  627. <div class="form-row">
  628. <div class="form-col-3">
  629. <div class="form-group">
  630. <label class="form-label">详细地址</label>
  631. <input type="text" class="form-input" v-model="selectedSchool.Address">
  632. </div>
  633. </div>
  634. </div>
  635. </div>
  636. <!-- 联系信息 -->
  637. <div class="form-section">
  638. <div class="form-section-title">联系信息</div>
  639. <div class="form-row">
  640. <div class="form-col-4">
  641. <div class="form-group">
  642. <label class="form-label">招生电话(逗号分隔)</label>
  643. <input type="text" class="form-input" v-model="selectedSchool.Phone1">
  644. </div>
  645. </div>
  646. <div class="form-col-4">
  647. <div class="form-group">
  648. <label class="form-label">招生电话(国际课程班)</label>
  649. <input type="text" class="form-input" v-model="selectedSchool.Phone2">
  650. </div>
  651. </div>
  652. </div>
  653. <div class="form-row">
  654. <div class="form-col-3">
  655. <div class="form-group">
  656. <label class="form-label">学校网址</label>
  657. <input type="text" class="form-input" v-model="selectedSchool.Website">
  658. </div>
  659. </div>
  660. </div>
  661. <div class="form-row">
  662. <div class="form-col-3">
  663. <div class="form-group">
  664. <label class="form-label">联系时间</label>
  665. <input type="text" class="form-input" v-model="selectedSchool.ContactTime">
  666. </div>
  667. </div>
  668. </div>
  669. </div>
  670. </div>
  671. <!-- 第三列 -->
  672. <div class="form-column" style="flex: 1; padding: 0 12px;">
  673. <!-- 其他信息 -->
  674. <div class="form-section">
  675. <div class="form-section-title">其他信息</div>
  676. <div class="form-row">
  677. <div class="form-col-3">
  678. <div class="form-group">
  679. <label class="form-label">学校简介</label>
  680. <textarea class="form-textarea"
  681. v-model="selectedSchool.Introduction"></textarea>
  682. </div>
  683. </div>
  684. </div>
  685. <div class="form-row">
  686. <div class="form-col-3">
  687. <div class="form-group">
  688. <label class="form-label">美育特色介绍</label>
  689. <textarea class="form-textarea"
  690. v-model="selectedSchool.Introduction2"></textarea>
  691. </div>
  692. </div>
  693. </div>
  694. <div class="form-row">
  695. <div class="form-col-3">
  696. <div class="form-group">
  697. <label class="form-label">备注</label>
  698. <textarea class="form-textarea" v-model="selectedSchool.Remark"></textarea>
  699. </div>
  700. </div>
  701. </div>
  702. </div>
  703. <div class="btn-group">
  704. <button type="button" class="btn btn-default" @click="resetForm">重置表单</button>
  705. <button type="submit" class="btn btn-primary">保存</button>
  706. </div>
  707. </form>
  708. </div>
  709. </div>
  710. <div class="toast" :class="{ show: showToastFlag, [toastType]: showToastFlag }">{{ toastMessage }}</div>
  711. <script>
  712. // 区域数据
  713. const arrDistrict = [{
  714. ID: "01",
  715. Name: "黄浦区",
  716. Count: ""
  717. },
  718. {
  719. ID: "02",
  720. Name: "徐汇区",
  721. Count: ""
  722. },
  723. {
  724. ID: "03",
  725. Name: "长宁区",
  726. Count: ""
  727. },
  728. {
  729. ID: "04",
  730. Name: "静安区",
  731. Count: ""
  732. },
  733. {
  734. ID: "05",
  735. Name: "普陀区",
  736. Count: ""
  737. },
  738. {
  739. ID: "06",
  740. Name: "虹口区",
  741. Count: ""
  742. },
  743. {
  744. ID: "07",
  745. Name: "杨浦区",
  746. Count: ""
  747. },
  748. {
  749. ID: "08",
  750. Name: "闵行区",
  751. Count: ""
  752. },
  753. {
  754. ID: "09",
  755. Name: "宝山区",
  756. Count: ""
  757. },
  758. {
  759. ID: "10",
  760. Name: "嘉定区",
  761. Count: ""
  762. },
  763. {
  764. ID: "11",
  765. Name: "浦东新区",
  766. Count: ""
  767. },
  768. {
  769. ID: "12",
  770. Name: "金山区",
  771. Count: ""
  772. },
  773. {
  774. ID: "13",
  775. Name: "松江区",
  776. Count: ""
  777. },
  778. {
  779. ID: "14",
  780. Name: "青浦区",
  781. Count: ""
  782. },
  783. {
  784. ID: "15",
  785. Name: "奉贤区",
  786. Count: ""
  787. },
  788. {
  789. ID: "16",
  790. Name: "崇明区",
  791. Count: ""
  792. }];
  793. new Vue({
  794. el: '#app',
  795. data: {
  796. searchText: '',
  797. districts: [],
  798. selectedSchool: null,
  799. originalSchool: null,
  800. searchTimeout: null,
  801. districtID: '',
  802. arrDistrict: arrDistrict,
  803. toastMessage: '',
  804. toastType: 'info',
  805. showToastFlag: false
  806. },
  807. methods: {
  808. // 清空搜索
  809. clearSearch() {
  810. this.searchText = '';
  811. this.loadDistricts();
  812. },
  813. // 搜索学校
  814. searchSchools() {
  815. // 如果搜索框为空,恢复所有学校显示
  816. if (!this.searchText.trim()) {
  817. this.loadDistricts();
  818. return;
  819. }
  820. const keyword = this.searchText.trim();
  821. // 使用提供的接口搜索学校
  822. fetch(`/api/GetMPSSchool?RowCount=20&Key=${keyword}`)
  823. .then(response => response.json())
  824. .then(data => {
  825. data = data.result;
  826. if (data && data.length > 0) {
  827. // 将搜索结果按区域分组
  828. const districtMap = {};
  829. data.forEach(school => {
  830. if (!districtMap[school.District]) {
  831. districtMap[school.District] = {
  832. id: school.DistrictID,
  833. name: school.District,
  834. count: 0,
  835. schools: [],
  836. highSchools: [],
  837. middleSchools: [],
  838. isOpen: true
  839. };
  840. }
  841. districtMap[school.District].schools.push(school);
  842. // 按学校类型分类
  843. if (school.SchoolType1 === '高中' || school.SchoolType2?.includes('高中')) {
  844. districtMap[school.District].highSchools.push(school);
  845. } else if (school.SchoolType1 === '初中' ||
  846. (school.SchoolType2 === '初中' && !school.SchoolType2?.includes('高中'))) {
  847. districtMap[school.District].middleSchools.push(school);
  848. }
  849. districtMap[school.District].count = districtMap[school.District].schools.length;
  850. });
  851. this.districts = Object.values(districtMap);
  852. } else {
  853. this.showToast('未找到匹配的学校', 'info');
  854. }
  855. })
  856. .catch(error => {
  857. console.error('搜索学校时出错:', error);
  858. alert('搜索失败,请稍后重试');
  859. });
  860. },
  861. // 防抖搜索
  862. debounceSearch() {
  863. if (this.searchTimeout) {
  864. clearTimeout(this.searchTimeout);
  865. }
  866. this.searchTimeout = setTimeout(() => {
  867. this.searchSchools();
  868. }, 500);
  869. },
  870. // 切换区域展开/折叠状态
  871. toggleDistrict(district) {
  872. // 如果展开且该区域下还没有加载学校数据,则加载
  873. if (!district.schools || district.schools.length === 0) {
  874. this.loadSchoolsByDistrict(district);
  875. }
  876. else {
  877. district.isOpen = !district.isOpen;
  878. }
  879. },
  880. // 加载特定区域下的学校
  881. loadSchoolsByDistrict(district) {
  882. fetch(`/api/GetMPSSchool?Usage=web&DistrictID=${district.id}`)
  883. .then(response => response.json())
  884. .then(data => {
  885. data = data.result;
  886. if (data && data.length > 0) {
  887. // 将学校按类型分类
  888. district.highSchools = data.filter(school =>
  889. school.SchoolType1 === '高中' ||
  890. school.SchoolType2?.includes('高中')
  891. );
  892. district.middleSchools = data.filter(school =>
  893. school.SchoolType1 === '初中' ||
  894. (school.SchoolType2 === '初中' && !school.SchoolType2?.includes('高中'))
  895. );
  896. // 保持原有的schools数组,以保持兼容性
  897. district.schools = data;
  898. } else {
  899. district.highSchools = [];
  900. district.middleSchools = [];
  901. district.schools = [];
  902. }
  903. district.isOpen = !district.isOpen;
  904. district.count = data.length
  905. })
  906. .catch(error => {
  907. console.error(`加载${district.name}区域学校数据时出错:`, error);
  908. district.highSchools = [];
  909. district.middleSchools = [];
  910. district.schools = [];
  911. });
  912. },
  913. // 选择学校
  914. selectSchool(school) {
  915. // 如果已经选择了该学校,不需要重新加载
  916. if (this.selectedSchool && this.selectedSchool.ID === school.ID) {
  917. return;
  918. }
  919. // 显示加载状态
  920. this.selectedSchool = { ...school, loading: true };
  921. // 调用API获取详细的学校信息
  922. fetch(`/api/GetMPSSchoolInfo?Usage=web&SchoolID=${school.ID}`)
  923. .then(response => response.json())
  924. .then(data => {
  925. if (data && data.result) {
  926. // 处理API返回的数据
  927. const schoolData = { ...data.result };
  928. // 处理详细类型(SchoolType2)
  929. const validSchoolTypes = [
  930. "",
  931. "市实验性示范性高中",
  932. "享受市实验性示范性高中招生政策高中",
  933. "区实验性示范性高中 (市特色普通高中)",
  934. "区实验性示范性高中",
  935. "一般高中"
  936. ];
  937. // 如果SchoolType2不在有效选项中,设置为未知
  938. if (!validSchoolTypes.includes(schoolData.SchoolType2)) {
  939. schoolData.SchoolType2 = ""; // 设置为未知
  940. }
  941. // 处理学校性质(PublicOrPrivate)
  942. const validPublicOrPrivate = ["", "公办", "民办", "中外合作"];
  943. if (!validPublicOrPrivate.includes(schoolData.PublicOrPrivate)) {
  944. schoolData.PublicOrPrivate = ""; // 如果值无效,设置为"未知"
  945. }
  946. // 处理住宿情况(Accommodation)
  947. const validAccommodations = ["", "全部寄宿", "部分寄宿", "无寄宿"];
  948. if (!validAccommodations.includes(schoolData.Accommodation)) {
  949. schoolData.Accommodation = ""; // 如果值无效,设置为"未知"
  950. }
  951. this.selectedSchool = schoolData;
  952. this.originalSchool = { ...schoolData };
  953. } else {
  954. // 如果API没有返回有效数据,则使用列表中的基本信息,并设置默认值
  955. const schoolData = { ...school };
  956. // 处理详细类型,如果不是有效值则设为"未知"
  957. const validSchoolTypes = [
  958. "",
  959. "市实验性示范性高中",
  960. "享受市实验性示范性高中招生政策高中",
  961. "区实验性示范性高中 (市特色普通高中)",
  962. "区实验性示范性高中",
  963. "一般高中"
  964. ];
  965. schoolData.SchoolType2 = validSchoolTypes.includes(schoolData.SchoolType2) ?
  966. schoolData.SchoolType2 : "";
  967. // 处理住宿情况,如果不是有效值则设为"未知"
  968. const validAccommodations = ["", "全部寄宿", "部分寄宿", "无寄宿"];
  969. schoolData.Accommodation = validAccommodations.includes(schoolData.Accommodation) ?
  970. schoolData.Accommodation : "";
  971. this.selectedSchool = schoolData;
  972. this.originalSchool = { ...schoolData };
  973. console.warn('未能获取到学校详细信息,使用基本信息显示');
  974. }
  975. })
  976. .catch(error => {
  977. console.error('获取学校详细信息时出错:', error);
  978. // 出错时使用列表中的基本信息
  979. this.selectedSchool = { ...school };
  980. this.originalSchool = { ...school };
  981. this.showToast('获取学校详细信息失败,请稍后重试', 'error');
  982. });
  983. },
  984. // 显示Toast通知
  985. showToast(message, type = 'info') {
  986. this.toastMessage = message;
  987. this.toastType = type;
  988. this.showToastFlag = true;
  989. // 自动隐藏
  990. setTimeout(() => {
  991. this.showToastFlag = false;
  992. }, 3000);
  993. },
  994. // 保存学校信息
  995. saveSchool() {
  996. if (!this.selectedSchool || !this.originalSchool) return;
  997. // 只收集修改过的字段
  998. const changedFields = {};
  999. const fieldsToCheck = [
  1000. 'SchoolFullName', 'SchoolShortName', 'SchoolOtherName', 'SchoolNumber',
  1001. 'Pinyin', 'HasSameName', 'Accommodation', 'AccommodationRemark',
  1002. 'Fees', 'SchoolType1', 'PublicOrPrivate', 'SchoolType2',
  1003. 'Coordinates', 'Address', 'Phone1', 'Phone2',
  1004. 'Website', 'ContactTime', 'Introduction', 'Introduction2', 'Remark'
  1005. ];
  1006. fieldsToCheck.forEach(field => {
  1007. if (this.selectedSchool[field] !== this.originalSchool[field]) {
  1008. changedFields[field] = this.selectedSchool[field];
  1009. }
  1010. });
  1011. // 确保ID字段始终包含
  1012. changedFields.ID = this.selectedSchool.ID;
  1013. // 如果没有字段被修改,不提交
  1014. if (Object.keys(changedFields).length <= 1) {
  1015. this.showToast('没有修改任何内容', 'info');
  1016. return;
  1017. }
  1018. // 提交修改过的字段
  1019. fetch('/api/SaveMPSSchool', {
  1020. method: 'POST',
  1021. headers: {
  1022. 'Content-Type': 'application/json'
  1023. },
  1024. body: JSON.stringify(changedFields)
  1025. })
  1026. .then(response => response.json())
  1027. .then(data => {
  1028. if (data && data.errcode == 10000) {
  1029. this.showToast('保存成功', 'success');
  1030. this.originalSchool = { ...this.selectedSchool };
  1031. // 更新列表中的学校名称
  1032. this.districts.forEach(district => {
  1033. // 更新schools数组中的学校名称
  1034. if (district.schools) {
  1035. district.schools.forEach(school => {
  1036. if (school.ID === this.selectedSchool.ID) {
  1037. school.SchoolFullName = this.selectedSchool.SchoolFullName;
  1038. }
  1039. });
  1040. }
  1041. // 更新highSchools数组中的学校名称
  1042. if (district.highSchools) {
  1043. district.highSchools.forEach(school => {
  1044. if (school.ID === this.selectedSchool.ID) {
  1045. school.SchoolFullName = this.selectedSchool.SchoolFullName;
  1046. }
  1047. });
  1048. }
  1049. // 更新middleSchools数组中的学校名称
  1050. if (district.middleSchools) {
  1051. district.middleSchools.forEach(school => {
  1052. if (school.ID === this.selectedSchool.ID) {
  1053. school.SchoolFullName = this.selectedSchool.SchoolFullName;
  1054. }
  1055. });
  1056. }
  1057. });
  1058. console.log('学校信息更新完成');
  1059. } else {
  1060. alert('保存失败,请稍后重试');
  1061. }
  1062. })
  1063. .catch(error => {
  1064. console.error('保存学校信息时出错:', error);
  1065. alert('保存失败,请稍后重试');
  1066. });
  1067. },
  1068. // 重置表单
  1069. resetForm() {
  1070. if (this.originalSchool) {
  1071. this.selectedSchool = { ...this.originalSchool };
  1072. }
  1073. },
  1074. // 加载所有区域
  1075. loadDistricts() {
  1076. // 直接使用arrDistrict数据
  1077. this.districts = arrDistrict.map(district => ({
  1078. id: district.ID,
  1079. name: district.Name,
  1080. count: district.Count,
  1081. isOpen: false,
  1082. schools: [] // 初始为空,点击展开时加载
  1083. }));
  1084. }
  1085. },
  1086. mounted() {
  1087. // 初始化加载区域数据
  1088. this.loadDistricts();
  1089. }
  1090. });
  1091. </script>
  1092. </body>
  1093. </html>