row.id || i}
+ dataSource={dataSource}
+ columns={columns}
+ pagination={false}
+ onRow={handleRow}
+ rowSelection={rowSelection}
+ expandedRowRender={expandedRowRender}
+ expandIconColumnIndex={expandIconColumnIndex}
+ expandIconAsCell={expandIconAsCell}
+ scroll={scroll}
+ />
+ {total > 10 && (!pagination) &&
+ }
+
+
+ )
+}
diff --git a/src/military/components/paginationTable/index.scss b/src/military/components/paginationTable/index.scss
new file mode 100644
index 00000000..af8420b1
--- /dev/null
+++ b/src/military/components/paginationTable/index.scss
@@ -0,0 +1,39 @@
+.pagination-table {
+ .ant-table {
+ border: 1px solid #ececec;
+ border-radius: 0 0 4px 4px;
+ }
+ .ant-table-thead tr th div {
+ color: #181818;
+ font-weight: 500;
+ }
+ .ant-table-wrapper {
+ ::-webkit-scrollbar {
+ width: 5px;
+ height: 5px;
+ }
+ .ant-table-hide-scrollbar {
+ margin-bottom: -5px;
+ overflow-y: hidden !important;
+ ::-webkit-scrollbar {
+ width: 5px;
+ height: 5px;
+ }
+ }
+ }
+
+ .ant-table-thead > tr > th, .ant-table-tbody > tr > td{
+ padding: 14px 8px;
+ }
+
+ .ant-pagination {
+ margin-top: 1.25rem;
+ text-align: right;
+ }
+
+ // .ant-table-row-cell-break-word{
+ // .ant-btn{
+ // display: inline-block;
+ // }
+ // }
+}
diff --git a/src/military/components/sortBox/index.scss b/src/military/components/sortBox/index.scss
index f3e8d0e9..3c6ae1c4 100644
--- a/src/military/components/sortBox/index.scss
+++ b/src/military/components/sortBox/index.scss
@@ -12,14 +12,14 @@
background-color: #fff;
&:hover {
background-color: #fff;
- color: #409eff;
+ color: #4154f1;
cursor: pointer;
}
}
.sort-item-checked {
- // background-color: #409eff;
+ // background-color: #4154f1;
// color: #fff;
- color: #409eff;
+ color: #4154f1;
}
.caret-up-down {
display: inline-flex;
@@ -29,7 +29,7 @@
color:#ccc;
}
.caret-checked{
- color: #409eff;
+ color: #4154f1;
}
.anticon-caret-up{
margin-bottom: -.15em;
diff --git a/src/military/components/statusNav/index.scss b/src/military/components/statusNav/index.scss
index ea87ad32..326d32ca 100644
--- a/src/military/components/statusNav/index.scss
+++ b/src/military/components/statusNav/index.scss
@@ -11,11 +11,11 @@
padding: 3px 15px;
cursor: pointer;
&:hover {
- color: #4cacff;
+ color: #4154f1;
}
}
.status-item-checked {
background: #f7f7f7;
- color: #4cacff ;
+ color: #4154f1 ;
}
diff --git a/src/military/expert.js b/src/military/expert.js
new file mode 100644
index 00000000..c338755d
--- /dev/null
+++ b/src/military/expert.js
@@ -0,0 +1,83 @@
+import React, { useEffect, useState } from "react";
+
+import { Route, Switch } from "react-router-dom";
+import { withRouter } from "react-router";
+import { SnackbarHOC } from "educoder";
+import { CNotificationHOC } from "../modules/courses/common/CNotificationHOC";
+import { TPMIndexHOC } from "../modules/tpm/TPMIndexHOC";
+import Loadable from "react-loadable";
+import Loading from "../Loading";
+import { getUserInfo } from './expert/api';
+import { ImageLayerOfCommentHOC } from "../modules/page/layers/ImageLayerOfCommentHOC";
+import './index.scss';
+
+const Review = Loadable({
+ loader: () => import("./expert/review/review"),
+ loading: Loading,
+});
+
+const AdminRouter = Loadable({
+ loader: () => import("./expert/adminRouter"),
+ loading: Loading,
+});
+
+// const ReviewTasks = Loadable({
+// loader: () => import("./expert/reviewTasks"),
+// loading: Loading,
+// })
+const ExpertUser = Loadable({
+ loader: () => import("./expert/expertUser"),
+ loading: Loading,
+})
+const Expert = (propsTransmit) => {
+
+ // 开发时,从代理的位置获取用户信息
+ const [currentUser, setCurrentUser] = useState(propsTransmit.current_user);
+ // const isDev = window.location.href.indexOf('3007') > -1 ? true : false;
+ useEffect(() => {
+ getUserInfo().then(res => {
+ if (res && res.data) {
+ setCurrentUser(res.data);
+ }
+ })
+ }, []);
+ let propsF = { ...propsTransmit };
+ propsF.current_user = {...propsF.current_user,...currentUser};
+
+ return (
+
+
+ {/* 专家注册、专家评审任务 */}
+ (
+
+ )}
+ >
+
+ {/* 管理员管理 */}
+ (
+
+ )}
+ >
+ (
+
+ )}
+ >
+
+
+
+
+ );
+}
+
+export default withRouter(
+ ImageLayerOfCommentHOC({
+ imgSelector: ".imageLayerParent img, .imageLayerParent .imageTarget",
+ parentSelector: ".newMain",
+ })(CNotificationHOC()(SnackbarHOC()(TPMIndexHOC(Expert))))
+);
diff --git a/src/military/expert/adminRouter.js b/src/military/expert/adminRouter.js
new file mode 100644
index 00000000..61d467f9
--- /dev/null
+++ b/src/military/expert/adminRouter.js
@@ -0,0 +1,92 @@
+import React from "react";
+
+import { Route, Switch } from "react-router-dom";
+import Loadable from "react-loadable";
+import Loading from "../../Loading";
+import AdminRouter from "../components/adminRouter";
+
+// 专家库
+const ExpertList = Loadable({
+ loader: () => import("./expertList"),
+ loading: Loading,
+});
+// 专家审核
+const RegisterList = Loadable({
+ loader: () => import("./registerList"),
+ loading: Loading,
+});
+//创客任务评审规则
+const ReviewRules = Loadable({
+ loader : () => import("./reviewRules"),
+ loading: Loading,
+});
+//创客任务选择评审专家
+const SelectExpert = Loadable({
+ loader: () => import("./selectExpert"),
+ loading: Loading,
+});
+//创客任务评审结果查看
+const ReviewResult = Loadable({
+ loader: () => import("./reviewResult"),
+ loading: Loading,
+});
+//竞赛评审任务列表
+const CompetitionList = Loadable({
+ loader: () => import("./competionList"),
+ loading: Loading,
+})
+
+const AdminPage = (propsF) => {
+
+ return (
+
+
+
+ {/* 专家审核 */}
+ (
+
+ )}
+ >
+ {/* 专家库列表 */}
+ (
+
+ )}
+ >
+ {/* 创客任务评审规则 */}
+ (
+
+ )}
+ >
+ {/* 创客任务选择评审专家 */}
+ (
+
+ )}
+ >
+ {/* 创客任务评审结果查看 */}
+ (
+
+ )}
+ >
+ {/* 竞赛评审任务列表 */}
+ (
+
+ )}
+ >
+
+
+ );
+}
+// }
+export default AdminPage;
diff --git a/src/military/expert/api.js b/src/military/expert/api.js
new file mode 100644
index 00000000..183956b4
--- /dev/null
+++ b/src/military/expert/api.js
@@ -0,0 +1,256 @@
+import fetch,{main_web_site_url} from './fetch';
+import { notification } from 'antd';
+
+// 专家列表查询
+export async function expertList(params) {
+ let res = await fetch({
+ url: '/api/experts/',
+ method: 'get',
+ params,
+ });
+ if (res.data) {
+ return res.data;
+ } else {
+ notification.open({
+ message: "提示",
+ description: res.message || '请求错误',
+ });
+ }
+}
+
+//删除专家
+export function deleteExpert(expertId) {
+ return fetch({
+ url: `/api/experts/${expertId}?isDelete=1`,
+ method: 'delete'
+ });
+}
+
+// 获取用户信息
+export function getUserInfo() {
+ return fetch({
+ url: '/user/getUserInfo',
+ method: 'get'
+ });
+}
+
+// 查看当前登录用户专家信息
+export function getCurrentExpert(params) {
+ return fetch({
+ url: '/api/experts/getCurrentExpert',
+ method: 'get',
+ params
+ });
+}
+
+//专家注册
+export async function expertRegister(data){
+ let res = await fetch({
+ url: '/api/experts/register',
+ method: 'post',
+ data,
+ });
+ return res;
+}
+
+//更新专家信息
+export async function expertUpdate(data){
+ let res = await fetch({
+ url: '/api/experts/',
+ method: 'put',
+ data,
+ });
+ return res;
+}
+
+//管理员审核专家信息
+export async function registerCheck(data){
+ let res = await fetch({
+ url: '/api/experts/adminCheckExpert',
+ method: 'post',
+ data,
+ });
+ return res;
+}
+
+// 获取文件信息
+export function getFile(id) {
+ return fetch({
+ url: `/busiAttachments/${id}`,
+ method: 'get'
+ });
+}
+
+// 获取评审任务列表
+export function getExpertTasks(params) {
+ return fetch({
+ url: `/api/taskExpert/getExpertTasksPageList`,
+ method: 'get',
+ params,
+ });
+}
+
+// 获取竞赛作品列表
+export function getCompetition(id) {
+ return fetch({
+ url: `${main_web_site_url}/api/v1/competitions/${id}/works`,
+ method: 'get',
+ });
+}
+
+// 获取竞赛详情接口
+export function getCompetitionDetail(id) {
+ return fetch({
+ url: `${main_web_site_url}/api/v1/competitions/${id}`,
+ method: 'get',
+ });
+}
+
+// 查看竞赛/任务的评分细则
+export function getScoringDetails(params) {
+ return fetch({
+ url: `/api/expertScoringDetails/getExpertScoringDetailsList`,
+ method: 'get',
+ params,
+ });
+}
+
+// 查看最终得分排行
+export function getFinalScoreRankingList(params) {
+ return fetch({
+ url: `/api/expertScoringDetails/getFinalScoreRankingList`,
+ method: 'get',
+ params,
+ });
+}
+
+// 查看单个竞赛/任务的所有评分细则
+export function getOpsScoringDetails(params) {
+ return fetch({
+ url: `/api/expertScoringDetails/getOpsExpertScoringDetailsList`,
+ method: 'get',
+ params,
+ });
+}
+
+// 初始化评分细则
+export function initScoringDetails(data){
+ return fetch({
+ url: '/api/expertScoringDetails/initExpertScoringDetails',
+ method: 'post',
+ data,
+ })
+}
+
+// 更新评分细则
+export function updateScoringDetails(data){
+ return fetch({
+ url: '/api/expertScoringDetails/',
+ method: 'put',
+ data,
+ });
+}
+
+//评选胜出者和公示者
+export function selectWinnersAndPublicists(data){
+ return fetch({
+ url: '/api/expertScoringDetails/selectWinnersAndPublicists',
+ method: 'post',
+ data,
+ });
+}
+
+//查看胜出者和公示名单
+export function getWinnersAndPublicists(params) {
+ return fetch({
+ url: `/api/expertScoringDetails/getWinnersAndPublicists`,
+ method: 'get',
+ params,
+ });
+}
+
+//获取创客任务评审规则
+export async function getRules(params){
+ let response = await fetch({
+ url: `/api/taskRuleCriteria/getRuleAndCriteria`,
+ method: 'get',
+ params
+ });
+ if(response && response.message === "success"){
+ let criterias = [];
+ response.data.criteriaOne && (criterias[criterias.length] = (criterias.length+1)+"、"+response.data.criteriaOne);
+ response.data.criteriaTwo && (criterias[criterias.length] = (criterias.length+1)+"、"+response.data.criteriaTwo);
+ response.data.criteriaThree && (criterias[criterias.length] = (criterias.length+1)+"、"+response.data.criteriaThree);
+ response.data.criteriaFour && (criterias[criterias.length] = (criterias.length+1)+"、"+response.data.criteriaFour);
+ response.data.criteriaFive && (criterias[criterias.length] = (criterias.length+1)+"、"+response.data.criteriaFive);
+ response.data.criterias = criterias;
+ response.data.reviewData = response.data.reviewStartOn.substring(0,response.data.reviewStartOn.length-3) + " ~ " + response.data.reviewEndOn.substring(0,response.data.reviewEndOn.length-3)
+ }
+ return response;
+}
+
+//编辑评审规则(第一次)
+export async function editRules(data){
+ let res = await fetch({
+ url: '/api/taskRuleCriteria/editRuleAndCriteria',
+ method: 'post',
+ data,
+ });
+ return res;
+}
+
+//更新评审规则(第一次)
+export async function updateRules(data){
+ let res = await fetch({
+ url: '/api/taskRuleCriteria/',
+ method: 'put',
+ data,
+ });
+ return res;
+}
+
+//为创客任务添加评审专家
+export async function assignExperts(data){
+ let res = await fetch({
+ url: '/api/taskExpert/assignExperts',
+ method: 'post',
+ data,
+ });
+ return res;
+}
+
+//删除指派专家
+export function deleteExperts(taskExpertId,isDelete) {
+ console.log('taskExpertId',taskExpertId,'isDelete',isDelete);
+ return fetch({
+ url: `/api/taskExpert/${taskExpertId}?isDelete=${isDelete}`,
+ method: 'delete'
+ });
+}
+
+//已选专家列表
+export function selectExpertList(params) {
+ return fetch({
+ url: `/api/taskExpert/selectedExpertPageList`,
+ method: 'get',
+ params
+ });
+}
+
+//竞赛任务列表
+export function getCompetitionList(params) {
+ return fetch({
+ url: `/api/competitionExpert/getCompetitionList`,
+ method: 'get',
+ params
+ });
+}
+
+// 修改竞赛是否加入专家评审流程
+export function updateCompetitionReview(data) {
+ return fetch({
+ url: `${main_web_site_url}/api/v1/competitions/update_expert_audit`,
+ method: 'post',
+ data,
+ });
+}
\ No newline at end of file
diff --git a/src/military/expert/competionList/index.jsx b/src/military/expert/competionList/index.jsx
new file mode 100644
index 00000000..c9ff51b5
--- /dev/null
+++ b/src/military/expert/competionList/index.jsx
@@ -0,0 +1,385 @@
+import { Button, message, Modal, Select, Tooltip } from "antd";
+import React, { useEffect, useMemo, useState } from "react";
+import Link from "react-router-dom/Link";
+import { publishExpertsAndRules } from "src/military/task/api";
+import PaginationTable from "../../components/paginationTable";
+import { expertReviewArr } from "../../task/static";
+import { getCompetitionList, getRules, selectExpertList, updateCompetitionReview } from "../api";
+import { competitionStatus } from "../static";
+
+import './index.scss';
+const Option = Select.Option;
+
+const statusArr = [];
+for (const item of competitionStatus) {
+ statusArr[item.value] = item.label;
+}
+
+// 竞赛任务状态 current_status 1报名中 2即将开始 3比赛进行中 4作品评选中 5公示中 6已结束
+function Competition(props){
+ const {mygetHelmetapi, showNotification, history} = props;
+ const {main_web_site_url} = mygetHelmetapi;
+ const {hash} = history && history.location;
+ const [loading, setLoading] = useState(false);
+ const [curPage, setCurPage] = useState(hashDate(hash) || 1);
+ //是否加入专家评审流程
+ const [expertReview,setExpertReview] = useState(undefined);
+ //竞赛任务总数
+ const [total, setTotal] = useState()
+ //竞赛任务列表
+ const [competitionList, setCompetitionList] = useState(undefined);
+
+ //查看评审规则、查看选取专家、发布评审任务
+ const [lookRules, setLookRules] = useState(false);
+ const [lookExperts, setLookExperts] = useState(false);
+ const [pulicReview, setPublicReview] = useState(false);
+ const [rules, setRules] = useState(undefined);
+ const [selectedExperts, setSelectedExperts] = useState(undefined);
+ const [publicTaskId, setPublicTaskId] = useState(undefined);
+ const [reload, setReload] = useState(undefined);
+
+ //竞赛任务列表 表格
+ const columns = useMemo(() => {
+ return [
+ {
+ title: "序号",
+ dataIndex: "index",
+ width: 50,
+ align: "center",
+ },
+ {
+ title: "竞赛主标题",
+ dataIndex: "title",
+ key: "title",
+ align: "center",
+ render:(text, record)=>{
+ return {text}
+ }
+ },
+ {
+ title: ,
+ dataIndex: 'is_expert_audit',
+ align: "center",
+ render: (text, record) => {
+ return
+ }
+ },
+ {
+ title: "竞赛状态",
+ dataIndex: "current_status",
+ key: "current_status",
+ align: "center",
+ render:(text, record)=>{
+ return statusArr[text];
+ }
+ },
+ {
+ title: "开始时间",
+ dataIndex: "start_time",
+ key: "startTime",
+ align: "center",
+ },
+ {
+ title: "截止时间",
+ dataIndex: "end_time",
+ key: "endTime",
+ align: "center",
+ },
+ {
+ title: "报名人数",
+ dataIndex: "team_members_count",
+ key: "teamMembersCount",
+ align: "center",
+ },
+ {
+ title: '评审规则',
+ dataIndex: 'current_status',
+ key: "rules",
+ render: (text, record) => {
+ return record.assignRuleAndExperts ? : record.is_expert_audit && text<4 ? 编辑 : 编辑
+ }
+ },
+ {
+ title: '专家选取',
+ dataIndex: 'current_status',
+ key: "experts",
+ render: (text, record) => {
+ return record.assignRuleAndExperts ? : record.is_expert_audit && text<4 ? 选择 : 选择
+ }
+ },
+ {
+ title: '评审任务',
+ dataIndex: 'current_status',
+ key: "review",
+ render: (text, record) => {
+ return record.assignRuleAndExperts ? 已发布 : record.is_expert_audit && text<4 ? : 发布
+ }
+ },
+ {
+ title: '评审结果',
+ dataIndex: 'assignRuleAndExperts',
+ key: "results",
+ render: (text, record) => {
+ return text ? 查看:查看
+ }
+ }
+ ];
+ }, [competitionList, curPage]);
+
+ //已选取专家 表格
+ const columnsExperts = useMemo(() => {
+ return [
+ {
+ title: '编号',
+ dataIndex: 'index',
+ width: 80,
+ align: 'center',
+ },
+ {
+ title: '专家姓名',
+ dataIndex: 'expertName',
+ key: 'expertName',
+ width: 120,
+ },
+ {
+ title: '手机号码',
+ dataIndex: 'phone',
+ width: 130,
+ key: 'phone',
+ },
+ {
+ title: '最高学历',
+ dataIndex: 'highestDegree',
+ key: 'highestDegree',
+ },
+ {
+ title: '专业职称',
+ dataIndex: 'professionalTitle',
+ },
+ {
+ title: '专家类别',
+ dataIndex: 'expertType',
+ },
+ {
+ title: '评审领域',
+ dataIndex: 'reviewAreas',
+ align: 'center',
+ width: 260,
+ },
+ {
+ title: '专家评分',
+ dataIndex: 'expertScore',
+ align: 'center',
+ render:(text,record)=>{
+ return record.expertScore || '--';
+ }
+ }
+ ];
+ }, []);
+
+ //发布评审任务
+ function publishTaskReview(record){
+ if(!record.ruleEdited || !record.expertSelected){
+ message.error("请先编辑评审规则以及选取评选专家再发布此任务");
+ }else{
+ getRules({containerId: record.id, containerType: 2, statusString: 3}).then(response=>{
+ if(response && response.message === "success"){
+ setRules(response.data);
+ }
+ })
+ selectExpertList({containerId: record.id, containerType: 2, pageSize: 10000, curPage: 1}).then(response=>{
+ if(response && response.message === "success" && Array.isArray(response.data.rows)){
+ let index = 1;
+ for (const item of response.data.rows) {
+ item.reviewAreas = `${item.reviewAreaOne} ${item.reviewAreaTwo ? `、${item.reviewAreaTwo}`:''} ${item.reviewAreaThree ? `、${item.reviewAreaThree}`:''}`;
+ item.index = (index++) + (curPage > 1 ? (curPage - 1) * 10 : 0);
+ }
+ setPublicTaskId(record.id);
+ setSelectedExperts(response.data.rows);
+ setPublicReview(true);
+ }
+ });
+ }
+ }
+
+ //已发布任务 查看评审规则
+ function viewRules(record){
+ getRules({containerId: record.id, containerType: 2, statusString: '-1,1,2'}).then(response=>{
+ if(response && response.message === "success"){
+ setRules(response.data);
+ setLookRules(true);
+ }
+ });
+ }
+
+ //已发布任务 查看已选专家
+ function viewExperts(record){
+ selectExpertList({containerId: record.id, containerType: 2, pageSize: 10000, curPage: 1,}).then(response=>{
+ if(response && response.message === "success" && Array.isArray(response.data.rows)){
+ let index = 1;
+ for (const item of response.data.rows) {
+ item.reviewAreas = `${item.reviewAreaOne} ${item.reviewAreaTwo ? `、${item.reviewAreaTwo}`:''} ${item.reviewAreaThree ? `、${item.reviewAreaThree}`:''}`;
+ item.index = (index++) + (curPage > 1 ? (curPage - 1) * 10 : 0);
+ }
+ setSelectedExperts(response.data.rows);
+ setLookExperts(true);
+ }
+ });
+ }
+
+ // 修改竞赛是否加入专家评审流程
+ function changeExpertReviewStatus(expertReviewStatus, taskId) {
+ updateCompetitionReview({id: taskId, is_expert_audit: expertReviewStatus==1}).then(res => {
+ if (res && res.message === '更新成功') {
+ showNotification('操作成功!');
+ setReload(Math.random());
+ } else {
+ showNotification('操作失败');
+ }
+ })
+ }
+
+ // 修改路由,跳转到第几页
+ function updateUrl(page){
+ setCurPage(page);
+ window.location.href=`/expert/admin/competition/#page=${page}`;
+ }
+
+ function hashDate(hash) {
+ return parseInt(hash.split("&")[0].substring(hash.split("&")[0].indexOf("=")+1));
+ }
+
+ //获取竞赛任务列表
+ useEffect(()=>{
+ setLoading(true);
+ const params = {
+ curPage,
+ pageSize: 10,
+ isExpertAudit: expertReview
+ }
+ getCompetitionList(params).then(response=>{
+ if(response && response.message === "success"){
+ response.data.map((item, i)=>{
+ item.index = ++i;
+ item.start_time = item.start_time.replace('T', ' ').substring(0,16);
+ item.end_time = item.end_time.replace('T', ' ').substring(0,16);
+ })
+ setCompetitionList(response.data || []);
+ setTotal(response.total);
+ }
+ }).finally(()=>{
+ setLoading(false);
+ })
+ }, [curPage, expertReview, reload])
+
+ //监听lookRules,lookExperts,pulicReview的变化,弹框
+ useEffect(()=>{
+ //评审规则
+ lookRules && rules && Modal.info({
+ className: 'publishReview',
+ title: "评审规则",
+ content:
+
+ {rules && rules.rule}
+ 评分标准
+
+ {rules.criterias.map(item=>{return
{item}
})}
+
+ 评审时间
+ {rules.reviewData}
+
+ ,
+ });
+ lookRules && setLookRules(false);
+
+ //已选取评审专家
+ lookExperts && selectedExperts && Modal.info({
+ className: 'publishReview',
+ title: "已选取评审专家",
+ content:
+ ,
+ });
+ lookExperts && setLookExperts(false);
+
+ //发布评审任务
+ pulicReview && rules && selectedExperts && Modal.confirm({
+ className: 'publishReview',
+ title: "发布评审任务",
+ centered: true,
+ content:
+
+
+
+ 确定发布此评审任务?确定发布后评审规则与评审专家信息将无法重新编辑
+
+ 评审规则
+ {rules && rules.rule}
+ 评分标准
+
+ {rules.criterias.map(item=>{return
{item}
})}
+
+ 评审时间
+ {rules.reviewData}
+ 已选取评审专家
+
+
+ ,
+ okText: '确定',
+ cancelText: '取消',
+ onOk() {
+ publishExpertsAndRules(publicTaskId, 2).then(response=>{
+ if(response && response.message==="发布成功"){
+ setReload(Math.random());
+ }
+ })
+ },
+ });
+ pulicReview && setPublicReview(false);
+ },[lookRules,lookExperts,pulicReview])
+
+ //监听hash路由的变化,由此控制页数
+ useEffect(()=>{
+ setCurPage(hashDate(hash) || 1);
+ },[hash])
+
+ return(
+
+
{updateUrl(page)}}
+ current={curPage}
+ />
+
+ )
+}
+export default Competition;
\ No newline at end of file
diff --git a/src/military/expert/competionList/index.scss b/src/military/expert/competionList/index.scss
new file mode 100644
index 00000000..fcc4fec7
--- /dev/null
+++ b/src/military/expert/competionList/index.scss
@@ -0,0 +1,63 @@
+a.primary-link{
+ color: #4154f1;
+ &:hover{
+ opacity: 0.8;
+ }
+}
+.gary_span{
+ color: rgba(176, 176, 176, 1);
+}
+
+// 发布评审任务弹框样式
+.publishReview{
+ width: 1050px !important;
+ .ant-modal-body{
+ padding: 0;
+ }
+ .ant-modal-confirm-btns {
+ margin: 15px 35px 10px;
+ }
+ .ant-modal-confirm-title{
+ border-bottom: 1px solid #eeeeee;
+ padding: 20px 25px;
+ background: #f2f2ff;
+ font-size: 18px;
+ }
+ .ant-modal-confirm-body > .anticon{
+ display: none;
+ }
+ .ant-modal-confirm-body > .anticon + .ant-modal-confirm-title + .ant-modal-confirm-content{
+ margin-left: 0;
+ }
+ .ant-modal-confirm-content{
+ &>p{
+ font-size: 16px;
+ color: #333333;
+ border-bottom: 1px solid #eeeeee;
+ padding: 10px 35px;
+ font-weight: bold;
+ }
+ &>div{
+ padding: 10px 45px;
+ }
+ .tip{
+ padding: 10px 35px;
+ i{
+ color: #ca0002;
+ }
+ .publicTitle {
+ font-size: 15px;
+ margin-left: 3px;
+ }
+ }
+ }
+ .pagination-table .ant-table-tbody > tr > td{
+ padding: 3px 8px;
+ }
+}
+
+.competitionList{
+ .ant-select-selection{
+ width: 115px;
+ }
+}
\ No newline at end of file
diff --git a/src/military/expert/components/Upload.jsx b/src/military/expert/components/Upload.jsx
new file mode 100644
index 00000000..8722e054
--- /dev/null
+++ b/src/military/expert/components/Upload.jsx
@@ -0,0 +1,94 @@
+import React, { useEffect, useState } from "react";
+import { Upload, Button } from 'antd';
+import { appendFileSizeToUploadFileAll } from 'educoder';
+import { httpUrl } from '../fetch';
+
+function Uploads({ className, size, actionUrl, fileList, showNotification, load, accept, disabled,count }) {
+ const [files, setFiles] = useState(undefined);
+
+ useEffect(() => {
+ if (fileList) {
+ init();
+ }
+ }, [fileList]);
+
+ function init() {
+ let f = appendFileSizeToUploadFileAll(fileList);
+ setFiles(f);
+ }
+ function onAttachmentRemove(file) {
+ if (!file.percent || file.percent === 100) {
+ deleteAttachment(file);
+ return false;
+ }
+ }
+ function deleteAttachment(file) {
+ let id = (file.response && file.response.data && file.response.data.id) || file.id;
+
+ // 暂时不直接删除上传的文件,只在最后保存的时候进行修改
+ let nf = files.filter(item => {
+ let itemId = (item.response && item.response.data && item.response.data.id) || item.id;
+ return itemId !== id;
+ });
+ setFiles(nf);
+ backFiles(nf);
+ }
+
+ function backFiles(fileList) {
+ let filesId = [];
+ for (const item of fileList) {
+ if (item) {
+ let itemId = (item.response && item.response.data && item.response.data.id) || item.id;
+ itemId && filesId.push(itemId);
+ }
+ }
+ load && load(fileList, filesId.join());
+ }
+
+
+ function handleChange(info) {
+ if (info.file.status === 'uploading' || info.file.status === 'done' || info.file.status === 'removed') {
+ let fileList = info.fileList;
+ if(count){
+ fileList = fileList.slice(-count);
+ }
+ setFiles(appendFileSizeToUploadFileAll(fileList));
+ if (info.file.response) {
+ for (let i = 0; i < fileList.length; i++) {
+ if (fileList[i].response && !fileList[i].response.data) {
+ fileList.splice(i, 1);
+ }
+ }
+ backFiles(fileList);
+ if (!info.file.response.data) {
+ info.file.response && showNotification(info.file.response.message)
+ }
+ }
+ }
+ }
+
+ function beforeUpload(file) {
+ const isLt100M = file.size / 1024 / 1024 < size;
+ if (!isLt100M) {
+ showNotification(`文件大小必须小于${size}MB!`);
+ }
+ return isLt100M;
+ }
+
+ const upload = {
+ name: 'file',
+ fileList: files,
+ disabled: disabled,
+ action: (httpUrl || actionUrl) + `/busiAttachments/upload`,
+ onChange: handleChange,
+ onRemove: onAttachmentRemove,
+ beforeUpload: beforeUpload,
+ };
+ return (
+
+
+ (你可以上传小于{size}MB的文件)
+
+ )
+}
+export default Uploads;
\ No newline at end of file
diff --git a/src/military/expert/components/exportExcel.js b/src/military/expert/components/exportExcel.js
new file mode 100644
index 00000000..52124505
--- /dev/null
+++ b/src/military/expert/components/exportExcel.js
@@ -0,0 +1,152 @@
+export const exportExcel = (tableClass, fileName) => {
+ if (getExplorer() === 'ie') {
+ //创建AX对象excel
+ const curTbl = document.querySelector(tableClass).cloneNode(true);
+ // eslint-disable-next-line no-undef
+ let oXL = new ActiveXObject("Excel.Application");
+ let oWB = oXL.Workbooks.Add(); //获取workbook对象
+ let xlSheet = oWB.Worksheets(1); //激活当前sheet
+ let sel = document.body.createTextRange(); //把表格中的内容移到TextRange中
+ sel.moveToElementText(curTbl);
+ sel.select;//全选TextRange中内容
+ sel.execCommand("Copy");//复制TextRange中内容
+ xlSheet.Paste(); //粘贴到活动的EXCEL中
+ oXL.Visible = true; //设置excel可见属性
+ let fName = null;
+ try {
+ fName = oXL.Application.GetSaveAsFilename("Excel.xls", "Excel Spreadsheets (*.xls), *.xls");
+ } catch (e) {
+ } finally {
+ oWB.SaveAs(fName);
+ // oWB.Close(savechanges = false);
+ oXL.Quit();
+ oXL = null;
+ // 下面代码用于解决IE call Excel的一个BUG, MSDN中提供的方法:
+ // setTimeout(CollectGarbage, 1);
+ // 由于不能清除(或同步)网页的受信任状态, 所以将导致SaveAs()等方法在
+ // 下次调用时无效.
+ window.location.reload();
+ }
+
+ } else {
+ tableToExcel(tableClass, fileName, 'worksheet')
+ }
+}
+
+
+const traverseNodes = (node, newTd) => {
+ if (node.hasChildNodes) {
+ const sonNodes = node.childNodes;
+ const filterElement = ['button'];
+ for (let sonNode of sonNodes) {
+ if (!filterElement.includes(sonNode.nodeName.toLowerCase())) { // 对不必要对element过滤
+ traverseNodes(sonNode, newTd);
+ }
+
+ }
+ }
+ return display(node, newTd);
+}
+
+const display = (node, newTd) => {
+ const {nodeName, nodeValue} = node;
+ let newSpan = document.createElement("span");
+ newSpan.innerText = nodeValue;
+ if (nodeName === 'INPUT' || nodeName === 'TEXTAREA') { // 对 input 处理
+ const {type, checked, value} = node;
+ newSpan.innerText = value;
+ if (type === 'radio' || type === 'checkbox') {
+ console.log("type", type)
+ newSpan.innerText = type === 'radio' ? (checked ? "●" : "○") : (checked ? "■" : "□");
+ newSpan.style.fontSize = '16px';
+ newSpan.style.paddingLeft = '15px';
+ }
+ }
+ if (node.nodeName === 'IMG') {
+ const {width, height} = node;
+ newTd.appendChild(node);
+ newTd.style.height = height + "px";
+ newTd.style.width = width + "px";
+ }
+ if (newSpan.innerText.trim()) {
+ newTd.appendChild(newSpan);
+ }
+
+ return newTd
+}
+
+
+const tableToExcel = (table, fileName, worksheet) => {
+ const uri = 'data:application/vnd.ms-excel;base64,';
+ // 定义文档的类型
+ const template = '';
+ const base64 = function (s) {
+ return window.btoa(unescape(encodeURIComponent(s)))
+ };
+ // 将template中的变量替换为页面内容ctx获取到的值
+ const format = function (s, c) {
+ return s.replace(/{(\w+)}/g, function (m, p) {
+ return c[p];
+ })
+ }
+ if (!table.nodeType) {
+ table = document.querySelector(table).cloneNode(true);
+ }
+
+ let newTable = document.createElement("table");
+ const trArray = table.getElementsByTagName('tr');
+ for (let trItem of trArray) {
+ let newTr = document.createElement("tr");
+ const thArray = trItem.getElementsByTagName('th');
+ const tdArray = trItem.getElementsByTagName('td');
+ for (let thItem of thArray) {
+ let newTh = document.createElement("th");
+ const {rowSpan = 1, colSpan = 1, style} = thItem;
+ traverseNodes(thItem, newTh);
+ newTh.rowSpan = rowSpan; //跨行
+ newTh.colSpan = colSpan; //跨列
+ newTh.style = style; // 样式
+ newTr.appendChild(newTh);
+ }
+ for (let tdItem of tdArray) {
+ let newTd = document.createElement("td");
+ const {rowSpan = 1, colSpan = 1, style} = tdItem;
+ traverseNodes(tdItem, newTd);
+ newTd.rowSpan = rowSpan; //跨行
+ newTd.colSpan = colSpan; //跨列
+ newTd.style = style; // 样式
+ newTr.appendChild(newTd);
+ }
+ if (newTr.childNodes.length > 1) {
+ newTable.appendChild(newTr);
+ }
+ }
+ newTable.innerHTML = newTable.innerHTML.replace(/ {
+ const explorer = window.navigator.userAgent;
+ if (explorer.indexOf("MSIE") >= 0) { //ie
+ return 'ie';
+ }
+ else if (explorer.indexOf("Firefox") >= 0) { //firefox
+ return 'Firefox';
+ }
+ else if (explorer.indexOf("Chrome") >= 0) { //Chrome
+ return 'Chrome';
+ }
+ else if (explorer.indexOf("Opera") >= 0) { //Opera
+ return 'Opera';
+ }
+ else if (explorer.indexOf("Safari") >= 0) { //Safari
+ return 'Safari';
+ }
+}
\ No newline at end of file
diff --git a/src/military/expert/components/exportExcel/index.js b/src/military/expert/components/exportExcel/index.js
new file mode 100644
index 00000000..38e57814
--- /dev/null
+++ b/src/military/expert/components/exportExcel/index.js
@@ -0,0 +1,200 @@
+import React, {Component} from 'react';
+import {Button} from 'antd';
+import PropTypes from "prop-types";
+
+const propTypes = {
+ tableClass: PropTypes.string, // tableClass
+ fileName: PropTypes.string, // 导出文件的名字
+ worksheet: PropTypes.string, //导出工作簿名字
+ // colors: PropTypes.string, // button 样式
+ // size: PropTypes.string, //按钮大小(lg xg sm md)
+ // style: PropTypes.string, // 按钮样式
+ // exportIcon: PropTypes.element, // 自定义导出图标
+ title: PropTypes.element, //名称标题
+ filterElement: PropTypes.array, //过滤元素
+};
+
+const defaultProps = {
+ tableClass: '',
+ fileName: "filename",
+ worksheet: 'worksheet',
+ // colors: "primary",
+ // size: 'sm',
+ // style: '',
+ exportIcon: null,
+ title: '导出',
+ filterElement: ['button']
+};
+
+class ExportExcel extends Component {
+ exportExcel = () => {
+ const {tableClass, fileName, worksheet} = this.props;
+ if (this.getExplorer() === 'ie') {
+ //创建AX对象excel
+ const curTbl = document.querySelector(tableClass).cloneNode(true);
+ // eslint-disable-next-line no-undef
+ let oXL = new ActiveXObject("Excel.Application");
+ let oWB = oXL.Workbooks.Add(); //获取workbook对象
+ let xlSheet = oWB.Worksheets(1); //激活当前sheet
+ let sel = document.body.createTextRange(); //把表格中的内容移到TextRange中
+ sel.moveToElementText(curTbl);
+ sel.select;//全选TextRange中内容
+ sel.execCommand("Copy");//复制TextRange中内容
+ xlSheet.Paste(); //粘贴到活动的EXCEL中
+ oXL.Visible = true; //设置excel可见属性
+ let fName = null;
+ try {
+ fName = oXL.Application.GetSaveAsFilename("Excel.xls", "Excel Spreadsheets (*.xls), *.xls");
+ } catch (e) {
+ } finally {
+ oWB.SaveAs(fName);
+ // oWB.Close(savechanges = false);
+ oXL.Quit();
+ oXL = null;
+ // 下面代码用于解决IE call Excel的一个BUG, MSDN中提供的方法:
+ // setTimeout(CollectGarbage, 1);
+ // 由于不能清除(或同步)网页的受信任状态, 所以将导致SaveAs()等方法在
+ // 下次调用时无效.
+ window.location.reload();
+ }
+
+ } else {
+ this.tableToExcel(tableClass, fileName, worksheet)
+ }
+ }
+
+
+ traverseNodes = (node, newTd) => {
+ if (node.hasChildNodes) {
+ const sonNodes = node.childNodes;
+ const {filterElement} = this.props;
+ for (let sonNode of sonNodes) {
+ if (!filterElement.includes(sonNode.nodeName.toLowerCase())) { // 对不必要对element过滤
+ this.traverseNodes(sonNode, newTd);
+ }
+
+ }
+ }
+ return this.display(node, newTd);
+ }
+
+ display = (node, newTd) => {
+ const {nodeName, nodeValue} = node;
+ let newSpan = document.createElement("span");
+ newSpan.innerText = nodeValue;
+ if (nodeName === 'INPUT' || nodeName === 'TEXTAREA') { // 对 input 处理
+ const {type, checked, value} = node;
+ newSpan.innerText = value;
+ if (type === 'radio' || type === 'checkbox') {
+ console.log("type", type)
+ newSpan.innerText = type === 'radio' ? (checked ? "●" : "○") : (checked ? "■" : "□");
+ newSpan.style.fontSize = '16px';
+ newSpan.style.paddingLeft = '15px';
+ }
+ }
+ if (node.nodeName === 'IMG') {
+ const {width, height} = node;
+ newTd.appendChild(node);
+ newTd.style.height = height + "px";
+ newTd.style.width = width + "px";
+ }
+ if (newSpan.innerText.trim()) {
+ newTd.appendChild(newSpan);
+ }
+
+ return newTd
+ }
+
+
+ tableToExcel = (table, fileName, worksheet) => {
+ const uri = 'data:application/vnd.ms-excel;base64,';
+ // 定义文档的类型
+ const template = '';
+ const base64 = function (s) {
+ return window.btoa(unescape(encodeURIComponent(s)))
+ };
+ // 将template中的变量替换为页面内容ctx获取到的值
+ const format = function (s, c) {
+ return s.replace(/{(\w+)}/g, function (m, p) {
+ return c[p];
+ })
+ }
+ if (!table.nodeType) {
+ table = document.querySelector(table).cloneNode(true);
+ }
+
+ let newTable = document.createElement("table");
+ const trArray = table.getElementsByTagName('tr');
+ for (let trItem of trArray) {
+ let newTr = document.createElement("tr");
+ const thArray = trItem.getElementsByTagName('th');
+ const tdArray = trItem.getElementsByTagName('td');
+ for (let thItem of thArray) {
+ let newTh = document.createElement("th");
+ const {rowSpan = 1, colSpan = 1, style} = thItem;
+ this.traverseNodes(thItem, newTh);
+ newTh.rowSpan = rowSpan; //跨行
+ newTh.colSpan = colSpan; //跨列
+ newTh.style = style; // 样式
+ newTr.appendChild(newTh);
+ }
+ for (let tdItem of tdArray) {
+ let newTd = document.createElement("td");
+ const {rowSpan = 1, colSpan = 1, style} = tdItem;
+ this.traverseNodes(tdItem, newTd);
+ newTd.rowSpan = rowSpan; //跨行
+ newTd.colSpan = colSpan; //跨列
+ newTd.style = style; // 样式
+ newTr.appendChild(newTd);
+ }
+ if (newTr.childNodes.length > 1) {
+ newTable.appendChild(newTr);
+ }
+ }
+ const ctx = {worksheet, table: newTable.innerHTML}; // 获取表单的名字和表单查询的内容
+ const a = document.createElement("a"); // 虚拟一个a 标签
+ // format()函数:通过格式操作使任意类型的数据转换成一个字符串
+ // base64():进行编码
+ a.href = uri + base64(format(template, ctx));
+ a.download = fileName + ".xls";//设置文件的名字
+ a.click();// 下载
+ }
+
+ // 获取当前浏览器
+ getExplorer = () => {
+ const explorer = window.navigator.userAgent;
+ if (explorer.indexOf("MSIE") >= 0) { //ie
+ return 'ie';
+ }
+ else if (explorer.indexOf("Firefox") >= 0) { //firefox
+ return 'Firefox';
+ }
+ else if (explorer.indexOf("Chrome") >= 0) { //Chrome
+ return 'Chrome';
+ }
+ else if (explorer.indexOf("Opera") >= 0) { //Opera
+ return 'Opera';
+ }
+ else if (explorer.indexOf("Safari") >= 0) { //Safari
+ return 'Safari';
+ }
+ }
+
+ render() {
+ const {colors, exportIcon, size, title} = this.props;
+ return (
+
+ )
+ }
+}
+
+ExportExcel.propTypes = propTypes;
+ExportExcel.defaultProps = defaultProps;
+export default ExportExcel;
diff --git a/src/military/expert/components/wordsInput.jsx b/src/military/expert/components/wordsInput.jsx
new file mode 100644
index 00000000..810b4e55
--- /dev/null
+++ b/src/military/expert/components/wordsInput.jsx
@@ -0,0 +1,22 @@
+import React, { useState, forwardRef, useEffect } from "react";
+import { Input } from 'antd';
+
+const { TextArea } = Input;
+
+//右下角 实时动态 显示用户输入字数
+const WordsInput = forwardRef((props, _ref) => {
+ const [wordCount, setWordCount] = useState(0);
+ const {value} = props;
+
+ //初始化 字数
+ useEffect(()=>{
+ setWordCount(value && value.length || 0);
+ },[props])
+ return(
+
+
+ )
+})
+export default WordsInput;
\ No newline at end of file
diff --git a/src/military/expert/expertList/index.jsx b/src/military/expert/expertList/index.jsx
new file mode 100644
index 00000000..21666b5f
--- /dev/null
+++ b/src/military/expert/expertList/index.jsx
@@ -0,0 +1,401 @@
+import React, { useState, useMemo, useEffect } from "react";
+import { Input, Select, Button, Form, Table, Upload, Modal, Popconfirm, message } from 'antd';
+import cookie from 'react-cookies';
+import { exportExcel } from '../components/exportExcel.js';
+import Paginationtable from "../../components/paginationTable";
+import { Info } from '../../components/ModalFun';
+import { expertList, deleteExpert } from "../api";
+import { professionalType, reviewArea } from "../static";
+import { httpUrl } from '../fetch';
+
+import './index.scss';
+import '../index.scss';
+const { Search } = Input;
+const Option = Select.Option;
+
+function RegisterList({ showNotification }) {
+ const [reload, setReload] = useState();
+ const [loading, setLoading] = useState(false);
+ const [curPage, setCurPage] = useState(1);
+ const [pageSize, setPageSize] = useState(10);
+ const [dataList, setDataList] = useState([]);
+ const [total, setTotal] = useState(0);
+
+ const [searchInput, setSearchInput] = useState('');
+ const [searchReviewArea, setSearchReviewArea] = useState('');
+ const [expertType, setExpertType] = useState('')
+ const [dataAll, setDataAll] = useState([]);
+ const [download, setDownload] = useState();
+ const [downloading, setDownloading] = useState(false);
+ const [visible, setVisible] = useState(false);
+
+ function onShowSizeChange(current, pageSize) {
+ setCurPage(current);
+ setPageSize(pageSize);
+ }
+
+ const columns = useMemo(() => {
+ return [{
+ title: '姓名',
+ dataIndex: 'expertName',
+ width: 85,
+ key: 'expertName',
+ fixed: 'left',
+ },
+ {
+ title: '手机号码',
+ dataIndex: 'phone',
+ key: 'phone',
+ },
+ {
+ title: '最高学历',
+ dataIndex: 'highestDegree',
+ key: 'highestDegree',
+ width: 80,
+ },
+ {
+ title: '专家评估',
+ dataIndex: 'expertScore',
+ key: 'expertScore',
+ width: 80,
+ render: (text, record) => {
+ return text || '--'
+ }
+ },
+ {
+ title: '工作单位',
+ dataIndex: 'workplace',
+ key: 'workplace',
+ // width: 250,
+ },
+ {
+ title: '单位类别',
+ dataIndex: 'workplaceType',
+ key: 'workplaceType',
+ width: 80,
+ },
+ {
+ title: '工作性质',
+ dataIndex: 'workNature',
+ key: 'workNature',
+ width: 80,
+ },
+ {
+ title: '专业职称',
+ dataIndex: 'professionalTitle',
+ key: 'professionalTitle',
+ width: 120,
+ },
+ {
+ title: '职称职级',
+ dataIndex: 'titleRank',
+ key: 'titleRank',
+ width: 80,
+ },
+ {
+ title: '专家类别',
+ dataIndex: 'expertType',
+ key: 'expertType',
+ width: 80,
+ },
+ {
+ title: '评审领域1',
+ dataIndex: 'reviewAreaOne',
+ key: 'reviewAreaOne',
+ width: 100,
+ },
+ {
+ title: '评审领域2',
+ dataIndex: 'reviewAreaTwo',
+ key: 'reviewAreaTwo',
+ width: 100,
+ },
+ {
+ title: '评审领域3',
+ dataIndex: 'reviewAreaThree',
+ key: 'reviewAreaThree',
+ width: 100,
+ },
+ {
+ title: '毕业院校',
+ dataIndex: 'graduatedFrom',
+ key: 'graduatedFrom',
+ },
+ {
+ title: '院校专业',
+ dataIndex: 'major',
+ key: 'major',
+ },
+ {
+ title: '身份证号',
+ dataIndex: 'idNumber',
+ key: 'idNumber',
+ width: 170,
+ },
+ {
+ title: '邮箱地址',
+ dataIndex: 'expertEmail',
+ key: 'expertEmail',
+ width: 200,
+ },
+ {
+ title: '开户银行',
+ dataIndex: 'bankName',
+ key: 'bankName',
+ width: 110,
+ },
+ {
+ title: '银行账号',
+ dataIndex: 'bankAccount',
+ key: 'bankAccount',
+ render: (text, record) => {
+ return '\t' + text
+ }
+ },
+ {
+ title: '个人简介',
+ dataIndex: 'resumeAttachments',
+ key: 'resumeAttachments',
+ render: (text, record) => {
+ return text && text.map(item => {
+ return { downFile(item.id) }}>{item.fileName}
+ })
+ }
+ },
+ {
+ title: '职称证明',
+ dataIndex: 'titleCertificateAttachments',
+ key: 'titleCertificateAttachments',
+ render: (text, record) => {
+ return text && text.map(item => {
+ return { downFile(item.id) }}>{item.fileName}
+ })
+ }
+ },
+ {
+ title: '学术成果',
+ dataIndex: 'academicAchievementsAttachments',
+ key: 'academicAchievementsAttachments',
+ render: (text, record) => {
+ return text && text.map(item => {
+ return { downFile(item.id) }}>{item.fileName}
+ })
+ }
+ },
+ {
+ title: '荣誉称号',
+ dataIndex: 'honorsAttachments',
+ key: 'honorsAttachments',
+ render: (text, record) => {
+ return text && text.map(item => {
+ return { downFile(item.id) }}>{item.fileName}
+ })
+ }
+ },
+ {
+ title: '操作',
+ dataIndex: 'id',
+ key: 'action',
+ fixed: 'right',
+ render: (text, record)=>{
+ return { delExpert(text);}} okText="是" cancelText="否">
+ }
+ }
+ ];
+ }, []);
+
+ function downFile(id) {
+ let url = httpUrl + '/busiAttachments/download/' + id;
+ window.open(url);
+ }
+
+ // 获取列表
+ useEffect(() => {
+ setLoading(true);
+ let params = {
+ searchInput,
+ reviewArea: searchReviewArea,
+ expertType,
+ pageSize,
+ curPage,
+ statusString: '1',
+ };
+ expertList(params).then(data => {
+ setDataList(data.rows || []);
+ setLoading(false);
+ setTotal(data && data.total);
+ });
+ }, [curPage, reload, searchInput, searchReviewArea, expertType, pageSize]);
+
+ // 获取下载数据的列表
+ useEffect(() => {
+ if (!download) {
+ return;
+ }
+ setDownloading(true);
+ let params = {
+ searchInput,
+ reviewArea: searchReviewArea,
+ expertType,
+ pageSize: 10000000,
+ curPage: 1,
+ statusString: '1',
+ };
+ expertList(params).then(data => {
+ setDataAll(data.rows || []);
+ setDownloading(false);
+ exportExcel("#exportList .ant-table-scroll", "专家列表");
+ });
+ }, [download]);
+
+ // 删除专家
+ const delExpert=(expertId)=>{
+ setLoading(true);
+ deleteExpert(expertId).then(response=>{
+ if(response && response.message === "删除专家成功"){
+ message.success("删除成功");
+ setReload(Math.random());
+ }else{
+ message.error("删除失败");
+ }
+ }).finally(()=>{
+ setLoading(false);
+ })
+ }
+
+ function beforeUpload(file) {
+ const isExcel = file.type.indexOf('xlsx') || file.type.indexOf('xls') || file.type.indexOf('sheet');
+ if (!isExcel) {
+ showNotification(`只支持.xlsx、xls格式!`);
+ }
+ return isExcel;
+ }
+
+ function handleChange(info) {
+ if (info.file.status === 'uploading' || info.file.status === 'done') {
+ if (info.file.response) {
+ let resData = info.file.response.data;
+ if (resData) {
+ Info({
+ title: '提示',
+ content:
+ {resData.successMessage && }
+ {resData.failMessage && }
+ ,
+ });
+ setReload(Math.random());
+ setVisible(false);
+ } else {
+ showNotification(info.file.response.message || '系统错误');
+ }
+ }
+ }
+ if (info.file.status === 'error') {
+ showNotification(info.file.response.message || '系统错误');
+ }
+ }
+
+ const upload = {
+ name: 'file',
+ action: `${httpUrl}/api/experts/registerByExcel`,
+ onChange: handleChange,
+ beforeUpload: beforeUpload,
+ accept: ".xlsx,.xls",
+ showUploadList: true,
+ withCredentials: true,
+ headers: {
+ Authorization: cookie.load('autologin_forge_military') || sessionStorage.osredmToken,
+ },
+ };
+
+ return (
+
+
+
+
+ { setSearchInput(value); setCurPage(1); }}
+ />
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ row.id}
+ />
+
+ { setVisible(false) }}
+ className="upload-modal"
+ footer={}
+ key={Math.random()}
+ >
+
+
+
+ { window.open(httpUrl + '/busiAttachments/download/883') }}>专家注册表模板.xlsx
+ 提示:只能在导入模版上增减数据,才能导入成功!
+
+ )
+}
+export default RegisterList;
\ No newline at end of file
diff --git a/src/military/expert/expertList/index.scss b/src/military/expert/expertList/index.scss
new file mode 100644
index 00000000..7f3befd5
--- /dev/null
+++ b/src/military/expert/expertList/index.scss
@@ -0,0 +1,52 @@
+.expert-list{
+ .ant-table-thead > tr > th, .ant-table-tbody > tr > td{
+ padding:16px 6px;
+ }
+ .center-screen{
+ display: flex;
+ justify-content: space-between;
+ }
+ .center-right-but{
+ flex:auto;
+ justify-content: space-between;
+ margin-right: 4em;
+ }
+
+ .ant-form-item-control-wrapper{
+ display: inline-block;
+ }
+ .btn-group{
+ display: flex;
+ }
+}
+.import-important{
+ text-align: left;
+ .mess{
+ padding-left: 20px;
+ &.fail{
+ max-height: 300px;
+ overflow-y: auto;
+ }
+ }
+ span{
+ color: #df0002;
+ margin-left: 5px;
+ }
+}
+.upload-modal{
+ .ant-modal-body{
+ text-align: center;
+ }
+ p{
+ line-height: 2rem;
+ }
+ .hint{
+ color: #df0002;
+ }
+ .link{
+ color: #4154f1;
+ &:hover{
+ opacity: 0.8;
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/military/expert/expertUser/index.jsx b/src/military/expert/expertUser/index.jsx
new file mode 100644
index 00000000..ed1e33e9
--- /dev/null
+++ b/src/military/expert/expertUser/index.jsx
@@ -0,0 +1,79 @@
+import React from "react";
+
+import { Route, Switch, Link } from "react-router-dom";
+import Loadable from "react-loadable";
+import Loading from "src/Loading";
+import '../index.scss';
+import './index.scss';
+
+
+const Register = Loadable({
+ loader: () => import("./register"),
+ loading: Loading,
+});
+
+const ReviewTasks = Loadable({
+ loader: () => import("./reviewTasks"),
+ loading: Loading,
+})
+
+const TaskDetail = Loadable({
+ loader: () => import("./taskDetail"),
+ loading: Loading,
+})
+
+
+const ExpertUser = (propsF) => {
+ const functional = propsF.match.params.functional;
+ return (
+
+
+ 专家评审系统 >
+ {functional === 'register' && 登记专家资料}
+ {functional === 'tasks' && 我的评审任务}
+
+
+
+ 登记专家资料
+ {propsF.current_user.isExpert && 我的评审任务}
+
+
+ {
+ }
+ (
+
+ )}
+ >
+
+ (
+
+ )}
+ >
+
+
+ (
+
+ )}
+ >
+
+ (
+
+ )}
+ >
+
+
+
+
+
+ );
+}
+
+export default ExpertUser;
diff --git a/src/military/expert/expertUser/index.scss b/src/military/expert/expertUser/index.scss
new file mode 100644
index 00000000..416ea4da
--- /dev/null
+++ b/src/military/expert/expertUser/index.scss
@@ -0,0 +1,58 @@
+.centerbox.detail {
+ font-size: 20px;
+ .navigation {
+ font-size: 0.6em;
+ margin: -35px 0 15px;
+ a:hover{
+ color: #4154f1;
+ }
+ }
+
+ .center_flex {
+ display: flex;
+ justify-content: space-between;
+
+ .register_left {
+ display: flex;
+ flex-direction: column;
+ height: 10em;
+ width: 9.375rem;
+ font-size: 0.7em;
+ background-color: white;
+ padding: 0.4vw;
+ flex: none;
+ a{
+ padding: 0 1.3em;
+ margin: 5px;
+ height: 2.55em;
+ line-height: 2.55em;
+ border-radius: 4px;
+ &:hover{
+ color: #4154f1;
+ }
+ &.active {
+ color: white;
+ background-color: #4154f1;
+ &:hover{
+ opacity: .8;
+ }
+ }
+
+ }
+
+
+ }
+ .register_right {
+ flex: auto;
+ margin-left: .95rem;
+ .user-title{
+ border-bottom: 1px solid #eeeeee;
+ padding: 0.5em 2em;
+ color: #181818;
+ font-size: 1rem;
+ font-weight: bold;
+ background: white;
+ }
+ }
+ }
+}
diff --git a/src/military/expert/expertUser/register/image/required.svg b/src/military/expert/expertUser/register/image/required.svg
new file mode 100644
index 00000000..0af22cac
--- /dev/null
+++ b/src/military/expert/expertUser/register/image/required.svg
@@ -0,0 +1,13 @@
+
+
\ No newline at end of file
diff --git a/src/military/expert/expertUser/register/image/warning.svg b/src/military/expert/expertUser/register/image/warning.svg
new file mode 100644
index 00000000..3a44bfe1
--- /dev/null
+++ b/src/military/expert/expertUser/register/image/warning.svg
@@ -0,0 +1,17 @@
+
+
\ No newline at end of file
diff --git a/src/military/expert/expertUser/register/index.jsx b/src/military/expert/expertUser/register/index.jsx
new file mode 100644
index 00000000..b4f822c7
--- /dev/null
+++ b/src/military/expert/expertUser/register/index.jsx
@@ -0,0 +1,593 @@
+import React, { useEffect, useState, useCallback } from 'react';
+import { Button, Icon, Form, Modal, Input, Select, message } from 'antd';
+import Upload from '../../components/Upload';
+import { unitType, natureOfWork, highestEducation, positionLevel, professionalType, reviewArea } from '../../static';
+import { expertRegister, getCurrentExpert, getFile, expertUpdate } from '../../api';
+
+import './index.scss';
+import '../../index.scss';
+const Option = Select.Option;
+
+export default Form.create()(({ match, history, showNotification, form, current_user }) => {
+ const { getFieldDecorator, validateFields, setFieldsValue } = form;
+ const [cancelConfirmValue, setCancelConfirmValue] = useState(false);
+ const [submitConfirmValue, setSubmitConfirmValue] = useState(false);
+ const [expertRegisterValues, setExpertRegisterValues] = useState();
+ const [lastRegister, setLastRegister] = useState();
+ const [forbidden, setForbidden] = useState(false);
+
+ const [resumeList, setResumeList] = useState([]);
+ const [resumeIds, setResumeIds] = useState();
+
+ const [titleCertList, setTitleCertList] = useState([]);
+ const [titleCertIds, setTitleCertIds] = useState();
+
+ const [achievementList, setAchievementList] = useState([]);
+ const [achievementIds, setAchievementIds] = useState();
+
+ const [honorList, setHonorList] = useState([]);
+ const [honorIds, setHonorIds] = useState();
+
+ const [reload, setReload] = useState();
+
+ const [reviewAreaOne, setReviewAreaOne] = useState();
+ const [reviewAreaTwo, setReviewAreaTwo] = useState();
+ const [reviewAreaThree, setReviewAreaThree] = useState();
+
+ // 获取列表
+ useEffect(() => {
+ let params = {};
+ getCurrentExpert(params).then(async res => {
+ if (res && res.data && res.data.length) {
+ let lastRegister = res.data[0];
+ if (res.data.length > 1 && res.data[0].status === 1) {
+ lastRegister = res.data[1];
+ }
+ let params = {
+ bankAccount: lastRegister.bankAccount || "",
+ bankName: lastRegister.bankName || "",
+ expertEmail: lastRegister.expertEmail || "",
+ expertName: lastRegister.expertName || "",
+ expertType: lastRegister.expertType || "",
+ graduatedFrom: lastRegister.graduatedFrom || "",
+ highestDegree: lastRegister.highestDegree || "",
+ idNumber: lastRegister.idNumber || "",
+ major: lastRegister.major || "",
+ phone: lastRegister.phone || "",
+ professionalTitle: lastRegister.professionalTitle || "",
+ reviewAreaOne: lastRegister.reviewAreaOne || "",
+ reviewAreaTwo: lastRegister.reviewAreaTwo || "",
+ reviewAreaThree: lastRegister.reviewAreaThree || "",
+ titleRank: lastRegister.titleRank || "",
+ workNature: lastRegister.workNature || "",
+ workplace: lastRegister.workplace || "",
+ workplaceType: lastRegister.workplaceType || "",
+ }
+
+ setReviewAreaOne(lastRegister.reviewAreaOne);
+ setReviewAreaTwo(lastRegister.reviewAreaTwo);
+ setReviewAreaThree(lastRegister.reviewAreaThree);
+
+ setFieldsValue(params);
+ setExpertRegisterValues(params);
+ setLastRegister(lastRegister);
+ setForbidden(lastRegister && lastRegister.status === -1);
+
+ // 回写文件
+ if (lastRegister.resume) {
+ setResumeList(lastRegister.resumeAttachments);
+ setResumeIds(lastRegister.resume);
+
+ }
+
+ if (lastRegister.titleCertificate) {
+ setTitleCertList(lastRegister.titleCertificateAttachments);
+ setTitleCertIds(lastRegister.titleCertificate);
+ }
+
+ if (lastRegister.academicAchievements) {
+ setAchievementList(lastRegister.academicAchievementsAttachments);
+ setAchievementIds(lastRegister.academicAchievements);
+ }
+
+ if (lastRegister.honors) {
+ setHonorList(lastRegister.honorsAttachments);
+ setHonorIds(lastRegister.honors);
+ }
+ } else if(res && res.message=="未登录"){
+ history.push('/403');
+ }
+ else {
+ setForbidden(false);
+ }
+ });
+ }, [reload]);
+
+ function getFiles(ids) {
+ let idArr = ids.split(',');
+ let requireArr = idArr.map(i => {
+ return new Promise((resolve) => {
+ getFile(i).then((res) => {
+ if (res) {
+ res.data && resolve(res.data);
+ }
+ });
+ });
+ })
+ return Promise.all(requireArr);
+ }
+
+
+ // 上传附件后得到的文件数组
+ function uploadResume(fileList, files) {
+ setResumeList(fileList);
+ setResumeIds(files);
+ }
+
+ function uploadTitleCert(fileList, files) {
+ setTitleCertList(fileList);
+ setTitleCertIds(files);
+ }
+
+ function uploadAchievement(fileList, files) {
+ setAchievementList(fileList);
+ setAchievementIds(files);
+ }
+
+ function uploadHonor(fileList, files) {
+ setHonorList(fileList);
+ setHonorIds(files);
+ }
+
+
+ // form表单公共处理函数
+ const helper = useCallback(
+ (label, name, rules, widget) => (
+
+ {getFieldDecorator(name, { rules, validateFirst: true })(widget)}
+
+ ),
+ []
+ );
+
+ //表单提交
+ function expertRegisterSubmit(e) {
+ form.validateFields((err, values) => {
+ if (!err) {
+ setSubmitConfirmValue(true);
+ setExpertRegisterValues(values);
+ }
+ })
+ }
+
+ //注册
+ function expertRegisterOk() {
+ if (expertRegisterValues) {
+ let params = {
+ bankAccount: expertRegisterValues.bankAccount || "",
+ bankName: expertRegisterValues.bankName || "",
+ expertEmail: expertRegisterValues.expertEmail || "",
+ expertName: expertRegisterValues.expertName || "",
+ expertType: expertRegisterValues.expertType || "",
+ graduatedFrom: expertRegisterValues.graduatedFrom || "",
+ highestDegree: expertRegisterValues.highestDegree || "",
+ idNumber: expertRegisterValues.idNumber || "",
+ major: expertRegisterValues.major || "",
+ phone: expertRegisterValues.phone || "",
+ professionalTitle: expertRegisterValues.professionalTitle || "",
+ reviewAreaOne: expertRegisterValues.reviewAreaOne || "",
+ reviewAreaTwo: expertRegisterValues.reviewAreaTwo || "",
+ reviewAreaThree: expertRegisterValues.reviewAreaThree || "",
+ titleRank: expertRegisterValues.titleRank || "",
+ workNature: expertRegisterValues.workNature || "",
+ workplace: expertRegisterValues.workplace || "",
+ workplaceType: expertRegisterValues.workplaceType || "",
+ resume: resumeIds,
+ titleCertificate: titleCertIds,
+ academicAchievements: achievementIds,
+ honors: honorIds,
+ userId: current_user && current_user.user_id,
+ status: -1,
+ };
+
+ if (lastRegister && [2, 3].includes(lastRegister.status)) {
+ expertUpdate({
+ ...params,
+ id: lastRegister.id
+ }).then(res => {
+ dealBack(res);
+ });
+ } else {
+ expertRegister(params).then(res => {
+ dealBack(res)
+ });
+ }
+ }
+ }
+
+ function draft() {
+ form.validateFields((err, values) => {
+ if (!err) {
+ let params = {
+ ...values,
+ resume: resumeIds,
+ titleCertificate: titleCertIds,
+ academicAchievements: achievementIds,
+ honors: honorIds,
+ userId: current_user.user_id,
+ status: 3
+ };
+
+ if (lastRegister && [2, 3].includes(lastRegister.status)) {
+ expertUpdate({
+ ...params,
+ id: lastRegister.id
+ }).then(res => {
+ dealBack(res);
+ });
+ } else {
+ expertRegister(params).then(res => {
+ dealBack(res)
+ });
+ }
+ }
+ })
+ }
+
+ function dealBack(res) {
+ if (res && res.message && (res.message.indexOf("成功") > -1 || res.message.indexOf("更新") > -1)) {
+ message.success("保存成功")
+ setSubmitConfirmValue(false);
+ setReload(Math.random());
+ } else {
+ message.error(res && res.message || "保存失败");
+ }
+ }
+
+ function cancel() {
+ if (lastRegister && lastRegister.status === -1) {
+ history.go(-1);
+ } else {
+ setCancelConfirmValue(true);
+ }
+ }
+
+ return (
+
+ {
+ lastRegister && lastRegister.status === -1 &&
+ 您的资料正在审核,请耐心等待!
+
+ }
+ {
+ lastRegister && lastRegister.status === 2 &&
+ 您提交的资料已被拒绝,请完善资料后重新提交
+ {lastRegister.reviewerAdvice && 拒绝原因:{lastRegister.reviewerAdvice} }
+
+ }
+ {
+ lastRegister && lastRegister.status === 1 &&
+ 您的资料已审核通过,已成为专家!若修改资料,修改后需要管理员重新审核,审核过程中不会影响您的专家身份
+
+ }
+
+ 专家资料
+
+
+
+
+
+
+
+
+
+
+
+
+ 提示:个人简介、职称证明、学术成果、荣誉称号都只能上传一个文件,建议上传zip或rar格式的压缩文件
+
+
+ {/* 专家: 修改,非专家: 提交 */}
+
+ {(!lastRegister || lastRegister.status !== 1) && }
+
+
+ setSubmitConfirmValue(false)}
+ wrapClassName="expert_modal submit"
+ closeIcon={}
+ >
+ 资料提交后无法修改,将等待管理员审核,
+ 确认{lastRegister && lastRegister.status === 1 ? '修改' : '提交'}?
+
+
+ { history.go(-1) }}
+ onCancel={() => setCancelConfirmValue(false)}
+ wrapClassName="expert_modal"
+ >
+ 有内容没有保存,确定退出编辑吗?
+ 退出编辑后,更新的内容不会自动保存
+
+
+
+ )
+})
diff --git a/src/military/expert/expertUser/register/index.scss b/src/military/expert/expertUser/register/index.scss
new file mode 100644
index 00000000..3fe6d79e
--- /dev/null
+++ b/src/military/expert/expertUser/register/index.scss
@@ -0,0 +1,101 @@
+.center_flex {
+ display: flex;
+ justify-content: space-between;
+ .register_left {
+ height: 10em;
+ font-size: 0.7em;
+ background-color: white;
+ padding: 0.4vw;
+ }
+ .register_right {
+ .advance {
+ padding: 0.5em 2em;
+ color: #181818;
+ font-size: 0.9rem;
+ font-weight: bold;
+ margin-bottom: 1.25rem !important;
+ background: white;
+ }
+
+ .iconfont {
+ font-weight: 400;
+ }
+ .fail {
+ background: #ffefef;
+ border: 1px solid #ff3838;
+ color: #ff3838;
+ }
+
+ .checking {
+ background: #edf2ff;
+ border: 1px solid #4154f1;
+ color: #4154f1;
+ }
+ .succeed {
+ background: #edf2ff;
+ border: 1px solid green;
+ color: green;
+ }
+ .ant-form {
+ background-color: white;
+ padding: 1em 0;
+ }
+ .register-form {
+ .ant-form-item {
+ display: inline-block;
+ width: 44%;
+ margin: 1em 2.5% 0;
+ }
+ .hint {
+ margin: 1em 3% 0 4%;
+ color: #999;
+ }
+ .upload-form {
+ display: inline-flex;
+ align-items: flex-start;
+ }
+
+ .ant-form-item-label {
+ width: 6em;
+ line-height: 2.8em;
+ }
+ .ant-form-item-required::before {
+ position: relative;
+ top: -1px;
+ content: url("./image/required.svg");
+ }
+ .ant-form-item-control-wrapper {
+ width: 70%;
+ display: inline-block;
+ }
+ .ant-input,
+ .ant-select-selection {
+ // width: 30.1em;
+ box-shadow: none;
+ &:focus,
+ &:hover {
+ border: 1px solid #4154f1 !important;
+ }
+ }
+ .ant-input,
+ .ant-input .ant-input-suffix {
+ background-color: #ffffff !important;
+ }
+ .ant-select-open .ant-select-selection {
+ border: 1px solid #4154f1 !important;
+ }
+ }
+ .ant-cascader-menu-item:hover {
+ background: #f2f3ff;
+ }
+ .buts {
+ font-size: 0.7em;
+ padding: 1.5em 2em;
+ background-color: #f5f5f5;
+ }
+ }
+}
+.expert_register .ant-select-dropdown-menu-item:hover,
+.ant-select-dropdown-menu-item-active:not(.ant-select-dropdown-menu-item-disabled) {
+ background-color: #f2f3ff;
+}
diff --git a/src/military/expert/expertUser/reviewTasks/index.jsx b/src/military/expert/expertUser/reviewTasks/index.jsx
new file mode 100644
index 00000000..2d5953b6
--- /dev/null
+++ b/src/military/expert/expertUser/reviewTasks/index.jsx
@@ -0,0 +1,203 @@
+import React, { useState, useCallback, useMemo, useEffect } from "react";
+import { Input, Select, Button, Form, DatePicker, Table, Pagination, Upload, Modal } from 'antd';
+import { Link } from "react-router-dom";
+import { formatDuring } from 'educoder';
+import Paginationtable from "../../../components/paginationTable";
+import { getExpertTasks } from "../../api";
+import { taskType, expertTaskStatus } from "../../static";
+import { main_web_site_url } from '../../fetch';
+
+import './index.scss';
+import '../../index.scss';
+const Option = Select.Option;
+
+function ReviewTasks({ form, showNotification, match, history }) {
+ const { getFieldDecorator, setFieldsValue, getFieldsValue } = form;
+
+ const [reload, setReload] = useState();
+ const [loading, setLoading] = useState(false);
+ const [curPage, setCurPage] = useState(1);
+ const [pageSize, setPageSize] = useState(10);
+ const [dataList, setDataList] = useState([]);
+ const [total, setTotal] = useState(0);
+
+ let initSearchObj = sessionStorage.expertTask ? JSON.parse(sessionStorage.expertTask) : {
+ containerName: '',
+ containerType: 1,
+ statusString: -1,
+ };
+ const [searchObj, setSearchObj] = useState(initSearchObj);
+
+ useEffect(() => {
+ setFieldsValue(initSearchObj);
+ }, []);
+
+ const columns = useMemo(() => {
+ return [
+ {
+ title: '序号',
+ dataIndex: 'index',
+ render: (text, record, index) => {
+ return index + 1
+ }
+ },
+ {
+ title: '任务名称',
+ dataIndex: 'containerName',
+ key: 'containerName',
+ render: (text, record) => {
+ return record.containerType===1?{text}:
+ {text}
+ }
+ },
+ {
+ title: '评审截止时间',
+ dataIndex: 'reviewEndOn',
+ key: 'reviewEndOn',
+ },
+ {
+ title: '剩余评审时间',
+ dataIndex: 'surplus',
+ key: 'surplus',
+ },
+ {
+ title: '评审状态',
+ dataIndex: 'status',
+ key: 'status',
+ render: (text, record) => {
+ return text === -1 ? '未评审' : record.commitReview ? '已评审' : '已过期'
+ }
+ },
+ {
+ title: '操作',
+ dataIndex: 'status',
+ key: 'action',
+ render: (text, record) => {
+ return {text === -1 ? '评审' : '查看结果'}
+ }
+ }
+ ];
+ }, []);
+
+ // 获取列表
+ useEffect(() => {
+ setLoading(true);
+ let params = {
+ ...searchObj,
+ pageSize,
+ curPage,
+ };
+ getExpertTasks(params).then(res => {
+ for (const item of res.data.rows) {
+ if (new Date(item.reviewEndOn) > new Date()) {
+ item.surplus = formatDuring((new Date(item.reviewEndOn) - new Date()) / 1000);
+ } else {
+ item.surplus = '- -';
+ }
+ }
+ setDataList(res.data.rows || []);
+ setLoading(false);
+ setTotal(res.data.total);
+ });
+ }, [searchObj, curPage, reload, pageSize]);
+
+
+ function onSearch() {
+ let values = getFieldsValue(['containerName', 'containerType', 'statusString']);
+ sessionStorage.setItem('expertTask', JSON.stringify(values));
+ setSearchObj(values);
+ }
+
+ function clearSearch() {
+ let initSearchObj={
+ containerName: '',
+ containerType: 1,
+ statusString: -1,
+ };
+ setFieldsValue(initSearchObj);
+ setSearchObj(initSearchObj);
+ sessionStorage.setItem('expertTask', JSON.stringify(initSearchObj));
+ setCurPage(1);
+ }
+
+
+ const helper = useCallback(
+ (label, name, rules, widget, initialValue) => (
+
+ {getFieldDecorator(name, { rules, initialValue, validateFirst: true, })(widget)}
+
+ ), []);
+
+
+ function onShowSizeChange(current, pageSize) {
+ setCurPage(current);
+ setPageSize(pageSize);
+ }
+
+ return (
+
+
+ 我的评审任务
+
+
+ {helper(
+ "任务名称",
+ "containerName",
+ [{ max: 20, message: '长度不能超过20个字符' }],
+
+ )}
+
+ {helper(
+ "任务类型",
+ "containerType",
+ [],
+ ,
+ 1
+ )}
+
+ {helper(
+ "评审状态",
+ "statusString",
+ [],
+ ,
+ -1
+ )}
+
+
+
+
+
+
+
+
+
+ )
+}
+export default Form.create()(ReviewTasks);
\ No newline at end of file
diff --git a/src/military/expert/expertUser/reviewTasks/index.scss b/src/military/expert/expertUser/reviewTasks/index.scss
new file mode 100644
index 00000000..056f24c6
--- /dev/null
+++ b/src/military/expert/expertUser/reviewTasks/index.scss
@@ -0,0 +1,45 @@
+.register_right.task_right {
+ background: #fff;
+ padding-bottom: 1rem;
+ .search-list {
+ display: flex;
+ flex-wrap: wrap;
+ margin: 0;
+ padding: 1rem 2rem;
+ // align-items: center;
+ .ant-form-item {
+ width: 48%;
+ margin-bottom:1rem;
+ label{
+ font-weight: bold;
+ }
+ }
+ .ant-col{
+ display: inline-block;
+ }
+ }
+ .pagination-table .ant-table-thead tr th div {
+ font-weight: bold;
+ }
+ .task-head {
+ border-bottom: 1px solid #eeeeee;
+ padding: 0.5em 2em;
+ color: #181818;
+ background: #fff;
+ font-size: 0.8em;
+ font-weight: bold;
+ }
+ .button-div {
+ margin-left:.25rem;
+ line-height: 1.5;
+ }
+ .pagination-table{
+ margin:0 2rem;
+ .toReview{
+ color: #4154f1;
+ &:hover{
+ opacity: 0.8;
+ }
+ }
+ }
+}
diff --git a/src/military/expert/expertUser/taskDetail/index.jsx b/src/military/expert/expertUser/taskDetail/index.jsx
new file mode 100644
index 00000000..04e020b1
--- /dev/null
+++ b/src/military/expert/expertUser/taskDetail/index.jsx
@@ -0,0 +1,511 @@
+import React, { useState, useCallback, useMemo, useEffect } from "react";
+import { Tabs, Button, Form, InputNumber, Modal, Tooltip, } from 'antd';
+import { Link } from "react-router-dom";
+import Paginationtable from "../../../components/paginationTable";
+import { Info, Confirm } from '../../../components/ModalFun';
+import WordsInput from 'military/expert/components/wordsInput';
+import { getScoringDetails, initScoringDetails, getRules, updateScoringDetails, getCompetition } from "../../api";
+import { readyCheckPapers } from "../../../task/api";
+import { httpUrl, main_web_site_url } from '../../fetch';
+
+import './index.scss';
+import '../../index.scss';
+const { TabPane } = Tabs;
+
+function ReviewTasks({ showNotification, match, history, current_user }) {
+ const containerId = match.params.containerId;
+ const containerType = match.params.containerType;
+
+ // 主table参数
+ const [reload, setReload] = useState();
+ const [loading, setLoading] = useState(false);
+ const [dataList, setDataList] = useState([]);
+
+ const [taskId, setTaskId] = useState();
+ const [competitionId, setCompetitionId] = useState();
+
+ // 评分规则
+ const [rules, setRules] = useState({});
+
+ // 模态框
+ const [visible, setVisible] = useState(false);
+ const [activeIndex, setActiveIndex] = useState(false);
+ const [comments, setComments] = useState();
+
+ // 按钮禁止提交
+ const [disabled, setDisabled] = useState(false);
+
+ // 通用列
+ const columns = [
+ {
+ title: '序号',
+ dataIndex: 'index',
+ width: 50,
+ render: (text, record, index) => {
+ return index + 1
+ }
+ },
+ {
+ title: '投稿详情',
+ dataIndex: 'opsContent',
+ key: 'opsContent',
+ className: 'text-tooltip',
+ render: (text, record, index) => {
+ return {text}
+ }
+ },
+ {
+ title: '附件下载',
+ dataIndex: 'opsFilesAttachments',
+ key: 'opsFilesAttachments',
+ className: 'text-tooltip',
+ render: (text, record) => {
+ return text && text.map(item => {
+ return
+ { downFile(item) }}>{item.fileName}
+
+ })
+ }
+ },
+
+ {
+ title: '平均分',
+ dataIndex: 'gradesAverage',
+ key: 'gradesAverage',
+ width: 70,
+ },
+ {
+ title: '评审意见',
+ dataIndex: 'comments',
+ key: 'comments',
+ width: 80,
+ render: (text, record, index) => {
+ return
+ { writeComments(text, index, 'comments') }}>{record.status === 2 ? text ? '编辑' : '填写' : '查看'}意见
+
+
+ }
+ },
+ ];
+
+ // 评分列
+ const gradesColumns = [{
+ title: '评分一',
+ dataIndex: 'gradesOne',
+ key: 'gradesOne',
+ render: (text, record, index) => {
+ return { editGrade(value, index, 'gradesOne') }}
+ />
+ }
+ },
+ {
+ title: '评分二',
+ dataIndex: 'gradesTwo',
+ key: 'gradesTwo',
+ render: (text, record, index) => {
+ return { editGrade(value, index, 'gradesTwo') }}
+ />
+ }
+ },
+ {
+ title: '评分三',
+ dataIndex: 'gradesThree',
+ key: 'gradesThree',
+ render: (text, record, index) => {
+ return { editGrade(value, index, 'gradesThree') }}
+ />
+ }
+ },
+ {
+ title: '评分四',
+ dataIndex: 'gradesFour',
+ key: 'gradesFour',
+ render: (text, record, index) => {
+ return { editGrade(value, index, 'gradesFour') }}
+ />
+ }
+ },
+ {
+ title: '评分五',
+ dataIndex: 'gradesFive',
+ key: 'gradesFive',
+ render: (text, record, index) => {
+ return { editGrade(value, index, 'gradesFive') }}
+ />
+ }
+ }];
+
+ let gradesNum = rules.criterias && rules.criterias.length;
+
+ if (gradesNum) {
+ let thisGradesColumns = gradesColumns.slice(0, gradesNum);
+ columns.splice(3, 0, ...thisGradesColumns);
+ }
+
+ useEffect(() => {
+ getRules({ containerId, containerType }).then(res => {
+ if (res && res.message === "success") {
+ setRules(res.data);
+ if (res.data.status === 1 || res.data.status === 2) {
+ setDisabled(true);
+ }
+ }
+ });
+ }, [])
+
+ // 获取成果列表
+ useEffect(() => {
+ let params = {
+ taskId,
+ checkStatus: '1',
+ pageSize: 10000,
+ curPage: 1,
+ status: '',
+ parentId: 0,
+ }
+ // 没有数据才能去查成果,并展示数据
+ !dataList.length && taskId && current_user.expertId && readyCheckPapers(params).then(data => {
+ let dataArr = [];
+ if (data && Array.isArray(data.rows)) {
+ for (const item of data.rows) {
+ dataArr.push({
+ comments: "",
+ expertId: current_user.expertId,
+ gradesAverage: '',
+ gradesFive: '',
+ gradesFour: '',
+ gradesOne: '',
+ gradesThree: '',
+ gradesTwo: '',
+ opsContent: item.paperDetail && item.paperDetail.content,
+ opsFiles: item.paperDetail && item.paperDetail.files,
+ opsFilesAttachments: item.paperDetail && item.paperDetail.busiAttachments,
+ opsId: item.id,
+ opsParentId: containerId,
+ opsParentType: containerType,
+ opsType: containerType,
+ status: 2
+ });
+ }
+ }
+ setDataList(dataArr);
+ disabled && setLoading(false);
+ !disabled && dataArr.length && rules && initScoringDetails(dataArr).then(res => {
+ if (res) {
+ setReload(Math.random());
+ setLoading(false);
+ }
+ });
+ });
+ }, [taskId, disabled, current_user.expertId]);
+
+ // 获取竞赛作品列表
+ useEffect(() => {
+ // 没有数据才能去查作品列表,并展示数据
+ !dataList.length && competitionId && current_user.expertId && getCompetition(competitionId).then(res => {
+ let dataArr = [];
+ if (res && Array.isArray(res.data)) {
+ for (const item of res.data) {
+ dataArr.push({
+ comments: "",
+ expertId: current_user.expertId,
+ gradesAverage: '',
+ gradesFive: '',
+ gradesFour: '',
+ gradesOne: '',
+ gradesThree: '',
+ gradesTwo: '',
+ opsContent: item.works_remark,
+ opsFiles: item.work_file.id,
+ opsFilesAttachments: item.work_file,
+ opsId: item.id,
+ opsParentId: containerId,
+ opsParentType: containerType,
+ opsType: containerType,
+ status: 2
+ });
+ }
+ }
+ setDataList(dataArr);
+ !dataArr.length && setLoading(false);
+ disabled && setLoading(false);
+ !disabled && dataArr.length && rules && initScoringDetails(dataArr).then(res => {
+ if (res) {
+ setReload(Math.random());
+ setLoading(false);
+ }
+ });
+ });
+ }, [competitionId, disabled, current_user.expertId]);
+
+
+ function downFile(item) {
+ if (containerType == 1) {
+ let url = httpUrl + '/busiAttachments/download/' + item.id;
+ window.open(url);
+ } else {
+ let url = main_web_site_url + `/attachments/send_file/${item.id}?disposition=attachment`;
+ window.open(url);
+ }
+ }
+
+ function editGrade(value, index, dataIndex) {
+ let dataListNew = dataList.slice();
+ dataListNew[index][dataIndex] = value;
+ // 计算平均分
+ if (gradesNum) {
+ let gradesArr = [];
+ let item = dataListNew[index];
+ typeof item.gradesOne === 'number' && gradesArr.push(item.gradesOne);
+ typeof item.gradesTwo === 'number' && gradesArr.push(item.gradesTwo);
+ typeof item.gradesThree === 'number' && gradesArr.push(item.gradesThree);
+ typeof item.gradesFour === 'number' && gradesArr.push(item.gradesFour);
+ typeof item.gradesFive === 'number' && gradesArr.push(item.gradesFive);
+ if (gradesArr.length === gradesNum) {
+ const sum = gradesArr.reduce((previousValue, currentValue) => { return previousValue + currentValue }, 0);
+ const ave = (sum / gradesNum).toFixed(2);
+ dataListNew[index].gradesAverage = ave > 100 ? 100 : ave;
+ } else {
+ dataListNew[index].gradesAverage = '';
+ }
+ }
+
+ setDataList(dataListNew);
+ }
+
+ // 获取评分列表
+ useEffect(() => {
+ setLoading(true);
+ let params = {
+ containerId,
+ containerType,
+ expertId: current_user.expertId,
+ };
+ current_user.expertId && getScoringDetails(params).then(res => {
+ if (res.data && res.data.length) {
+ setDataList(res.data);
+ setLoading(false);
+ if (res.data[0].status === 1) {
+ setDisabled(true);
+ }
+ } else {
+ containerType == 1 ? setTaskId(containerId) : setCompetitionId(containerId);
+ }
+ });
+ }, [reload, current_user.expertId]);
+
+
+ function cancel() {
+ history.go(-1);
+ }
+
+ function writeComments(text, index) {
+ setVisible(true);
+ setActiveIndex(index);
+ setComments(text);
+ }
+
+ // 修改意见
+ function commit() {
+ if (disabled) {
+ setVisible(false);
+ return;
+ }
+ if (comments) {
+ let data = dataList[activeIndex];
+ let dataListNew = dataList.slice();
+ data.comments = comments;
+ updateScoringDetails([data]).then(res => {
+ if (res && res.message) {
+ if (res.message.indexOf("成功")) {
+ showNotification("保存成功");
+ dataListNew[activeIndex].comments = comments;
+ setDataList(dataListNew);
+ setVisible(false);
+ } else {
+ showNotification(res.message);
+ }
+ }
+ })
+ }
+ }
+
+ // 提交草稿
+ function draft() {
+ updateScoringDetails(dataList).then(res => dealCommitRes(res));
+ }
+
+ // 提交评审结果
+ function commitGrades() {
+ if (verify()) {
+ Confirm({
+ title: '提醒',
+ okText: '确定提交',
+ content:
+ 提交后将完成此次评审,无法继续修改评分与评审意见
+ 确定提交此次评审结果?
+ ,
+ onOk: () => {
+ let dataArr = dataList.slice();
+ for (const item of dataArr) {
+ item.status = 1;
+ }
+ updateScoringDetails(dataArr).then(res => dealCommitRes(res));
+ }
+ });
+ }
+ }
+
+ // 提交前校验
+ function verify() {
+ let errorArr = [];
+ let commentsError = [];
+ let scoringArr = [];
+ for (const [index, item] of dataList.entries()) {
+ let gradesArr = [];
+ typeof item.gradesOne === 'number' && gradesArr.push(item.gradesOne);
+ typeof item.gradesTwo === 'number' && gradesArr.push(item.gradesTwo);
+ typeof item.gradesThree === 'number' && gradesArr.push(item.gradesThree);
+ typeof item.gradesFour === 'number' && gradesArr.push(item.gradesFour);
+ typeof item.gradesFive === 'number' && gradesArr.push(item.gradesFive);
+ if (gradesArr.length < gradesNum && gradesArr.length) {
+ errorArr.push(index + 1);
+ } else if (!item.comments && gradesArr.length) {
+ commentsError.push(index + 1);
+ } else if (gradesArr.length) {
+ scoringArr.push(index);
+ }
+ }
+
+ if (errorArr.length) {
+ Info({
+ title: '提醒',
+ content: `第${errorArr.join(',')}行数据请填写完整`,
+ });
+ return;
+ }
+
+ if (commentsError.length) {
+ Info({
+ title: '提醒',
+ content: `第${commentsError.join(',')}行数据请填写意见`,
+ });
+ return;
+ }
+
+ if (!scoringArr.length) {
+ Info({
+ title: '提醒',
+ content: '请至少填写一行分数',
+ });
+ return;
+ }
+
+ return !errorArr.length && !commentsError.length;
+ }
+
+ function dealCommitRes(res) {
+ if (res && res.message) {
+ if (res.message.indexOf("成功")) {
+ showNotification("保存成功");
+ setReload(Math.random());
+ } else {
+ showNotification(res.message);
+ }
+ }
+ }
+
+ return (
+
+
+ {containerType == 1 ? '创客成果' : '竞赛作品'}评审
+
+
+
+
+
+
+
+
+ {containerType == 1 ? '任务信息' : '赛事信息'}
+
+
+ {containerType == 1 ? '任务' : '赛事'}名称
+ {rules.containerName}
+
+
+
+
+
+
+
+
+ 评分标准
+
+ {rules.criterias && rules.criterias.map((item, index) => { return {item} })}
+
+
+
+
+ 评审时间
+ {rules.reviewData}
+
+
+
+
+
+
+
+ 对单个作品评分时,需填写完整每个评分项及评审意见,请勿少填、漏填
+
+
+
+
+
+
+
+
+
+
+
+
+ { setVisible(false) }}
+ className="form-edit-modal"
+ >
+
+
+
+
+
+ )
+}
+export default ReviewTasks;
\ No newline at end of file
diff --git a/src/military/expert/expertUser/taskDetail/index.scss b/src/military/expert/expertUser/taskDetail/index.scss
new file mode 100644
index 00000000..67b1838f
--- /dev/null
+++ b/src/military/expert/expertUser/taskDetail/index.scss
@@ -0,0 +1,115 @@
+.register_right.task_detail {
+ background: #fff;
+ padding-bottom: 1rem;
+
+ .ant-tabs {
+ background: #f5f5f5;
+ .ant-tabs-content {
+ background: #fff;
+ }
+ .ant-tabs-bar {
+ background: #fff;
+ margin-bottom: 1.25rem;
+ }
+
+ .ant-tabs-tab {
+ margin: 0;
+ padding: 19px 32px;
+ font-size: 1rem;
+ &:hover {
+ color: #4154f1;
+ }
+ }
+
+ .ant-tabs-ink-bar {
+ background-color: #4154f1;
+ }
+ }
+
+ .ant-tabs-nav .ant-tabs-tab-active, .taskLink {
+ color: #4154f1;
+ }
+ .taskLink:hover{
+ opacity: 0.8;
+ }
+ .rules-head, .task-head, .ant-tabs-nav .ant-tabs-tab-active, .font-w, .pagination-table .ant-table-thead tr th div{
+ font-weight: bold;
+ }
+
+ .task-head {
+ position: relative;
+ border-bottom: 1px solid #eeeeee;
+ padding: 0.5em 2em;
+ color: #181818;
+ background: #fff;
+ font-size: 0.8em;
+ .back-button{
+ position: absolute;
+ z-index: 1;
+ right: 1rem;
+ bottom: -52px;
+ padding: 0 10px;
+ }
+ }
+ .button-div {
+ line-height: 1.5;
+ }
+ .pagination-table {
+ margin: .75rem 1.75rem 1.25rem;
+ a{
+ color: #4154f1;
+ &:hover{
+ opacity: 0.8;
+ }
+ }
+ }
+
+ .task-rules {
+ background: #f5f5f5;
+ .rules-box{
+ margin-bottom: 1.25rem;
+ background: #fff;
+ }
+ .rules-head {
+ font-size: 16px;
+ color: rgba(51, 51, 51, 1);
+ border-bottom: 1px solid #eeeeee;
+ padding: 10px 20px;
+ }
+ .rules-content{
+ padding: 10px 20px 30px;
+ }
+ .rules-content-last{
+ padding: 10px 20px;
+ }
+ .rules-content-item{
+ line-height: 2rem;
+ }
+ }
+
+ .warning{
+ color: #DE0000;
+ font-size: .7rem;
+ margin: .75rem 1.75rem;
+ }
+
+ .text-tooltip{
+ max-width: 150px;
+ overflow: hidden;
+ span{
+ display: block;
+ white-space: nowrap;
+ overflow: hidden;
+ text-overflow: ellipsis;
+ }
+ .link{
+ color: #4154f1;
+ white-space: nowrap;
+ overflow: hidden;
+ text-overflow: ellipsis;
+ &:hover{
+ opacity: 0.8;
+ }
+ }
+ }
+}
diff --git a/src/military/expert/fetch.js b/src/military/expert/fetch.js
new file mode 100644
index 00000000..e6d22ff3
--- /dev/null
+++ b/src/military/expert/fetch.js
@@ -0,0 +1,11 @@
+
+import javaFetch from '../javaFetch';
+
+
+let settings = localStorage.chromesetting && JSON.parse(localStorage.chromesetting);
+let actionUrl = settings && settings.api_urls && settings.api_urls.expert ? settings.api_urls.expert : 'http://117.50.100.12:8066';
+// http://117.50.100.12:8067/
+const service = javaFetch(actionUrl);
+export const httpUrl = actionUrl;
+export const main_web_site_url = settings && settings.main_web_site_url;
+export default service;
\ No newline at end of file
diff --git a/src/military/expert/image/warning.svg b/src/military/expert/image/warning.svg
new file mode 100644
index 00000000..3a44bfe1
--- /dev/null
+++ b/src/military/expert/image/warning.svg
@@ -0,0 +1,17 @@
+
+
\ No newline at end of file
diff --git a/src/military/expert/index.scss b/src/military/expert/index.scss
new file mode 100644
index 00000000..8f2cb28e
--- /dev/null
+++ b/src/military/expert/index.scss
@@ -0,0 +1,181 @@
+// 公共样式
+.but41_fill,
+.but41_border,
+.butE3_border {
+ padding: 0 1.3em;
+ height: 36px;
+ border-radius: 4px;
+ cursor: pointer;
+}
+.but41_fill {
+ color: white;
+ background-color: #4154f1;
+ &:hover {
+ background-color: #5d6eff;
+ }
+ &:active {
+ background-color: #374bf2;
+ }
+}
+.but41_border {
+ color: #4154f1;
+ border: 1px solid #4154f1;
+ &:hover {
+ color: #5d6eff;
+ border: 1px solid #5d6eff;
+ }
+ &:active {
+ color: #374bf2;
+ border: 1px solid #374bf2;
+ }
+}
+.butE3_border {
+ color: #404660;
+ border: 1px solid #e3e7ed;
+ &:hover {
+ background-color: #f8f8f8;
+ border: 1px solid #e3e7ed;
+ }
+ &:active {
+ background-color: #f3f3f3;
+ border: 1px solid #e3e7ed;
+ }
+}
+
+.ant-btn-primary {
+ background-color: #4154f1;
+ border-color: #4154f1;
+ &:hover,
+ &:active,
+ &:focus {
+ background-color: #5d6eff;
+ border-color: #5d6eff;
+ }
+}
+
+.font-w{
+ font-weight: bold;
+}
+.font-color-18{
+ color: #181818;
+}
+.mt10.pb20 .taskLink{
+ color:#4154F1;
+ &:hover{opacity: 0.8;}
+}
+
+//弹出确认框样式
+.expert_modal .ant-modal-content {
+ width: 550px;
+ height: 318px;
+ .ant-modal-header {
+ padding: 0.6em 2.1em;
+ background: #f2f2ff;
+ .ant-modal-title {
+ text-align: left;
+ }
+ }
+ .ant-modal-body {
+ padding-left: 120px;
+ p {
+ font-size: 16px;
+ color: #666666;
+ font-family: PingFangSC-Regular, PingFang SC;
+ line-height: 2.9em;
+ }
+ .weight_bold {
+ font-weight: bold;
+ }
+ .warning::before {
+ content: url("./image/warning.svg");
+ width: 32px;
+ position: relative;
+ top: 11px;
+ left: -15px;
+ }
+ }
+ .ant-btn {
+ padding: 0 1.3em;
+ height: 2.55em;
+ border-radius: 4px;
+ cursor: pointer;
+ color: #404660;
+ border: 1px solid #e3e7ed;
+ width: 7em;
+ &:hover {
+ background-color: #f8f8f8;
+ border: 1px solid #e3e7ed;
+ }
+ &:active {
+ background-color: #f3f3f3;
+ border: 1px solid #e3e7ed;
+ }
+ }
+ .ant-btn.ant-btn-primary {
+ color: white;
+ background-color: #4154f1;
+ margin-left: 2.5em;
+ &:hover {
+ background-color: #5d6eff;
+ }
+ &:active {
+ background-color: #374bf2;
+ }
+ }
+ .ant-modal-footer {
+ margin-top: 15px;
+ }
+}
+.expert_modal.submit .ant-modal-body {
+ padding-left: 0;
+ text-align: center;
+}
+
+.ant-form-explain,
+.ant-form-split {
+ position: absolute;
+ margin-top: -5px;
+ font-size: 12px;
+ color: #f5222d;
+}
+
+.form-edit-modal {
+ .ant-modal-header {
+ background: #f2f2ff;
+ padding: 9px 24px;
+ .ant-modal-title {
+ text-align: left;
+ }
+
+
+ }
+
+ .ant-modal-close {
+ top: 0px !important;
+ }
+
+ .ant-modal-body{
+ padding-bottom: 0;
+ }
+ .ant-form-item{
+ margin-bottom: 24px;
+ }
+ .ant-form-explain, .ant-form-extra{
+ margin-top: 0;
+ }
+ .ant-modal-footer{
+ padding-bottom: 1.5rem;
+ }
+}
+
+.expert-tooltip{
+ .ant-tooltip-inner{
+ background-color: #fff;
+ color: #333;
+ }
+ .ant-tooltip-arrow::before{
+ background-color: #fff;
+ }
+}
+
+
diff --git a/src/military/expert/registerList/index.jsx b/src/military/expert/registerList/index.jsx
new file mode 100644
index 00000000..b6895c04
--- /dev/null
+++ b/src/military/expert/registerList/index.jsx
@@ -0,0 +1,300 @@
+import React, { useState, useCallback, useMemo, useEffect } from "react";
+import { Input, Select, Button, Form, Modal } from 'antd';
+import Paginationtable from "../../components/paginationTable";
+import { Confirm } from '../../components/ModalFun';
+import { expertList, registerCheck } from "../api";
+import { httpUrl } from '../fetch';
+
+import './index.scss';
+import '../index.scss';
+const { Search, TextArea } = Input;
+
+function RegisterList({ showNotification, form }) {
+ const { getFieldDecorator, validateFields, setFieldsValue, } = form;
+ const [reload, setReload] = useState();
+ const [loading, setLoading] = useState(false);
+ const [curPage, setCurPage] = useState(1);
+ const [dataList, setDataList] = useState([]);
+ const [total, setTotal] = useState(0);
+ const [searchInput, setSearchInput] = useState('');
+ const [pageSize, setPageSize] = useState(10);
+
+ const [visible, setVisible] = useState(false);
+ const [active, setActive] = useState({});
+
+ const columns = useMemo(() => {
+ return [{
+ title: '姓名',
+ dataIndex: 'expertName',
+ width: 75,
+ key: 'expertName',
+ fixed: 'left',
+ // render: (text, record) => {
+ // return record.user ? record.user.nickname || record.user.login : ''
+ // }
+ },
+ {
+ title: '最高学历',
+ dataIndex: 'highestDegree',
+ key: 'highestDegree',
+ width: 80,
+ },
+ {
+ title: '手机号码',
+ dataIndex: 'phone',
+ key: 'phone',
+ },
+ {
+ title: '工作单位',
+ dataIndex: 'workplace',
+ key: 'workplace',
+ },
+ {
+ title: '单位类别',
+ dataIndex: 'workplaceType',
+ width: 80,
+ },
+ {
+ title: '工作性质',
+ dataIndex: 'workNature',
+ width: 80,
+ },
+ {
+ title: '专业职称',
+ dataIndex: 'professionalTitle',
+ width: 120,
+ },
+ {
+ title: '职称职级',
+ dataIndex: 'titleRank',
+ width: 80,
+ },
+ {
+ title: '专家类别',
+ dataIndex: 'expertType',
+ width: 80,
+ },
+ {
+ title: '评审领域1',
+ dataIndex: 'reviewAreaOne',
+ width: 100,
+ },
+ {
+ title: '评审领域2',
+ dataIndex: 'reviewAreaTwo',
+ width: 100,
+ },
+ {
+ title: '评审领域3',
+ dataIndex: 'reviewAreaThree',
+ width: 100,
+ },
+ {
+ title: '毕业院校',
+ dataIndex: 'graduatedFrom',
+ },
+ {
+ title: '院校专业',
+ dataIndex: 'major',
+ },
+ {
+ title: '身份证号',
+ dataIndex: 'idNumber',
+ width: 170,
+ },
+ {
+ title: '邮箱地址',
+ dataIndex: 'expertEmail',
+ width: 200,
+ },
+ {
+ title: '开户银行',
+ dataIndex: 'bankName',
+ width: 110,
+ },
+ {
+ title: '银行账号',
+ dataIndex: 'bankAccount',
+ },
+ {
+ title: '个人简介',
+ dataIndex: 'resumeAttachments',
+ render: (text, record) => {
+ return text && text.map(item => {
+ return {downFile(item.id)}}>{item.fileName}
+ })
+ }
+ },
+ {
+ title: '职称证明',
+ dataIndex: 'titleCertificateAttachments',
+ render: (text, record) => {
+ return text && text.map(item => {
+ return {downFile(item.id)}}>{item.fileName}
+ })
+ }
+ },
+ {
+ title: '学术成果',
+ dataIndex: 'academicAchievementsAttachments',
+ render: (text, record) => {
+ return text && text.map(item => {
+ return {downFile(item.id)}}>{item.fileName}
+ })
+ }
+ },
+ {
+ title: '荣誉称号',
+ dataIndex: 'honorsAttachments',
+ render: (text, record) => {
+ return text && text.map(item => {
+ return {downFile(item.id)}}>{item.fileName}
+ })
+ }
+ },
+ {
+ title: '操作',
+ dataIndex: 'action',
+ width: 120,
+ fixed: 'right',
+ render: (text, record) => {
+ return
+
+
+
+ }
+ }
+ ];
+ }, []);
+
+ function downFile(id) {
+ let url = httpUrl + '/busiAttachments/download/' + id;
+ window.open(url);
+ }
+
+ function onShowSizeChange(current, pageSize){
+ setCurPage(current);
+ setPageSize(pageSize);
+ }
+
+ // 获取列表
+ useEffect(() => {
+ setLoading(true);
+ let params = {
+ searchInput,
+ pageSize,
+ curPage,
+ statusString: '-1',
+ };
+ expertList(params).then(data => {
+ if (data && Array.isArray(data.rows)) {
+ for (const item of data.rows) {
+ item.detail = item.paperDetail && item.paperDetail.content;
+ }
+ }
+ setDataList(data.rows || []);
+ setLoading(false);
+ setTotal(data.total);
+ });
+ }, [curPage, reload, searchInput]);
+
+ function check(record, checkStatus) {
+ Confirm({
+ title: "提醒",
+ content: checkStatus == '1' ? "您确定要审核通过吗?通过后该用户将成为专家库的一员" : "您确定要拒绝吗?拒绝后该用户此次不能成为专家",
+ okText: '确定',
+ cancelText: '取消',
+ onOk() {
+ registerCheck({
+ expertId: record.id,
+ isPassed: checkStatus,
+ userId: record.userId,
+ }).then(res => {
+ if (res.message === 'success') {
+ showNotification('操作成功!');
+ setReload(Math.random());
+ }
+ });
+ },
+ });
+ }
+
+ const helper = useCallback(
+ (name, rules, widget) => (
+
+ {getFieldDecorator(name, { rules, validateFirst: true })(widget)}
+
+ ),
+ []
+ );
+
+ function refuse() {
+ validateFields((err, values) => {
+ if (!err) {
+ registerCheck({
+ expertId: active.id,
+ isPassed: 2,
+ userId: active.userId,
+ reviewerAdvice:values.reviewerAdvice,
+ }).then(res => {
+ if (res.message === 'success') {
+ showNotification('操作成功!');
+ setReload(Math.random());
+ setFieldsValue({
+ reviewerAdvice:''
+ });
+ setVisible(false);
+ setActive({});
+ }
+ });
+ }
+ });
+
+
+ }
+
+
+
+ return (
+
+
+ { setSearchInput(value); setCurPage(1); }}
+ />
+
+
+
+ { setVisible(false) }}
+ className="form-edit-modal"
+ >
+ {helper(
+ "reviewerAdvice",
+ [{ required: visible, message: '请给出拒绝的原因' }],
+
+ )}
+
+ )
+}
+export default Form.create()(RegisterList);
\ No newline at end of file
diff --git a/src/military/expert/registerList/index.scss b/src/military/expert/registerList/index.scss
new file mode 100644
index 00000000..443ae6dc
--- /dev/null
+++ b/src/military/expert/registerList/index.scss
@@ -0,0 +1,5 @@
+.expert-list{
+ .ant-table-thead > tr > th, .ant-table-tbody > tr > td{
+ padding:16px 6px;
+ }
+}
\ No newline at end of file
diff --git a/src/military/expert/review/image/system.svg b/src/military/expert/review/image/system.svg
new file mode 100644
index 00000000..6282989e
--- /dev/null
+++ b/src/military/expert/review/image/system.svg
@@ -0,0 +1,26 @@
+
+
\ No newline at end of file
diff --git a/src/military/expert/review/review.jsx b/src/military/expert/review/review.jsx
new file mode 100644
index 00000000..d9221d3a
--- /dev/null
+++ b/src/military/expert/review/review.jsx
@@ -0,0 +1,23 @@
+import React from "react";
+import { Link } from "react-router-dom";
+import system from './image/system.svg';
+
+import './review.scss';
+import '../index.scss';
+
+function Review(){
+ return(
+
+
+ 首页 > 专家评审系统
+
+
+ 
+ 红山开源平台专家评审系统
+ 您尚未被入选本平台专家团队,可提交专家资料进行注册申请加入专家团队
+
+
+
+ )
+}
+export default Review;
\ No newline at end of file
diff --git a/src/military/expert/review/review.scss b/src/military/expert/review/review.scss
new file mode 100644
index 00000000..9b9089ce
--- /dev/null
+++ b/src/military/expert/review/review.scss
@@ -0,0 +1,40 @@
+.expert_review_system{
+ height: 500px;
+ font-size: 20px;
+ .center_flex{
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ }
+ .navigation{
+ font-size: 0.6em;
+ margin: -35px 0 15px;
+ }
+ .notExpert{
+ height: 80%;
+ flex-direction: column;
+ background: #FAFCFF;
+ border-radius: 4px 4px 0px 0px;
+ border: 1px solid rgba(42, 97, 255, 0.23);
+ &>img{
+ width: 5.5vw;
+ }
+ .ne_title{
+ font-size: 1em;
+ font-weight: bold;
+ color: #181818;
+ }
+ .ne_tips{
+ font-size: 0.75em;
+ color: #595959;
+ }
+ .ne_bar{
+ width: 30vw;
+ border-top: 1px solid #EEEEEE;
+ margin: 50px 0 30px !important;
+ }
+ .but41_fill{
+ font-size: 0.7em;
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/military/expert/reviewResult/gradesModal/index.jsx b/src/military/expert/reviewResult/gradesModal/index.jsx
new file mode 100644
index 00000000..53f0d2b5
--- /dev/null
+++ b/src/military/expert/reviewResult/gradesModal/index.jsx
@@ -0,0 +1,162 @@
+import React, { useState, useEffect } from "react";
+import { Modal } from 'antd';
+import Paginationtable from "../../../components/paginationTable";
+import { getOpsScoringDetails, getRules } from "../../api";
+import sucess from '../image/sucess.svg';
+
+import './index.scss';
+import '../../index.scss';
+
+function GradesModal({ setVisible, visible, taskId, opsDetail, containerType }) {
+ // 主table参数
+ const [loading, setLoading] = useState(false);
+ const [dataList, setDataList] = useState([]);
+ // 评分规则
+ const [rules, setRules] = useState({});
+ // 通用列
+ const columns = [
+ {
+ title: '评审专家',
+ dataIndex: 'expertName',
+ key: 'expertName',
+ width: 100,
+ },
+ {
+ title: '电话',
+ dataIndex: 'expertPhone',
+ key: 'expertPhone',
+ width: 130,
+ },
+ {
+ title: '评审打分',
+ dataIndex: 'gradesAverage',
+ key: 'gradesAverage',
+ render: (text, record, index) => {
+ return text == 0 ? 0 : text || '--'
+ }
+ },
+ {
+ title: '评审意见',
+ dataIndex: 'comments',
+ key: 'comments',
+ width: 250,
+ render: (text, record, index) => {
+ return text|| '--'
+ }
+ },
+ {
+ title: '评审时间',
+ dataIndex: 'reviewedOn',
+ key: 'reviewedOn',
+ render: (text, record, index) => {
+ return text|| '--'
+ }
+ },
+ ];
+
+ // 评分列
+ const gradesColumns = [{
+ title: '评分一',
+ dataIndex: 'gradesOne',
+ key: 'gradesOne',
+ render: (text, record, index) => {
+ return text == 0 ? 0 : text || '--'
+ }
+ },
+ {
+ title: '评分二',
+ dataIndex: 'gradesTwo',
+ key: 'gradesTwo',
+ render: (text, record, index) => {
+ return text == 0 ? 0 : text || '--'
+ }
+ },
+ {
+ title: '评分三',
+ dataIndex: 'gradesThree',
+ key: 'gradesThree',
+ render: (text, record, index) => {
+ return text == 0 ? 0 : text || '--'
+ }
+ },
+ {
+ title: '评分四',
+ dataIndex: 'gradesFour',
+ key: 'gradesFour',
+ render: (text, record, index) => {
+ return text == 0 ? 0 : text || '--'
+ }
+ },
+ {
+ title: '评分五',
+ dataIndex: 'gradesFive',
+ key: 'gradesFive',
+ render: (text, record, index) => {
+ return text == 0 ? 0 : text || '--'
+ }
+ }];
+
+ let gradesNum = rules && rules.criterias && rules.criterias.length || 5;
+
+ if (gradesNum) {
+ let thisGradesColumns = gradesColumns.slice(0, gradesNum);
+ columns.splice(4, 0, ...thisGradesColumns);
+ }
+
+ // 获取评分列表
+ useEffect(() => {
+ setLoading(true);
+ let params = {
+ opsId: opsDetail && opsDetail.opsId,
+ opsType: opsDetail && opsDetail.opsType,
+ orderBy: 'gradesAverageDesc',
+ containerId: taskId,
+ containerType,
+ };
+ //获取评审规则
+ const paramsRule = {
+ containerId: taskId,
+ containerType,
+ statusString: '-1,1',
+ };
+ taskId && getRules(paramsRule).then(response=>{
+ if(response && response.message === "success"){
+ setRules(response.data);
+ }
+ });
+ opsDetail && opsDetail.opsId && getOpsScoringDetails(params).then(res => {
+ if (res.data && res.data.length) {
+ setDataList(res.data);
+ setLoading(false);
+ }
+ });
+ }, [opsDetail]);
+
+
+ return (
+ { setVisible(false) }}
+ footer={null}
+ draggable={true}
+ width={1050}
+ wrapClassName="task_review_detail"
+ >
+
+ 综合排名: {opsDetail && opsDetail.id}
+ 应征者: {opsDetail && (opsDetail.applicantInfo.nickname == null ? opsDetail.applicantInfo.login : opsDetail.applicantInfo.nickname)}
+ 平均得分: {opsDetail && opsDetail.finalGrades || `--`}
+ 是否胜出: {opsDetail && opsDetail.isWin ?  胜出 : '未胜出'}
+
+
+
+ )
+}
+export default GradesModal;
\ No newline at end of file
diff --git a/src/military/expert/reviewResult/gradesModal/index.scss b/src/military/expert/reviewResult/gradesModal/index.scss
new file mode 100644
index 00000000..8cb237da
--- /dev/null
+++ b/src/military/expert/reviewResult/gradesModal/index.scss
@@ -0,0 +1,97 @@
+.register_right.task_detail {
+ background: #fff;
+ padding-bottom: 1rem;
+
+ .ant-tabs {
+ background: #f5f5f5;
+ .ant-tabs-content {
+ background: #fff;
+ }
+ .ant-tabs-bar {
+ background: #fff;
+ margin-bottom: 1.25rem;
+ }
+
+ .ant-tabs-tab {
+ margin: 0;
+ padding: 19px 32px;
+ font-size: 1rem;
+ &:hover {
+ color: #4154f1;
+ }
+ }
+
+ .ant-tabs-ink-bar {
+ background-color: #4154f1;
+ }
+ }
+
+ .ant-tabs-nav .ant-tabs-tab-active {
+ color: #4154f1;
+ }
+
+ .task-head {
+ position: relative;
+ border-bottom: 1px solid #eeeeee;
+ padding: 0.5em 2em;
+ color: #181818;
+ background: #fff;
+ font-size: 0.8em;
+ font-weight: bold;
+ .back-button{
+ position: absolute;
+ z-index: 1;
+ right: 1rem;
+ bottom: -52px;
+ }
+ }
+
+ .button-div {
+ line-height: 1.5;
+ }
+ .pagination-table {
+ margin: .75rem 1.75rem 1.25rem;
+ }
+
+ .task-rules {
+ background: #f5f5f5;
+ .rules-box{
+ margin-bottom: 1.25rem;
+ background: #fff;
+ }
+ .rules-head {
+ font-size: 16px;
+ color: rgba(51, 51, 51, 1);
+ border-bottom: 1px solid #eeeeee;
+ padding: 10px 20px;
+ }
+ .rules-content{
+ padding: 10px 20px 30px;
+ }
+ .rules-content-last{
+ padding: 10px 20px;
+ }
+ .rules-content-item{
+ line-height: 2rem;
+ }
+ }
+
+ .warning{
+ color: #DE0000;
+ font-size: .7rem;
+ margin: .75rem 1.75rem;
+ }
+}
+.task_review_detail .pagination-table .ant-table-thead tr th div {
+ font-weight: bold;
+}
+.opsDetail{
+ display: flex;
+ margin-bottom: 15px;
+ color: #333;
+ .sucess{
+ color: #fd7700;
+ justify-content: center;
+ img{width: 20px;}
+ }
+}
\ No newline at end of file
diff --git a/src/military/expert/reviewResult/image/sucess.svg b/src/military/expert/reviewResult/image/sucess.svg
new file mode 100644
index 00000000..02f08e96
--- /dev/null
+++ b/src/military/expert/reviewResult/image/sucess.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/military/expert/reviewResult/index.jsx b/src/military/expert/reviewResult/index.jsx
new file mode 100644
index 00000000..7aa7e084
--- /dev/null
+++ b/src/military/expert/reviewResult/index.jsx
@@ -0,0 +1,236 @@
+import React, { useEffect, useState } from "react";
+import Link from "react-router-dom/Link";
+import PaginationTable from "src/military/components/paginationTable";
+import GradesModal from "./gradesModal";
+import { getCompetitionDetail, getFinalScoreRankingList, getWinnersAndPublicists, selectWinnersAndPublicists } from "../api";
+import { getTaskDetail } from "src/military/task/api";
+import { Checkbox, Input, message, Modal, Spin } from "antd";
+import sucess from './image/sucess.svg';
+import './index.scss';
+import '../index.scss';
+import { queryString } from "educoder";
+
+function ReviewResult({ history, match, mygetHelmetapi}) {
+ const {main_web_site_url} = mygetHelmetapi;
+ //id:竞赛或者创客任务id,containerType,1创客2竞赛
+ const {containerId, containerType} = match.params;
+ let {identifier, status, name, taskModeId} = queryString.parse(window.location.hash.slice(1));
+ const [dataList, setDateList] = useState(undefined);
+ const [openResultVisible, setOpenResultVisible] = useState(false);
+ const [winIds, setWinIds] = useState(undefined);
+ const [openRange, setOpenRange] = useState(undefined);
+ const [errorMessage,setErrorMessage] = useState();
+ const [result, setResult] = useState(undefined);
+ const [goNum, setGoNum] = useState(-1);
+ const [loading, setLoading] = useState(false);
+
+ // 模态框
+ const [opsDetail, setOpsDetail] = useState(undefined);
+ const [visible, setVisible] = useState(false);
+
+ const columns = [
+ {
+ title: '综合排名',
+ dataIndex: 'id',
+ },
+ {
+ title: '应征者',
+ dataIndex: 'applicantInfo.nickname',
+ key: 'expertName',
+ render: (text, record) => {
+ return text === null ? record.applicantInfo.login : text
+ }
+ },
+ {
+ title: '平均得分',
+ dataIndex: 'finalGrades',
+ key: 'phone',
+ },
+ {
+ title: '评审明细',
+ ket: 'detali',
+ render: (text, record) => {
+ return {detail(record)}}>查看明细
+ }
+ }
+ ];
+
+ //如果是创客任务,那么多出一列 选择胜出者
+ if(containerType == 1){
+ columns.splice(4, 0, {
+ title: '是否胜出',
+ ket: 'isWin',
+ align: 'center',
+ render: (text, record) => {
+ return record.isWin ?  胜出 : status == 4 ? {changeIsWin(record.applicantInfo.id, e.target.checked)}}>胜出 : '未胜出';
+ }
+ });
+ }
+
+ useEffect(()=>{
+ //获取评分
+ const params = {
+ containerId,
+ containerType,
+ orderBy: 'finalGradesDesc'
+ }
+ getFinalScoreRankingList(params).then(response=>{
+ if(response && Array.isArray(response.data)){
+ //finalGrades 最终得分为null 未到评审时间 0 专家未评审任务
+ let index = 1;
+ response.data.map(item=>{item.id = index++;setResult(item.finalGrades) })
+ containerType == 1 && status >4 ? getWinnersAndPublicists({
+ containerId,
+ containerType
+ }).then(res=>{
+ if(res && res.message === "success"){
+ response.data.map(item=>{
+ item.isWin = res.data.winUserIds.indexOf(item.applicantInfo.id) !== -1;
+ item.isPublic = res.data.publicityUserIds.indexOf(item.applicantInfo.id) !== -1;
+ })
+ }
+ setDateList(response.data);
+ }):setDateList(response.data)
+ }
+ })
+ },[status])
+
+ //监听status, name, taskModeId 的变化,如果其中任意一个没有值都去请求任务详情接口获取其数据
+ useEffect(()=>{
+ const bool = status && name && taskModeId;
+ if(containerType == 1 && !bool){
+ setLoading(true);
+ //创客任务
+ containerId && getTaskDetail(containerId).then(response=>{
+ if(response){
+ window.location.href=`${window.location.href}#status=${response.status}&name=${response.name}&taskModeId=${response.taskModeId}`;
+ }
+ }).finally(()=>{
+ setLoading(false);
+ })
+ }
+
+ const competitionBool = status && name && identifier;
+ if(containerType == 2 && !competitionBool){
+ setLoading(true);
+ //竞赛
+ containerId && getCompetitionDetail(containerId).then(response=>{
+ if(response && response.message == "success"){
+ window.location.href=`${window.location.href}#status=${response.data.current_status}&identifier=${response.data.identifier}&name=${response.data.title}`;
+ }
+ }).finally(()=>{
+ setLoading(false);
+ })
+ }
+ },[status, name, taskModeId, identifier])
+
+ function detail(item){
+ setOpsDetail(item);
+ setVisible(true);
+ }
+
+ function changeIsWin(id, checked){
+ const ids = new Set(winIds);
+ checked ? ids.add(id) : ids.delete(id);
+ setWinIds(Array.from(ids));
+ }
+
+ function openResult(){
+ if(result === null){
+ message.error("还没有到评审结束时间,不能公示结果! ");
+ return;
+ }
+ containerType == 2 && setOpenResultVisible(true);
+ if(containerType ==1 && winIds && winIds.length>0){
+ taskModeId == 1 && winIds.length >1 ? message.error("此任务是单人悬赏模式, 只能设置一个中标者 ! ") : setOpenResultVisible(true);
+ }
+ }
+
+ function onOk(){
+ setErrorMessage("");
+ let ids = [];
+ if(!openRange){
+ dataList.map(i=> {ids[ids.length] = i.applicantInfo.id;});
+ }else if(openRange && isNaN(openRange)){
+ setErrorMessage('请输入数字!');
+ }else if(openRange && (openRange.indexOf('.')!==-1 || openRange.indexOf('-')!==-1)){
+ setErrorMessage('请输入正整数!');
+ }else if(openRange && containerType == 1 && openRange < winIds.length){
+ setErrorMessage('公示范围不能少于获胜人数!');
+ }else if(openRange && openRange > dataList.length){
+ setErrorMessage('公示范围超过应征者总数!');
+ }else{
+ ids[ids.length] = dataList.filter(item=>item.id<=openRange).map(i=>i.applicantInfo.id);
+ }
+ let params = {
+ containerId,
+ containerType,
+ id: 0,
+ publicityUserIds : ids.toString()
+ };
+ containerType==1 && (params[`winUserIds`] = winIds.toString());
+ ids.length!=0 && selectWinnersAndPublicists(params).then(response=>{
+ if(response && response.message === "success"){
+ message.success("操作成功");
+ if(containerType==1){
+ window.location.href=`${window.location.href.replace('status=4','status=5')}`;
+ status = 5;
+ setGoNum(-2);
+ }
+ setOpenResultVisible(false);
+ }
+ })
+ }
+ return (
+
+
+
+
+ 评审结果
+
+
+ {containerType ==1 ? '任务':'竞赛'}名称{decodeURI(name)}
+
+ {containerType ==1 ? '任务':'竞赛'}链接
+ {containerType == 1 && {`${window.location.origin}/task/taskDetail/${containerId}`}}
+ {containerType == 2 && {`${main_web_site_url}/competitions/${identifier}/home`}}
+
+
+ {status > 3 ?
+ 应征者排名
+
+
+ {status == 4 && }
+
+ : 暂无数据,此任务暂未进入成果评选阶段。 }
+ setOpenResultVisible(false)}
+ onOk={onOk}>
+
+ 公示排名前
+ {setOpenRange(e.target.value)}}/>
+ 名
+
+ {errorMessage || "若未填写此排名,则公示所有名次"}
+
+
+
+
+
+ )
+}
+export default ReviewResult;
\ No newline at end of file
diff --git a/src/military/expert/reviewResult/index.scss b/src/military/expert/reviewResult/index.scss
new file mode 100644
index 00000000..11c74078
--- /dev/null
+++ b/src/military/expert/reviewResult/index.scss
@@ -0,0 +1,64 @@
+.expert_review_system.centerbox{
+ background: white;
+ font-family: 'PingFangSC-Semibold';
+ padding: 0 1.5em;
+ .font-w{
+ font-weight: bold;
+ }
+ .df{
+ display: flex;
+ justify-content: space-between;
+ align-items: center;
+ }
+ .mt10.pb20{border-bottom: 1px solid #eeeeee;}
+ .openResult{
+ text-align: center;
+ padding: 35px 0;
+ }
+ .lookDetail{
+ color: #4154F1;
+ &:hover{
+ opacity: 0.8;
+ }
+ }
+ .disableBut{
+ background: #f8f8f8;
+ padding: 0 1.3em;
+ height: 2.55em;
+ border-radius: 4px;
+ cursor: pointer
+ }
+ .pagination-table .ant-table-thead > tr > th span{
+ font-weight: bold;
+ }
+ .nodata{
+ height: 300px;
+ line-height: 300px;
+ text-align: center;
+ }
+ .sucess{
+ color: #fd7700;
+ justify-content: center;
+ img{width: 20px;}
+ }
+}
+.openResultModal{
+ .ant-modal-body{
+ text-align: center;
+ }
+ .df{
+ justify-content: center;
+ align-items: center;
+ input{
+ width: 65px;
+ margin: 0 12px;
+ font-size: 13px;
+ }
+ }
+ .ant-modal-title {
+ text-align: left;
+ }
+ .errorMes{
+ color: #d40000;
+ }
+}
diff --git a/src/military/expert/reviewRules/image/beCarful.svg b/src/military/expert/reviewRules/image/beCarful.svg
new file mode 100644
index 00000000..afc625f6
--- /dev/null
+++ b/src/military/expert/reviewRules/image/beCarful.svg
@@ -0,0 +1,11 @@
+
diff --git a/src/military/expert/reviewRules/index.jsx b/src/military/expert/reviewRules/index.jsx
new file mode 100644
index 00000000..e0db76e9
--- /dev/null
+++ b/src/military/expert/reviewRules/index.jsx
@@ -0,0 +1,196 @@
+import React, { useEffect, useState } from "react";
+import { DatePicker, Form, message } from "antd";
+import WordsInput from "../components/wordsInput";
+import './index.scss';
+import '../index.scss';
+import Link from "react-router-dom/Link";
+import { editRules, getRules, updateRules } from "../api";
+import moment from "moment";
+import { queryString } from "educoder";
+
+const {RangePicker} = DatePicker;
+
+function ReviewRules({form, history, match, mygetHelmetapi}) {
+ const {main_web_site_url} = mygetHelmetapi;
+ //id:竞赛或者创客任务id,containerType,1创客2竞赛
+ const {containerId, containerType} = match.params;
+ const {identifier, name, status, createdAt, collectingEndTime, choosingDays, reviewStartTime, reviewEndTime} = queryString.parse(window.location.search.slice(1));
+ const { getFieldDecorator,setFieldsValue } = form;
+ //是否有初始值
+ const [ initValue, setInitValue] = useState(false);
+ const disabledDate = (current) =>{
+ if(containerType == 1){
+ //创客任务
+ if(status == 1){
+ const start = new Date((new Date(createdAt.replace("%20", " "))/1000 - 86400)*1000);
+ return current && current < moment(start).endOf('day');
+ }else if(status == 3){
+ const start = new Date((new Date(collectingEndTime.replace("%20", " "))/1000 - 86400)*1000);
+ const endDate = new Date((new Date(collectingEndTime.replace("%20", " "))/1000 + 86400*(choosingDays))*1000);
+ return current && current < moment(start).endOf('day') || current > moment(endDate).endOf('day');
+ }
+ }else{
+ //竞赛任务
+ const start = new Date((new Date(reviewStartTime.replace("%20", " "))/1000 - 86400)*1000);
+ return current && current < moment(start).endOf('day') || current > moment(new Date(reviewEndTime.replace("%20", " "))).endOf('day');
+ }
+ }
+
+ useEffect(()=>{
+ //获取评审规则
+ const params = {
+ containerId,
+ containerType,
+ statusString: 3,
+ };
+ getRules(params).then(response=>{
+ if(response && response.message === "success"){
+ const { criteriaFive, criteriaFour, criteriaOne, criteriaThree, criteriaTwo, rule } = response.data;
+ const data = { criteriaFive, criteriaFour, criteriaOne, criteriaThree, criteriaTwo, rule }
+ setFieldsValue(data);
+ setInitValue(response.data);
+ }
+ })
+ }, [])
+
+ function rulesSubmit(){
+ form.validateFields((err, values) => {
+ if (!err) {
+ let data = {
+ containerId,
+ containerName: decodeURI(name),
+ containerType,
+ criteriaOne: values.criteriaOne,
+ reviewStartOn: values.reviewDate[0].format('YYYY-MM-DD HH:mm:ss'),
+ reviewEndOn: values.reviewDate[1].format('YYYY-MM-DD HH:mm:ss'),
+ rule: values.rule,
+ criteriaTwo: values.criteriaTwo,
+ criteriaThree: values.criteriaThree,
+ criteriaFour: values.criteriaFour,
+ criteriaFive: values.criteriaFive,
+ status: 3
+ }
+ containerType == 2 && (data[`containerIdentifier`]=identifier);
+ if(initValue){
+ //更新评审规则
+ updateRules({...data, id: initValue.id}).then(response=>{
+ if(response && response.message === '更新成功'){
+ message.success('更新成功');
+ history.go(-1);
+ }else{
+ message.error(response.message);
+ }
+ })
+ }else{
+ //新增评审规则
+ editRules(data).then(response=>{
+ if(response && response.message === '成功'){
+ message.success('保存成功');
+ history.go(-1);
+ setInitValue({id: response.data});
+ }else{
+ message.error(response.message);
+ }
+ })
+ }
+
+ }
+ })
+ }
+
+ return (
+
+
+
+ 任务信息
+
+
+ {containerType ==1 ? '任务':'竞赛'}名称{decodeURI(name)}
+
+ {containerType ==1 ? '任务':'竞赛'}链接
+ {containerType == 1 && {`${window.location.origin}/task/taskDetail/${containerId}`}}
+ {containerType == 2 && {`${main_web_site_url}/competitions/${identifier}/home`}}
+
+
+
+ {getFieldDecorator('rule', {
+ rules: [{ required: true, message: '请输入评审规则' }],
+ })(
+ ,
+ )}
+
+
+ 评分标准注:管理员可设置1-5个评分项及对应评分标准,每个评分项固定设置为100分
+
+ {getFieldDecorator('criteriaOne', {
+ rules: [{ required: true, message: '请输入一个评分标准' }],
+ })(
+ ,
+ )}
+
+
+ {getFieldDecorator('criteriaTwo', {
+ rules: [{}],
+ })(
+ ,
+ )}
+
+
+ {getFieldDecorator('criteriaThree', {
+ rules: [{}],
+ })(
+ ,
+ )}
+
+
+ {getFieldDecorator('criteriaFour', {
+ rules: [{}],
+ })(
+ ,
+ )}
+
+
+ {getFieldDecorator('criteriaFive', {
+ rules: [{}],
+ })(
+ ,
+ )}
+
+
+
+ {getFieldDecorator('reviewDate', {
+ rules: [{ required: true, message: '请选择评审时间' }],
+ initialValue: initValue && [moment(initValue.reviewStartOn) , moment(initValue.reviewEndOn)]
+ })(
+ ,
+ )}
+
+
+
+
+
+
+
+ )
+}
+export default Form.create()(ReviewRules);
\ No newline at end of file
diff --git a/src/military/expert/reviewRules/index.scss b/src/military/expert/reviewRules/index.scss
new file mode 100644
index 00000000..d8dcdb56
--- /dev/null
+++ b/src/military/expert/reviewRules/index.scss
@@ -0,0 +1,52 @@
+.setRules.centerbox{
+ .head_title, .ant-form{
+ padding: 0 2em;
+ background: white;
+ }
+ .-layout{
+ justify-content: space-between;
+ margin: 0 -2em;
+ border-bottom: 1px solid #EEEEEE;
+ padding: 0.5em 1em;
+ }
+ .ant-form .ant-form-item label, .criteria_title{
+ color: #333333;
+ .be_carful{
+ color: #E02020;
+ &::before{
+ content: url('./image/beCarful.svg');
+ margin-right: 8px;
+ }
+ }
+ }
+ .ant-form{
+ padding: 1em 2em 2em;
+ .ant-form-item{
+ margin-bottom: 10px;
+ &:first-child label, &:last-child label{
+ font-size: 16px;
+ font-weight: bold;
+ }
+ .ant-form-item-label > label::after{
+ content: none;
+ }
+ }
+ .ant-input{
+ background-color: white !important;
+ &:hover{
+ border: 1px solid #5d6eff !important;
+ }
+ }
+ }
+ .rules_buttom{
+ text-align: center;
+ }
+ .but41_fill, .but41_border, .butE3_border{
+ width: 6.5em;
+ }
+ .but41_border{padding: 0;}
+ .rules_bar{
+ margin: 25px -2em;
+ border-bottom: 1px solid #EEEEEE;
+ }
+}
\ No newline at end of file
diff --git a/src/military/expert/selectExpert/index.jsx b/src/military/expert/selectExpert/index.jsx
new file mode 100644
index 00000000..15d7d998
--- /dev/null
+++ b/src/military/expert/selectExpert/index.jsx
@@ -0,0 +1,419 @@
+import React, { useState, useEffect, useMemo } from "react";
+import { Tabs, Input, Select, Button, Modal, Form, message, Popconfirm } from 'antd';
+import { professionalType, reviewArea } from '../static.js';
+import { assignExperts, deleteExperts, expertList, selectExpertList } from "../api.js";
+import Paginationtable from "../../components/paginationTable";
+import './index.scss';
+import '../index.scss';
+import { Link } from "react-router-dom";
+import { queryString } from "educoder";
+
+const { TabPane } = Tabs;
+const { Option } = Select;
+const { Search } = Input;
+
+function SelectExpert(props) {
+ const { history, form, current_user, match, mygetHelmetapi } = props;
+ const {main_web_site_url} = mygetHelmetapi;
+ //id:竞赛或者创客任务id,containerType,1创客2竞赛
+ const {containerId, containerType} = match.params;
+ const {identifier, name} = queryString.parse(window.location.search.slice(1));
+ const { getFieldDecorator, setFieldsValue } = form;
+ const [reload, setReload] = useState();
+ const [loading, setLoading] = useState(false);
+ const [curPage, setCurPage] = useState(1);
+ const [dataList, setDataList] = useState([]);
+ const [total, setTotal] = useState(0);
+ const [pageSize, setPageSize] = useState(10);
+ const [searchInput, setSearchInput] = useState('');
+ const [expertType, setExpertType] = useState('');
+ const [reviewAreaSel, setReviewAreaSel] = useState('');
+ //专家多选确认框
+ const [okConfirmExps, setOkConfirmExps] = useState(false);
+ //批量删除专家确认框
+ const [okConfirmDelete, setOkConfirmDelete] = useState(false);
+ //批量添加 选择专家编号
+ const [selectedRowKeys, setSelectedRowKeys] = useState(undefined);
+ //随机抽取专家确认框
+ const [okConfirmExtract, setOkConfirmExtract] = useState(false);
+ //随机抽取 用户输入数
+ const [randomCount, setRandomCount] = useState(undefined);
+ //随机抽取错误提示语句
+ const [randomErrorMessage, setRandomErrorMessage] = useState(undefined);
+ //tab栏
+ const [activeKey, setActiveKey] = useState(0);
+ //已选专家列表
+ const [selectedExperts, setSelectExperts] = useState([]);
+ const [selectedExpertTotal, setSelectedExpertTotal] = useState(0);
+ //全部已选专家
+ const [allSelectedExpertsId, setAllSelectedExpertsId] = useState();
+
+ const columns = useMemo(() => {
+ return [
+ {
+ title: '编号',
+ dataIndex: 'index',
+ width: 80,
+ align: 'center',
+ },
+ {
+ title: '专家姓名',
+ dataIndex: 'expertName',
+ key: 'expertName',
+ },
+ {
+ title: '手机号码',
+ dataIndex: 'phone',
+ width: 150,
+ key: 'phone',
+ },
+ {
+ title: '最高学历',
+ dataIndex: 'highestDegree',
+ key: 'highestDegree',
+ },
+ {
+ title: '专业职称',
+ dataIndex: 'professionalTitle',
+ width: 120,
+ },
+ {
+ title: '专家类别',
+ dataIndex: 'expertType',
+ },
+ {
+ title: '评审领域',
+ dataIndex: 'reviewAreas',
+ align: 'center',
+ },
+ {
+ title: '专家评估',
+ dataIndex: 'expertScore',
+ align: 'center',
+ render:(text,record)=>{
+ return record.expertScore || '--';
+ }
+ },
+ {
+ title: '操作',
+ dataIndex: 'action',
+ width: 180,
+ align: 'center',
+ render: (text, record) => {
+ return
+ {activeKey == "1" && {SelectExperts([record.id])}}>添加}
+ {activeKey == "0" && { deleteExpert(record.taskExpertId, record.id)}} okText="是" cancelText="否">}
+
+ }
+ }
+ ];
+ }, [activeKey, allSelectedExpertsId]);
+
+ const rowSelection = {
+ selectedRowKeys,
+ onChange: (selectedRowKeys, selectedRows) => {
+ setSelectedRowKeys(selectedRowKeys);
+ }
+ };
+
+ const ExpertDetail = (record)=>{
+ return
+
+ 工作单位:{record.workplace}
+ 单位类别:{record.workplaceType}
+ 工作性质:{record.workNature}
+ 职称职级:{record.titleRank}
+
+
+ 邮箱地址:{record.expertEmail || '--'}
+ 毕业院校:{record.graduatedFrom || '--'}
+ 院校专业:{record.major || '--'}
+
+
+ 身份证号:{record.idNumber || '--'}
+ 开户银行:{record.bankName || '--'}
+ 银行账号:{record.bankAccount || '--'}
+
+
+ }
+
+ const TaskMess = ()=>{
+ return
+ }
+
+ //全部已选专家
+ useEffect(()=>{
+ setLoading(true);
+ const params = {
+ containerId,
+ containerType,
+ curPage:curPage,
+ pageSize: 10000,
+ curPage: 1,
+ }
+ selectExpertList(params).then(response=>{
+ if (response && response.data && Array.isArray(response.data.rows)) {
+ const ids = new Set();
+ response.data.rows.map((item)=>{
+ ids.add(item.id);
+ })
+ setAllSelectedExpertsId(ids);
+ }
+ }).finally(()=>{
+ setLoading(false);
+ })
+ },[])
+
+ // 专家列表
+ useEffect(() => {
+ setLoading(true);
+ let params = {
+ searchInput,
+ expertType: expertType === 'all' ? '' : expertType,
+ reviewArea: reviewAreaSel === 'all' ? '' : reviewAreaSel,
+ pageSize,
+ curPage,
+ statusString: '1',
+ selectedExpertIds: allSelectedExpertsId && Array.from(allSelectedExpertsId).toString()
+ };
+ expertList(params).then(data => {
+ if (data && Array.isArray(data.rows)) {
+ let index = 1;
+ for (const item of data.rows) {
+ item.reviewAreas = `${item.reviewAreaOne} ${item.reviewAreaTwo ? `、${item.reviewAreaTwo}`:''} ${item.reviewAreaThree ? `、${item.reviewAreaThree}`:''}`;
+ item.index = (index++) + (curPage > 1 ? (curPage - 1) * 10 : 0);
+ }
+ }
+ setDataList(data && data.rows);
+ setLoading(false);
+ setTotal(data && data.total);
+ });
+ }, [curPage, reload, searchInput, expertType, reviewAreaSel, allSelectedExpertsId]);
+
+ //已选专家列表
+ useEffect(()=>{
+ setLoading(true);
+ const params = {
+ containerId,
+ containerType,
+ curPage,
+ pageSize,
+ }
+ selectExpertList(params).then(response=>{
+ if (response && response.data && Array.isArray(response.data.rows)) {
+ let index = 1;
+ for (const item of response.data.rows) {
+ item.reviewAreas = `${item.reviewAreaOne} ${item.reviewAreaTwo ? `、${item.reviewAreaTwo}`:''} ${item.reviewAreaThree ? `、${item.reviewAreaThree}`:''}`;
+ item.index = (index++) + (curPage > 1 ? (curPage - 1) * 10 : 0);
+ }
+ setSelectExperts(response && response.data.rows);
+ setSelectedExpertTotal(response && response.data.total);
+ }
+ }).finally(()=>{
+ setLoading(false);
+ })
+ },[curPage, reload])
+
+ //随机抽取专家
+ function random(){
+ setRandomErrorMessage('');
+ if(!randomCount){
+ setRandomErrorMessage('请输入随机抽取的专家数量!');
+ }else if(isNaN(randomCount)){
+ setRandomErrorMessage('请输入数字!');
+ }else if(randomCount.indexOf('.')!==-1 || randomCount.indexOf('-')!==-1){
+ setRandomErrorMessage('请输入正整数!');
+ }else{
+ let params = {
+ searchInput,
+ expertType: expertType === 'all' ? '' : expertType,
+ reviewArea: reviewAreaSel === 'all' ? '' : reviewAreaSel,
+ randomCount,
+ curPage:1,
+ pageSize: 10000,
+ selectedExpertIds: Array.from(allSelectedExpertsId).toString(),
+ };
+ expertList(params).then(response=>{
+ if(response && Array.isArray(response.rows)){
+ const randomIds = [];
+ response.rows.map(item=>{
+ randomIds[randomIds.length] = item.id;
+ })
+ SelectExperts([...randomIds]);
+ setOkConfirmExtract(false);
+ }
+ })
+ }
+ }
+
+ //为创客任务添加评审专家
+ const SelectExperts = (id) =>{
+ const params = {
+ assignorId: parseInt(current_user.user_id),
+ containerId,
+ containerName: decodeURI(name),
+ containerType,
+ expertIds: id.toString(),
+ status: 3
+ }
+ assignExperts(params).then(response=>{
+ if(response && response.message === '专家指派成功'){
+ id.map(i=>setAllSelectedExpertsId(allSelectedExpertsId.add(i)));
+ setOkConfirmExps(false);
+ message.success(response.message);
+ setSelectedRowKeys([]);
+ setReload(Math.random());
+ }
+ })
+ }
+
+ //删除评审专家
+ const deleteExpert=(taskExpertId, expertId)=>{
+ setLoading(true);
+ deleteExperts(taskExpertId,1).then(response=>{
+ if(response && response.message === "删除成功"){
+ message.success("删除成功");
+ allSelectedExpertsId.delete(expertId);
+ setReload(Math.random());
+ }else{
+ message.error("删除失败");
+ }
+ }).finally(()=>{
+ setLoading(false);
+ })
+ }
+
+ return (
+
+
+ 评审专家选取
+
+
+ {setActiveKey(activeKey);setSelectedRowKeys([]);setCurPage(1);}}>
+
+
+
+ 已选取评审专家
+
+ {/* */}
+ { history.go(-1) }}
+ onCancel={() => setOkConfirmDelete(false)}
+ wrapClassName="expert_modal"
+ >
+ 您确定要删除选中的{selectedRowKeys && selectedRowKeys.length}个专家吗?
+ 此操作将删除选中的{selectedRowKeys && selectedRowKeys.length}个专家,请进行确认以防数据丢失。
+
+
+
+
+
+
+
+
+ 添加评审专家
+
+
+ {allSelectedExpertsId && allSelectedExpertsId.size === total ? : }
+ SelectExperts(selectedRowKeys)}
+ onCancel={() => setOkConfirmExps(false)}
+ wrapClassName="expert_modal"
+ >
+ 您确定要添加选中的{selectedRowKeys && selectedRowKeys.length}个专家吗?
+ 此操作将添加选中的{selectedRowKeys && selectedRowKeys.length}个专家,请进行确认。
+
+
+ setOkConfirmExtract(false)}
+ wrapClassName="expert_modal extract"
+ >
+ 请输入数量:{setRandomCount(e.target.value)}}>
+ {randomErrorMessage}
+
+
+
+
+
+ {getFieldDecorator('searchInput', {})( { setSearchInput(value); setCurPage(1); }}
+ />)}
+
+
+ {getFieldDecorator('expertType', {})(
+ )}
+
+
+ {getFieldDecorator('reviewAreaSel', {})(
+ )}
+
+
+
+
+ {setCurPage(curPage++);setSelectedRowKeys([])}}
+ current={curPage}
+ rowSelection={rowSelection}
+ expandedRowRender={ExpertDetail}
+ expandIconColumnIndex={9}
+ expandIconAsCell={false}
+ />
+
+
+ )
+}
+export default Form.create()(SelectExpert);
\ No newline at end of file
diff --git a/src/military/expert/selectExpert/index.scss b/src/military/expert/selectExpert/index.scss
new file mode 100644
index 00000000..53087d73
--- /dev/null
+++ b/src/military/expert/selectExpert/index.scss
@@ -0,0 +1,112 @@
+.centerbox.select_expert{
+ margin: -10px auto;
+ margin-bottom: 2vh;
+ padding-top: 16px;
+ background: white;
+ .title_one, .ant-tabs-nav-wrap, .ant-tabs .ant-tabs-top-content{
+ padding: 0 2em 1vw;
+ }
+ .box{
+ height: 20px;
+ margin: 0 -2em;
+ background: #FAFAFA;
+ }
+ .df{
+ display: flex;
+ justify-content: space-between;
+ align-items: center;
+ &.ant-form{
+ width: 78vw;
+ }
+ }
+ .search{
+ .ant-form-item{
+ display: flex;
+ }
+ }
+ .ant-pagination{
+ text-align: center;
+ margin: 20px 0;
+ }
+ .ant-table-thead > tr > th, .ant-table-tbody > tr > td{
+ padding: 16px 0 16px 10px;
+ }
+ .ml120{
+ margin-left: 120px;
+ width: 6em;
+ }
+ .ant-table-row-expand-icon{
+ width: 65px;
+ height: 26px;
+ line-height: 24px;
+ font-size: 12px;
+ color: white;
+ background: #4154F1;
+ }
+ .ant-table-row-collapsed::after, .ant-table-row-expanded::after {
+ content: '专家详情';
+ }
+ .expert_detail_div{
+ justify-content: space-around;
+ align-items: flex-start;
+ div{width: 28%;}
+ }
+ .select{
+ color: #4154F1;
+ padding: 0 8px;
+ }
+ .selected{
+ color: #999999;
+ }
+ .ant-tabs .ant-tabs-bar{
+ border: none;
+ margin: 0;
+ .ant-tabs-tab{
+ background: none;
+ border: none;
+ color:#666666;
+ font-size: 16px;
+ &:hover{color: #4154F1;}
+ }
+ .ant-tabs-tab-active{
+ font-weight: bold;
+ color: #4154F1;
+ border-bottom: 1px solid #4154F1;
+ }
+ }
+ .invalid_extraction{
+ background: #F8F8F8;
+ }
+ .pagination-table .ant-table-thead > tr > th span, .ant-form label{
+ font-weight: bold;
+ }
+ .select_title{
+ height: 36px;
+ }
+}
+.expert_modal.extract{
+ .ant-modal-content {
+ width: 387px;
+ height: 230px;
+ .ant-modal-body {
+ padding: 3.5vh 3.5vw 0;
+ div{
+ display: flex;
+ align-items: center;
+ }
+ p{
+ color: red;
+ height: 2.9em;
+ }
+ .ml_40{
+ margin-left: -40px;
+ }
+ }
+ .ant-modal-footer {
+ margin-top: 0;
+ }
+ }
+ .ant-input{
+ width: 8vw;
+ }
+}
\ No newline at end of file
diff --git a/src/military/expert/static.js b/src/military/expert/static.js
new file mode 100644
index 00000000..c2d3b0fc
--- /dev/null
+++ b/src/military/expert/static.js
@@ -0,0 +1,74 @@
+// 专家注册页面需要的静态数据
+export const unitType = [
+ { value: "企业", label: "企业" },
+ { value: "科研院所", label: "科研院所" },
+ { value: "高等院校", label: "高等院校" },
+ { value: "医疗机构", label: "医疗机构" },
+ { value: "行政机关", label: "行政机关" },
+ { value: "社会团体", label: "社会团体" },
+ { value: "其他", label: "其他" }
+];
+
+export const natureOfWork = [
+ { value: "研究", label: "研究" },
+ { value: "管理", label: "管理" },
+ { value: "开发", label: "开发" },
+ { value: "服务", label: "服务" },
+ { value: "其他", label: "其他" }
+];
+
+export const highestEducation = [
+ { value: "博士", label: "博士" },
+ { value: "硕士", label: "硕士" },
+ { value: "本科", label: "本科" },
+ { value: "大专", label: "大专" },
+ { value: "其他", label: "其他" }
+];
+
+export const positionLevel = [
+ { value: "正高级", label: "正高级" },
+ { value: "副高级", label: "副高级" },
+ { value: "中级", label: "中级" },
+ { value: "初级", label: "初级" },
+ { value: "未取得", label: "未取得" }
+];
+
+export const professionalType = [
+ { value: "技术类", label: "技术类" },
+ { value: "经济类", label: "经济类" },
+ { value: "管理类", label: "管理类" }
+];
+
+export const reviewArea = [
+ { value: "军事理论", label: "军事理论" },
+ { value: "政策法规", label: "政策法规" },
+ { value: "医学", label: "医学" },
+ { value: "电子", label: "电子" },
+ { value: "通信", label: "通信" },
+ { value: "计算机科学", label: "计算机科学" },
+ { value: "软件工程", label: "软件工程" },
+ { value: "有机化学", label: "有机化学" },
+ { value: "人工智能", label: "人工智能" },
+ { value: "文学交流", label: "文学交流" },
+ { value: "体育活动", label: "体育活动" }
+];
+
+export const taskType = [
+ { value: 1, label: "创客评审任务" },
+ { value: 2, label: "竞赛评审任务" },
+];
+
+export const expertTaskStatus = [
+ { value: -1, label: "未评审" },
+ { value: '1,2', label: "已评审" },
+];
+
+export const competitionStatus = [
+ { value: 0, label: "未开始" },
+ { value: 1, label: "报名中" },
+ { value: 2, label: "即将开始" },
+ { value: 3, label: "竞赛进行中" },
+ { value: 4, label: "竞赛评选中" },
+ { value: 5, label: "公示中" },
+ { value: 6, label: "已结束" },
+];
\ No newline at end of file
diff --git a/src/military/index.scss b/src/military/index.scss
index d3bf5f41..d698d19b 100644
--- a/src/military/index.scss
+++ b/src/military/index.scss
@@ -9,7 +9,7 @@
color: #ff6800;
}
.color-deep-blue {
- color: #1b8fff;
+ color: #4154f1;
}
.centerbox {
width: 1200px;
@@ -27,7 +27,7 @@
display: inline-flex;
align-items: center;
&:hover {
- color: #409eff;
+ color: #4154f1;
}
}
}
@@ -65,11 +65,11 @@
}
.center-left-butD:hover {
background-color: #fff;
- color: #409eff;
+ color: #4154f1;
cursor: pointer;
}
.center-left-butDACT {
- background-color: #409eff;
+ background-color: #4154f1;
color: #fff;
}
@@ -215,7 +215,7 @@
background-color: #f1f1f1;
}
a {
- color: #409eff;
+ color: #4154f1;
cursor: pointer;
}
}
@@ -224,6 +224,47 @@
text-align: center;
}
+.text-left{
+ text-align: left;
+}
+
+.search-screen {
+ display: flex;
+ flex-flow: row wrap;
+ justify-content: space-between;
+ margin: 1.25rem 0;
+ padding: 1.25rem;
+ background-color: #fff;
+ border-bottom: 1px solid #dedede;
+
+ > .ant-row {
+ min-width: 41%;
+ margin-right: 2rem;
+ .ant-form-item-label {
+ float: left;
+ }
+ .ant-form-item-control-wrapper {
+ overflow: hidden;
+ }
+ }
+
+ .center-right-but {
+ .ant-form-item {
+ margin: 0 1rem 0 0;
+ }
+ .ant-form-item-control-wrapper {
+ display: inline-block;
+ }
+ }
+ .button-div {
+ margin-right: 1.5rem;
+ }
+
+ .link{
+ color:#4154f1;
+ }
+}
+
@media screen and (max-width: 1200px) {
.centerbox {
width: 98%;
diff --git a/src/military/javaFetch.js b/src/military/javaFetch.js
index 90e7e925..1a47425a 100644
--- a/src/military/javaFetch.js
+++ b/src/military/javaFetch.js
@@ -66,7 +66,7 @@ service.interceptors.response.use(
});
return Promise.reject('error');
}
- if (response.status !== 200 && res.status !== 200) {
+ if (!res.status.toString().startsWith('2')) {
notification.open({
message: "提示",
description: res.message,
@@ -97,7 +97,9 @@ service.interceptors.response.use(
message: "提示",
description: res.data.message || '无权限!',
});
- window.location.href="/403";
+ if(window.location.port !== "3007"){
+ window.location.href="/403";
+ }
return Promise.reject('error');
}
diff --git a/src/military/notice/components/itemList/index.scss b/src/military/notice/components/itemList/index.scss
index 7b2e1be9..c920cd3e 100644
--- a/src/military/notice/components/itemList/index.scss
+++ b/src/military/notice/components/itemList/index.scss
@@ -15,7 +15,7 @@
}
}
.list-title:hover {
- color: #409eff;
+ color: #4154f1;
}
.list-title span {
padding: 3px 5px;
diff --git a/src/military/notice/fetch.js b/src/military/notice/fetch.js
index 38f2a078..457eb5fb 100644
--- a/src/military/notice/fetch.js
+++ b/src/military/notice/fetch.js
@@ -2,8 +2,8 @@
import javaFetch from '../javaFetch';
-let settings=JSON.parse(localStorage.chromesetting);
-let actionUrl = settings.api_urls? settings.api_urls.notice :'https://info.osredm.com';
+let settings =localStorage.chromesetting && JSON.parse(localStorage.chromesetting);
+let actionUrl = settings && settings.api_urls ? settings.api_urls.notice : 'https://info.osredm.com';
const service = javaFetch(actionUrl);
export const httpUrl = actionUrl;
diff --git a/src/military/task.js b/src/military/task.js
index 7aa3f4ea..2cd35a11 100644
--- a/src/military/task.js
+++ b/src/military/task.js
@@ -51,7 +51,7 @@ const Index = (propsTransmit) => {
})
}, [])
let propsF = { ...propsTransmit };
- propsF.current_user = currentUser;
+ propsF.current_user = {...propsF.current_user,...currentUser};
return (
diff --git a/src/military/task/api.js b/src/military/task/api.js
index 98313f63..01655030 100644
--- a/src/military/task/api.js
+++ b/src/military/task/api.js
@@ -581,4 +581,22 @@ export function closeTask(taskId) {
url: `/api/tasks/backend/admin/task/close/${taskId}`,
method: 'post',
});
-}
\ No newline at end of file
+}
+
+// 任务添加专家评审流程,expertReview: 1 加入 -1 不加入
+export function addExpertReview(taskId,expertReview){
+ return fetch({
+ url: `/api/tasks/backend/joinExpertReview/${taskId}?expertReview=${expertReview}`,
+ method: 'put',
+ });
+}
+
+//发布评审任务
+export function publishExpertsAndRules(taskId, containerType){
+ return fetch({
+ url: `/api/taskRuleCriteria/publishExpertsAndRules?containerId=${taskId}&containerType=${containerType}&status=-1`,
+ method: 'put'
+ })
+}
+
+// 管理页面修改创业
\ No newline at end of file
diff --git a/src/military/task/components/adminRouter/index.jsx b/src/military/task/components/adminRouter/index.jsx
index 4132b4c5..944de375 100644
--- a/src/military/task/components/adminRouter/index.jsx
+++ b/src/military/task/components/adminRouter/index.jsx
@@ -1,6 +1,6 @@
import React, { useMemo } from 'react';
import { Menu, Dropdown, } from 'antd';
-import { current_main_site_url,main_web_site_url} from '../../static';
+import { current_main_site_url, main_web_site_url } from '../../static';
import './index.scss';
@@ -96,9 +96,9 @@ export default props => {
return (
-
+
- 项目
+ 项目
@@ -131,6 +131,8 @@ export default props => {
网站配置
+
+
)
}
\ No newline at end of file
diff --git a/src/military/task/components/itemDelayManage/index.jsx b/src/military/task/components/itemDelayManage/index.jsx
index 41146d46..8a32a7ee 100644
--- a/src/military/task/components/itemDelayManage/index.jsx
+++ b/src/military/task/components/itemDelayManage/index.jsx
@@ -189,7 +189,7 @@ export default Form.create()((props) => {
{
- item.status === 4 && item.papersCount > 0 && (!item.isProofBoolean) && '未上传佐证材料'
+ item.status === 4 && item.papersCount > 0 && (!item.isProofBoolean) && (!item.expertReview) && '未上传佐证材料'
}
{item.status === 6 && item.agreementSigning === 0 && '未选择协议签订方式'}
diff --git a/src/military/task/components/itemListMyTask/index.jsx b/src/military/task/components/itemListMyTask/index.jsx
index 33fa35e7..8224691b 100644
--- a/src/military/task/components/itemListMyTask/index.jsx
+++ b/src/military/task/components/itemListMyTask/index.jsx
@@ -226,7 +226,7 @@ export default Form.create()((props) => {
}
{
- item.status === 4 && item.papersCount > 0 && (!item.isProofBoolean) && (!item.isProofBoolean) &&
+ !item.expertReview && item.status === 4 && item.papersCount > 0 && (!item.isProofBoolean) && (!item.expertReview) &&
{ uploadProofs(item) }} className="line_1 color-blue">上传佐证材料
}
diff --git a/src/military/task/components/itemListPaper/index.jsx b/src/military/task/components/itemListPaper/index.jsx
index 70c1f949..3f8580ac 100644
--- a/src/military/task/components/itemListPaper/index.jsx
+++ b/src/military/task/components/itemListPaper/index.jsx
@@ -11,6 +11,9 @@ import { reportPaper, thumbUpPaper, commentAdd, confirmReceipt } from '../../api
import { paperCheckStatusArr } from '../../static';
import { httpUrl } from '../../fetch';
import winpng from '../../image/winner.png';
+import win1 from '../../image/win1.svg';
+import win2 from '../../image/win2.svg';
+import win3 from '../../image/win3.svg';
import './index.scss';
const { TextArea } = Input;
@@ -21,7 +24,7 @@ for (const item of paperCheckStatusArr) {
}
export default Form.create()((props) => {
- const { list, curPage, total, changePage, loading, applyStatusAllNameArr, reloadList, showNotification, current_user, form, detailStatus } = props;
+ const { list, curPage, total, changePage, loading, applyStatusAllNameArr, reloadList, showNotification, current_user, form, detailStatus, expertReview } = props;
const { getFieldDecorator, validateFields, setFieldsValue } = form;
const [page, setPage] = useState(1);
const pageSize = props.pageSize || 10;
@@ -144,19 +147,23 @@ export default Form.create()((props) => {
{loading || loadingChild ? :
{
- list.map(item => {
+ list.map((item,i) => {
+ const winReview = [5,6,7,8].includes(detailStatus) && expertReview && item.reviewFinalGrades!==null;
return (
-
- -
+
-
{ item.user.nickname === "******" ? "" : goUser(item.user.login) }}>
{item.user.nickname || item.user.login}
{timeAgo(item.createdAt)}
{item.status === 2 ?
: {item.checkStatus !== 1 ? paperCheckStatus[item.checkStatus] : applyStatusAllNameArr[item.status]}}
+ {winReview && 评审得分:{item.reviewFinalGrades}}
+ {winReview && i ==0 && 第一名}
+ {winReview && i ==1 && 第二名}
+ {winReview && i ==2 && 第三名}
-
{((item.needComplain && detailStatus === 3) || (detailStatus === 5 && item.publicTaskComplain && item.checkStatus === 1 && item.status !== 2)) && (current_user.login === item.user.login) &&
diff --git a/src/military/task/components/itemListPaper/index.scss b/src/military/task/components/itemListPaper/index.scss
index 4458d140..a39527f6 100644
--- a/src/military/task/components/itemListPaper/index.scss
+++ b/src/military/task/components/itemListPaper/index.scss
@@ -20,11 +20,11 @@
.fileCommentsList {
background: #fafafa;
- padding-top: .25rem;
+ padding-top: 0.25rem;
}
-.comments-item{
- margin-top:1rem;
+.comments-item {
+ margin-top: 1rem;
}
.comments-content {
text-align: left;
@@ -36,11 +36,33 @@
background-color: #fff;
}
-.small-head{
+.small-head {
max-width: 2rem;
}
-.clickable:hover{
+.clickable:hover {
color: #4cacff;
cursor: pointer;
-}
\ No newline at end of file
+}
+
+.paper-grades {
+ margin-left:4rem;
+ font-size: 1rem;
+ color: #333333;
+
+ .paper-grades-num{
+ color: #FF0000;
+ }
+}
+.taskReview{
+ width: 100%;
+ .winReview{
+ position: absolute;
+ right: 0px;
+ color: #ff5f00;
+ font-size: 18px;
+ img{
+ margin-right: 8px;
+ }
+ }
+}
diff --git a/src/military/task/components/itemListTask/index.scss b/src/military/task/components/itemListTask/index.scss
index 23ff84ab..7accfd22 100644
--- a/src/military/task/components/itemListTask/index.scss
+++ b/src/military/task/components/itemListTask/index.scss
@@ -10,7 +10,7 @@
.user-box{
cursor: pointer;
&:hover{
- color: #409eff;
+ color: #4154f1;
}
.head-log-small{
position: relative;
@@ -34,7 +34,7 @@
}
}
.list-title:hover {
- color: #409eff;
+ color: #4154f1;
}
.list-title span {
padding: 0px 10px;
diff --git a/src/military/task/fetch.js b/src/military/task/fetch.js
index 9140d89e..520f5352 100644
--- a/src/military/task/fetch.js
+++ b/src/military/task/fetch.js
@@ -2,8 +2,9 @@
import javaFetch from '../javaFetch';
-let settings=JSON.parse(localStorage.chromesetting);
-let actionUrl = settings.api_urls? settings.api_urls.task :'https://task.osredm.com';
+let settings=localStorage.chromesetting&&JSON.parse(localStorage.chromesetting);
+let actionUrl = settings && settings.api_urls? settings.api_urls.task :'https://task.osredm.com';
+// let actionUrl = 'http://117.50.100.12:8066'
const service = javaFetch(actionUrl);
export const httpUrl = actionUrl;
diff --git a/src/military/task/image/win1.svg b/src/military/task/image/win1.svg
new file mode 100644
index 00000000..971c2773
--- /dev/null
+++ b/src/military/task/image/win1.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/military/task/image/win2.svg b/src/military/task/image/win2.svg
new file mode 100644
index 00000000..ef565ee6
--- /dev/null
+++ b/src/military/task/image/win2.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/military/task/image/win3.svg b/src/military/task/image/win3.svg
new file mode 100644
index 00000000..ac530094
--- /dev/null
+++ b/src/military/task/image/win3.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/military/task/index.scss b/src/military/task/index.scss
index a29ae373..107587d2 100644
--- a/src/military/task/index.scss
+++ b/src/military/task/index.scss
@@ -87,7 +87,7 @@ span.list-gray {
background: #bababa;
}
-.ant-pagination {
+.center-content .ant-pagination {
margin: 2rem auto;
text-align: center;
}
diff --git a/src/military/task/static.js b/src/military/task/static.js
index 08714fcd..c0caa1e1 100644
--- a/src/military/task/static.js
+++ b/src/military/task/static.js
@@ -41,7 +41,7 @@ export const proofArr = [
{ dicItemCode: 2, name: "待审核", dicItemName: "待审核" },
]
-export const publicityArr=[
+export const publicityArr = [
{ dicItemCode: 1, name: "已受理", dicItemName: "已受理" },
{ dicItemCode: 0, name: "不受理", dicItemName: "不受理" },
]
@@ -52,7 +52,7 @@ export const agreementArr = [
{ dicItemCode: 2, name: "待审核", dicItemName: "待审核" },
]
-export const publishModeArr=["自主提交","统筹任务"];
+export const publishModeArr = ["自主提交", "统筹任务"];
export const delayTaskArr = [
{ dicItemCode: 3, name: "成果征集中", dicItemName: '成果征集中' },
@@ -102,27 +102,27 @@ export const applyStatusAllArr = [
{ dicItemCode: '4', name: "待确认", dicItemName: '待确认' },
];
-export const paperCheckStatusArr=[
+export const paperCheckStatusArr = [
{ dicItemCode: '0', name: "待审核", dicItemName: '待审核' },
{ dicItemCode: '1', name: "通过", dicItemName: '通过' },
{ dicItemCode: '2', name: "未通过", dicItemName: '未通过' },
];
-export const paperCheckTextArr=["您已成功提交,请等待审核!","您的成果已经审核通过!","您的成果审核未通过"];
+export const paperCheckTextArr = ["您已成功提交,请等待审核!", "您的成果已经审核通过!", "您的成果审核未通过"];
-export const paperComplainStatusArr=[
+export const paperComplainStatusArr = [
{ dicItemCode: '0', name: "未通过", dicItemName: '未通过' },
{ dicItemCode: '1', name: "通过", dicItemName: '通过' },
{ dicItemCode: '2', name: "待审核", dicItemName: '待审核' },
]
-export const showUserModeArr=[
+export const showUserModeArr = [
{ dicItemCode: 0, name: "不公示", dicItemName: '不公示' },
{ dicItemCode: 1, name: "自动公示", dicItemName: '自动公示' },
{ dicItemCode: 2, name: "手动公示", dicItemName: '手动公示' },
]
-export const myPaperStatusArr =["待确认","未采纳","评选胜出"]
+export const myPaperStatusArr = ["待确认", "未采纳", "评选胜出"]
export const formItemLayout = {
labelCol: {
@@ -137,9 +137,9 @@ export const formItemLayout = {
},
};
-export const main_web_site_url = JSON.parse(localStorage.chromesetting).main_web_site_url;
+export const main_web_site_url = localStorage.chromesetting && JSON.parse(localStorage.chromesetting).main_web_site_url;
-export const current_main_site_url = JSON.parse(localStorage.chromesetting).current_main_site_url;
+export const current_main_site_url = localStorage.chromesetting && JSON.parse(localStorage.chromesetting).current_main_site_url;
export const formModalLayout = {
@@ -166,5 +166,9 @@ export const tailFormItemLayout = {
},
};
-export const agreementContent='
投稿协议内容示例,请在管理 — 创客 — 基础数据 — 应征投稿协议内容 修改. 在您通过本平台在线签署应征投稿合同前,请您认真细致地阅读以下《应征投稿协议》,特别是其中以粗体下划线明显标注的条款,并在您同意了下述协议条款再正式进入后续程序 本协议由甲方(任务发布方)和乙方(应征者)在线签订,请甲乙双方仔细阅读协议内容, 请务必审慎阅读、充分理解各条款内容,特别是免除或者限制责任的条款、法律适用和争议解决条款。 甲乙双方点击接受本协议,即意味着已阅读、理解并接受本协议所有条款,并对本协议条款的含义及相应的法律后果已全部知晓并充分认可。甲乙双方点击确认本协议后,本协议即产生法律约束力。 本协议内容包括协议正文及甲乙双方在线相互确认的合同。所签订的合同、合同附件为本协议不可分割的一部分,与本协议正文具有同等法律效力。若您继续使用本平台创客空间,则表明您已经完全知晓、认可并同意遵守本协议内容、所有汇新云已经发布的各类规则以及签订的合同。 在阅读本协议的过程中,如不同意本协议或其中任何条款约定,应拒绝接受本协议所约定的内容,甲乙双方都有权自主选择拒绝达成合作。 1.定义除非本协议另有约定,在本协议中所用下列术语定义如下: 1.1 本平台:是指www.XXXXXX.com 为用户提供任务信息发布、交流,第三方以“企业”或“个人”入驻的形式应征任务的电子商务交易服务平台; 1.2 用户:指在本平台合法注册,接受并认可服务平台相关协议、规则、规范、制度等的自然人、法人或其他非法人组织。 1.3 甲方:指在本平台上发布创客任务的用户。 1.4 乙方:是指经本平台审核通过入驻本平台,根据任务方发布的任务,提供各种定制服务或IT产品,在平台开展业务经营的企业或个人。 1.5 服务任务:指甲方基于自身任务向乙方提出的具体服务要求。 1.6 项目款:指甲方和乙方的交易金额,即本协议约定交易金额或后续经协商调整后确定的交易总金额。 1.7 平台账户:指用户在本平台注册的帐号,用户只能通过该帐户登陆服务平台进行交易。 2.甲方权利义务2.1 甲方应当根据服务任务主动向乙方提交本项目所需的相关资料,并保证该资料的真实性、合法性、准确性、完整性,如因甲方未按照前述标准提供资料导致乙方无法履行协议义务,由此产生的责任由甲方自行承担。 2.2 甲方在向乙方提交项目所涉及资料时有权一并对乙方的服务提出建议和思路,同时有权在验收时对乙方的服务成果提出修改意见,但甲方提出的服务建议或思路以及修改意见应当明确具体,如不明确,有权不听取建议或拒绝修改,同时甲方不得借机拖延进度及应支付的款项,甲方提出超出协议或合同约定范围的修改要求,乙方有权拒绝或者另行收取费用。 2.3 甲方未按照合同在约定的日期内支付项目款的,乙方有权拒绝或顺延提供服务。 2.4 甲方应充分了解且同意遵守服务平台公布的所有协议、规则、制度等文件,并按照服务平台的相关规定处理相关交易事项。 2.5 甲方应及时验收乙方交付的服务成果(包括阶段成果和最终成果),如乙方向甲方提交服务成果后在规定期限日内甲方未给出具体验收意见的,视为乙方提交的服务成果合格。如有下一阶段服务的,乙方有权继续推进;如下一阶段服务因甲方原因导致无法继续推进的,乙方不承担任何责任。 2.6 甲方有义务向乙方提供必要的配合义务,包括提供必要资料、及时验收、及时回复等。 2.7 甲方同意并知晓,乙方仅提供合法、合规、合理的服务,对甲方违背法律法规或行政规章的服务要求,乙方有权拒绝提供服务。 2.8 甲方应当保证委托的服务事项不违反任何法律法规或侵犯他人合法权利,否则乙方有权拒绝提供服务并有权立即解除本协议。 2.9 甲方应当保证合法使用乙方提交的服务成果,不得将服务成果用于任何违法违规或侵犯他人合法权益的活动,甲方应自行承担服务成果使用过程中发生的全部责任。 2.10 甲方同意,为便于双方交易,本协议作为交易的主要内容和双方之间权利义务的根本性约定,具体服务项目、期限、金额等甲方在平台与乙方签订电子合同时在合同上予以标注,甲方对在合同中提供的所有信息的真实性负责。 2.11 甲方在签订线下子合同时,应仔细确认所需要的服务内容、价格、数量、交付方式等信息。该信息将作为甲方的真实意思表示,甲方应对该等信息的法律后果承担责任。 2.12 甲方理解并同意:签订线下合同时系统生成的订单信息是计算机信息系统根据乙方填写的内容自动生成的数据,仅是乙方发出的合同要约;甲方收到乙方的合同信息内容并确认签字后,合同生效。 2.13 甲方同意并授权平台方保存其信息(包括但不限于注册信息) 3. 乙方权利义务3.1 乙方应按照合同约定的时间和质量向甲方提供服务。 3.2 乙方应当积极听取甲方的修改意见,甲方提出合理任务且提出明确的修改意见的,乙方在提交服务成果后可提供修改服务,但超出合同约定内容的修改任务乙方有权拒绝。 3.3 乙方应当对甲方提供的相关资料承担保密义务,除为履行本协议义务及法律规定外,不得向第三方透露。 3.4 乙方有权要求甲方按照合同约定的日期支付相应款项,否则乙方有权拒绝、顺延提供服务和不发起项目验收; 3.5 甲方与乙方约定分阶段工作的,乙方完成阶段性工作并发起验收,甲方应在规定期限日内予以验收确认,验收合格后乙方有权要求甲方支付下一开发阶段的项目启动资金;如甲方在规定期限日内未予以验收的,则视为验收合格。 3.6 在双方签订的合同生效后,乙方有权要求甲方先支付阶段性工作的项目启动资金进行托管后,再进行工作。 3.7 因乙方自身原因导致约定分阶段工作未能如期完成并交付,则乙方需要与甲方提前协商沟通,并在汇新云平台上发起项目延期函,甲方进行确认后方可生效。若乙方未提前发起项目延期函并与甲方确认,否则乙方需按照约定的日期进行交付,由此产生的责任由乙方自行承担。 3.8 乙方应按照法律规定自行缴纳相应税费。 3.9 乙方可能会向实现甲方任务所必须的关联方或合作伙伴共享甲方的订单信息,以保障为甲方提供的服务顺利进行。比如乙方必须将甲方的订单信息与第三方服务商共享来实现甲方的服务任务,并使其完成后续的售后服务,甲方对此无异议。 3.10 乙方应将平台方公布的最新信息传递给甲方,维护三方合作关系。 3.11 乙方对服务中产生的因己方原因造成的甲方损失负有责任,应负责解决;若因此对平台造成损失的,乙方应赔偿平台方全部损失。 4.服务平台方权利义务4.1 平台方对甲乙双方的注册申请有审核决定的权利; 4.2 平台方享有为维护系统而短暂停止服务的权利,暂停服务之前,平台方将在系统进行通知,甲乙双方应留意公告并做好相应备份工作。 4.3 平台方有权根据中国法律法规的调整、行政执法机关的命令和社会伦理道德的变化相应调整在线管理服务的审核标准,甲乙双方不得以类似“以前曾通过汇新云服务审核”的理由要求平台方继续审核通过; 4.4 乙方使用服务平台的账号密码所进行的一切操作视为乙方行为。乙方应妥善平台的账号密码,否则由此造成的一切后果由乙方承担;一旦发生安全问题应立即通知平台方以共同采取措施包括但不限于冻结账号等。 4.5 平台方有权根据自身任务改变平台服务规则,并在服务平台进行公告; 4.6 若乙方超过90天不使用平台账号的,平台方有权屏蔽或注销其账号。 5. 知识产权5.1 本协议所产生成果的知识产权在甲方支付完全部项目款后,归甲方所有,乙方或乙方委托提供服务的第三方保留法律规定禁止转让部分的知识产权,同时保留服务成果用于案例展示、评选的权利。但甲方与乙方另有约定的除外。 5.2 乙方应当保证服务成果符合国家法律法规的规定,不存在任何侵犯第三方的所有权、知识产权、名誉权、肖像权等侵权行为,并承担因此产生的全部责任。 5.3 甲方的服务任务如需采购第三方知识产权产品的,乙方应当及时告知甲方经甲方书面同意且支付采购费用后,乙方予以采购并使用或由甲方自行采购并提供给乙方使用。 5.4 甲方在未付清所有服务费用之前,不得使用服务成果,不得主张服务成果的知识产权。如甲方在未付清服务费用之前自行或许可他人使用(包含但不限于直接使用、修改后使用)乙方提交的服务成果的,导致乙方或者其他第三方遭受损失的,甲方应承担由此产生的全部责任。 5.5 甲方应积极就服务成果申请相关知识产权(如有),如发生第三方侵权的,乙方可协助甲方维权,但不对维权结果承担任何责任。 - 责任限制
乙方依照法律规定履行基础保障义务,但对于下述原因导致的合同履行障碍、履行瑕疵、履行延后或履行内容变更等情形,乙方并不承担相应的违约责任: 6、因自然灾害、罢工、暴乱、战争、政府行为、司法行政命令等不可抗力因素; 6、因电力供应故障、通讯网络故障等公共服务因素或第三人因素; 6、在乙方已尽善意管理的情况下,因常规或紧急的设备与系统维护、设备与系统故障、网络信息与数据安全等因素。 - 违约责任
7.1 乙方未按照合同的约定按时提交服务成果的,应向甲方支付合同中规定的违约金。 7.2 甲方在服务期间无正当理由单方终止协议的,已支付费用无权要求返还。 7.3 乙方在服务期间无正当理由单方终止协议的,所收取的费用应当全部退回给甲方。 7.4 甲乙双方应遵守平台规则以及维护平台商业形象以及维护平台方正常运营,若因甲乙双方任何一方的原因给平台方造成损失的,平台方有权追究其责任,要求其支付违约金,并有权冻结其享有的平台账号;若平台方以法律手段维护其权益的,平台方所支付的全部费用,包括但不限于律师费、诉讼费等,全部由违约方承担。 - 争议解决
8.1 因本协议及与本协议有关的争议、解释等,均适用中华人民共和国法律。 8.2 本协议签订或履行过程中,如有争议,双方应当友好协商解决;协商不成,双方一致同意提交平台方所在地人民法院解决。 - 其他
9.1 本协议以电子文本形式生成,甲方与乙方完成协议订立手续后,即具有与手写签名同等的法律效力。 9.2 本协议中的任何约定如违反法律法规的规定而无效的,该无效条款不影响本协议其他条款的效力,甲方与乙方仍因履行其他条款所约定的权利义务。 9.3 本协议内容中以加粗方式显著标识的条款,请着重阅读。甲乙方点击“确认”按钮即视为完全接受本协议,在点击之前请再次确认已知悉并完全理解本协议的全部内容 ';
+export const agreementContent = '投稿协议内容示例,请在管理 — 创客 — 基础数据 — 应征投稿协议内容 修改. 在您通过本平台在线签署应征投稿合同前,请您认真细致地阅读以下《应征投稿协议》,特别是其中以粗体下划线明显标注的条款,并在您同意了下述协议条款再正式进入后续程序 本协议由甲方(任务发布方)和乙方(应征者)在线签订,请甲乙双方仔细阅读协议内容, 请务必审慎阅读、充分理解各条款内容,特别是免除或者限制责任的条款、法律适用和争议解决条款。 甲乙双方点击接受本协议,即意味着已阅读、理解并接受本协议所有条款,并对本协议条款的含义及相应的法律后果已全部知晓并充分认可。甲乙双方点击确认本协议后,本协议即产生法律约束力。 本协议内容包括协议正文及甲乙双方在线相互确认的合同。所签订的合同、合同附件为本协议不可分割的一部分,与本协议正文具有同等法律效力。若您继续使用本平台创客空间,则表明您已经完全知晓、认可并同意遵守本协议内容、所有汇新云已经发布的各类规则以及签订的合同。 在阅读本协议的过程中,如不同意本协议或其中任何条款约定,应拒绝接受本协议所约定的内容,甲乙双方都有权自主选择拒绝达成合作。 1.定义除非本协议另有约定,在本协议中所用下列术语定义如下: 1.1 本平台:是指www.XXXXXX.com 为用户提供任务信息发布、交流,第三方以“企业”或“个人”入驻的形式应征任务的电子商务交易服务平台; 1.2 用户:指在本平台合法注册,接受并认可服务平台相关协议、规则、规范、制度等的自然人、法人或其他非法人组织。 1.3 甲方:指在本平台上发布创客任务的用户。 1.4 乙方:是指经本平台审核通过入驻本平台,根据任务方发布的任务,提供各种定制服务或IT产品,在平台开展业务经营的企业或个人。 1.5 服务任务:指甲方基于自身任务向乙方提出的具体服务要求。 1.6 项目款:指甲方和乙方的交易金额,即本协议约定交易金额或后续经协商调整后确定的交易总金额。 1.7 平台账户:指用户在本平台注册的帐号,用户只能通过该帐户登陆服务平台进行交易。 2.甲方权利义务2.1 甲方应当根据服务任务主动向乙方提交本项目所需的相关资料,并保证该资料的真实性、合法性、准确性、完整性,如因甲方未按照前述标准提供资料导致乙方无法履行协议义务,由此产生的责任由甲方自行承担。 2.2 甲方在向乙方提交项目所涉及资料时有权一并对乙方的服务提出建议和思路,同时有权在验收时对乙方的服务成果提出修改意见,但甲方提出的服务建议或思路以及修改意见应当明确具体,如不明确,有权不听取建议或拒绝修改,同时甲方不得借机拖延进度及应支付的款项,甲方提出超出协议或合同约定范围的修改要求,乙方有权拒绝或者另行收取费用。 2.3 甲方未按照合同在约定的日期内支付项目款的,乙方有权拒绝或顺延提供服务。 2.4 甲方应充分了解且同意遵守服务平台公布的所有协议、规则、制度等文件,并按照服务平台的相关规定处理相关交易事项。 2.5 甲方应及时验收乙方交付的服务成果(包括阶段成果和最终成果),如乙方向甲方提交服务成果后在规定期限日内甲方未给出具体验收意见的,视为乙方提交的服务成果合格。如有下一阶段服务的,乙方有权继续推进;如下一阶段服务因甲方原因导致无法继续推进的,乙方不承担任何责任。 2.6 甲方有义务向乙方提供必要的配合义务,包括提供必要资料、及时验收、及时回复等。 2.7 甲方同意并知晓,乙方仅提供合法、合规、合理的服务,对甲方违背法律法规或行政规章的服务要求,乙方有权拒绝提供服务。 2.8 甲方应当保证委托的服务事项不违反任何法律法规或侵犯他人合法权利,否则乙方有权拒绝提供服务并有权立即解除本协议。 2.9 甲方应当保证合法使用乙方提交的服务成果,不得将服务成果用于任何违法违规或侵犯他人合法权益的活动,甲方应自行承担服务成果使用过程中发生的全部责任。 2.10 甲方同意,为便于双方交易,本协议作为交易的主要内容和双方之间权利义务的根本性约定,具体服务项目、期限、金额等甲方在平台与乙方签订电子合同时在合同上予以标注,甲方对在合同中提供的所有信息的真实性负责。 2.11 甲方在签订线下子合同时,应仔细确认所需要的服务内容、价格、数量、交付方式等信息。该信息将作为甲方的真实意思表示,甲方应对该等信息的法律后果承担责任。 2.12 甲方理解并同意:签订线下合同时系统生成的订单信息是计算机信息系统根据乙方填写的内容自动生成的数据,仅是乙方发出的合同要约;甲方收到乙方的合同信息内容并确认签字后,合同生效。 2.13 甲方同意并授权平台方保存其信息(包括但不限于注册信息) 3. 乙方权利义务3.1 乙方应按照合同约定的时间和质量向甲方提供服务。 3.2 乙方应当积极听取甲方的修改意见,甲方提出合理任务且提出明确的修改意见的,乙方在提交服务成果后可提供修改服务,但超出合同约定内容的修改任务乙方有权拒绝。 3.3 乙方应当对甲方提供的相关资料承担保密义务,除为履行本协议义务及法律规定外,不得向第三方透露。 3.4 乙方有权要求甲方按照合同约定的日期支付相应款项,否则乙方有权拒绝、顺延提供服务和不发起项目验收; 3.5 甲方与乙方约定分阶段工作的,乙方完成阶段性工作并发起验收,甲方应在规定期限日内予以验收确认,验收合格后乙方有权要求甲方支付下一开发阶段的项目启动资金;如甲方在规定期限日内未予以验收的,则视为验收合格。 3.6 在双方签订的合同生效后,乙方有权要求甲方先支付阶段性工作的项目启动资金进行托管后,再进行工作。 3.7 因乙方自身原因导致约定分阶段工作未能如期完成并交付,则乙方需要与甲方提前协商沟通,并在汇新云平台上发起项目延期函,甲方进行确认后方可生效。若乙方未提前发起项目延期函并与甲方确认,否则乙方需按照约定的日期进行交付,由此产生的责任由乙方自行承担。 3.8 乙方应按照法律规定自行缴纳相应税费。 3.9 乙方可能会向实现甲方任务所必须的关联方或合作伙伴共享甲方的订单信息,以保障为甲方提供的服务顺利进行。比如乙方必须将甲方的订单信息与第三方服务商共享来实现甲方的服务任务,并使其完成后续的售后服务,甲方对此无异议。 3.10 乙方应将平台方公布的最新信息传递给甲方,维护三方合作关系。 3.11 乙方对服务中产生的因己方原因造成的甲方损失负有责任,应负责解决;若因此对平台造成损失的,乙方应赔偿平台方全部损失。 4.服务平台方权利义务4.1 平台方对甲乙双方的注册申请有审核决定的权利; 4.2 平台方享有为维护系统而短暂停止服务的权利,暂停服务之前,平台方将在系统进行通知,甲乙双方应留意公告并做好相应备份工作。 4.3 平台方有权根据中国法律法规的调整、行政执法机关的命令和社会伦理道德的变化相应调整在线管理服务的审核标准,甲乙双方不得以类似“以前曾通过汇新云服务审核”的理由要求平台方继续审核通过; 4.4 乙方使用服务平台的账号密码所进行的一切操作视为乙方行为。乙方应妥善平台的账号密码,否则由此造成的一切后果由乙方承担;一旦发生安全问题应立即通知平台方以共同采取措施包括但不限于冻结账号等。 4.5 平台方有权根据自身任务改变平台服务规则,并在服务平台进行公告; 4.6 若乙方超过90天不使用平台账号的,平台方有权屏蔽或注销其账号。 5. 知识产权5.1 本协议所产生成果的知识产权在甲方支付完全部项目款后,归甲方所有,乙方或乙方委托提供服务的第三方保留法律规定禁止转让部分的知识产权,同时保留服务成果用于案例展示、评选的权利。但甲方与乙方另有约定的除外。 5.2 乙方应当保证服务成果符合国家法律法规的规定,不存在任何侵犯第三方的所有权、知识产权、名誉权、肖像权等侵权行为,并承担因此产生的全部责任。 5.3 甲方的服务任务如需采购第三方知识产权产品的,乙方应当及时告知甲方经甲方书面同意且支付采购费用后,乙方予以采购并使用或由甲方自行采购并提供给乙方使用。 5.4 甲方在未付清所有服务费用之前,不得使用服务成果,不得主张服务成果的知识产权。如甲方在未付清服务费用之前自行或许可他人使用(包含但不限于直接使用、修改后使用)乙方提交的服务成果的,导致乙方或者其他第三方遭受损失的,甲方应承担由此产生的全部责任。 5.5 甲方应积极就服务成果申请相关知识产权(如有),如发生第三方侵权的,乙方可协助甲方维权,但不对维权结果承担任何责任。 - 责任限制
乙方依照法律规定履行基础保障义务,但对于下述原因导致的合同履行障碍、履行瑕疵、履行延后或履行内容变更等情形,乙方并不承担相应的违约责任: 6、因自然灾害、罢工、暴乱、战争、政府行为、司法行政命令等不可抗力因素; 6、因电力供应故障、通讯网络故障等公共服务因素或第三人因素; 6、在乙方已尽善意管理的情况下,因常规或紧急的设备与系统维护、设备与系统故障、网络信息与数据安全等因素。 - 违约责任
7.1 乙方未按照合同的约定按时提交服务成果的,应向甲方支付合同中规定的违约金。 7.2 甲方在服务期间无正当理由单方终止协议的,已支付费用无权要求返还。 7.3 乙方在服务期间无正当理由单方终止协议的,所收取的费用应当全部退回给甲方。 7.4 甲乙双方应遵守平台规则以及维护平台商业形象以及维护平台方正常运营,若因甲乙双方任何一方的原因给平台方造成损失的,平台方有权追究其责任,要求其支付违约金,并有权冻结其享有的平台账号;若平台方以法律手段维护其权益的,平台方所支付的全部费用,包括但不限于律师费、诉讼费等,全部由违约方承担。 - 争议解决
8.1 因本协议及与本协议有关的争议、解释等,均适用中华人民共和国法律。 8.2 本协议签订或履行过程中,如有争议,双方应当友好协商解决;协商不成,双方一致同意提交平台方所在地人民法院解决。 - 其他
9.1 本协议以电子文本形式生成,甲方与乙方完成协议订立手续后,即具有与手写签名同等的法律效力。 9.2 本协议中的任何约定如违反法律法规的规定而无效的,该无效条款不影响本协议其他条款的效力,甲方与乙方仍因履行其他条款所约定的权利义务。 9.3 本协议内容中以加粗方式显著标识的条款,请着重阅读。甲乙方点击“确认”按钮即视为完全接受本协议,在点击之前请再次确认已知悉并完全理解本协议的全部内容 ';
+export const expertReviewArr = [
+ { dicItemCode: 1, name: "提交评审", dicItemName: '提交评审' },
+ { dicItemCode: -1, name: "不提交评审", dicItemName: '不提交评审' },
+]
\ No newline at end of file
diff --git a/src/military/task/taskAdmin/image/down.svg b/src/military/task/taskAdmin/image/down.svg
new file mode 100644
index 00000000..b5085499
--- /dev/null
+++ b/src/military/task/taskAdmin/image/down.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/military/task/taskAdmin/image/right.svg b/src/military/task/taskAdmin/image/right.svg
new file mode 100644
index 00000000..c7bbb9bb
--- /dev/null
+++ b/src/military/task/taskAdmin/image/right.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/military/task/taskAdmin/index.jsx b/src/military/task/taskAdmin/index.jsx
index c60c3414..8241c23a 100644
--- a/src/military/task/taskAdmin/index.jsx
+++ b/src/military/task/taskAdmin/index.jsx
@@ -1,12 +1,14 @@
import React, { useCallback, useEffect, useState, useMemo } from 'react';
import classNames from 'classnames';
-import { Input, Select, Button, Form, DatePicker, Table, Pagination, Modal } from 'antd';
-import { Link } from "react-router-dom";
+import { Input, Select, Button, Form, DatePicker, Table, Pagination, Modal, message } from 'antd';
+import { Link } from 'react-router-dom';
-import { paperCheckStatusArr, publishModeArr, taskStatusAllArr, showUserModeArr, main_web_site_url } from '../static';
-import { getTaskAdminList, changeShowUserMode, deleteTask, recommendTask } from '../api';
+import { paperCheckStatusArr, publishModeArr, taskStatusAllArr, showUserModeArr, main_web_site_url, expertReviewArr } from '../static';
+import { getTaskAdminList, changeShowUserMode, deleteTask, recommendTask, addExpertReview, publishExpertsAndRules } from '../api';
import '../index.scss';
import './index.scss';
+import { getRules, selectExpertList } from 'src/military/expert/api';
+import PaginationTable from '../../../../src/military/components/paginationTable';
const format = "YYYY-MM-DD HH:mm:ss";
const Option = Select.Option;
@@ -20,9 +22,9 @@ for (const item of paperCheckStatusArr) {
}
-export default Form.create()(({ form, showNotification, match, history }) => {
+export default Form.create()(({ form, showNotification, match, history, state }) => {
const { getFieldDecorator, setFieldsValue, getFieldsValue } = form;
-
+ const { hash} = history && history.location;
const [reload, setReload] = useState();
const [loading, setLoading] = useState(false);
const [statusString, setStatusString] = useState('');
@@ -34,10 +36,22 @@ export default Form.create()(({ form, showNotification, match, history }) => {
const [sort, setSort] = useState('Desc');
const [order, setOrder] = useState('createdAt');
const [searchObj, setSearchObj] = useState({});
- const [curPage, setCurPage] = useState(1);
+ const [curPage, setCurPage] = useState(hashDate(hash) || 1);
const [total, setTotal] = useState(0);
const [taskList, setTaskList] = useState([]);
+ const [expertReview, setExpertReview] = useState('');
+ //查看评审规则、查看选取专家、发布评审任务
+ const [lookRules, setLookRules] = useState(false);
+ const [lookExperts, setLookExperts] = useState(false);
+ const [pulicReview, setPublicReview] = useState(false);
+ const [rules, setRules] = useState(undefined);
+ const [selectedExperts, setSelectedExperts] = useState(undefined);
+ const [publicTaskId, setPublicTaskId] = useState(undefined);
+
+ useEffect(()=>{
+ setCurPage(hashDate(hash) || 1);
+ },[hash])
useEffect(() => {
const params = {
@@ -50,6 +64,7 @@ export default Form.create()(({ form, showNotification, match, history }) => {
orderBy: order + sort,
isDelete,
recommend,
+ expertReview: expertReview==='-1'?"":expertReview,
};
setLoading(true);
getTaskAdminList(params).then(data => {
@@ -59,7 +74,7 @@ export default Form.create()(({ form, showNotification, match, history }) => {
}
setLoading(false);
})
- }, [statusString, order, sort, publishMode, showUserMode, curPage, searchObj, isDelete, reload, recommend]);
+ }, [statusString, order, sort, publishMode, showUserMode, curPage, searchObj, isDelete, reload, recommend, expertReview]);
const helper = useCallback(
@@ -69,13 +84,17 @@ export default Form.create()(({ form, showNotification, match, history }) => {
), []);
-
+ function hashDate(hash) {
+ return parseInt(hash.split("&")[0].substring(hash.split("&")[0].indexOf("=")+1));
+ }
function onSearch() {
let values = getFieldsValue(['nameInput', 'endTime', 'startTime', 'enterpriseNameInput']);
if (values.startTime) values.startTime = values.startTime.format(format);
if (values.endTime) values.endTime = values.endTime.format(format);
if (values.checkStatus === '0,1,2') values.checkStatus = '';
setSearchObj(values);
+ setCurPage1(1);
+ // window.location.href=`/task/taskAdmin`;
}
function clearSearch() {
@@ -90,31 +109,48 @@ export default Form.create()(({ form, showNotification, match, history }) => {
const columns = useMemo(() => {
return [
- {
- title: '序号',
- dataIndex: 'index',
- render: (text, record, index) => {
- return {index + 1}
- }
- },
- {
- title: '任务编号',
- dataIndex: 'number',
- },
{
title: '任务名称',
dataIndex: 'name',
- width: "15%",
+ width: "13%",
render: (text, record) => (
{text}
),
},
+ {
+ title: ,
+ dataIndex: 'expertReview',
+ render: (text, record) => {
+ return
+ }
+ },
{
title: ,
- width: '10%',
+ width: '6%',
dataIndex: 'status',
render: (text, record) => {
return record.exceptClosedBoolean ? '已关闭' : statusArr[text]
}
},
- {
- title: '稿件数',
- dataIndex: 'papersCount',
- },
{
title: '发布主体',
dataIndex: 'enterpriseName',
+ width: '9%',
},
{
title: '发布时间',
dataIndex: 'publishedAt',
- render: (text, record) => {
- return text || '--'
- }
- },
- {
- title: '截稿时间',
- dataIndex: 'collectingEndTime',
+ width: '7%',
render: (text, record) => {
return text || '--'
}
@@ -176,7 +203,7 @@ export default Form.create()(({ form, showNotification, match, history }) => {
defaultValue={'0,1,2'}
onChange={setShowUserMode}
>
-
+
{
showUserModeArr.map(item => {
return
@@ -184,6 +211,7 @@ export default Form.create()(({ form, showNotification, match, history }) => {
}
,
dataIndex: 'showUserMode',
+ width:'8%',
render: (text, record) => {
return
}
},
+ {
+ title: '评审规则',
+ dataIndex: 'ruleEditedCount',
+ render: (text, record) => {
+ return record.assignRuleAndExperts ? : record.expertReview && (record.status === 1 || record.status === 3) ? 编辑 : 编辑
+ }
+ },
+ {
+ title: '专家选取',
+ dataIndex: 'expertSelectedCount',
+ render: (text, record) => {
+ return record.assignRuleAndExperts ? : record.expertReview && (record.status === 1 || record.status === 3) ? 选择 : 选择
+ }
+ },
+ {
+ title: '评审任务',
+ dataIndex: 'expertReview1',
+ render: (text, record) => {
+ return record.assignRuleAndExperts ? 已发布 : record.expertReview && (record.status === 1 || record.status === 3) ? : 发布
+ }
+ },
+ {
+ title: '评审结果',
+ dataIndex: 'expertReview2',
+ render: (text, record) => {
+ return record.assignRuleAndExperts ? 查看:查看
+ }
+ },
{
title: '操作',
key: 'action',
+ width: '6%',
render: (text, record) => (
@@ -224,7 +281,58 @@ export default Form.create()(({ form, showNotification, match, history }) => {
),
},
]
- }, [isDelete]);
+ }, [isDelete, curPage]);
+
+ //已选取专家
+ const columnsExperts = useMemo(() => {
+ return [
+ {
+ title: '编号',
+ dataIndex: 'index',
+ width: 80,
+ align: 'center',
+ },
+ {
+ title: '专家姓名',
+ dataIndex: 'expertName',
+ key: 'expertName',
+ width: 120,
+ },
+ {
+ title: '手机号码',
+ dataIndex: 'phone',
+ width: 130,
+ key: 'phone',
+ },
+ {
+ title: '最高学历',
+ dataIndex: 'highestDegree',
+ key: 'highestDegree',
+ },
+ {
+ title: '专业职称',
+ dataIndex: 'professionalTitle',
+ },
+ {
+ title: '专家类别',
+ dataIndex: 'expertType',
+ },
+ {
+ title: '评审领域',
+ dataIndex: 'reviewAreas',
+ align: 'center',
+ width: 260,
+ },
+ {
+ title: '专家评估',
+ dataIndex: 'expertScore',
+ align: 'center',
+ render:(text,record)=>{
+ return record.expertScore || '--';
+ }
+ }
+ ];
+ }, []);
function recommendItem(id, recommend) {
Modal.confirm({
@@ -260,6 +368,128 @@ export default Form.create()(({ form, showNotification, match, history }) => {
});
}
+ //监听lookRules,lookExperts,pulicReview的变化,弹框
+ useEffect(()=>{
+
+ //评审规则
+ lookRules && rules && Modal.info({
+ className: 'publishReview',
+ title: "评审规则",
+ content:
+
+ {rules && rules.rule}
+ 评分标准
+
+ {rules.criterias.map(item=>{return {item} })}
+
+ 评审时间
+ {rules.reviewData}
+
+ ,
+ });
+ lookRules && setLookRules(false);
+
+ //已选取评审专家
+ lookExperts && selectedExperts && Modal.info({
+ className: 'publishReview',
+ title: "已选取评审专家",
+ content:
+ ,
+ });
+ lookExperts && setLookExperts(false);
+
+ //发布评审任务
+ pulicReview && rules && selectedExperts && Modal.confirm({
+ className: 'publishReview',
+ title: "发布评审任务",
+ centered: true,
+ content:
+
+
+
+ 确定发布此评审任务?确定发布后评审规则与评审专家信息将无法重新编辑
+
+ 评审规则
+ {rules && rules.rule}
+ 评分标准
+
+ {rules.criterias.map(item=>{return {item} })}
+
+ 评审时间
+ {rules.reviewData}
+ 已选取评审专家
+
+
+ ,
+ okText: '确定',
+ cancelText: '取消',
+ onOk() {
+ publishExpertsAndRules(publicTaskId,1).then(response=>{
+ if(response && response.message==="发布成功"){
+ setReload(Math.random());
+ }
+ })
+ },
+ });
+ pulicReview && setPublicReview(false);
+ },[lookRules,lookExperts,pulicReview])
+
+ //发布评审任务
+ function publishTaskReview(record){
+ if(!record.ruleEditedCount || !record.expertSelectedCount){
+ message.error("请先编辑评审规则以及选取评选专家再发布此任务");
+ }else{
+ getRules({containerId: record.id, containerType: 1, statusString: 3}).then(response=>{
+ if(response && response.message === "success"){
+ setRules(response.data);
+ }
+ })
+ selectExpertList({containerId: record.id, containerType: 1, curPage:curPage, pageSize: 10000, curPage: 1,}).then(response=>{
+ if(response && response.message === "success" && Array.isArray(response.data.rows)){
+ let index = 1;
+ for (const item of response.data.rows) {
+ item.reviewAreas = `${item.reviewAreaOne} ${item.reviewAreaTwo ? `、${item.reviewAreaTwo}`:''} ${item.reviewAreaThree ? `、${item.reviewAreaThree}`:''}`;
+ item.index = (index++) + (curPage > 1 ? (curPage - 1) * 10 : 0);
+ }
+ setPublicTaskId(record.id);
+ setSelectedExperts(response.data.rows);
+ setPublicReview(true);
+ }
+ });
+ }
+ }
+
+ //已发布任务 查看评审规则
+ function viewRules(record){
+ getRules({containerId: record.id, containerType: 1, statusString: '-1,1,2'}).then(response=>{
+ if(response && response.message === "success"){
+ setRules(response.data);
+ setLookRules(true);
+ }
+ });
+ }
+
+ //已发布任务 查看已选专家
+ function viewExperts(record){
+ selectExpertList({containerId: record.id, containerType: 1, curPage:curPage, pageSize: 10000, curPage: 1,}).then(response=>{
+ if(response && response.message === "success" && Array.isArray(response.data.rows)){
+ let index = 1;
+ for (const item of response.data.rows) {
+ item.reviewAreas = `${item.reviewAreaOne} ${item.reviewAreaTwo ? `、${item.reviewAreaTwo}`:''} ${item.reviewAreaThree ? `、${item.reviewAreaThree}`:''}`;
+ item.index = (index++) + (curPage > 1 ? (curPage - 1) * 10 : 0);
+ }
+ setSelectedExperts(response.data.rows);
+ setLookExperts(true);
+ }
+ });
+ }
+
function changeStatus(showUserMode, taskId) {
changeShowUserMode({
taskId,
@@ -271,22 +501,37 @@ export default Form.create()(({ form, showNotification, match, history }) => {
})
}
+ function changeExpertReviewStatus(expertReviewStatus, taskId) {
+ addExpertReview(taskId,expertReviewStatus).then(res => {
+ if (res && res.message === 'success') {
+ showNotification('操作成功!');
+ setReload(Math.random());
+ } else {
+ showNotification('操作失败');
+ }
+ })
+ }
+
+ function setCurPage1(page){
+ setCurPage(page);
+ window.location.href=`/task/taskAdmin#page=${page}`;
+ }
// 改变排序字段
const changeSortName = useCallback((sortType) => {
setOrder(sortType);
- setCurPage(1);
+ setCurPage1(1);
}, []);
// 改变排序
const changeSort = useCallback((sort) => {
setSort(sort);
- setCurPage(1);
+ setCurPage1(1);
}, []);
const changeShow = useCallback((isDelete) => {
setIsDelete(isDelete);
- setCurPage(1);
+ setCurPage1(1);
});
const changeRecommend = useCallback((recommend) => {
@@ -295,16 +540,24 @@ export default Form.create()(({ form, showNotification, match, history }) => {
} else {
setRecommend(recommend);
}
- setCurPage(1);
+ setCurPage1(1);
});
+ const ExpertDetail = (record)=>{
+ return
+ 任务编号:{record.number}
+ 截稿时间:{record.collectingEndTime || '--'}
+ 稿件数:{record.papersCount || '--'}
+
+ }
+
function downloadFile() {
window.open(main_web_site_url + '/admin/tasks.xlsx');
}
return (
-
+
{helper(
"任务名称",
@@ -403,10 +656,6 @@ export default Form.create()(({ form, showNotification, match, history }) => {
-
-
-
-
{
columns={columns}
pagination={false}
className="mt10"
+ expandedRowRender={ExpertDetail}
/>
{total > 10 &&
{ setCurPage(page) }}
+ onChange={(page) => { setCurPage1(page) }}
current={curPage}
total={total}
/>}
diff --git a/src/military/task/taskAdmin/index.scss b/src/military/task/taskAdmin/index.scss
index 087e99cc..e6c859dc 100644
--- a/src/military/task/taskAdmin/index.scss
+++ b/src/military/task/taskAdmin/index.scss
@@ -41,7 +41,7 @@
}
.ant-table-thead > tr > th,
.ant-table-tbody > tr > td {
- padding: 1rem 0.2rem;
+ padding: 1rem 0.1rem;
text-align: center;
}
@@ -53,7 +53,19 @@
display: flex;
justify-content: space-between;
}
-
+ .ant-table-row-expand-icon{
+ width: 35px;
+ height: 20px;
+ line-height: 20px;
+ }
+ .expert_detail_div{
+ display: flex;
+ justify-content: space-around;
+ }
+
+ // .ant-table-row-collapsed::after, .ant-table-row-expanded::after {
+ // content: url('./image/down.svg');
+ // }
}
.inline-form {
@@ -74,3 +86,55 @@
.sort-active {
color: #29bd8b;
}
+
+.gary_span{
+ color: rgba(176, 176, 176, 1);
+}
+
+// 发布评审任务弹框样式
+.publishReview{
+ width: 1050px !important;
+ .ant-modal-body{
+ padding: 0;
+ }
+ .ant-modal-confirm-btns {
+ margin: 15px 35px 10px;
+ }
+ .ant-modal-confirm-title{
+ border-bottom: 1px solid #eeeeee;
+ padding: 20px 25px;
+ background: #f2f2ff;
+ font-size: 18px;
+ }
+ .ant-modal-confirm-body > .anticon{
+ display: none;
+ }
+ .ant-modal-confirm-body > .anticon + .ant-modal-confirm-title + .ant-modal-confirm-content{
+ margin-left: 0;
+ }
+ .ant-modal-confirm-content{
+ &>p{
+ font-size: 16px;
+ color: #333333;
+ border-bottom: 1px solid #eeeeee;
+ padding: 10px 35px;
+ font-weight: bold;
+ }
+ &>div{
+ padding: 10px 45px;
+ }
+ .tip{
+ padding: 10px 35px;
+ i{
+ color: #ca0002;
+ }
+ .publicTitle {
+ font-size: 15px;
+ margin-left: 3px;
+ }
+ }
+ }
+ .pagination-table .ant-table-tbody > tr > td{
+ padding: 3px 8px;
+ }
+}
diff --git a/src/military/task/taskAdminRouter.js b/src/military/task/taskAdminRouter.js
index 6c790a6b..e6badd65 100644
--- a/src/military/task/taskAdminRouter.js
+++ b/src/military/task/taskAdminRouter.js
@@ -3,7 +3,7 @@ import React from "react";
import { Route, Switch } from "react-router-dom";
import Loadable from "react-loadable";
import Loading from "../../Loading";
-import AdminRouter from "./components/adminRouter";
+import AdminRouter from "../components/adminRouter";
const TaskManage = Loadable({
diff --git a/src/military/task/taskDetail/index.jsx b/src/military/task/taskDetail/index.jsx
index eadd35ed..b390dff5 100644
--- a/src/military/task/taskDetail/index.jsx
+++ b/src/military/task/taskDetail/index.jsx
@@ -8,10 +8,11 @@ import Upload from '../../components/Upload';
import StatusNav from '../../components/statusNav';
import ItemListPaper from '../components/itemListPaper';
import ProofModal from '../components/proofModal';
-import { getTaskDetail, getTaskCategory, getTaskPaper, makePublic, addPaper, getAgreement, agreement, checkAgreement, checkHavePaper } from '../api';
+import { getTaskDetail, getTaskCategory, getTaskPaper, makePublic, addPaper, getAgreement, agreement, checkAgreement, checkHavePaper, addExpertReview } from '../api';
import { taskModeIdArr, applyStatusArr, applyStatusAllArr, agreementContent, paperCheckTextArr } from '../static';
import { httpUrl } from '../fetch';
import './index.scss';
+import { getRules } from 'src/military/expert/api';
const { TextArea } = Input;
@@ -52,6 +53,8 @@ export default Form.create()(
const [relaodChildList, setRelaodChildList] = useState(0);
const [visibleProofs, setVisibleProofs] = useState(false);
+ // 已发布评审任务 评审规则
+ const [publishedReviewRules, setPublishedReviewRules] = useState(undefined);
// 获取任务领域配置数据
useEffect(() => {
@@ -73,6 +76,11 @@ export default Form.create()(
history.push('/task');
}
setDetailData(data || {});
+ if(data && data.assignRuleAndExperts){
+ getRules({ containerId: data.id, containerType: 1, statusString: '-1,1,2', }).then(response=>{
+ response && setPublishedReviewRules(response.data || undefined);
+ })
+ }
});
}, [id, reload]);
@@ -278,6 +286,22 @@ export default Form.create()(
}
}
+ function addExpertReviewModal(){
+ Modal.confirm({
+ title: '提示',
+ content: '确定将此创客任务添加专家评审流程?',
+ onOk: () => {
+ addExpertReview(id,1).then(res => {
+ if (res && res.message === 'success') {
+ setReload(Math.random());
+ } else {
+ showNotification('操作失败');
+ }
+ })
+ }
+ })
+ }
+
const reloadList = useCallback(() => {
setRelaodChildList(Math.random());
});
@@ -435,6 +459,14 @@ export default Form.create()(
应征者提交的稿件必须是设计作品,广告等无效交稿一律不采用!
+ {publishedReviewRules &&
+ 评审规则:
+ {publishedReviewRules.rule}
+ 评分标准:
+ {publishedReviewRules.criterias.map(item=>{return {item} })}
+ 评审时间:
+ {publishedReviewRules.reviewData}
+ }
{!current_user.enterpriseCertification &&
@@ -448,10 +480,12 @@ export default Form.create()(
{!detailData.showUserStatus &&
}
- {detailData.status === 4 && dataList.length && (!detailData.isProofBoolean) && detailData.user && (current_user.admin || current_user.login === detailData.user.login) ?
+ {detailData.status === 4 && dataList.length && (!detailData.isProofBoolean) && (!detailData.expertReview) && detailData.user && (current_user.admin || current_user.login === detailData.user.login) ?
{ setVisibleProofs(true) }}>上传佐证材料 : ''}
{dataList.length > 0 && taskLimit && { window.open(`${httpUrl}/api/paper/papers/download/${id}`) }}>一键导出成果物 >>}
- {(!detailData.showUserStatus) && taskLimit && 应征者名单公示 >>}
+ {(!detailData.showUserStatus) && !detailData.expertReview && taskLimit && 应征者名单公示 >>}
+ {/* [添加专家评审流程]按钮入口,仅管理员可见 */}
+ {taskLimit && !detailData.expertReview && detailData.status<4 && 添加专家评审流程}
diff --git a/src/military/task/taskDetail/index.scss b/src/military/task/taskDetail/index.scss
index 3d5f9f21..9f7a0549 100644
--- a/src/military/task/taskDetail/index.scss
+++ b/src/military/task/taskDetail/index.scss
@@ -6,7 +6,7 @@
display: inline-flex;
align-items: center;
&:hover {
- color: #409eff;
+ color: #4154f1;
}
}
}
@@ -105,7 +105,7 @@
}
.content-download {
- color: #409eff;
+ color: #4154f1;
}
@@ -152,8 +152,8 @@
.task-detail{
.ant-btn-primary{
- background-color:#409eff;
- border-color: #409eff;
+ background-color:#4154f1;
+ border-color: #4154f1;
}
}
diff --git a/src/military/task/taskEdit/index.jsx b/src/military/task/taskEdit/index.jsx
index d2d71725..f4d39729 100644
--- a/src/military/task/taskEdit/index.jsx
+++ b/src/military/task/taskEdit/index.jsx
@@ -1,5 +1,5 @@
import React, { forwardRef, useCallback, useEffect, useState } from 'react';
-import { Form, Radio, Input, InputNumber, Icon, Button, Modal } from 'antd';
+import { Form, Radio, Input, InputNumber, Icon, Button, Modal, Checkbox } from 'antd';
import classNames from 'classnames';
import moment from 'moment';
import ReactWEditor from 'wangeditor-for-react';
@@ -358,6 +358,13 @@ export default Form.create()(forwardRef(({ current_user, form, showNotification,
注:任务发布之后,将会公开展示在交易中心。不要把与项目、客户相关等隐私信息,以及QQ号、微信号、电话号码等联系方式填写在任务中。
+
+ {getFieldDecorator('expertReview', {
+ validateFirst: true,
+ initialValue: false
+ })(是否增加专家评审流程?添加后可联系管理员发布此专家评审任务)}
+
+
{/*mt100 mb100*/}
-
- 您尚未被授权访问此页面,请先获取相关权限
- 您可尝试
- {(!current_user || !current_user.login) && (
- 您可尝试登录或
- )}
- 返回首页,也可以通过
+
+ 您可以稍后尝试 返回首页
+ {/* ,或者
QQ向我们反馈
-
+ href="//shang.qq.com/wpa/qunwpa?idkey=2f2043d88c1bd61d182b98bf1e061c6185e23055bec832c07d8148fe11c5a6cd"
+ className="color-blue">QQ反馈>> */}
+
{/**/}
{/*载入中... */}
diff --git a/src/modules/404/Shixunnopage.js b/src/modules/404/Shixunnopage.js
index e59d718e..e5e2e21c 100644
--- a/src/modules/404/Shixunnopage.js
+++ b/src/modules/404/Shixunnopage.js
@@ -26,23 +26,22 @@ class http500 extends Component {
render() {
const { current_user } = this.props;
return (
-
-
- {/*mt100 mb100*/}
- })
-
- 你访问的页面不存在
- 您可尝试
- {(!current_user || !current_user.login) && (
- 您可尝试登录或
- )}
- 返回首页
- ,也可通过
- QQ向我们反馈
-
-
+
+ {
+ this.state.isAdmins? :
+ {/*mt100 mb100*/}
+ })
+
+ 您可以稍后尝试 返回首页
+ {/* ,或者
+ QQ反馈>> */}
+
+
+ }
+
{/* */}
{/* 载入中... */}
{/* */}
diff --git a/src/modules/tpm/NewHeader.js b/src/modules/tpm/NewHeader.js
index 965e523e..604b64cc 100644
--- a/src/modules/tpm/NewHeader.js
+++ b/src/modules/tpm/NewHeader.js
@@ -1,7 +1,8 @@
import React, { Component } from 'react';
import { Link } from "react-router-dom";
import AccountProfile from "../user/AccountProfile";
-import { getImageUrl,getLogoImageUrl } from 'educoder'
+import { getImageUrl,getLogoImageUrl } from 'educoder';
+import { getUserInfo } from 'src/military/expert/api';
import axios from 'axios';
import { Modal, Input, message, notification, Button } from 'antd';
@@ -48,12 +49,17 @@ class NewHeader extends Component {
mydisplay: false,
headtypesonClickbool: false,
headtypess: "/",
+ mygetHelmetapi2: null,
settings: null,
goshowqqgtounp: false,
visiblemyss: false,
+ isExpert: false,
}
}
componentDidMount() {
+ getUserInfo().then(response =>{
+ response && this.setState({isExpert: response.data && response.data.expert});
+ });
// this.getAppdata();
this.geturlsdata();
window._header_componentHandler = this;
@@ -521,7 +527,6 @@ class NewHeader extends Component {
if (oldLink) {
document.head.removeChild(oldLink);
}
- console.log("ac12111:",response.data.setting.tab_logo_url);
document.head.appendChild(link);
}
@@ -592,13 +597,13 @@ class NewHeader extends Component {
})
}
render() {
- const { match } = this.props;
+ const { match,current_user } = this.props;
let { Addcoursestypes,
tojoinitemtype,
tojoinclasstitle,
code_notice,
- checked_notice,activeIndex,
+ checked_notice,
AccountProfiletype,
submitapplications,
submitapplicationsvalue,
@@ -609,8 +614,9 @@ class NewHeader extends Component {
headtypess,
settings,
goshowqqgtounp,
+ mygetHelmetapi2,
} = this.state;
-
+ let activeIndex =match.path === '/'?true: '';
let headtypes = '/';
if (settings) {
if (settings.navbar) {
@@ -658,6 +664,7 @@ class NewHeader extends Component {
}
})
}
+
return (
|