This commit is contained in:
zhouhefeng
2026-06-01 08:36:26 +08:00
parent f05e534e52
commit 8b47088953
47 changed files with 1733 additions and 301 deletions
@@ -103,6 +103,7 @@ public class SysConfController {
private void ensureConfigValueColumn(Sys_config conf) {
if (conf == null || (!"AppHomeImg".equals(conf.getConfigKey())
&& !"H5AppHomeImg".equals(conf.getConfigKey())
&& !"AppFeaturedActivityImg".equals(conf.getConfigKey())
&& !"AppFestivalBenefitImg".equals(conf.getConfigKey()))) {
return;
@@ -140,6 +141,8 @@ public class SysConfController {
@SaCheckPermission("sys.manager.conf")
public Object data(@Param("pageNumber") int pageNumber, @Param("pageSize") int pageSize, @Param("pageOrderName") String pageOrderName, @Param("pageOrderBy") String pageOrderBy) {
try {
ensureAppImageConfig("AppHomeImg", "PC首页轮播图");
ensureAppImageConfig("H5AppHomeImg", "移动端首页轮播图");
ensureAppImageConfig("AppFeaturedActivityImg", "精彩活动页顶部图片");
ensureAppImageConfig("AppFestivalBenefitImg", "节日福利页顶部图片");
Cnd cnd = Cnd.NEW();
@@ -273,7 +273,7 @@ public class SysHomeController {
}
FieldFilter fieldFilter = FieldFilter.locked(Sys_home_template.class, "allowUserSql|classPath");
List<Sys_home_template> list = Daos.ext(dao, fieldFilter).query(Sys_home_template.class,
Cnd.NEW().desc("top").desc("sortNo"));
Cnd.where("enable", "=", 1).asc("sortNo"));
return Result.success(list);
}
@@ -167,7 +167,8 @@ public class SysUnionController {
cnd.asc("gh.unionCode");
cnd.groupBy("gh.id");
if (AuthUtil.hasRole(RoleConstant.BRANCH_UNION_CHAIRMAN.name())) {
boolean schoolUnionAdmin = AuthUtil.hasRoleOr(RoleConstant.SYSADMIN.name(), RoleConstant.SCHOOL_UNION_ADMIN.name());
if (!schoolUnionAdmin && AuthUtil.hasRole(RoleConstant.BRANCH_UNION_CHAIRMAN.name())) {
cnd.and("gh.id", "=", SecurityUtil.getUnionId());
}
@@ -39,7 +39,7 @@ public class SysWorkTemplateController {
public Result pageData(@Valid SysHomeTemplatePageForm pageForm) {
Cnd cnd = Cnd.NEW();
cnd.and(Cnd.likeEX(Sys_home_template::getName, pageForm.getName()));
cnd.desc(Sys_home_template::getSortNo);
cnd.asc(Sys_home_template::getSortNo);
Pagination pagination = sysHomeTemplateService.listPage(pageForm.getPageNumber(), pageForm.getPageSize(), cnd);
return Result.success(pagination);
}
@@ -82,6 +82,28 @@ public class SysWorkTemplateController {
return Result.success();
}
@At
@SaCheckPermission("sys.worktemplate")
@ApiOperation("修改模板文件")
public Result updateTemplateFile(@Valid String id, String templateFile) {
if (StrUtil.isBlank(id)) {
return Result.error("参数错误");
}
sysHomeTemplateService.update(Chain.make("templateFile", templateFile), Cnd.where("id", "=", id));
return Result.success();
}
@At
@SaCheckPermission("sys.worktemplate")
@ApiOperation("修改排序")
public Result updateSortNo(@Valid String id, Integer sortNo) {
if (StrUtil.isBlank(id)) {
return Result.error("参数错误");
}
sysHomeTemplateService.update(Chain.make("sortNo", sortNo == null ? 0 : sortNo), Cnd.where("id", "=", id));
return Result.success();
}
@At
@SaCheckPermission("sys.worktemplate")
@ApiOperation("置顶")
@@ -33,6 +33,11 @@ public class Sys_home_template extends BaseModel {
@Comment("模板图标")
private String templateIcon;
@Column
@ColDefine(type = ColType.VARCHAR, width = 1000)
@Comment("模板文件")
private String templateFile;
@Column
@ColDefine(type = ColType.VARCHAR, width = 255)
@Comment("模板封面")
@@ -309,9 +309,9 @@ public class SysUserServiceImpl extends BaseServiceImpl<Sys_user> implements Sys
String decodePwd = Base64Decoder.decodeStr(passowrd);
String hashedPassword = PwdUtil.getPassword(decodePwd, user.getSalt());
if (!Strings.sNull(hashedPassword).equalsIgnoreCase(user.getPassword())) {
// if (Globals.sso){
if (Globals.sso) {
throw new BaseException("用户名或者密码不正确");
// }
}
}
user = this.fetchLinks(user, "unit");
if (Lang.isNotEmpty(user.getUnit()) && StrUtil.isNotBlank(user.getUnit().getUnionId())) {
@@ -110,12 +110,17 @@ public class ActivityCultureApplyActivityController {
tissue.setUserId(SecurityUtil.getUserId());
tissue.setApplyTime(DateUtil.now());
if (StrUtil.isBlank(tissue.getId())){
cleanNewActivityData(tissue);
activityCultureService.insertWith(tissue, "tissuePersonList");
}else{
tissue.getTissuePersonList().forEach(tissuePerson -> tissuePerson.setTissueId(tissue.getId()));
if (tissue.getTissuePersonList() != null) {
tissue.getTissuePersonList().forEach(tissuePerson -> tissuePerson.setTissueId(tissue.getId()));
}
activityCultureService.insertOrUpdate(tissue);
activityCultureService.dao().clear(ActivityTissuePerson.class, Cnd.where(ActivityTissuePerson::getTissueId, "=", tissue.getId()));
activityCultureService.insert(tissue.getTissuePersonList());
if (tissue.getTissuePersonList() != null) {
activityCultureService.insert(tissue.getTissuePersonList());
}
}
return Result.success();
@@ -132,7 +137,12 @@ public class ActivityCultureApplyActivityController {
}
tissue.setUserId(SecurityUtil.getUserId());
tissue.setApplyTime(DateUtil.now());
activityCultureService.insertOrUpdate(tissue);
if (StrUtil.isBlank(tissue.getId())) {
cleanNewActivityData(tissue);
activityCultureService.insertWith(tissue, "tissuePersonList");
} else {
activityCultureService.insertOrUpdate(tissue);
}
if (List.of(40002, 40003).contains(tissue.getActivity_type()) && tissue.getIsEnrollSystem()) {
// 开启流程实例
@@ -185,6 +195,36 @@ public class ActivityCultureApplyActivityController {
return Result.success();
}
private void cleanNewActivityData(ActivityTissue tissue) {
tissue.setId(null);
tissue.setAuditId(null);
tissue.setState(null);
tissue.setCreatedBy(null);
tissue.setCreatedAt(null);
tissue.setUpdatedBy(null);
tissue.setUpdatedAt(null);
tissue.setDelFlag(null);
if (tissue.getTissuePersonList() == null) {
return;
}
tissue.getTissuePersonList().forEach(this::cleanNewActivityPersonData);
}
private void cleanNewActivityPersonData(ActivityTissuePerson tissuePerson) {
tissuePerson.setId(null);
tissuePerson.setTissueId(null);
tissuePerson.setSignId(null);
tissuePerson.setSign(false);
tissuePerson.setSignTime(null);
tissuePerson.setApplyDateTime(null);
tissuePerson.setDynamicFormData(null);
tissuePerson.setCreatedBy(null);
tissuePerson.setCreatedAt(null);
tissuePerson.setUpdatedBy(null);
tissuePerson.setUpdatedAt(null);
tissuePerson.setDelFlag(null);
}
@At
@SaCheckPermission(value = {"activity.culture.applyActivity.school", "activity.culture.applyActivity.union", "activity.culture.applyActivity.club"}, mode = SaMode.OR)
public Result findUser(String serachWord,
@@ -115,6 +115,9 @@ public class ActivityCultureInfoManageController {
if (oldHomeTemplate.getTemplateIcon() != null) {
sysHomeTemplate.setTemplateIcon(oldHomeTemplate.getTemplateIcon());
}
if (oldHomeTemplate.getTemplateFile() != null) {
sysHomeTemplate.setTemplateFile(oldHomeTemplate.getTemplateFile());
}
}
activityCultureService.dao().insertOrUpdate(sysHomeTemplate);
return Result.success();
@@ -1,12 +1,17 @@
package com.budwk.app.zhgh.activity.family.controller.manage;
import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.dev33.satoken.annotation.SaMode;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.StrUtil;
import com.budwk.app.base.annotation.SLog;
import com.budwk.app.base.constant.RoleConstant;
import com.budwk.app.base.page.Pagination;
import com.budwk.app.base.param.PageForm;
import com.budwk.app.base.result.Result;
import com.budwk.app.sys.models.Sys_home_activity;
import com.budwk.app.sys.models.Sys_home_template;
import com.budwk.app.web.commons.auth.utils.AuthUtil;
import com.budwk.app.zhgh.activity.basic.service.ActivityBasicScopeService;
import com.budwk.app.zhgh.activity.family.models.*;
import com.budwk.app.zhgh.activity.family.service.FamilyActivityService;
@@ -68,7 +73,57 @@ public class FamilyActivityController {
cnd.andEX("year", "=", year);
cnd.and(Cnd.likeEX("activityName", activityName));
cnd.orderBy("createdAt", "desc");
return Result.success().addData(familyActivityManageService.pageData(pageForm, cnd));
Pagination<FamilyActivity> pagination = familyActivityManageService.pageData(pageForm, cnd);
List<FamilyActivity> list = pagination.getList(FamilyActivity.class);
if (list != null && !list.isEmpty()) {
List<String> ids = list.stream().map(FamilyActivity::getId).toList();
List<Sys_home_template> templateList = dao.query(Sys_home_template.class, Cnd.where("id", "in", ids));
List<String> templateIds = templateList.stream().map(Sys_home_template::getId).toList();
list.forEach(activity -> activity.setIsTemplate(templateIds.contains(activity.getId())));
}
return Result.success().addData(pagination);
}
@At
@ApiOperation("设为模板")
@SaCheckPermission("family.manage")
public Result setTemplate(String id) {
if (!AuthUtil.hasRoleOr(RoleConstant.SYSADMIN.name(), RoleConstant.SCHOOL_UNION_ADMIN.name())) {
return Result.error("无权操作");
}
FamilyActivity activity = familyActivityManageService.fetch(id);
if (activity == null) {
return Result.error("活动不存在");
}
Sys_home_template oldHomeTemplate = dao.fetch(Sys_home_template.class, id);
Sys_home_template sysHomeTemplate = activity.covertToSysHomeTemplate();
if (oldHomeTemplate != null) {
sysHomeTemplate.setTop(oldHomeTemplate.getTop());
sysHomeTemplate.setPush(oldHomeTemplate.getPush());
sysHomeTemplate.setSortNo(oldHomeTemplate.getSortNo());
if (oldHomeTemplate.getTemplateName() != null) {
sysHomeTemplate.setTemplateName(oldHomeTemplate.getTemplateName());
}
if (oldHomeTemplate.getTemplateIcon() != null) {
sysHomeTemplate.setTemplateIcon(oldHomeTemplate.getTemplateIcon());
}
if (oldHomeTemplate.getTemplateFile() != null) {
sysHomeTemplate.setTemplateFile(oldHomeTemplate.getTemplateFile());
}
}
dao.insertOrUpdate(sysHomeTemplate);
return Result.success();
}
@At
@ApiOperation("取消模板")
@SaCheckPermission("family.manage")
public Result cancelTemplate(String id) {
if (!AuthUtil.hasRoleOr(RoleConstant.SYSADMIN.name(), RoleConstant.SCHOOL_UNION_ADMIN.name())) {
return Result.error("无权操作");
}
dao.delete(Sys_home_template.class, id);
return Result.success();
}
@At
@@ -76,6 +131,9 @@ public class FamilyActivityController {
@SaCheckPermission("family.manage")
@SLog(tag = "亲子活动-活动管理", msg = "删除活动")
public Result onDelete(String id) {
if (dao.fetch(Sys_home_template.class, id) != null) {
return Result.error("该活动已设为模板,请先取消模板后再删除");
}
Trans.exec(() -> {
familyActivityManageService.delete(id);
dao.clear(FamilyCourse.class, Cnd.where("activityId", "=", id));
@@ -102,7 +160,7 @@ public class FamilyActivityController {
@At
@ApiOperation("查询单个活动")
@SaCheckPermission("family")
@SaCheckPermission(value = {"family", "family.manage", "family.newcativity"}, mode = SaMode.OR)
public Result findOne(@Param("id") @NotNull String id) {
NutMap dataMap = familyActivityManageService.findOne(id, null, "");
String activityStartTime = dataMap.getString("activityStartTime");
@@ -150,10 +208,11 @@ public class FamilyActivityController {
@At
@Ok("json:full")
@ApiOperation("亲子活动新增/修改")
@SaCheckPermission("family.manage")
@SaCheckPermission(value = {"family.manage", "family.newcativity"}, mode = SaMode.OR)
@SLog(tag = "亲子活动-活动管理", msg = "新增/修改活动")
public Result doHandle(FamilyActivity activity) {
if (StrUtil.isBlank(activity.getId())) {
cleanNewActivityData(activity);
familyActivityManageService.add(activity, null);
} else {
familyActivityManageService.edit(activity);
@@ -161,10 +220,67 @@ public class FamilyActivityController {
return Result.success();
}
private void cleanNewActivityData(FamilyActivity activity) {
if (activity == null) {
return;
}
activity.setId(null);
activity.setIsTemplate(false);
activity.setCreatedBy(null);
activity.setCreatedAt(null);
activity.setUpdatedBy(null);
activity.setUpdatedAt(null);
activity.setDelFlag(null);
if (activity.getTypeLimits() != null) {
activity.getTypeLimits().forEach(this::cleanNewTypeLimitData);
}
if (activity.getCourseList() != null) {
activity.getCourseList().forEach(this::cleanNewCourseData);
}
}
private void cleanNewTypeLimitData(FamilyTypeLimit typeLimit) {
if (typeLimit == null) {
return;
}
typeLimit.setId(null);
typeLimit.setActivityId(null);
}
private void cleanNewCourseData(FamilyCourse course) {
if (course == null) {
return;
}
course.setId(null);
course.setActivityId(null);
course.setCreatedBy(null);
course.setCreatedAt(null);
course.setUpdatedBy(null);
course.setUpdatedAt(null);
course.setDelFlag(null);
course.setHasRegisterNum(null);
course.setHasWaitingNum(null);
course.setIsSign(false);
course.setCanSignThisCourseType(null);
if (course.getCourseTimeList() != null) {
course.getCourseTimeList().forEach(this::cleanNewCourseTimeData);
}
}
private void cleanNewCourseTimeData(FamilyActivityCourse courseTime) {
if (courseTime == null) {
return;
}
courseTime.setId(null);
courseTime.setActivityId(null);
courseTime.setCourseId(null);
courseTime.setHasRegisterNum(null);
}
@At
@Ok("json:full")
@ApiOperation("获取分工会人数限制")
@SaCheckPermission("family.manage")
@SaCheckPermission(value = {"family.manage", "family.newcativity"}, mode = SaMode.OR)
public Result getUnionLimit(@Param(value = "activityScopeId") String activityScopeId) {
Sql sql = Sqls.create("""
SELECT
@@ -188,7 +304,7 @@ public class FamilyActivityController {
@At
@Ok("json:full")
@ApiOperation("获取报名人员数量")
@SaCheckPermission("family.manage")
@SaCheckPermission(value = {"family.manage", "family.newcativity"}, mode = SaMode.OR)
public Result getRegisterUserCount(@Param(value = "courseId") String courseId) {
return Result.success().addData(dao.count(FamilyUser.class, Cnd.where("courseId", "=", courseId)));
}
@@ -196,7 +312,7 @@ public class FamilyActivityController {
@At
@Ok("json:full")
@ApiOperation("获取历史活动列表")
@SaCheckPermission("family.manage")
@SaCheckPermission(value = {"family.manage", "family.newcativity"}, mode = SaMode.OR)
public Result getHistoricalActList() {
List<FamilyActivity> query = dao.query(FamilyActivity.class, Cnd.NEW().desc("activityStartTime"));
return Result.success().addData(query);
@@ -0,0 +1,18 @@
package com.budwk.app.zhgh.activity.family.controller.manage;
import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.dev33.satoken.annotation.SaMode;
import org.nutz.ioc.loader.annotation.IocBean;
import org.nutz.mvc.annotation.At;
import org.nutz.mvc.annotation.Ok;
@IocBean
@At("/platform/family/newcativity")
public class FamilyNewActivityController {
@At("")
@SaCheckPermission(value = {"family.manage", "family.newcativity"}, mode = SaMode.OR)
@Ok("beetl:/platform/zhgh/activity/family/newcativity/index.html")
public void index() {
}
}
@@ -2,6 +2,7 @@ package com.budwk.app.zhgh.activity.family.models;
import com.budwk.app.base.model.BaseModel;
import com.budwk.app.sys.models.Sys_home_activity;
import com.budwk.app.sys.models.Sys_home_template;
import com.budwk.app.sys.services.SysHomeConvert;
import lombok.Data;
import lombok.EqualsAndHashCode;
@@ -111,6 +112,8 @@ public class FamilyActivity extends BaseModel implements Serializable, SysHomeCo
@Many(field = "activityId")
private List<FamilyTypeLimit> typeLimits;
private Boolean isTemplate;
@Column
@Comment("活动类型")
@ColDefine(type = ColType.VARCHAR, width = 20)
@@ -159,4 +162,23 @@ public class FamilyActivity extends BaseModel implements Serializable, SysHomeCo
sysHomeActivity.setClassPath(this.getClass().getPackageName() + this.getClass().getName());
return sysHomeActivity;
}
public Sys_home_template covertToSysHomeTemplate() {
Sys_home_template sysHomeTemplate = new Sys_home_template();
sysHomeTemplate.setId(this.getId());
sysHomeTemplate.setName(this.getActivityName());
sysHomeTemplate.setTemplateName(this.getActivityName());
sysHomeTemplate.setCover(this.getCover());
sysHomeTemplate.setContent(this.getIntroduce());
sysHomeTemplate.setUrl("/platform/family/newcativity?mode=edit&id=" + this.getId());
sysHomeTemplate.setH5Url("");
if (Lang.isNotEmpty(this.getActivitySignUpStartTime())) {
sysHomeTemplate.setStartDate(this.getActivitySignUpStartTime());
sysHomeTemplate.setEndDate(this.getActivitySignUpEndTime());
}
sysHomeTemplate.setAllowUserGroupId(this.getActivityGroupId());
sysHomeTemplate.setEnable(!this.isDisabled());
sysHomeTemplate.setClassPath(this.getClass().getPackageName() + this.getClass().getName());
return sysHomeTemplate;
}
}
@@ -8,6 +8,7 @@ import com.budwk.app.base.constant.RoleConstant;
import com.budwk.app.base.page.Pagination;
import com.budwk.app.base.param.PageForm;
import com.budwk.app.base.result.Result;
import com.budwk.app.sys.models.Sys_home_template;
import com.budwk.app.web.commons.auth.utils.AuthUtil;
import com.budwk.app.web.commons.auth.utils.SecurityUtil;
import com.budwk.app.zhgh.activity.basic.service.ActivityBasicScopeService;
@@ -90,11 +91,13 @@ public class ActivitySportsInfoManageController {
school.activityCode,
school.foundDate,
school.applyType,
IF(sht.id IS NULL, 0, 1) isTemplate,
(SELECT COUNT(1) FROM activity_school_apply asa WHERE asa.activityId = school.id and status=2) applyNum
FROM
activity_school school
LEFT JOIN activity_basic_settings ba ON ba.`code` = school.activityLevel
LEFT JOIN sys_union un ON un.id = school.belongUnionId
LEFT JOIN sys_home_template sht ON sht.id = school.id
$condition
""");
@@ -131,6 +134,48 @@ public class ActivitySportsInfoManageController {
return Result.success(pagination);
}
@At
@ApiOperation("设置为模板")
@SaCheckPermission("activity.sports.info")
public Result setTemplate(String id) {
if (!AuthUtil.hasRoleOr(RoleConstant.SYSADMIN.name(), RoleConstant.SCHOOL_UNION_ADMIN.name())) {
return Result.error("无权操作");
}
ActivitySchool activitySchool = activitySportsService.fetch(id);
if (activitySchool == null) {
return Result.error("活动不存在");
}
Sys_home_template oldHomeTemplate = dao.fetch(Sys_home_template.class, id);
Sys_home_template sysHomeTemplate = activitySchool.covertToSysHomeTemplate();
if (oldHomeTemplate != null) {
sysHomeTemplate.setTop(oldHomeTemplate.getTop());
sysHomeTemplate.setPush(oldHomeTemplate.getPush());
sysHomeTemplate.setSortNo(oldHomeTemplate.getSortNo());
if (oldHomeTemplate.getTemplateName() != null) {
sysHomeTemplate.setTemplateName(oldHomeTemplate.getTemplateName());
}
if (oldHomeTemplate.getTemplateIcon() != null) {
sysHomeTemplate.setTemplateIcon(oldHomeTemplate.getTemplateIcon());
}
if (oldHomeTemplate.getTemplateFile() != null) {
sysHomeTemplate.setTemplateFile(oldHomeTemplate.getTemplateFile());
}
}
dao.insertOrUpdate(sysHomeTemplate);
return Result.success();
}
@At
@ApiOperation("取消模板")
@SaCheckPermission("activity.sports.info")
public Result cancelTemplate(String id) {
if (!AuthUtil.hasRoleOr(RoleConstant.SYSADMIN.name(), RoleConstant.SCHOOL_UNION_ADMIN.name())) {
return Result.error("无权操作");
}
dao.delete(Sys_home_template.class, id);
return Result.success();
}
@At
@SaCheckPermission(value = {"activity.sports.info", "activity.sports.new"}, mode = SaMode.OR)
@@ -168,12 +213,41 @@ public class ActivitySportsInfoManageController {
@SaCheckPermission(value = {"activity.sports.info", "activity.sports.new"}, mode = SaMode.OR)
public Result doAdd(@Param(value = "data") ActivitySchool activitySchool,
@Param(value = "events") ActivitySchoolEvent[] events) {
cleanNewActivityData(activitySchool, events);
String id = activitySportsService.doAdd(activitySchool, events);
return Result.success().addData(id);
}
private void cleanNewActivityData(ActivitySchool activitySchool, ActivitySchoolEvent[] events) {
if (activitySchool != null) {
activitySchool.setId(null);
activitySchool.setFoundDate(null);
activitySchool.setCreatedBy(null);
activitySchool.setCreatedAt(null);
activitySchool.setUpdatedBy(null);
activitySchool.setUpdatedAt(null);
activitySchool.setDelFlag(null);
}
if (events != null) {
for (ActivitySchoolEvent event : events) {
if (event == null) {
continue;
}
if (!"allItems".equals(event.getId())) {
event.setId(null);
}
event.setActivityId(null);
event.setCreatedBy(null);
event.setCreatedAt(null);
event.setUpdatedBy(null);
event.setUpdatedAt(null);
event.setDelFlag(null);
}
}
}
@At
@SaCheckPermission(value = {"activity.sports.info", "activity.sports.new"}, mode = SaMode.OR)
public Result findOne(String id) {
@@ -198,6 +272,9 @@ public class ActivitySportsInfoManageController {
@SLog(tag = "体育活动", msg = "删除活动")
@SaCheckPermission("activity.sports.info")
public Result doDelete(String id) {
if (dao.fetch(Sys_home_template.class, id) != null) {
return Result.error("该活动已设为模板,请先取消模板后再删除");
}
activitySportsService.doDelete(id);
return Result.success();
}
@@ -3,10 +3,12 @@ package com.budwk.app.zhgh.activity.sports.models;
import cn.hutool.core.date.DateUtil;
import com.budwk.app.base.model.BaseModel;
import com.budwk.app.sys.models.Sys_home_activity;
import com.budwk.app.sys.models.Sys_home_template;
import com.budwk.app.sys.services.SysHomeConvert;
import lombok.Data;
import lombok.EqualsAndHashCode;
import org.nutz.dao.entity.annotation.*;
import org.nutz.lang.Lang;
import java.io.Serializable;
import java.util.List;
@@ -213,4 +215,23 @@ public class ActivitySchool extends BaseModel implements Serializable , SysHomeC
sysHomeActivity.setClassPath(this.getClass().getPackageName() + this.getClass().getName());
return sysHomeActivity;
}
public Sys_home_template covertToSysHomeTemplate() {
Sys_home_template sysHomeTemplate = new Sys_home_template();
sysHomeTemplate.setId(this.getId());
sysHomeTemplate.setName(this.getName());
sysHomeTemplate.setTemplateName(this.getName());
sysHomeTemplate.setCover(this.getImage());
sysHomeTemplate.setContent(Lang.isNotEmpty(this.getEventNotification()) ? this.getEventNotification() : this.getPrecautions());
sysHomeTemplate.setUrl("/platform/activity/sports/new?mode=edit&id=" + this.getId() + (this.getApplyType() == null ? "" : "&applyType=" + this.getApplyType()));
sysHomeTemplate.setH5Url("");
if (Lang.isNotEmpty(this.getApplyStartTime())) {
sysHomeTemplate.setStartDate(DateUtil.parseDate(this.getApplyStartTime()));
sysHomeTemplate.setEndDate(DateUtil.parseDate(this.getApplyEndTime()));
}
sysHomeTemplate.setAllowUserGroupId(this.getActivityGroupId());
sysHomeTemplate.setEnable(!Boolean.TRUE.equals(this.getClose()));
sysHomeTemplate.setClassPath(this.getClass().getPackageName() + this.getClass().getName());
return sysHomeTemplate;
}
}
@@ -111,6 +111,9 @@ public class TrainSignUpManageController {
if (oldHomeTemplate.getTemplateIcon() != null) {
sysHomeTemplate.setTemplateIcon(oldHomeTemplate.getTemplateIcon());
}
if (oldHomeTemplate.getTemplateFile() != null) {
sysHomeTemplate.setTemplateFile(oldHomeTemplate.getTemplateFile());
}
}
dao.insertOrUpdate(sysHomeTemplate);
return Result.success();
@@ -213,6 +216,7 @@ public class TrainSignUpManageController {
@SLog(tag = "品牌活动-活动管理", msg = "新增/修改活动")
public Result doHandle(TrainSignUpActivity activity) {
if (StrUtil.isBlank(activity.getId())) {
cleanNewActivityData(activity);
trainSignUpActivityManageService.add(activity, null);
} else {
trainSignUpActivityManageService.edit(activity);
@@ -220,6 +224,63 @@ public class TrainSignUpManageController {
return Result.success();
}
private void cleanNewActivityData(TrainSignUpActivity activity) {
if (activity == null) {
return;
}
activity.setId(null);
activity.setIsTemplate(false);
activity.setCreatedBy(null);
activity.setCreatedAt(null);
activity.setUpdatedBy(null);
activity.setUpdatedAt(null);
activity.setDelFlag(null);
if (activity.getTypeLimits() != null) {
activity.getTypeLimits().forEach(this::cleanNewTypeLimitData);
}
if (activity.getCourseList() != null) {
activity.getCourseList().forEach(this::cleanNewCourseData);
}
}
private void cleanNewTypeLimitData(TrainSignUpTypeLimit typeLimit) {
if (typeLimit == null) {
return;
}
typeLimit.setId(null);
typeLimit.setActivityId(null);
}
private void cleanNewCourseData(TrainSignUpCourse course) {
if (course == null) {
return;
}
course.setId(null);
course.setActivityId(null);
course.setCreatedBy(null);
course.setCreatedAt(null);
course.setUpdatedBy(null);
course.setUpdatedAt(null);
course.setDelFlag(null);
course.setHasRegisterNum(null);
course.setHasWaitingNum(null);
course.setIsSign(false);
course.setCanSignThisCourseType(null);
if (course.getCourseTimeList() != null) {
course.getCourseTimeList().forEach(this::cleanNewCourseTimeData);
}
}
private void cleanNewCourseTimeData(TrainSignUpActivityCourse courseTime) {
if (courseTime == null) {
return;
}
courseTime.setId(null);
courseTime.setActivityId(null);
courseTime.setCourseId(null);
courseTime.setHasRegisterNum(null);
}
@At
@Ok("json:full")
@ApiOperation("获取分工会人数限制")
@@ -267,13 +328,10 @@ public class TrainSignUpManageController {
@SaCheckPermission(value = {"trainSignUp.manage", "trainSignUp.applyActivity"}, mode = SaMode.OR)
public Result selectUnitAndClub() {
List<NutMap> result = new ArrayList<>();
List<Sys_unit> unitList = dao.query(Sys_unit.class, Cnd.NEW().asc(Sys_unit::getUnitcode));
java.util.Set<String> optionKeys = new java.util.HashSet<>();
List<Sys_unit> unitList = dao.query(Sys_unit.class, Cnd.where(Sys_unit::getUnitLevel, "=", 2).asc(Sys_unit::getUnitcode));
for (Sys_unit unit : unitList) {
NutMap map = new NutMap();
map.put("id", unit.getId());
map.put("name", unit.getName());
map.put("type", "unit");
result.add(map);
addSelectOption(result, optionKeys, unit.getId(), unit.getName(), "unit");
}
List<SysClub> clubList = dao.query(SysClub.class, Cnd.NEW().asc(SysClub::getClubCode));
@@ -286,12 +344,23 @@ public class TrainSignUpManageController {
List<SysClub> passClubList = clubList.stream().filter(o -> passList.contains(o.getId())).toList();
for (SysClub sysClub : passClubList) {
NutMap map = new NutMap();
map.put("id", sysClub.getId());
map.put("name", sysClub.getClubName());
map.put("type", "club");
result.add(map);
addSelectOption(result, optionKeys, sysClub.getId(), sysClub.getClubName(), "club");
}
return Result.success(result);
}
private void addSelectOption(List<NutMap> result, java.util.Set<String> optionKeys, String id, String name, String type) {
if (StrUtil.isBlank(id) || StrUtil.isBlank(name)) {
return;
}
String key = type + ":" + name;
if (!optionKeys.add(key)) {
return;
}
NutMap map = new NutMap();
map.put("id", id);
map.put("name", name);
map.put("type", type);
result.add(map);
}
}
@@ -1,17 +1,21 @@
package com.budwk.app.zhgh.activity.workscollection.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.dev33.satoken.annotation.SaMode;
import cn.hutool.core.thread.ThreadUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.http.HtmlUtil;
import com.budwk.app.base.constant.RoleConstant;
import com.budwk.app.base.page.Pagination;
import com.budwk.app.base.param.PageForm;
import com.budwk.app.base.result.Result;
import com.budwk.app.base.service.BaseService;
import com.budwk.app.sys.models.Sys_home_activity;
import com.budwk.app.sys.models.Sys_home_template;
import com.budwk.app.sys.models.Sys_user;
import com.budwk.app.sys.services.SysMsgService;
import com.budwk.app.web.commons.auth.utils.AuthUtil;
import com.budwk.app.web.commons.auth.utils.SecurityUtil;
import com.budwk.app.zhgh.activity.basic.service.ActivityBasicScopeService;
import com.budwk.app.zhgh.activity.workscollection.models.Activity_works_collection;
@@ -63,11 +67,18 @@ public class ActivityWorksCollectionManageController {
public Result pageData(@Valid PageForm pageForm, Long year) {
Sql sql = Sqls.create("""
select
wc.*,
wc.id,
wc.name,
wc.createdAt,
wc.startDateTime,
wc.endDateTime,
wc.enable,
IF(sht.id IS NULL, 0, 1) isTemplate,
u.username as userName
from
activity_works_collection wc
LEFT JOIN vw_user u on u.id = wc.createdBy
LEFT JOIN sys_home_template sht ON sht.id = wc.id
$condition
""");
Cnd cnd = Cnd.NEW();
@@ -82,8 +93,49 @@ public class ActivityWorksCollectionManageController {
@At
@SaCheckPermission("activity.workscollection.manage")
public Result setTemplate(String id) {
if (!AuthUtil.hasRoleOr(RoleConstant.SYSADMIN.name(), RoleConstant.SCHOOL_UNION_ADMIN.name())) {
return Result.error("无权操作");
}
Activity_works_collection worksCollection = dao.fetch(Activity_works_collection.class, id);
if (worksCollection == null) {
return Result.error("活动不存在");
}
Sys_home_template oldHomeTemplate = dao.fetch(Sys_home_template.class, id);
Sys_home_template sysHomeTemplate = worksCollection.covertToSysHomeTemplate();
if (oldHomeTemplate != null) {
sysHomeTemplate.setTop(oldHomeTemplate.getTop());
sysHomeTemplate.setPush(oldHomeTemplate.getPush());
sysHomeTemplate.setSortNo(oldHomeTemplate.getSortNo());
if (oldHomeTemplate.getTemplateName() != null) {
sysHomeTemplate.setTemplateName(oldHomeTemplate.getTemplateName());
}
if (oldHomeTemplate.getTemplateIcon() != null) {
sysHomeTemplate.setTemplateIcon(oldHomeTemplate.getTemplateIcon());
}
if (oldHomeTemplate.getTemplateFile() != null) {
sysHomeTemplate.setTemplateFile(oldHomeTemplate.getTemplateFile());
}
}
dao.insertOrUpdate(sysHomeTemplate);
return Result.success();
}
@At
@SaCheckPermission("activity.workscollection.manage")
public Result cancelTemplate(String id) {
if (!AuthUtil.hasRoleOr(RoleConstant.SYSADMIN.name(), RoleConstant.SCHOOL_UNION_ADMIN.name())) {
return Result.error("无权操作");
}
dao.delete(Sys_home_template.class, id);
return Result.success();
}
@At
@SaCheckPermission(value = {"activity.workscollection.manage", "activity.workscollection.new"}, mode = SaMode.OR)
@Aop(TransAop.READ_COMMITTED)
public Result insert(@Param("data") @Valid Activity_works_collection worksCollection) {
cleanNewActivityData(worksCollection);
worksCollection.setIsSubmit(true);
dao.insertWith(worksCollection, "subjectTypes");
worksCollection.getSubjectTypes().forEach(item -> {
@@ -94,9 +146,10 @@ public class ActivityWorksCollectionManageController {
}
@At
@SaCheckPermission("activity.workscollection.manage")
@SaCheckPermission(value = {"activity.workscollection.manage", "activity.workscollection.new"}, mode = SaMode.OR)
@Aop(TransAop.READ_COMMITTED)
public Result save(@Param("data") @Valid Activity_works_collection worksCollection) {
cleanNewActivityData(worksCollection);
worksCollection.setIsSubmit(false);
dao.insertWith(worksCollection, "subjectTypes");
worksCollection.getSubjectTypes().forEach(item -> {
@@ -105,8 +158,48 @@ public class ActivityWorksCollectionManageController {
return Result.success();
}
private void cleanNewActivityData(Activity_works_collection worksCollection) {
if (worksCollection == null) {
return;
}
worksCollection.setId(null);
worksCollection.setCreatedBy(null);
worksCollection.setCreatedAt(null);
worksCollection.setUpdatedBy(null);
worksCollection.setUpdatedAt(null);
worksCollection.setDelFlag(null);
if (worksCollection.getSubjectTypes() != null) {
worksCollection.getSubjectTypes().forEach(subjectType -> {
if (subjectType == null) {
return;
}
subjectType.setId(null);
subjectType.setActivityId(null);
subjectType.setCreatedBy(null);
subjectType.setCreatedAt(null);
subjectType.setUpdatedBy(null);
subjectType.setUpdatedAt(null);
subjectType.setDelFlag(null);
if (subjectType.getWorksTypes() != null) {
subjectType.getWorksTypes().forEach(worksType -> {
if (worksType == null) {
return;
}
worksType.setId(null);
worksType.setSubjectId(null);
worksType.setCreatedBy(null);
worksType.setCreatedAt(null);
worksType.setUpdatedBy(null);
worksType.setUpdatedAt(null);
worksType.setDelFlag(null);
});
}
});
}
}
@At
@SaCheckPermission("activity.workscollection.manage")
@SaCheckPermission(value = {"activity.workscollection.manage", "activity.workscollection.new"}, mode = SaMode.OR)
@Aop(TransAop.READ_COMMITTED)
public Result update(@Param("data") @Valid Activity_works_collection worksCollection) {
dao.update(worksCollection);
@@ -134,6 +227,9 @@ public class ActivityWorksCollectionManageController {
@SaCheckPermission("activity.workscollection.manage")
@Aop(TransAop.READ_COMMITTED)
public Result delete(@Valid String id) {
if (dao.fetch(Sys_home_template.class, id) != null) {
return Result.error("该活动已设为模板,请先取消模板后再删除");
}
dao.delete(Activity_works_collection.class, id);
dao.clear(Activity_works_collection_upload.class, Cnd.where(Activity_works_collection_upload::getActivityId, "=", id));
dao.clear(Activity_works_subjectType.class, Cnd.where(Activity_works_subjectType::getActivityId, "=", id));
@@ -142,7 +238,7 @@ public class ActivityWorksCollectionManageController {
}
@At
@SaCheckPermission("activity.workscollection.manage")
@SaCheckPermission(value = {"activity.workscollection.manage", "activity.workscollection.new"}, mode = SaMode.OR)
public Result findOne(@Valid String id) {
Activity_works_collection worksCollection = dao.fetch(Activity_works_collection.class, id);
dao.fetchLinks(worksCollection, "subjectTypes");
@@ -0,0 +1,18 @@
package com.budwk.app.zhgh.activity.workscollection.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.dev33.satoken.annotation.SaMode;
import org.nutz.ioc.loader.annotation.IocBean;
import org.nutz.mvc.annotation.At;
import org.nutz.mvc.annotation.Ok;
@IocBean
@At("/platform/activity/worksCollection/new")
public class ActivityWorksCollectionNewController {
@At("")
@Ok("beetl:/platform/zhgh/activity/workscollection/manage/index.html")
@SaCheckPermission(value = {"activity.workscollection.manage", "activity.workscollection.new"}, mode = SaMode.OR)
public void index() {
}
}
@@ -2,6 +2,7 @@ package com.budwk.app.zhgh.activity.workscollection.models;
import com.budwk.app.base.model.BaseModel;
import com.budwk.app.sys.models.Sys_home_activity;
import com.budwk.app.sys.models.Sys_home_template;
import com.budwk.app.sys.services.SysHomeConvert;
import lombok.Data;
import lombok.EqualsAndHashCode;
@@ -142,4 +143,21 @@ public class Activity_works_collection extends BaseModel implements SysHomeConve
return sysHomeActivity;
}
public Sys_home_template covertToSysHomeTemplate() {
Sys_home_template sysHomeTemplate = new Sys_home_template();
sysHomeTemplate.setId(this.getId());
sysHomeTemplate.setName(this.getName());
sysHomeTemplate.setTemplateName(this.getName());
sysHomeTemplate.setCover(this.getCover());
sysHomeTemplate.setContent(this.getContent());
sysHomeTemplate.setUrl("/platform/activity/worksCollection/new?mode=edit&id=" + this.getId());
sysHomeTemplate.setH5Url("");
sysHomeTemplate.setStartDate(this.getStartDateTime());
sysHomeTemplate.setEndDate(this.getEndDateTime());
sysHomeTemplate.setAllowUserGroupId(this.getActivityGroupId());
sysHomeTemplate.setEnable(Boolean.TRUE.equals(this.getEnable()));
sysHomeTemplate.setClassPath(this.getClass().getPackageName() + this.getClass().getName());
return sysHomeTemplate;
}
}
@@ -104,4 +104,8 @@ public class WelfareProjectSubjectOption extends BaseModel implements Serializab
@Comment("简短备注")
@ColDefine(type = ColType.VARCHAR,width = 100)
private String simpleDesc;
private Integer selectedTotal;
private Integer rankNo;
}
@@ -41,10 +41,45 @@ public class WelfareProjectServiceImpl extends BaseServiceImpl<WelfareProject> i
@Override
public WelfareProject projectInfo(String projectId) {
WelfareProject project = fetch(projectId);
if (project == null) {
return null;
}
fetchLinks(project, "options", Cnd.NEW().asc("optionSort"));
fillOptionRank(projectId, project.getOptions());
return project;
}
private void fillOptionRank(String projectId, List<WelfareProjectSubjectOption> options) {
if (options == null || options.isEmpty()) {
return;
}
Sql sql = Sqls.create("""
SELECT
selectOptionId,
SUM(IFNULL(selectNum, 0)) AS selectedTotal
FROM welfare_project_user_selection
WHERE welfareId = @projectId
AND selectOptionId IS NOT NULL
GROUP BY selectOptionId
""");
sql.setParam("projectId", projectId);
Map<String, Integer> selectedTotalMap = listMap(sql).stream()
.collect(Collectors.toMap(
item -> item.getString("selectOptionId"),
item -> item.getInt("selectedTotal", 0),
Integer::sum
));
options.forEach(option -> option.setSelectedTotal(selectedTotalMap.getOrDefault(option.getId(), 0)));
List<WelfareProjectSubjectOption> rankOptions = new ArrayList<>(options);
rankOptions.sort(Comparator
.comparing((WelfareProjectSubjectOption option) -> option.getSelectedTotal() == null ? 0 : option.getSelectedTotal()).reversed()
.thenComparing(option -> option.getOptionSort() == null ? Integer.MAX_VALUE : option.getOptionSort()));
for (int i = 0; i < rankOptions.size(); i++) {
rankOptions.get(i).setRankNo(i + 1);
}
}
@Override
@Aop(TransAop.READ_COMMITTED)
public void saveProject(WelfareProject project) {
@@ -0,0 +1,2 @@
ALTER TABLE `sys_home_template`
ADD COLUMN `templateFile` varchar(1000) DEFAULT NULL COMMENT 'template file' AFTER `templateIcon`;
@@ -3,6 +3,7 @@ CREATE TABLE IF NOT EXISTS `sys_home_template` (
`name` varchar(50) DEFAULT NULL COMMENT 'template name',
`templateName` varchar(50) DEFAULT NULL COMMENT 'display template name',
`templateIcon` varchar(255) DEFAULT NULL COMMENT 'template icon',
`templateFile` varchar(1000) DEFAULT NULL COMMENT 'template file',
`cover` varchar(255) DEFAULT NULL COMMENT 'template cover',
`content` text COMMENT 'template content',
`url` varchar(1000) DEFAULT NULL COMMENT 'pc url',
@@ -123,11 +123,17 @@
}
}
function historyBack(func) {
function historyBack(fallbackUrl, func) {
if (typeof fallbackUrl === "function") {
func = fallbackUrl
fallbackUrl = "/platform/h5/home"
} else if (typeof fallbackUrl !== "string" || !fallbackUrl) {
fallbackUrl = "/platform/h5/home"
}
if (window.history.length > 1) {
window.history.back()
} else {
window.location.href = "/platform/h5/home"
window.location.replace(fallbackUrl)
}
func && typeof func === "function" && func()
}
@@ -139,8 +145,8 @@
Vue.mixin({
methods: {
historyBack: function(func = function(){}) {
historyBack(func)
historyBack: function(fallbackUrl = "/platform/h5/home", func = function(){}) {
historyBack(fallbackUrl, func)
},
returnH5Home: function(activeTab = "home") {
returnH5Home(activeTab)
+23 -21
View File
@@ -1,7 +1,7 @@
const act = {
template: /*language=HTML*/ `
<!-- 活动 -->
<div class="section-wrapper">
<div class="activity-section-wrapper">
<div class="section-act">
<!-- Swiper容器 -->
@@ -77,8 +77,8 @@ const act = {
/*初始化Swiper*/
initSwiper() {
this.swiper = new Swiper('.activity-swiper', {
slidesPerView: 'auto',
spaceBetween: 30,
slidesPerView: 1,
spaceBetween: 18,
centeredSlides: false,
loop: false,
navigation: {
@@ -91,13 +91,13 @@ const act = {
},
breakpoints: {
768: {
slidesPerView: 1,
},
1024: {
slidesPerView: 2,
},
1024: {
slidesPerView: 4,
},
1200: {
slidesPerView: 3,
slidesPerView: 5,
}
}
})
@@ -131,7 +131,7 @@ const act = {
this.listAct()
},
style: /*language=CSS*/ `
.section-wrapper {
.activity-section-wrapper {
width: 100%;
}
@@ -176,7 +176,7 @@ const act = {
.activity-swiper-container {
position: relative;
width: 100%;
padding: 20px;
padding: 9px 14px;
/*margin-top: 30px;*/
}
@@ -217,7 +217,7 @@ const act = {
/* 进度条样式 */
.activity-swiper-container .swiper-pagination {
position: relative;
margin-top: 30px;
margin-top: 12px;
height: 4px;
}
@@ -239,8 +239,8 @@ const act = {
.activity-swiper .swiper-slide .item .img-box {
width: 100%;
height: 200px;
border-radius: 12px;
height: 128px;
border-radius: 8px;
overflow: hidden;
position: relative;
}
@@ -250,10 +250,12 @@ const act = {
left: 0;
top: 0;
background: #c11623;
padding: 6px 2px;
min-width: 50px;
padding: 4px 2px;
min-width: 42px;
color: #ffffff;
border-radius: 0 0 50% 0;
font-size: 12px;
line-height: 1.2;
}
@@ -269,16 +271,16 @@ const act = {
}
.activity-swiper .swiper-slide .item h4 {
font-size: 20px;
margin-top: 10px;
height: 60px;
font-size: 15px;
margin: 8px 0 0;
height: 42px;
color: #333;
display: -webkit-box;
-webkit-line-clamp: 2;
-webkit-box-orient: vertical;
overflow: hidden;
text-overflow: ellipsis;
line-height: 1.5;
line-height: 1.4;
text-align: left;
transition: color 0.3s ease;
}
@@ -292,14 +294,14 @@ const act = {
}
.activity-swiper .swiper-slide .item .time p {
font-size: 13px;
font-size: 12px;
margin: 0;
/*line-height: 1.5;*/
line-height: 1.4;
color: #666;
}
.activity-swiper .swiper-slide .item .time i {
margin-right: 5px;
margin-right: 4px;
color: var(--color-primary);
}
@@ -1,7 +1,7 @@
const entry = {
template: /*language=HTML*/ `
<div class="entry-wrapper">
<div class="entry-section" v-for="section in entrySections" :key="section.key">
<div :class="['entry-section', 'entry-section-' + section.key]" v-for="section in entrySections" :key="section.key">
<div class="entry-section-header">
<div class="entry-section-title">
<i :class="section.icon"></i>
@@ -126,6 +126,11 @@ const entry = {
margin-top: 22px;
}
/* 临时屏蔽“我的收藏”分组,保留原节点和数据逻辑便于恢复 */
.entry-section-fav {
display: none;
}
.entry-section-header {
display: flex;
align-items: center;
@@ -16,14 +16,8 @@ layout("/layouts/v4/baseLayout.html"){
.section-banner .banner-img img {
width: 100%;
/*height: 100%;*/
height: 470px;
object-fit: cover;
}
/* 临时屏蔽首页背景图,保留原图片节点便于恢复 */
.section-banner .banner-img > img {
display: none;
height: auto;
display: block;
}
.section-wrapper {
@@ -61,12 +55,44 @@ layout("/layouts/v4/baseLayout.html"){
align-items: center;
min-width: 320px;
background: white;
border-radius: 12px;
box-shadow: 0 4px 12px rgba(0,0,0,0.08);
padding: 16px;
border-radius: 8px;
box-shadow: 0 4px 12px rgba(0,0,0,0.06);
padding: 11px;
transition: transform 0.2s, box-shadow 0.2s;
}
.home-section {
width: 100%;
}
.home-section-header {
display: flex;
align-items: center;
justify-content: space-between;
margin-bottom: 10px;
}
.home-section-title {
display: inline-flex;
align-items: baseline;
gap: 6px;
color: #19324d;
font-size: 18px;
font-weight: 700;
}
.home-section-title i {
color: #409eff;
font-size: 16px;
}
.home-section-title em {
color: #b5c0d6;
font-size: 14px;
font-style: normal;
font-weight: 500;
}
</style>
<div class="v4-container" id="v4-home-app">
@@ -87,6 +113,21 @@ layout("/layouts/v4/baseLayout.html"){
</div>
</div>
<div class="home-grid">
<div class="home-section">
<div class="home-section-header">
<div class="home-section-title">
<i class="fa fa-calendar"></i>
<span>最新活动</span>
<em>/Activities</em>
</div>
</div>
<div class="act-card">
<act></act>
</div>
</div>
</div>
<work-template v-if="$auth.hasRoleOr(['SYSADMIN','SCHOOL_UNION_ADMIN'])"></work-template>
<jcdt :list="websiteNews"></jcdt>
@@ -126,6 +126,11 @@ const stats = {
/*border: 1px solid #e8e8e8;*/
}
/* 子内容临时屏蔽时,同步收起统计容器,避免首页 banner 下方出现空白 */
.stats-section {
display: none;
}
.stats-grid {
display: grid;
grid-template-columns: repeat(2, 1fr);
@@ -135,6 +140,11 @@ const stats = {
margin-left: auto;
}
/* 临时屏蔽首页右上角“待办、已办、消息、发起”统计卡片,保留原模板便于恢复 */
.stats-grid {
display: none;
}
.stat-item {
background: #f8f9fa;
color: #495057;
@@ -138,20 +138,28 @@ const workTemplate = {
}
.work-template-icon {
width: 46px;
height: 46px;
width: 55px;
height: 55px;
margin-bottom: 8px;
display: flex;
align-items: center;
justify-content: center;
overflow: hidden;
}
.work-template-icon img {
width: 100%;
height: 100%;
object-fit: contain;
width: 55px !important;
height: 55px !important;
max-width: none;
max-height: none;
object-fit: cover;
border-radius: 8px;
}
.work-template-name {
min-height: 34px;
font-size: 12px;
font-size: 12px !important;
font-weight: 400;
color: #333;
line-height: 1.4;
word-break: break-word;
@@ -305,7 +305,7 @@ const user = {
.user-container {
width: 80%;
margin: 20px auto;
margin: 12px auto 20px;
display: grid;
grid-template-columns: 0.7fr 2.3fr;
gap: 24px;
@@ -92,12 +92,24 @@ layout("/layouts/platform.html"){
key="AppHomeImg"
style="--upload-width: 214px;--upload-height:64px"
:value.sync="formData.configValue"
:upload_number="10"
:upload_number="5"
upload_mode="image"
upload_result_category="interval"
upload_result_type="url"
></file-upload>
<span>最佳分辨率:2756 x 732,最多可上传 10 张,首页按上传顺序轮播</span>
<span>PC 首页轮播图,最佳分辨率:2756 x 732,最多可上传 5 张,首页按上传顺序轮播</span>
</template>
<template v-else-if="formData.configKey === 'H5AppHomeImg'">
<file-upload
key="H5AppHomeImg"
style="--upload-width: 214px;--upload-height:110px"
:value.sync="formData.configValue"
:upload_number="5"
upload_mode="image"
upload_result_category="interval"
upload_result_type="url"
></file-upload>
<span>移动端首页轮播图,建议分辨率:750 x 386,最多可上传 5 张,首页按上传顺序轮播</span>
</template>
<template v-else-if="formData.configKey === 'AppFeaturedActivityImg'">
<file-upload
@@ -24,6 +24,18 @@ layout("/layouts/platform.html"){
</el-input>
</template>
</el-table-column>
<el-table-column label="排序" prop="sortNo" width="120px" align="center">
<template slot-scope="scope">
<el-input-number
v-model="scope.row.sortNo"
size="mini"
:min="0"
:controls="false"
style="width: 80px"
@change="updateSortNo(scope.row)">
</el-input-number>
</template>
</el-table-column>
<el-table-column label="名称" prop="name"></el-table-column>
<el-table-column label="PC端链接" prop="url" show-overflow-tooltip></el-table-column>
<el-table-column label="模板图标" prop="templateIcon" width="120px" align="center">
@@ -40,13 +52,20 @@ layout("/layouts/platform.html"){
</file-upload>
</template>
</el-table-column>
<el-table-column label="是否置顶" prop="top" width="100px">
<el-table-column label="模板文件" prop="templateFile" width="170px" align="center">
<template slot-scope="scope">
<el-tag size="mini" v-if="scope.row.top" type="success"></el-tag>
<el-tag size="mini" v-else type="info"></el-tag>
<file-upload
class="template-file-upload"
:upload_number="1"
:value="scope.row.templateFile"
accept=".doc,.docx,.xls,.xlsx,.pdf,.ppt,.pptx,.jpg,.jpeg,.png"
upload_result_type="url"
upload_result_category="interval"
upload_mode="file"
@update:value="onTemplateFileChange(scope.row, $event)">
</file-upload>
</template>
</el-table-column>
<el-table-column label="关联类路径" prop="classPath" show-overflow-tooltip></el-table-column>
<el-table-column label="状态" prop="enable" width="80px">
<template slot-scope="scope">
<i v-if="!scope.row.enable" class="fa fa-circle text-danger ml5"></i>
@@ -57,8 +76,6 @@ layout("/layouts/platform.html"){
<template slot-scope="scope">
<el-link type="danger" size="mini" @click="disable(scope.row.id)" v-if="scope.row.enable">关闭</el-link>
<el-link type="primary" size="mini" @click="enable(scope.row.id)" v-if="!scope.row.enable">开启</el-link>
<el-link type="primary" size="mini" @click="topUp(scope.row.id)" v-if="!scope.row.top">置顶</el-link>
<el-link type="danger" size="mini" @click="cancelTopUp(scope.row.id)" v-if="scope.row.top">取消置顶</el-link>
</template>
</el-table-column>
</el-table>
@@ -84,6 +101,8 @@ layout("/layouts/platform.html"){
if (resp.code === 0) {
this.$message.success(resp.msg)
this.pageData()
} else {
this.$message.error(resp.msg)
}
})
})
@@ -98,34 +117,8 @@ layout("/layouts/platform.html"){
if (resp.code === 0) {
this.$message.success(resp.msg)
this.pageData()
}
})
})
},
topUp(id) {
this.$confirm("您确定要置顶吗?", "提示", {
type: "warning",
confirmButtonText: "确定",
cancelButtonText: "取消"
}).then(() => {
this.$axios.post(loc() + "/topUp", {id}).then((resp) => {
if (resp.code === 0) {
this.$message.success(resp.msg)
this.pageData()
}
})
})
},
cancelTopUp(id) {
this.$confirm("您确定要取消置顶吗?", "提示", {
type: "warning",
confirmButtonText: "确定",
cancelButtonText: "取消"
}).then(() => {
this.$axios.post(loc() + "/cancelTopUp", {id}).then((resp) => {
if (resp.code === 0) {
this.$message.success(resp.msg)
this.pageData()
} else {
this.$message.error(resp.msg)
}
})
})
@@ -142,6 +135,19 @@ layout("/layouts/platform.html"){
}
})
},
updateSortNo(row) {
this.$axios.post(loc() + "/updateSortNo", {
id: row.id,
sortNo: row.sortNo
}).then((resp) => {
if (resp.code === 0) {
this.$message.success(resp.msg)
this.pageData()
} else {
this.$message.error(resp.msg)
}
})
},
onTemplateIconChange(row, templateIcon) {
if (templateIcon === undefined && !row.templateIcon) {
return
@@ -162,6 +168,27 @@ layout("/layouts/platform.html"){
}
})
})
},
onTemplateFileChange(row, templateFile) {
if (templateFile === undefined && !row.templateFile) {
return
}
row.templateFile = templateFile
this.updateTemplateFile(row)
},
updateTemplateFile(row) {
this.$nextTick(() => {
this.$axios.post(loc() + "/updateTemplateFile", {
id: row.id,
templateFile: row.templateFile
}).then((resp) => {
if (resp.code === 0) {
this.$message.success(resp.msg)
} else {
this.$message.error(resp.msg)
}
})
})
}
},
created() {
@@ -170,20 +197,24 @@ layout("/layouts/platform.html"){
})
</script>
<style>
.template-icon-upload {
.template-icon-upload,
.template-file-upload {
--upload-width: 48px;
--upload-height: 48px;
}
.template-icon-upload .el-upload-list--picture-card .el-upload-list__item,
.template-icon-upload .el-upload--picture-card {
.template-icon-upload .el-upload--picture-card,
.template-file-upload .el-upload-list--picture-card .el-upload-list__item,
.template-file-upload .el-upload--picture-card {
width: 48px !important;
height: 48px !important;
line-height: 48px !important;
margin: 0;
}
.template-icon-upload .el-upload--picture-card i {
.template-icon-upload .el-upload--picture-card i,
.template-file-upload .el-upload--picture-card i {
font-size: 18px;
}
</style>
@@ -523,9 +523,9 @@ const ACTIVITY_CULTURE_APPLY_ACTIVITY = {
</el-tabs>
</el-form>
<el-row type="flex" justify="end" class="mt20">
<el-button type="primary" plain @click="onSave">保存</el-button>
<el-button type="primary" plain @click="onSave">{{ copyTemplateMode ? "另存为" : "保存" }}</el-button>
<template v-if="formData.isEnrollSystem">
<el-button type="primary" @click="onSubmit" v-if="!taskId">提交</el-button>
<el-button type="primary" @click="onSubmit" v-if="!taskId">{{ copyTemplateMode ? "新活动提交" : "提交" }}</el-button>
<el-button type="primary" @click="onFinishTask" v-else>提交</el-button>
</template>
@@ -581,6 +581,8 @@ const ACTIVITY_CULTURE_APPLY_ACTIVITY = {
bizId: "",
taskId: "",
copyTemplateMode: false,
copyTemplateName: "",
activeName: "1",
pageForm: {
year: new Date().getFullYear() + ""
@@ -646,6 +648,81 @@ const ACTIVITY_CULTURE_APPLY_ACTIVITY = {
const resp = await this.$axios.post("/platform/club/examine/apply/getClubsByRole")
return resp.data
},
buildSubmitData() {
const formData = JSON.parse(JSON.stringify(this.formData))
formData.activity_type = this.activity_type
const {time, applyTime2, plannedDate} = formData
if (applyTime2 && applyTime2.length) {
formData.applyStartTime = applyTime2[0]
formData.applyEndTime = applyTime2[1]
formData.applyTime2 = null
}
if (time && time.length) {
formData.startTime = formData.time[0]
formData.endTime = formData.time[1]
formData.time = null
}
if (plannedDate && plannedDate.length) {
formData.startPlannedDate = formData.plannedDate[0]
formData.endPlannedDate = formData.plannedDate[1]
formData.plannedDate = null
}
if (this.copyTemplateMode) {
this.cleanCopyTemplateData(formData)
}
return formData
},
cleanCopyTemplateData(data) {
data.id = null
data.auditId = null
data.state = null
data.instanceId = null
data.businessNo = null
data.taskId = null
data.startTaskId = null
data.isTemplate = false
data.createdBy = null
data.createdAt = null
data.updatedBy = null
data.updatedAt = null
data.delFlag = null
if (Array.isArray(data.tissuePersonList)) {
data.tissuePersonList = data.tissuePersonList.map((person) => {
person.id = null
person.tissueId = null
person.signId = null
person.signTime = null
person.applyDateTime = null
person.dynamicFormData = null
person.isSign = false
person.createdBy = null
person.createdAt = null
person.updatedBy = null
person.updatedAt = null
person.delFlag = null
return person
})
}
},
async setupCopyTemplateData(data) {
this.cleanCopyTemplateData(data)
this.bizId = ""
this.taskId = ""
data.activityCode = await this.generateActivityCode()
this.userData = Array.isArray(data.tissuePersonList) ? clone(data.tissuePersonList) : []
},
validateCopyTemplateName() {
if (!this.copyTemplateMode) {
return true
}
const currentName = (this.formData.name || "").trim()
const templateName = (this.copyTemplateName || "").trim()
if (currentName && templateName && currentName === templateName) {
this.$message.warning("请修改活动名称,不能与模板名称一致")
return false
}
return true
},
// 保存
onSave() {
if (!this.formData.projectTypeCode) {
@@ -656,29 +733,15 @@ const ACTIVITY_CULTURE_APPLY_ACTIVITY = {
this.$message.error("请选择活动所属社团")
return
}
this.$confirm("您确定保存吗?", "提示", {
if (!this.validateCopyTemplateName()) {
return
}
this.$confirm(this.copyTemplateMode ? "您确定另存为新活动吗?" : "您确定保存吗?", "提示", {
confirmButtonText: "确定",
cancelButtonText: "取消",
type: "warning"
}).then(() => {
const formData = JSON.parse(JSON.stringify(this.formData))
formData.activity_type = this.activity_type
const {time, applyTime2, plannedDate} = formData
if (applyTime2 && applyTime2.length) {
formData.applyStartTime = applyTime2[0]
formData.applyEndTime = applyTime2[1]
formData.applyTime2 = null
}
if (time && time.length) {
formData.startTime = formData.time[0]
formData.endTime = formData.time[1]
formData.time = null
}
if (plannedDate && plannedDate.length) {
formData.startPlannedDate = formData.plannedDate[0]
formData.endPlannedDate = formData.plannedDate[1]
formData.plannedDate = null
}
const formData = this.buildSubmitData()
this.$axios.post('/platform/activity/culture/applyActivity/save', {
data: JSON.stringify(formData),
userData: JSON.stringify(this.userData)
@@ -704,29 +767,15 @@ const ACTIVITY_CULTURE_APPLY_ACTIVITY = {
onSubmit() {
this.$refs["addForm"].validate((valid) => {
if (valid) {
this.$confirm("您确定提交吗?", "提示", {
if (!this.validateCopyTemplateName()) {
return
}
this.$confirm(this.copyTemplateMode ? "您确定提交为新活动吗?" : "您确定提交吗?", "提示", {
confirmButtonText: "确定",
cancelButtonText: "取消",
type: "warning"
}).then(() => {
const formData = JSON.parse(JSON.stringify(this.formData))
formData.activity_type = this.activity_type
const {time, applyTime2, plannedDate} = formData
if (applyTime2 && applyTime2.length) {
formData.applyStartTime = applyTime2[0]
formData.applyEndTime = applyTime2[1]
formData.applyTime2 = null
}
if (time && time.length) {
formData.startTime = formData.time[0]
formData.endTime = formData.time[1]
formData.time = null
}
if (plannedDate && plannedDate.length) {
formData.startPlannedDate = formData.plannedDate[0]
formData.endPlannedDate = formData.plannedDate[1]
formData.plannedDate = null
}
const formData = this.buildSubmitData()
this.$axios.post('/platform/activity/culture/applyActivity/submit', {
data: JSON.stringify(formData)
}).then(res => {
@@ -949,6 +998,9 @@ const ACTIVITY_CULTURE_APPLY_ACTIVITY = {
return data
},
async init(id) {
if (!id && this.copyTemplateMode) {
return
}
this.formLoading = true
try {
if (id) {
@@ -1006,10 +1058,15 @@ const ACTIVITY_CULTURE_APPLY_ACTIVITY = {
if (data.applyStartTime) data.applyTime2 = [data.applyStartTime, data.applyEndTime]
if (data.startTime) data.time = [data.startTime, data.endTime]
if (data.startPlannedDate) data.plannedDate = [data.startPlannedDate, data.endPlannedDate]
this.userData = clone(data.tissuePersonList)
data.unionUserNumberLimit = JSON.parse(data.unionUserNumberLimit)
if (data.undertakeUnitIds) data.undertakeUnitIds = JSON.parse(data.undertakeUnitIds)
if (data.hostUnitIds) data.hostUnitIds = JSON.parse(data.hostUnitIds)
if (this.copyTemplateMode) {
this.copyTemplateName = data.name
await this.setupCopyTemplateData(data)
} else {
this.userData = clone(data.tissuePersonList)
}
this.formData = data
if (!this.formData.unionUserNumberLimit) {
this.getUnionData().then((data) => {
@@ -1029,6 +1086,7 @@ const ACTIVITY_CULTURE_APPLY_ACTIVITY = {
const mode = params.get("mode")
const id = params.get("id")
if (mode === "edit" && id) {
this.copyTemplateMode = true
this.openEdit({id})
}
}
@@ -1,5 +1,5 @@
<!--#include('courseTime.js'){}#-->
<!--#include('customForm.js'){}#-->
<!--#include("/platform/zhgh/activity/family/manage/courseTime.js"){}#-->
<!--#include("/platform/zhgh/activity/family/manage/customForm.js"){}#-->
const basicForm = {
template: /*language=HTML*/ `
<div>
@@ -290,8 +290,8 @@ const basicForm = {
<el-button @click="$emit('back')">取消</el-button>
<el-button v-if="step === 2" type="primary" @click="step = 1">上一步</el-button>
<el-button v-if="step === 1" type="primary" @click="step = 2">下一步</el-button>
<el-button type="primary" @click="onSave">保存</el-button>
<el-button type="primary" @click="onSubmit">提交</el-button>
<el-button type="primary" @click="onSave">{{ copyTemplateMode ? "另存为" : "保存" }}</el-button>
<el-button type="primary" @click="onSubmit">{{ copyTemplateMode ? "新活动提交" : "提交" }}</el-button>
</div>
<el-dialog :close-on-click-modal="false" :visible.sync="signUpDialog" title="设置报名限制" append-to-body>
@@ -326,6 +326,8 @@ const basicForm = {
return {
signUpDialog: false,
step: 1,
copyTemplateMode: false,
copyTemplateName: "",
formData: {
notice: false,
courseList: [
@@ -394,7 +396,7 @@ const basicForm = {
this.typeArray = [...uniqueMap.values(), ...withoutCode]
},
async validNumber(row, old) {
if (GetQueryString("id") === "") {
if (this.copyTemplateMode || GetQueryString("id") === "") {
if (row.courseReservedNumber > row.coursePeopleNumber && row.reserveMode === 1) {
this.$alert("预留人数不能大于" + this.activityType + "人数!", "提示", {
confirmButtonText: "确定"
@@ -503,6 +505,51 @@ const basicForm = {
this.formData = resp.data
this.typeChange(this.formData.trainType)
this.formData.id = ""
this.cleanCopyTemplateData(this.formData)
}
},
cleanCopyTemplateData(data) {
if (!data) {
return
}
data.id = null
data.isTemplate = false
data.createdBy = null
data.createdAt = null
data.updatedBy = null
data.updatedAt = null
data.delFlag = null
if (Array.isArray(data.typeLimits)) {
data.typeLimits = data.typeLimits.map((limit) => {
limit.id = null
limit.activityId = null
return limit
})
}
if (Array.isArray(data.courseList)) {
data.courseList = data.courseList.map((course) => {
course.id = null
course.activityId = null
course.hasRegisterNum = null
course.hasWaitingNum = null
course.isSign = false
course.canSignThisCourseType = null
course.createdBy = null
course.createdAt = null
course.updatedBy = null
course.updatedAt = null
course.delFlag = null
if (Array.isArray(course.courseTimeList)) {
course.courseTimeList = course.courseTimeList.map((courseTime) => {
courseTime.id = null
courseTime.activityId = null
courseTime.courseId = null
courseTime.hasRegisterNum = null
return courseTime
})
}
return course
})
}
},
typeChange(val) {
@@ -534,11 +581,17 @@ const basicForm = {
this.$message.warning("请输入活动名称")
return
}
await this.doHandle('保存')
if (!this.validateCopyTemplateName()) {
return
}
await this.doHandle(this.copyTemplateMode ? '另存为' : '保存')
},
onSubmit() {
this.$refs["form"].validate(async (valid, errMsg) => {
if (valid) {
if (!this.validateCopyTemplateName()) {
return
}
const courseValid = this.formData.courseList.some((v, i) => {
const basicValid = v.courseName && v.coursePeopleNumber && v.courseLocation && v.courseInstructor && v.courseType
const timeValid =
@@ -582,7 +635,7 @@ const basicForm = {
return
}
this.formData.isDisabled = false
await this.doHandle('提交')
await this.doHandle(this.copyTemplateMode ? '新活动提交' : '提交')
} else {
if(Object.keys(errMsg).length > 0) {
this.$message.warning(errMsg[Object.keys(errMsg)[0]][0].message)
@@ -592,8 +645,23 @@ const basicForm = {
}
})
},
validateCopyTemplateName() {
if (!this.copyTemplateMode) {
return true
}
const currentName = (this.formData.activityName || "").trim()
const templateName = (this.copyTemplateName || "").trim()
if (currentName && templateName && currentName === templateName) {
this.$message.warning("请修改活动名称,不能与模板名称一致")
return false
}
return true
},
async doHandle(type) {
const cloneData = clone(this.formData)
if (this.copyTemplateMode) {
this.cleanCopyTemplateData(cloneData)
}
cloneData.activitySignUpStartTime = cloneData.activitySignTime !== undefined ? cloneData.activitySignTime[0] : null
cloneData.activitySignUpEndTime = cloneData.activitySignTime !== undefined ? cloneData.activitySignTime[1] : null
cloneData.activityStartTime = cloneData.activityTime !== undefined ? cloneData.activityTime[0] : null
@@ -601,7 +669,7 @@ const basicForm = {
if (cloneData.activitySignUpStartTime !== undefined && cloneData.activitySignUpStartTime !== null) {
cloneData.year = new Date(cloneData.activitySignUpStartTime).getFullYear()
}
cloneData.typeLimits = JSON.stringify(this.formData.typeLimits)
cloneData.typeLimits = JSON.stringify(cloneData.typeLimits)
cloneData.courseList = JSON.stringify(cloneData.courseList)
const confirm = await this.$confirm("您确定要" + type + "吗?", "提示", {
confirmButtonText: "确定",
@@ -629,11 +697,16 @@ const basicForm = {
if (resp.code === 0) {
this.formData = resp.data
this.typeChange(this.formData.trainType)
if (this.copyTemplateMode) {
this.copyTemplateName = this.formData.activityName
this.cleanCopyTemplateData(this.formData)
}
if(this.formData.onlyKey) this.keyFocus()
}
}
},
async initData(row) {
async initData(row, copyTemplateMode = false) {
this.copyTemplateMode = copyTemplateMode
this.activityGroupList = await this.getActivityGroup()
this.historicalActList = await this.getHistoricalActList()
this.courseTypeList = await this.getAllType()
@@ -92,7 +92,13 @@ layout("/layouts/platform.html"){
<el-dropdown-item @click.native="makeCode(row)">签到二维码</el-dropdown-item>
<el-dropdown-item @click.native="onView(row)">查看</el-dropdown-item>
<el-dropdown-item @click.native="openEdit(row)">编辑</el-dropdown-item>
<el-dropdown-item @click.native="onDelete(row)">删除</el-dropdown-item>
<el-dropdown-item
v-if="$auth.hasRoleOr(['SYSADMIN','SCHOOL_UNION_ADMIN']) && !row.isTemplate"
@click.native="setTemplate(row)">设为模板</el-dropdown-item>
<el-dropdown-item
v-if="$auth.hasRoleOr(['SYSADMIN','SCHOOL_UNION_ADMIN']) && row.isTemplate"
@click.native="cancelTemplate(row)">取消模板</el-dropdown-item>
<el-dropdown-item :disabled="!!row.isTemplate" @click.native="onDelete(row)">删除</el-dropdown-item>
</el-dropdown-menu>
</el-dropdown>
</template>
@@ -190,14 +196,52 @@ layout("/layouts/platform.html"){
}
},
async onDelete(row) {
if (row.isTemplate) {
this.$message.warning("该活动已设为模板,请先取消模板后再删除")
return
}
this.$confirm("此操作将永久删除, 是否继续?", "提示", {
confirmButtonText: "确定",
cancelButtonText: "取消",
type: "warning"
}).then(async () => {
const resp = await this.$axios.post(loc() + "/onDelete", { id: row.id })
this.$message.success(resp.msg)
this.doSearch()
if (resp.code === 0) {
this.$message.success(resp.msg)
this.doSearch()
} else {
this.$message.error(resp.msg)
}
}).catch(() => {})
},
async setTemplate(row) {
this.$confirm("确定将该活动设为工作模板吗?", "提示", {
confirmButtonText: "确定",
cancelButtonText: "取消",
type: "warning"
}).then(async () => {
const resp = await this.$axios.post(loc() + "/setTemplate", { id: row.id })
if (resp.code === 0) {
this.$message.success(resp.msg)
this.doSearch()
} else {
this.$message.error(resp.msg)
}
}).catch(() => {})
},
async cancelTemplate(row) {
this.$confirm("确定取消该活动的工作模板吗?", "提示", {
confirmButtonText: "确定",
cancelButtonText: "取消",
type: "warning"
}).then(async () => {
const resp = await this.$axios.post(loc() + "/cancelTemplate", { id: row.id })
if (resp.code === 0) {
this.$message.success(resp.msg)
this.doSearch()
} else {
this.$message.error(resp.msg)
}
}).catch(() => {})
},
},
@@ -0,0 +1,62 @@
<!--#
layout("/layouts/platform.html"){
#-->
<style>
.my-drawer .el-col-4 {
text-align: right;
}
.my-drawer .el-row {
margin-bottom: 20px;
}
.el-drawer__body {
padding: 20px;
}
.el-row--flex {
align-items: center;
}
</style>
<div id="app" v-cloak>
<el-card shadow="never">
<basic-form ref="formRef" @back="back" @refresh="refresh"></basic-form>
</el-card>
</div>
<script nonce="${cspNonce!}">
<!--#include("/platform/zhgh/activity/family/manage/basicForm.js"){}#-->
new Vue({
el: "#app",
store,
dicts: ["USER_CAMPUS", "FAMILY_SIGNUP_TYPE"],
components: {
"basic-form": basicForm
},
methods: {
back() {
commonUtil.pjaxPush("/platform/family/manage")
},
refresh() {
},
initForm() {
const params = new URLSearchParams(window.location.search)
const mode = params.get("mode")
const id = params.get("id")
if (mode === "edit" && id) {
this.$refs.formRef.initData({id}, true)
} else {
this.$refs.formRef.initData()
}
}
},
mounted() {
this.$nextTick(() => {
this.initForm()
})
}
})
</script>
<!--#
}
#-->
@@ -604,6 +604,8 @@
planList: [],
events: [],
projectType: "",
copyTemplateMode: false,
copyTemplateName: "",
formRules: {
name: [{ required: true, message: "必填", trigger: ["blur", "change"] }],
address: [{ required: true, message: "必填", trigger: ["blur", "change"] }],
@@ -889,7 +891,7 @@
this.eventForm.checkedEventId = this.checkedEvents[0].id
this.projectType = this.checkedEvents[0].projectType
if (!formData.id || this.checkedEventInfo.length <= 0) {
if ((!formData.id && !this.copyTemplateMode) || this.checkedEventInfo.length <= 0) {
this.eventForm = {
checkedEventId: this.checkedEvents[0].id,
leanderNum: 0,
@@ -937,6 +939,8 @@
this.activityGroupList = data
},
async openAdd() {
this.copyTemplateMode = false
this.copyTemplateName = ""
this.events = await this.getEvents(2)
await this.getActivityGroup()
this.active = 0
@@ -964,9 +968,58 @@
const resp = await this.$axios.post("/platform/club/examine/apply/getClubsByRole")
return resp.data
},
async openEdit(row, flag) {
cleanCopyTemplateData(formData, events) {
if (formData) {
formData.id = null
formData.isTemplate = false
formData.createdBy = null
formData.createdAt = null
formData.updatedBy = null
formData.updatedAt = null
formData.delFlag = null
formData.foundDate = null
}
if (Array.isArray(events)) {
events.forEach((event) => {
if (event.id !== "allItems") {
event.id = null
}
event.activityId = null
event.createdBy = null
event.createdAt = null
event.updatedBy = null
event.updatedAt = null
event.delFlag = null
})
}
},
async setupCopyTemplateData(formData, events) {
this.cleanCopyTemplateData(formData, events)
if (formData && formData.activityLevel) {
const activityCode = await this.getActivityCode(formData.activityLevel)
this.$set(formData, "activityCode", activityCode)
}
this.eventsIds = []
this.checkedEvents = this.events.filter((event) => formData.eventsIds.some((id) => id === event.id))
if (this.checkedEvents.length > 0) {
await this.eventChange(this.checkedEvents[0].id)
}
},
validateCopyTemplateName() {
if (!this.copyTemplateMode) {
return true
}
const currentName = (this.formData.name || "").trim()
const templateName = (this.copyTemplateName || "").trim()
if (currentName && templateName && currentName === templateName) {
this.$message.warning("请修改活动名称,不能与模板名称一致")
return false
}
return true
},
async openEdit(row, flag, copyTemplateMode = false) {
this.copyTemplateMode = !!copyTemplateMode
this.active = flag ? 0 : this.active
await this.applyTypeChange(row.applyType)
await this.getActivityGroup()
const { id } = row
this.$set(row, "loading", true)
@@ -985,10 +1038,17 @@
v.unitSponsor = JSON.parse(v.unitSponsor)
v.undertakeUnit = JSON.parse(v.undertakeUnit)
v.unitJointly = JSON.parse(v.unitJointly)
v.applyType = parseInt(v.applyType)
v.activityGroupId = parseInt(v.activityGroupId)
v.activityLevel = parseInt(v.activityLevel)
const applyType = row.applyType ? parseInt(row.applyType) : v.applyType
await this.applyTypeChange(isNaN(applyType) ? v.applyType : applyType)
this.formData = clone(v)
this.checkedEventInfo = clone(v.schoolEvents)
if (this.copyTemplateMode) {
this.copyTemplateName = this.formData.name
await this.setupCopyTemplateData(this.formData, this.checkedEventInfo)
}
this.checkedEventInfo.map((v) => {
/*if (v.unionLimit) {
v.unionLimit = JSON.parse(v.unionLimit)
@@ -1014,9 +1074,15 @@
}
},
async doOperate() {
const method = this.formData.id ? "/doEdit" : "/doAdd"
if (!this.validateCopyTemplateName()) {
return
}
const method = this.copyTemplateMode || !this.formData.id ? "/doAdd" : "/doEdit"
const formData = clone(this.formData)
const events = clone(this.checkedEventInfo)
if (this.copyTemplateMode) {
this.cleanCopyTemplateData(formData, events)
}
formData.restrictMaxNum = formData.leanderNum + formData.coachNum + formData.athletesMaxNum + formData.substituteNum
formData.restrictMinNum = formData.athletesMaxNum
@@ -1035,6 +1101,7 @@
events: JSON.stringify(events)
})
if (resp.code === 0) {
this.copyTemplateMode = false
this.$emit("flip")
} else {
this.$notify.error({ title: "错误", message: resp.msg })
@@ -1042,6 +1109,10 @@
loading.close()
},
async operate() {
if (this.copyTemplateMode) {
await this.doOperate()
return
}
const deleteEventIds = this.eventsIds.filter((v) => !this.formData.eventsIds.includes(v))
const { data } = await $.get("/platform/activity/sports/info/mange/getEventApply", {
activityId: this.formData.id,
@@ -1061,7 +1132,10 @@
}
},
async doSave() {
let url = this.formData.id ? "/doEdit" : "/doAdd"
if (!this.validateCopyTemplateName()) {
return
}
let url = this.copyTemplateMode || !this.formData.id ? "/doAdd" : "/doEdit"
this.checkedEventInfo.forEach((v) => {
if (this.eventForm.projectType === "1" && this.eventForm.eventId === "eventId") {
@@ -1080,6 +1154,9 @@
let events = clone(this.checkedEventInfo)
const formData = clone(this.formData)
if (this.copyTemplateMode) {
this.cleanCopyTemplateData(formData, events)
}
formData.restrictMaxNum = formData.leanderNum + formData.coachNum + formData.athletesMaxNum + formData.substituteNum
formData.restrictMinNum = formData.athletesMaxNum
formData.isSave = true
@@ -1107,6 +1184,9 @@
this.$set(this.eventForm, "endAgeDate", this.eventForm.ageDate[1])
}
events = this.eventForm
if (this.copyTemplateMode) {
this.cleanCopyTemplateData(null, [events])
}
}
const loading = this.$loading({
lock: true,
@@ -1121,7 +1201,10 @@
})
if (resp.code === 0) {
this.$emit("flush")
if (!this.formData.id) formData.id = resp.data
if (this.copyTemplateMode || !this.formData.id) {
formData.id = resp.data
this.copyTemplateMode = false
}
await this.openEdit(formData, false)
this.$message.success(resp.msg)
} else {
@@ -85,7 +85,15 @@ layout("/layouts/platform.html"){
<el-dropdown-item :command="{type:'view',row}">查看</el-dropdown-item>
<el-dropdown-item :command="{type:'exportXlsx',row}">导出名单</el-dropdown-item>
<el-dropdown-item :command="{type:'edit',row}">编辑</el-dropdown-item>
<el-dropdown-item :command="{type:'delete',row}">删除</el-dropdown-item>
<el-dropdown-item
:command="{type:'setTemplate',row}"
v-if="$auth.hasRoleOr(['SYSADMIN','SCHOOL_UNION_ADMIN']) && !row.isTemplate"
>设为模板</el-dropdown-item>
<el-dropdown-item
:command="{type:'cancelTemplate',row}"
v-if="$auth.hasRoleOr(['SYSADMIN','SCHOOL_UNION_ADMIN']) && row.isTemplate"
>取消模板</el-dropdown-item>
<el-dropdown-item :command="{type:'delete',row}" :disabled="!!row.isTemplate">删除</el-dropdown-item>
</el-dropdown-menu>
</el-dropdown>
</template>
@@ -158,6 +166,10 @@ layout("/layouts/platform.html"){
this.openEdit(row)
} else if (type === "delete") {
this.doDelete(row)
} else if (type === "setTemplate") {
this.setTemplate(row)
} else if (type === "cancelTemplate") {
this.cancelTemplate(row)
} else if (type === "exportXlsx") {
window.open("/platform/activity/sports/info/mange/exportXlsx?id=" + row.id)
}
@@ -176,6 +188,10 @@ layout("/layouts/platform.html"){
},
doDelete(row) {
const { id } = row
if (row.isTemplate) {
this.$message.warning("该活动已设为模板,请先取消模板后再删除")
return
}
this.$confirm("确定要删除该活动吗?", "提示", { type: "warning" }).then(async () => {
this.$set(row, "loading", true)
const resp = await this.$axios.post(loc() + "/doDelete", { id })
@@ -188,6 +204,38 @@ layout("/layouts/platform.html"){
}
})
},
async setTemplate(row) {
try {
await this.$confirm("确定将该活动设为工作模板吗?", "提示", { type: "warning" })
this.$set(row, "loading", true)
const resp = await this.$axios.post(loc() + "/setTemplate", { id: row.id })
this.$set(row, "loading", false)
if (resp.code === 0) {
this.$message.success(resp.msg)
this.doSearch()
} else {
this.notifyWarning(resp.msg)
}
} catch (e) {
this.$set(row, "loading", false)
}
},
async cancelTemplate(row) {
try {
await this.$confirm("确定取消该工作模板吗?", "提示", { type: "warning" })
this.$set(row, "loading", true)
const resp = await this.$axios.post(loc() + "/cancelTemplate", { id: row.id })
this.$set(row, "loading", false)
if (resp.code === 0) {
this.$message.success(resp.msg)
this.doSearch()
} else {
this.notifyWarning(resp.msg)
}
} catch (e) {
this.$set(row, "loading", false)
}
},
async doOperate() {
await this.$refs.addActivity.operate()
},
@@ -6,8 +6,8 @@ layout("/layouts/platform.html"){
<el-card shadow="never">
<div slot="header">
<div class="sports-new-actions">
<el-button @click="doSave" type="primary">保 存</el-button>
<el-button @click="doOperate" type="primary">提 交</el-button>
<el-button @click="doSave" type="primary">{{ copyTemplateMode ? "另存为" : "保 存" }}</el-button>
<el-button @click="doOperate" type="primary">{{ copyTemplateMode ? "新活动提交" : "提 交" }}</el-button>
<!--<el-button @click="back">返 回</el-button>-->
</div>
</div>
@@ -31,6 +31,11 @@ layout("/layouts/platform.html"){
components: {
"add-activity": ACTIVITY_SPORTS_ADD_ACTIVITY
},
data() {
return {
copyTemplateMode: false
}
},
methods: {
back() {
commonUtil.pjaxPush("/platform/activity/sports/info/mange")
@@ -42,15 +47,19 @@ layout("/layouts/platform.html"){
},
async doOperate() {
await this.$refs.addActivity.operate()
this.copyTemplateMode = this.$refs.addActivity.copyTemplateMode
},
async doSave() {
await this.$refs.addActivity.doSave()
this.copyTemplateMode = this.$refs.addActivity.copyTemplateMode
},
initForm() {
const mode = GetQueryString("mode")
const id = GetQueryString("id")
if (mode === "edit" && id) {
this.$refs.addActivity.openEdit({id}, true)
const applyType = GetQueryString("applyType")
this.copyTemplateMode = mode === "edit" && !!id
if (this.copyTemplateMode) {
this.$refs.addActivity.openEdit({id, applyType}, true, true)
} else {
this.$refs.addActivity.openAdd()
}
@@ -42,7 +42,7 @@ layout("/layouts/platform.html"){
const mode = GetQueryString("mode")
const id = GetQueryString("id")
const row = mode === "edit" && id ? {id} : undefined
this.$refs.formRef.initData(row)
this.$refs.formRef.initData(row, mode === "edit" && !!id)
}
},
mounted() {
@@ -287,8 +287,8 @@ const basicForm = {
<el-button @click="$emit('back')">取消</el-button>
<el-button v-if="step === 2" type="primary" @click="step = 1">上一步</el-button>
<el-button v-if="step === 1" type="primary" @click="step = 2">下一步</el-button>
<el-button type="primary" @click="onSave">保存</el-button>
<el-button type="primary" @click="onSubmit">提交</el-button>
<el-button type="primary" @click="onSave">{{ copyTemplateMode ? "另存为" : "保存" }}</el-button>
<el-button type="primary" @click="onSubmit">{{ copyTemplateMode ? "新活动提交" : "提交" }}</el-button>
</div>
<el-dialog :close-on-click-modal="false" :visible.sync="signUpDialog" title="设置报名限制" append-to-body>
@@ -323,6 +323,8 @@ const basicForm = {
return {
signUpDialog: false,
step: 1,
copyTemplateMode: false,
copyTemplateName: "",
formData: {
notice: false,
courseList: [
@@ -359,7 +361,7 @@ const basicForm = {
},
methods: {
async validNumber(row, old) {
if (GetQueryString("id") === "") {
if (this.copyTemplateMode || GetQueryString("id") === "") {
if (row.courseReservedNumber > row.coursePeopleNumber && row.reserveMode === 1) {
this.$alert("预留人数不能大于" + this.trainType + "人数!", "提示", {
confirmButtonText: "确定"
@@ -468,6 +470,51 @@ const basicForm = {
this.formData = resp.data
this.typeChange(this.formData.trainType)
this.formData.id = ""
this.cleanCopyTemplateData(this.formData)
}
},
cleanCopyTemplateData(data) {
if (!data) {
return
}
data.id = null
data.isTemplate = false
data.createdBy = null
data.createdAt = null
data.updatedBy = null
data.updatedAt = null
data.delFlag = null
if (Array.isArray(data.typeLimits)) {
data.typeLimits = data.typeLimits.map((limit) => {
limit.id = null
limit.activityId = null
return limit
})
}
if (Array.isArray(data.courseList)) {
data.courseList = data.courseList.map((course) => {
course.id = null
course.activityId = null
course.hasRegisterNum = null
course.hasWaitingNum = null
course.isSign = false
course.canSignThisCourseType = null
course.createdBy = null
course.createdAt = null
course.updatedBy = null
course.updatedAt = null
course.delFlag = null
if (Array.isArray(course.courseTimeList)) {
course.courseTimeList = course.courseTimeList.map((courseTime) => {
courseTime.id = null
courseTime.activityId = null
courseTime.courseId = null
courseTime.hasRegisterNum = null
return courseTime
})
}
return course
})
}
},
typeChange(val) {
@@ -499,11 +546,17 @@ const basicForm = {
this.$message.warning("请输入活动名称")
return
}
await this.doHandle('保存')
if (!this.validateCopyTemplateName()) {
return
}
await this.doHandle(this.copyTemplateMode ? '另存为' : '保存')
},
onSubmit() {
this.$refs["form"].validate(async (valid, errMsg) => {
if (valid) {
if (!this.validateCopyTemplateName()) {
return
}
const courseValid = this.formData.courseList.some((v, i) => {
const basicValid = v.courseName && v.coursePeopleNumber && v.courseLocation && v.courseInstructor && v.courseType
const timeValid =
@@ -535,7 +588,7 @@ const basicForm = {
return
}
this.formData.isDisabled = false
await this.doHandle('提交')
await this.doHandle(this.copyTemplateMode ? '新活动提交' : '提交')
} else {
if(Object.keys(errMsg).length > 0) {
this.$message.warning(errMsg[Object.keys(errMsg)[0]][0].message)
@@ -545,8 +598,23 @@ const basicForm = {
}
})
},
validateCopyTemplateName() {
if (!this.copyTemplateMode) {
return true
}
const currentName = (this.formData.activityName || "").trim()
const templateName = (this.copyTemplateName || "").trim()
if (currentName && templateName && currentName === templateName) {
this.$message.warning("请修改活动名称,不能与模板名称一致")
return false
}
return true
},
async doHandle(type) {
const cloneData = clone(this.formData)
if (this.copyTemplateMode) {
this.cleanCopyTemplateData(cloneData)
}
cloneData.activitySignUpStartTime = cloneData.activitySignTime !== undefined ? cloneData.activitySignTime[0] : null
cloneData.activitySignUpEndTime = cloneData.activitySignTime !== undefined ? cloneData.activitySignTime[1] : null
cloneData.activityStartTime = cloneData.activityTime !== undefined ? cloneData.activityTime[0] : null
@@ -554,7 +622,7 @@ const basicForm = {
if (cloneData.activitySignUpStartTime !== undefined && cloneData.activitySignUpStartTime !== null) {
cloneData.year = new Date(cloneData.activitySignUpStartTime).getFullYear()
}
cloneData.typeLimits = JSON.stringify(this.formData.typeLimits)
cloneData.typeLimits = JSON.stringify(cloneData.typeLimits)
cloneData.courseList = JSON.stringify(cloneData.courseList)
cloneData.hostUnits = JSON.stringify(cloneData.hostUnits)
cloneData.helpUnits = JSON.stringify(cloneData.helpUnits)
@@ -584,10 +652,15 @@ const basicForm = {
if (resp.code === 0) {
this.formData = resp.data
this.typeChange(this.formData.trainType)
if (this.copyTemplateMode) {
this.copyTemplateName = this.formData.activityName
this.cleanCopyTemplateData(this.formData)
}
}
}
},
async initData(row) {
async initData(row, copyTemplateMode = false) {
this.copyTemplateMode = copyTemplateMode
this.activityGroupList = await this.getActivityGroup()
this.historicalActList = await this.getHistoricalActList()
this.courseTypeList = await this.getAllType()
@@ -48,11 +48,27 @@ layout("/layouts/platform.html"){
></el-switch>
</template>
</el-table-column>
<el-table-column label="操作" width="300">
<el-table-column align="center" header-align="center" label="操作" width="150">
<template slot-scope="scope">
<el-button size="mini" type="primary" @click="sendNotice(scope.row.id)">发送通知</el-button>
<el-button size="mini" type="primary" @click="openEdit(scope.row.id)">编辑</el-button>
<el-button size="mini" type="danger" @click="doDelete(scope.row.id)">删除</el-button>
<el-dropdown @command="dropdownCommand">
<el-button size="mini">
<i class="ti-settings"></i>
<span class="ti-angle-down"></span>
</el-button>
<el-dropdown-menu slot="dropdown">
<el-dropdown-item :command="{type:'sendNotice',row:scope.row}">发送通知</el-dropdown-item>
<el-dropdown-item :command="{type:'edit',row:scope.row}">编辑</el-dropdown-item>
<el-dropdown-item
:command="{type:'setTemplate',row:scope.row}"
v-if="$auth.hasRoleOr(['SYSADMIN','SCHOOL_UNION_ADMIN']) && !scope.row.isTemplate"
>设为模板</el-dropdown-item>
<el-dropdown-item
:command="{type:'cancelTemplate',row:scope.row}"
v-if="$auth.hasRoleOr(['SYSADMIN','SCHOOL_UNION_ADMIN']) && scope.row.isTemplate"
>取消模板</el-dropdown-item>
<el-dropdown-item :command="{type:'delete',row:scope.row}" :disabled="!!scope.row.isTemplate">删除</el-dropdown-item>
</el-dropdown-menu>
</el-dropdown>
</template>
</el-table-column>
</el-table>
@@ -61,6 +77,7 @@ layout("/layouts/platform.html"){
</template>
<template #edit>
<div v-if="formVisible">
<el-form :model="formData" ref="formRef" label-width="130px" :rules="formRules">
<el-form-item label="活动主题" prop="name">
<el-input placeholder="请输入活动主题" v-model="formData.name" clearable></el-input>
@@ -232,16 +249,17 @@ layout("/layouts/platform.html"){
</el-form>
<el-row class="mt20" justify="end" type="flex">
<el-button @click="close">取消</el-button>
<el-button type="primary" v-if="formData.isSubmit!=true" plain @click="doSave">保存</el-button>
<el-button type="primary" @click="doSubmit">确定</el-button>
<el-button type="primary" v-if="copyTemplateMode || formData.isSubmit!=true" plain @click="doSave">{{ copyTemplateMode ? "另存为" : "保存" }}</el-button>
<el-button type="primary" @click="doSubmit">{{ copyTemplateMode ? "新活动提交" : "确定" }}</el-button>
</el-row>
</div>
</template>
</guava>
<drawer-user-scope :group_id.sync="formData.activityGroupId" @group_change="getActivityGroup"
<drawer-user-scope v-if="formVisible" :group_id.sync="formData.activityGroupId" @group_change="getActivityGroup"
ref="drawerUserScope"></drawer-user-scope>
<el-dialog :close-on-click-modal="false" :visible.sync="settingDialogVisible" title="更多设置" top="4%" width="40%">
<el-dialog v-if="formVisible" :close-on-click-modal="false" :visible.sync="settingDialogVisible" title="更多设置" top="4%" width="40%">
<el-form :model="currentWorksType" label-width="160px" size="small">
<el-form-item label="作品介绍最多字数">
<el-input-number :max="10000" :min="1" style="width: 100%"
@@ -361,6 +379,11 @@ layout("/layouts/platform.html"){
activityTime: []
},
formVisible: false,
copyTemplateMode: false,
copyTemplateName: "",
formOptionsLoaded: false,
formOptionsPromise: null,
unitOptions: [],
clubOptions: [],
}
@@ -378,10 +401,73 @@ layout("/layouts/platform.html"){
}
},
methods: {
isNewPage() {
return window.location.pathname.toLowerCase() === "/platform/activity/workscollection/new"
},
backToManage() {
commonUtil.pjaxPush("/platform/activity/worksCollection/manage")
},
afterSaveSuccess() {
this.formVisible = false
if (this.isNewPage()) {
this.backToManage()
} else {
this.doSearch()
this.$refs.guava.index()
}
},
initNewPage() {
const params = new URLSearchParams(window.location.search)
const mode = params.get("mode")
const id = params.get("id")
if (mode === "edit" && id) {
this.openEdit(id, true)
} else {
this.openAdd()
}
},
async getActivityGroup() {
const {data} = await this.$axios.post("/platform/activity/basic/scope/getActivityUserScopeGroup")
return data
},
dropdownCommand(command) {
const {type, row} = command
if (type === "sendNotice") {
this.sendNotice(row.id)
} else if (type === "edit") {
this.openEdit(row.id)
} else if (type === "setTemplate") {
this.setTemplate(row)
} else if (type === "cancelTemplate") {
this.cancelTemplate(row)
} else if (type === "delete") {
this.doDelete(row.id)
}
},
async loadFormOptions() {
if (this.formOptionsLoaded) {
return
}
if (this.formOptionsPromise) {
return this.formOptionsPromise
}
this.formOptionsPromise = Promise.all([
this.getActivityGroup(),
this.getClubsByRole(),
this.$businessTool.listUnit()
]).then(([activityGroupList, clubOptions, units]) => {
this.activityGroupList = activityGroupList
this.clubOptions = clubOptions
this.clubOptions.map((v) => {
v.name = v.clubName
})
this.unitOptions = this.clubOptions.concat(units)
this.formOptionsLoaded = true
}).finally(() => {
this.formOptionsPromise = null
})
return this.formOptionsPromise
},
addType(index) {
let item = {}
this.initData(item)
@@ -410,7 +496,11 @@ layout("/layouts/platform.html"){
this.$set(worksType, "allowFileTypes", worksType.allowFileTypes ? worksType.allowFileTypes : [])
},
openAdd() {
async openAdd() {
this.copyTemplateMode = false
this.copyTemplateName = ""
await this.loadFormOptions()
this.formVisible = true
this.$refs.guava.edit()
this.$nextTick(() => {
this.formData = {
@@ -422,9 +512,80 @@ layout("/layouts/platform.html"){
this.initData(this.formData.subjectTypes[0].worksTypes[0])
})
},
async openEdit(id) {
const resp = await this.$axios.post(loc() + "/findOne", {id})
cleanCopyTemplateData(data) {
if (!data) {
return
}
data.id = null
data.isTemplate = false
data.createdBy = null
data.createdAt = null
data.updatedBy = null
data.updatedAt = null
data.delFlag = null
if (Array.isArray(data.subjectTypes)) {
data.subjectTypes = data.subjectTypes.map((subjectType) => {
subjectType.id = null
subjectType.activityId = null
subjectType.createdBy = null
subjectType.createdAt = null
subjectType.updatedBy = null
subjectType.updatedAt = null
subjectType.delFlag = null
if (Array.isArray(subjectType.worksTypes)) {
subjectType.worksTypes = subjectType.worksTypes.map((worksType) => {
worksType.id = null
worksType.subjectId = null
worksType.createdBy = null
worksType.createdAt = null
worksType.updatedBy = null
worksType.updatedAt = null
worksType.delFlag = null
return worksType
})
}
return subjectType
})
}
},
validateCopyTemplateName() {
if (!this.copyTemplateMode) {
return true
}
const currentName = (this.formData.name || "").trim()
const templateName = (this.copyTemplateName || "").trim()
if (currentName && templateName && currentName === templateName) {
this.$message.warning("请修改活动名称,不能与模板名称一致")
return false
}
return true
},
buildSubmitData() {
const data = clone(this.formData)
data.startDateTime = data.activityTime[0]
data.endDateTime = data.activityTime[1]
data.nbStartDateTime = data.nbTime ? data.nbTime[0] : null
data.nbEndDateTime = data.nbTime ? data.nbTime[1] : null
data.type = "1"
if (this.copyTemplateMode) {
this.cleanCopyTemplateData(data)
}
return data
},
async openEdit(id, copyTemplateMode = false) {
this.copyTemplateMode = !!copyTemplateMode
const [resp] = await Promise.all([
this.$axios.post("/platform/activity/worksCollection/manage/findOne", {id}),
this.loadFormOptions()
])
this.formVisible = true
this.formData = resp.data
if (this.copyTemplateMode) {
this.copyTemplateName = this.formData.name
this.cleanCopyTemplateData(this.formData)
} else {
this.copyTemplateName = ""
}
this.$set(this.formData, "activityTime", [this.formData.startDateTime, this.formData.endDateTime])
// this.formData.activityTime = [this.formData.startDateTime, this.formData.endDateTime]
if (this.formData.nbStartDateTime && this.formData.nbEndDateTime) {
@@ -436,27 +597,30 @@ layout("/layouts/platform.html"){
})
},
close() {
this.$refs.guava.index()
this.formVisible = false
if (this.isNewPage()) {
this.backToManage()
} else {
this.$refs.guava.index()
}
},
doSubmit() {
this.$refs.formRef.validate((valid) => {
if (valid) {
this.formData.startDateTime = this.formData.activityTime[0]
this.formData.endDateTime = this.formData.activityTime[1]
this.formData.nbStartDateTime = this.formData.nbTime[0]
this.formData.nbEndDateTime = this.formData.nbTime[1]
this.formData.type = "1"
if (!this.validateCopyTemplateName()) {
return
}
const submitData = this.buildSubmitData()
let loading = this.$loading({
lock: true,
text: "数据正在提交中,请稍后...",
spinner: "el-icon-loading",
background: "rgba(0, 0, 0, 0.7)"
})
this.$axios.post(loc() + (this.formData.id ? "/update" : "/insert"), {data: JSON.stringify(this.formData)}).then((res) => {
this.$axios.post("/platform/activity/worksCollection/manage" + (this.copyTemplateMode || !this.formData.id ? "/insert" : "/update"), {data: JSON.stringify(submitData)}).then((res) => {
if (res.code === 0) {
this.$message.success(res.msg)
this.doSearch()
this.$refs.guava.index()
this.afterSaveSuccess()
} else {
this.$message.warning(res.msg)
}
@@ -466,22 +630,20 @@ layout("/layouts/platform.html"){
})
},
doSave() {
this.formData.startDateTime = this.formData.activityTime[0]
this.formData.endDateTime = this.formData.activityTime[1]
this.formData.nbStartDateTime = this.formData.nbTime[0]
this.formData.nbEndDateTime = this.formData.nbTime[1]
this.formData.type = "1"
if (!this.validateCopyTemplateName()) {
return
}
const submitData = this.buildSubmitData()
let loading = this.$loading({
lock: true,
text: "数据正在保存中,请稍后...",
spinner: "el-icon-loading",
background: "rgba(0, 0, 0, 0.7)"
})
this.$axios.post("/platform/activity/worksCollection/manage" + (this.formData.id ? "/update" : "/insert"), {data: JSON.stringify(this.formData)}).then((res) => {
this.$axios.post("/platform/activity/worksCollection/manage" + (this.copyTemplateMode || !this.formData.id ? "/save" : "/update"), {data: JSON.stringify(submitData)}).then((res) => {
if (res.code === 0) {
this.$message.success(res.msg)
this.doSearch()
this.$refs.guava.index()
this.afterSaveSuccess()
} else {
this.$message.warning(res.msg)
}
@@ -489,6 +651,11 @@ layout("/layouts/platform.html"){
})
},
doDelete(id) {
const row = this.tableData.find((item) => item.id === id)
if (row && row.isTemplate) {
this.$message.warning("该活动已设为模板,请先取消模板后再删除")
return
}
this.$confirm("您确定要删除吗?", "提示", {
confirmButtonText: "确定",
cancelButtonText: "取消",
@@ -502,6 +669,32 @@ layout("/layouts/platform.html"){
})
})
},
async setTemplate(row) {
try {
await this.$confirm("确定将该活动设为工作模板吗?", "提示", {type: "warning"})
const resp = await this.$axios.post(loc() + "/setTemplate", {id: row.id})
if (resp.code === 0) {
this.$message.success(resp.msg)
this.doSearch()
} else {
this.$message.warning(resp.msg)
}
} catch (e) {
}
},
async cancelTemplate(row) {
try {
await this.$confirm("确定取消该工作模板吗?", "提示", {type: "warning"})
const resp = await this.$axios.post(loc() + "/cancelTemplate", {id: row.id})
if (resp.code === 0) {
this.$message.success(resp.msg)
this.doSearch()
} else {
this.$message.warning(resp.msg)
}
} catch (e) {
}
},
enableChange(enable, id) {
this.$axios.post(loc() + "/enableChange", {id, enable}).then((res) => {
@@ -540,15 +733,15 @@ layout("/layouts/platform.html"){
},
},
async created() {
this.activityGroupList = await this.getActivityGroup()
this.pageData()
this.clubOptions = await this.getClubsByRole()
this.clubOptions.map((v) => {
v.name = v.clubName
})
const units = await this.$businessTool.listUnit()
this.unitOptions = this.clubOptions.concat(units)
if (this.isNewPage()) {
await this.loadFormOptions()
this.$nextTick(() => {
this.initNewPage()
})
} else {
this.pageData()
this.loadFormOptions()
}
}
})
</script>
@@ -224,7 +224,7 @@ layout("/layouts/platform.html"){
unionChange(id) {
if (id) {
const union = this.unionList.find(c => c.id === id)
this.$set(this.formData, "helpUnitName", union.unionname)
this.$set(this.formData, "helpUnitName", union ? union.name : "")
} else {
this.$set(this.formData, "helpUnitName", '')
}
@@ -243,42 +243,61 @@ layout("/layouts/platform.html"){
}
if (val) {
const budgetType = this.budgetTypeOption.find(b => b.code === val)
this.$set(this.formData, "budgetTypeId", budgetType.code)
this.$set(this.formData, "budgetTypeId", budgetType ? budgetType.code : "")
}
},
async getActivityBudgetType() {
const data = await this.$businessTool.getDictOptions("ACTIVITY_BUDGET_TYPE")
let budgetTypeOption = []
if (this.$auth.hasPermission(['activity.budget.apply.system'])) {
const budgetTypeOption = []
if (this.canApplyAllBudgetType()) {
this.budgetTypeOption = data
} else {
if (this.$auth.hasPermission(['activity.budget.apply.schoolAdmin'])) {
data.map(v => {
if (["ACTIVITY_BUDGET_TYPE_ONE"].includes(v.code)) {
budgetTypeOption.push(v)
}
})
if (this.canApplySchoolBudget()) {
this.pushBudgetTypeOption(data, budgetTypeOption, "ACTIVITY_BUDGET_TYPE_ONE")
}
if (this.$auth.hasPermission(['activity.budget.apply.branchAdmin'])) {
data.map(v => {
if (["ACTIVITY_BUDGET_TYPE_TWO"].includes(v.code)) {
budgetTypeOption.push(v)
}
})
if (this.canApplyBranchBudget()) {
this.pushBudgetTypeOption(data, budgetTypeOption, "ACTIVITY_BUDGET_TYPE_TWO")
}
if (this.$auth.hasPermission(['activity.budget.apply.clubPresident'])) {
data.map(v => {
if (["ACTIVITY_BUDGET_TYPE_THREE"].includes(v.code)) {
budgetTypeOption.push(v)
}
})
if (this.canApplyClubBudget()) {
this.pushBudgetTypeOption(data, budgetTypeOption, "ACTIVITY_BUDGET_TYPE_THREE")
}
this.budgetTypeOption = budgetTypeOption
if (this.budgetTypeOption.length === 1){
this.$set(this.formData, "outlayManageSource", this.budgetTypeOption[0].code)
this.budgetTypeCodeChange(this.budgetTypeOption[0].code)
}
}
this.initDefaultBudgetType()
},
pushBudgetTypeOption(source, target, code) {
const option = source.find(v => v.code === code)
if (option && !target.some(v => v.code === code)) {
target.push(option)
}
},
canApplyAllBudgetType() {
return this.$auth.hasPermission('activity.budget.apply.system')
|| this.$auth.hasRoleOr(['SYSADMIN', 'SCHOOL_UNION_ADMIN'])
},
canApplySchoolBudget() {
return this.$auth.hasPermission('activity.budget.apply.schoolAdmin')
|| this.$auth.hasRoleOr(['SCHOOL_REIMBURSEMENT_MANAGER', 'SCHOOL_OUTLAY_ADMIN'])
},
canApplyBranchBudget() {
return this.$auth.hasPermission('activity.budget.apply.branchAdmin')
|| this.$auth.hasRoleOr(['UNION_REIMBURSEMENT_MANAGER', 'BRANCH_UNION_ADMIN', 'BRANCH_UNION_CHAIRMAN', 'BRANCH_UNION_OPERATOR', 'BRANCH_UNION_WENTI_SPORTS'])
},
canApplyClubBudget() {
return this.$auth.hasPermission('activity.budget.apply.clubPresident')
|| this.$auth.hasRoleOr(['CLUB_REIMBURSEMENT_MANAGER', 'CLUB_MANAGER', 'CLUB_PRESIDENT'])
},
initDefaultBudgetType() {
if (this.bizId || this.formData.outlayManageSource || this.budgetTypeOption.length === 0) {
return
}
const defaultBudgetType = this.budgetTypeOption[0].code
this.$set(this.formData, "outlayManageSource", defaultBudgetType)
this.budgetTypeCodeChange(defaultBudgetType)
},
async loadUnionList() {
const unionId = this.canApplyAllBudgetType() ? null : this.$store.state.user.union.id
this.unionList = await this.$businessTool.listUnion(unionId)
},
getSchoolBudget() {
this.$axios.post("/platform/activity/budget/apply/getSchoolBudget").then((res) => {
@@ -343,7 +362,7 @@ layout("/layouts/platform.html"){
this.init()
await this.getActivityBudgetType()
await this.getSchoolBudget()
this.unionList = await this.$businessTool.listUnion(this.$store.state.user.union.id)
await this.loadUnionList()
this.clubOption = await this.$businessTool.listClubByRole()
}
})
@@ -99,7 +99,7 @@ layout("/layouts/platform_tour_signup_h5.html"){
</style>
<div id="app">
<van-nav-bar title="疗休养报名" left-text="返回" left-arrow @click-left="historyBack" fixed placeholder></van-nav-bar>
<van-nav-bar title="疗休养报名" left-text="返回" left-arrow @click-left="historyBack('/platform/tour/signup/h5/signup')" fixed placeholder></van-nav-bar>
<div class="tour-apply-page">
<van-loading v-if="pageLoading" size="24px" vertical>加载中...</van-loading>
@@ -544,7 +544,7 @@ layout("/layouts/platform_tour_signup_h5.html"){
message: res.msg || "报名成功",
confirmButtonColor: "#1867b0"
}).then(() => {
window.location.href = "/platform/tour/signup/h5/signup"
window.location.replace("/platform/tour/signup/h5/signup")
})
} else {
vant.Dialog.alert({
@@ -173,7 +173,7 @@ layout("/layouts/platform_tour_signup_h5.html"){
</style>
<div id="app">
<van-nav-bar title="线路详情" left-text="返回" left-arrow @click-left="historyBack" fixed placeholder></van-nav-bar>
<van-nav-bar title="线路详情" left-text="返回" left-arrow @click-left="historyBack('/platform/tour/signup/h5/signup')" fixed placeholder></van-nav-bar>
<div class="tour-detail-page">
<van-loading v-if="detailLoading" size="24px" vertical>加载中...</van-loading>
@@ -379,7 +379,7 @@ layout("/layouts/platform_tour_signup_h5.html"){
</style>
<div id="app" class="tour-line-page">
<van-nav-bar title="疗休养线路" left-text="返回" left-arrow @click-left="historyBack" fixed placeholder></van-nav-bar>
<van-nav-bar title="疗休养线路" left-text="返回" left-arrow @click-left="historyBack('/platform/tour/signup/h5')" fixed placeholder></van-nav-bar>
<div class="tour-line-toolbar">
<div class="tour-line-search-row">
@@ -411,7 +411,8 @@ layout("/layouts/platform_h5.html"){
currentSegmentId: "",
studying: false,
pendingSeconds: 0,
heartbeatTimer: null
heartbeatTimer: null,
navigatingBack: false
}
},
computed: {
@@ -685,9 +686,29 @@ layout("/layouts/platform_h5.html"){
this.finishStudy(false)
this.playerVisible = false
},
goBack() {
this.finishStudy(true)
pjaxReplace("/platform/learning/course/h5")
async goBack() {
if (this.navigatingBack) return
this.navigatingBack = true
try {
await this.finishStudy(true)
} finally {
this.navigateBack()
}
},
navigateBack() {
if (window.history.length > 1) {
window.history.back()
return
}
$.pjax({
url: "/platform/learning/course/h5",
container: "#container",
maxCacheLength: 0,
push: false,
replace: true,
fragment: "#container",
timeout: 8000
})
}
},
async mounted() {
@@ -230,18 +230,18 @@ const home = {
.map(src => ({ src }))
},
listHomeBanner() {
const cached = this.readHomeCache("banner")
const cached = this.readHomeCache("h5Banner")
if (cached && cached.length) {
this.bannerList = cached
this.activeBannerIndex = 0
}
this.$axios.post("/open/common/getConfigKey", { key: "AppHomeImg" }).then((res) => {
this.$axios.post("/open/common/getConfigKey", { key: "H5AppHomeImg" }).then((res) => {
if (res.code === 0) {
const configBannerList = this.parseBannerList(res.data)
const nextBannerList = configBannerList.length > 0 ? configBannerList : this.defaultBannerList
this.bannerList = nextBannerList
this.activeBannerIndex = 0
this.writeHomeCache("banner", nextBannerList, this.homeCacheTtl.banner)
this.writeHomeCache("h5Banner", nextBannerList, this.homeCacheTtl.banner)
this.cacheBannerImages(nextBannerList)
}
}).catch(() => {
@@ -164,7 +164,7 @@ layout("/layouts/platform_h5.html"){
position: relative;
display: flex;
flex-direction: row;
height: 90px;
min-height: 120px;
}
.welfare-option.selected {
@@ -185,49 +185,87 @@ layout("/layouts/platform_h5.html"){
}
.welfare-option-image {
width: 90px;
height: 90px;
width: 100px;
height: 100px;
margin: 10px 0 10px 10px;
position: relative;
flex-shrink: 0;
border-radius: 8px;
overflow: hidden;
background: #f7f8fa;
}
.welfare-option-content {
padding: 6px 12px;
padding: 10px 12px;
flex: 1;
display: flex;
flex-direction: column;
position: relative;
min-width: 0;
}
.welfare-option-title {
font-size: 15px;
font-weight: bold;
color: var(--text-primary);
margin-bottom: 0;
padding-right: 30px;
margin-bottom: 5px;
padding-right: 34px;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
line-height: 1.4;
}
.welfare-option-type-tag {
display: inline-flex;
align-items: center;
height: 17px;
padding: 0 4px;
margin-right: 5px;
border-radius: 3px;
background: var(--primary-color);
color: #fff;
font-size: 11px;
line-height: 17px;
vertical-align: 1px;
}
.welfare-option-rank {
margin-bottom: 4px;
color: #d6a21e;
font-size: 12px;
line-height: 1.3;
display: flex;
align-items: center;
}
.welfare-option-rank .van-icon {
margin-right: 3px;
font-size: 14px;
}
.welfare-option-desc {
padding-right: 4px;
color: var(--text-secondary);
font-size: 12px;
line-height: 1.45;
overflow: hidden;
text-overflow: ellipsis;
display: -webkit-box;
-webkit-line-clamp: 2;
-webkit-box-orient: vertical;
line-height: 1.4;
}
.welfare-option-desc {
display: none;
}
.welfare-option-footer {
margin-top: auto;
display: flex;
justify-content: space-between;
justify-content: flex-end;
align-items: center;
gap: 10px;
}
.welfare-option-checkbox {
position: absolute;
bottom: 12px;
right: 12px;
flex-shrink: 0;
}
.welfare-option-checkbox .van-stepper {
@@ -240,13 +278,16 @@ layout("/layouts/platform_h5.html"){
}
.welfare-detail-btn {
position: absolute;
bottom: 12px;
left: 12px;
color: var(--primary-color);
height: 24px;
padding: 0 10px;
border-radius: 12px;
background: var(--primary-color);
color: #fff;
font-size: 13px;
display: flex;
align-items: center;
justify-content: center;
flex-shrink: 0;
}
.welfare-detail-btn .van-icon {
@@ -640,14 +681,17 @@ layout("/layouts/platform_h5.html"){
</div>
<div class="welfare-option-content">
<div class="welfare-option-title">{{ option.optionName }}</div>
<!-- 查看详情按钮 -->
<div class="welfare-detail-btn" @click.stop="showOptionDetail(option)">
<van-icon name="info-o"/>
<span style="position: relative; top: -0.5px">查看详情</span>
<div class="welfare-option-title">
<span class="welfare-option-type-tag">套餐</span>{{ option.optionName }}
</div>
<div class="welfare-option-rank">
<van-icon name="medal-o"/>
<span>{{ optionRankText(option) }}</span>
</div>
<div class="welfare-option-desc">{{ optionBrief(option) }}</div>
<!-- 单选模式使用单选按钮 -->
<div class="welfare-option-radio" v-if="projectInfo.isCheckBox === 'radio'">
<van-radio
@@ -658,21 +702,29 @@ layout("/layouts/platform_h5.html"){
></van-radio>
</div>
<!-- 多选模式使用步进器 -->
<div class="welfare-option-checkbox" v-else>
<van-stepper
:key="'input-number-'+index+'-'+option.selectNumKey|| 0"
v-model="option.selectNum"
integer
disable-input
:default-value="0"
:min="0"
:disabled="isDeadlinePassed"
input-width="40px"
button-size="22px"
@change="selectNumChange(index,option.selectNum)"
theme="round"
></van-stepper>
<div class="welfare-option-footer">
<!-- 查看详情按钮 -->
<div class="welfare-detail-btn" @click.stop="showOptionDetail(option)">
<van-icon name="info-o"/>
<span style="position: relative; top: -0.5px">查看详情</span>
</div>
<!-- 多选模式使用步进器 -->
<div class="welfare-option-checkbox" v-if="projectInfo.isCheckBox !== 'radio'">
<van-stepper
:key="'input-number-'+index+'-'+option.selectNumKey|| 0"
v-model="option.selectNum"
integer
disable-input
:default-value="0"
:min="0"
:disabled="isDeadlinePassed"
input-width="40px"
button-size="22px"
@change="selectNumChange(index,option.selectNum)"
theme="round"
></van-stepper>
</div>
</div>
</div>
</div>
@@ -894,6 +946,19 @@ layout("/layouts/platform_h5.html"){
},
methods: {
optionRankText(option) {
if (option.rankNo) {
return "此套餐在本次福利排行第" + option.rankNo + "名"
}
return "此套餐暂无排行数据"
},
optionBrief(option) {
const content = option.simpleDesc || option.description || option.supplier || ""
const div = document.createElement("div")
div.innerHTML = content
const text = (div.textContent || div.innerText || "").replace(/\s+/g, " ").trim()
return text || "暂无套餐详情"
},
selectNumChange(index, newValue) {
const option = this.projectInfo.options[index];
const maxSelect = this.projectInfo.multiSelectNum || this.projectInfo.options.length;
@@ -1221,8 +1286,6 @@ layout("/layouts/platform_h5.html"){
// 显示选项详情
showOptionDetail(option) {
// 阻止事件冒泡,避免触发父元素的点击事件
event.stopPropagation()
this.selectedOption = option
this.showOptionDetailDialog = true
},