Views for creating and editing SciDepartment items.
parent
c094c8aa58
commit
1c21f2a898
File diff suppressed because it is too large
Load Diff
|
|
@ -0,0 +1,26 @@
|
|||
{
|
||||
"name": "sci-types-department",
|
||||
"version": "7.0.0",
|
||||
"description": "JavaScript parts of the UI of sci-types-department",
|
||||
"main": "index.js",
|
||||
"scripts": {
|
||||
"build": "npm-run-all build:*",
|
||||
"build:js": "webpack"
|
||||
},
|
||||
"author": "Jens Pelzetter",
|
||||
"license": "LGPL-3.0-or-later",
|
||||
"devDependencies": {
|
||||
"@types/sortablejs": "^1.10.7",
|
||||
"npm-run-all": "^4.1.5",
|
||||
"ts-loader": "^9.2.6",
|
||||
"typescript": "^4.4.3",
|
||||
"webpack": "^5.55.1",
|
||||
"webpack-cli": "^4.8.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"sortablejs": "^1.14.0"
|
||||
},
|
||||
"targets": {
|
||||
"main": false
|
||||
}
|
||||
}
|
||||
|
|
@ -166,7 +166,7 @@
|
|||
</configuration>
|
||||
</plugin>
|
||||
|
||||
<!-- <plugin>
|
||||
<plugin>
|
||||
<groupId>com.github.eirslett</groupId>
|
||||
<artifactId>frontend-maven-plugin</artifactId>
|
||||
<configuration>
|
||||
|
|
@ -188,7 +188,7 @@
|
|||
<goal>npm</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<arguments> - -userconfig ../libreccm.npmrc install</arguments>
|
||||
<arguments>--userconfig ../libreccm.npmrc install</arguments>
|
||||
</configuration>
|
||||
</execution>
|
||||
<execution>
|
||||
|
|
@ -201,7 +201,7 @@
|
|||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>-->
|
||||
</plugin>
|
||||
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ public class SciDepartmentConfig {
|
|||
|
||||
@Setting
|
||||
private String memberRolesBundleName
|
||||
= "org.scientificcms.contenttypes.scidepartment.MemberRoles";
|
||||
= "org.scientificcms.contenttypes.scidepartment.DefaultMemberRoles";
|
||||
|
||||
@Setting
|
||||
private String textKeysBundleName
|
||||
|
|
|
|||
|
|
@ -0,0 +1,29 @@
|
|||
package org.scientificcms.contenttypes.scidepartment.ui;
|
||||
|
||||
import org.libreccm.configuration.ConfigurationManager;
|
||||
import org.libreccm.ui.AbstractMessagesBean;
|
||||
import org.scientificcms.contenttypes.scidepartment.SciDepartmentConfig;
|
||||
|
||||
import javax.enterprise.context.RequestScoped;
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author <a href="mailto:jens.pelzetter@googlemail.com">Jens Pelzetter</a>
|
||||
*/
|
||||
@RequestScoped
|
||||
@Named("SciDepartmentContactTypes")
|
||||
public class SciDepartmentContactTypes extends AbstractMessagesBean {
|
||||
|
||||
@Inject
|
||||
private ConfigurationManager confManager;
|
||||
|
||||
@Override
|
||||
protected String getMessageBundle() {
|
||||
return confManager
|
||||
.findConfiguration(SciDepartmentConfig.class)
|
||||
.getContactTypesBundleName();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -18,8 +18,11 @@
|
|||
*/
|
||||
package org.scientificcms.contenttypes.scidepartment.ui;
|
||||
|
||||
import com.arsdigita.kernel.KernelConfig;
|
||||
|
||||
import org.libreccm.api.Identifier;
|
||||
import org.libreccm.api.IdentifierParser;
|
||||
import org.libreccm.configuration.ConfigurationManager;
|
||||
import org.libreccm.l10n.GlobalizationHelper;
|
||||
import org.libreccm.l10n.LocalizedString;
|
||||
import org.libreccm.security.AuthorizationRequired;
|
||||
|
|
@ -90,6 +93,10 @@ public class SciDepartmentDescriptionStep extends AbstractMvcAuthoringStep {
|
|||
@Inject
|
||||
private BaseUrl baseUrl;
|
||||
|
||||
@Inject
|
||||
private ConfigurationManager confManager;
|
||||
|
||||
|
||||
@Inject
|
||||
private ContentItemRepository itemRepo;
|
||||
|
||||
|
|
@ -138,6 +145,9 @@ public class SciDepartmentDescriptionStep extends AbstractMvcAuthoringStep {
|
|||
@Inject
|
||||
private SciDepartmentTextsModel textsModel;
|
||||
|
||||
@Inject
|
||||
private SciDepartmentTexts texts;
|
||||
|
||||
@Override
|
||||
public Class<SciDepartmentDescriptionStep> getStepClass() {
|
||||
return SciDepartmentDescriptionStep.class;
|
||||
|
|
@ -428,9 +438,7 @@ public class SciDepartmentDescriptionStep extends AbstractMvcAuthoringStep {
|
|||
final String sectionIdentifier,
|
||||
@PathParam(MvcAuthoringSteps.DOCUMENT_PATH_PATH_PARAM_NAME)
|
||||
final String documentPath,
|
||||
@FormParam("textKey") final String textKey,
|
||||
@FormParam("locale") final String localeParam,
|
||||
@FormParam("textValue") final String textValue
|
||||
@FormParam("textKey") final String textKey
|
||||
) {
|
||||
try {
|
||||
init();
|
||||
|
|
@ -441,9 +449,11 @@ public class SciDepartmentDescriptionStep extends AbstractMvcAuthoringStep {
|
|||
}
|
||||
|
||||
if (itemPermissionChecker.canEditItem(getDepartment())) {
|
||||
final Locale locale = new Locale(localeParam);
|
||||
final Locale locale = confManager
|
||||
.findConfiguration(KernelConfig.class)
|
||||
.getDefaultLocale();
|
||||
final LocalizedString text = new LocalizedString();
|
||||
text.putValue(locale, textValue);
|
||||
text.putValue(locale, "");
|
||||
|
||||
departmentManager.addText(text, getDepartment(), textKey);
|
||||
itemRepo.save(getDepartment());
|
||||
|
|
@ -644,7 +654,7 @@ public class SciDepartmentDescriptionStep extends AbstractMvcAuthoringStep {
|
|||
@Path("/texts/remove/{textKey}")
|
||||
@Transactional(Transactional.TxType.REQUIRED)
|
||||
@AuthorizationRequired
|
||||
public String removeTextValue(
|
||||
public String removeText(
|
||||
@PathParam(MvcAuthoringSteps.SECTION_IDENTIFIER_PATH_PARAM)
|
||||
final String sectionIdentifier,
|
||||
@PathParam(MvcAuthoringSteps.DOCUMENT_PATH_PATH_PARAM_NAME)
|
||||
|
|
@ -1074,6 +1084,13 @@ public class SciDepartmentDescriptionStep extends AbstractMvcAuthoringStep {
|
|||
)
|
||||
)
|
||||
);
|
||||
textsModel.setAvailableTextKeys(
|
||||
texts
|
||||
.keySet()
|
||||
.stream()
|
||||
.filter(key -> !textsModel.getTexts().containsKey(key))
|
||||
.collect(Collectors.toList())
|
||||
);
|
||||
|
||||
contactsModel.setCanEdit(canEdit);
|
||||
contactsModel.setContacts(
|
||||
|
|
|
|||
|
|
@ -1,17 +1,26 @@
|
|||
package org.scientificcms.contenttypes.scidepartment.ui;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import javax.enterprise.context.RequestScoped;
|
||||
import javax.inject.Named;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author <a href="mailto:jens.pelzetter@googlemail.com">Jens Pelzetter</a>
|
||||
*/
|
||||
@RequestScoped
|
||||
@Named("SciDepartmentTextsModel")
|
||||
public class SciDepartmentTextsModel {
|
||||
|
||||
private boolean canEdit;
|
||||
|
||||
private List<String> availableTextKeys;
|
||||
|
||||
private Map<String, SciDepartmentTextModel> texts;
|
||||
|
||||
private String selectedText;
|
||||
|
|
@ -26,6 +35,14 @@ public class SciDepartmentTextsModel {
|
|||
this.canEdit = canEdit;
|
||||
}
|
||||
|
||||
public List<String> getAvailableTextKeys() {
|
||||
return Collections.unmodifiableList(availableTextKeys);
|
||||
}
|
||||
|
||||
protected void setAvailableTextKeys(final List<String> availableTextKeys) {
|
||||
this.availableTextKeys = new ArrayList<>(availableTextKeys);
|
||||
}
|
||||
|
||||
public Map<String, SciDepartmentTextModel> getTexts() {
|
||||
return Collections.unmodifiableMap(texts);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,125 @@
|
|||
package org.scientificcms.contenttypes.scidepartment.ui;
|
||||
|
||||
import org.jsoup.Jsoup;
|
||||
import org.librecms.contentsection.ContentItem;
|
||||
import org.librecms.contentsection.ContentItemRepository;
|
||||
import org.librecms.contentsection.ContentSection;
|
||||
import org.librecms.ui.contentsections.ContentSectionsUi;
|
||||
import org.librecms.ui.contentsections.ItemPermissionChecker;
|
||||
import org.librecms.ui.contentsections.documents.MvcAuthoringSteps;
|
||||
import org.scientificcms.contenttypes.scidepartment.SciDepartment;
|
||||
|
||||
import java.util.Locale;
|
||||
import java.util.Optional;
|
||||
import java.util.StringTokenizer;
|
||||
|
||||
import javax.enterprise.context.RequestScoped;
|
||||
import javax.inject.Inject;
|
||||
import javax.transaction.Transactional;
|
||||
import javax.ws.rs.ForbiddenException;
|
||||
import javax.ws.rs.GET;
|
||||
import javax.ws.rs.NotFoundException;
|
||||
import javax.ws.rs.Path;
|
||||
import javax.ws.rs.PathParam;
|
||||
import javax.ws.rs.Produces;
|
||||
import javax.ws.rs.core.MediaType;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author <a href="mailto:jens.pelzetter@googlemail.com">Jens Pelzetter</a>
|
||||
*/
|
||||
@RequestScoped
|
||||
@Path(MvcAuthoringSteps.PATH_PREFIX + "scidepartment-texts-resources")
|
||||
public class SciDepartmentTextsResources {
|
||||
|
||||
@Inject
|
||||
private ContentItemRepository itemRepo;
|
||||
|
||||
@Inject
|
||||
private ContentSectionsUi sectionsUi;
|
||||
|
||||
@Inject
|
||||
private ItemPermissionChecker itemPermissionChecker;
|
||||
|
||||
@GET
|
||||
@Path("/department-texts/{textKey}/wordcount/{locale}")
|
||||
@Produces(MediaType.TEXT_HTML)
|
||||
@Transactional(Transactional.TxType.REQUIRED)
|
||||
public String getDepartmentDescriptionWordCount(
|
||||
@PathParam(MvcAuthoringSteps.SECTION_IDENTIFIER_PATH_PARAM)
|
||||
final String sectionIdentifier,
|
||||
@PathParam(MvcAuthoringSteps.DOCUMENT_PATH_PATH_PARAM_NAME)
|
||||
final String documentPathParam,
|
||||
@PathParam("textKey") final String textKey,
|
||||
@PathParam("locale") final String localeParam
|
||||
) {
|
||||
final ContentSection contentSection = sectionsUi
|
||||
.findContentSection(sectionIdentifier)
|
||||
.orElseThrow(
|
||||
() -> new NotFoundException()
|
||||
);
|
||||
|
||||
final ContentItem document = itemRepo
|
||||
.findByPath(contentSection, documentPathParam)
|
||||
.orElseThrow(
|
||||
() -> new NotFoundException()
|
||||
);
|
||||
|
||||
if (!(document instanceof SciDepartment)) {
|
||||
throw new NotFoundException();
|
||||
}
|
||||
|
||||
final SciDepartment department = (SciDepartment) document;
|
||||
if (itemPermissionChecker.canEditItem(department)) {
|
||||
return Optional
|
||||
.ofNullable(department.getAdditionalTexts().get(textKey))
|
||||
.map(text -> text.getText().getValue(new Locale(localeParam)))
|
||||
.map(text -> Jsoup.parseBodyFragment(text))
|
||||
.map(jsoupDoc -> jsoupDoc.body().text())
|
||||
.map(text -> new StringTokenizer(text).countTokens())
|
||||
.map(Long::toString)
|
||||
.orElseThrow(() -> new NotFoundException());
|
||||
} else {
|
||||
throw new ForbiddenException();
|
||||
}
|
||||
}
|
||||
|
||||
@GET
|
||||
@Path("/department-texts/{textKey}/{locale}")
|
||||
@Produces(MediaType.TEXT_HTML)
|
||||
@Transactional(Transactional.TxType.REQUIRED)
|
||||
public String viewDepartmentDescriptionValue(
|
||||
@PathParam(MvcAuthoringSteps.SECTION_IDENTIFIER_PATH_PARAM)
|
||||
final String sectionIdentifier,
|
||||
@PathParam(MvcAuthoringSteps.DOCUMENT_PATH_PATH_PARAM_NAME)
|
||||
final String documentPathParam,
|
||||
@PathParam("textKey") final String textKey,
|
||||
@PathParam("locale") final String localeParam
|
||||
) {
|
||||
final ContentSection contentSection = sectionsUi
|
||||
.findContentSection(sectionIdentifier)
|
||||
.orElseThrow(
|
||||
() -> new NotFoundException()
|
||||
);
|
||||
|
||||
final ContentItem document = itemRepo
|
||||
.findByPath(contentSection, documentPathParam)
|
||||
.orElseThrow(
|
||||
() -> new NotFoundException()
|
||||
);
|
||||
|
||||
if (!(document instanceof SciDepartment)) {
|
||||
throw new NotFoundException();
|
||||
}
|
||||
|
||||
final SciDepartment department = (SciDepartment) document;
|
||||
if (itemPermissionChecker.canEditItem(department)) {
|
||||
return Optional
|
||||
.ofNullable(department.getAdditionalTexts().get(textKey))
|
||||
.map(text -> text.getText().getValue(new Locale(localeParam)))
|
||||
.orElseThrow(() -> new NotFoundException());
|
||||
} else {
|
||||
throw new ForbiddenException();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,39 @@
|
|||
<!DOCTYPE html [<!ENTITY times '×'>]>
|
||||
<html xmlns="http://www.w3.org/1999/xhtml"
|
||||
xmlns:bootstrap="http://xmlns.jcp.org/jsf/composite/components/bootstrap"
|
||||
xmlns:c="http://xmlns.jcp.org/jsp/jstl/core"
|
||||
xmlns:libreccm="http://xmlns.jcp.org/jsf/composite/components/libreccm"
|
||||
xmlns:librecms="http://xmlns.jcp.org/jsf/composite/components/librecms"
|
||||
xmlns:ui="http://xmlns.jcp.org/jsf/facelets">
|
||||
<ui:composition template="/WEB-INF/views/org/librecms/ui/contentsection/documents/authoringstep.xhtml">
|
||||
|
||||
<ui:define name="authoringStep">
|
||||
<div class="d-flex">
|
||||
<a class="btn btn-secondary btn-sm align-self-center mr-2"
|
||||
href="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description">
|
||||
<bootstrap:svgIcon icon="caret-left-fill" />
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['description_step.back']}</span>
|
||||
</a>
|
||||
|
||||
<h2>#{SciDepartmentMessageBundle['description_step.description.header.edit']}</h2>
|
||||
</div>
|
||||
|
||||
<c:if test="#{SciDepartmentDescriptionModel.canEdit}">
|
||||
<librecms:cmsEditor
|
||||
backUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description"
|
||||
baseUrl="#{mvc.basePath}"
|
||||
canEdit="#{SciDepartmentDescriptionModel.canEdit}"
|
||||
contentSection="#{ContentSectionModel.sectionName}"
|
||||
editMethod="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/description/edit"
|
||||
editorId="scidepartment-description-editor"
|
||||
objectIdentifier="#{CmsSelectedDocumentModel.itemPath}"
|
||||
selectedLocale="#{SciDepartmentDescriptionModel.selectedLocale}"
|
||||
title="#{SciDepartmentMessageBundle['description.editor.header']}"
|
||||
variantUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description-resources/department-description"
|
||||
/>
|
||||
</c:if>
|
||||
|
||||
</ui:define>
|
||||
|
||||
</ui:composition>
|
||||
</html>
|
||||
|
|
@ -0,0 +1,39 @@
|
|||
<!DOCTYPE html [<!ENTITY times '×'>]>
|
||||
<html xmlns="http://www.w3.org/1999/xhtml"
|
||||
xmlns:bootstrap="http://xmlns.jcp.org/jsf/composite/components/bootstrap"
|
||||
xmlns:c="http://xmlns.jcp.org/jsp/jstl/core"
|
||||
xmlns:h="http://xmlns.jcp.org/jsf/html"
|
||||
xmlns:libreccm="http://xmlns.jcp.org/jsf/composite/components/libreccm"
|
||||
xmlns:ui="http://xmlns.jcp.org/jsf/facelets">
|
||||
<ui:composition template="/WEB-INF/views/org/librecms/ui/contentsection/documents/authoringstep.xhtml">
|
||||
|
||||
<ui:define name="authoringStep">
|
||||
<div class="d-flex">
|
||||
<a class="btn btn-secondary btn-sm align-self-center mr-2"
|
||||
href="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemName}/@scidepartment-description">
|
||||
<bootstrap:svgIcon icon="caret-left-fill" />
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['description_step.back']}</span>
|
||||
</a>
|
||||
|
||||
<h2>#{SciDepartmentMessageBundle['description_step.description.header.view']}</h2>
|
||||
</div>
|
||||
|
||||
<c:if test="#{SciDepartmentDescriptionModel.canEdit}">
|
||||
<div class="text-right">
|
||||
<a class="btn btn-secondary"
|
||||
href="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/description/edit">
|
||||
<bootstrap:svgIcon icon="pen" />
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['description_step.edit']}</span>
|
||||
</a>
|
||||
</div>
|
||||
</c:if>
|
||||
<div class="cms-text-preview article-text border p-2">
|
||||
<h:outputText escape="false"
|
||||
value="#{SciDepartmentDescriptionModel.descriptionValues.get(SciDepartmentDescriptionModel.selectedLocale)}" />
|
||||
</div>
|
||||
</ui:define>
|
||||
|
||||
</ui:composition>
|
||||
|
||||
</html>
|
||||
|
||||
|
|
@ -0,0 +1,454 @@
|
|||
<!DOCTYPE html [<!ENTITY times '×'>]>
|
||||
<html xmlns="http://www.w3.org/1999/xhtml"
|
||||
xmlns:bootstrap="http://xmlns.jcp.org/jsf/composite/components/bootstrap"
|
||||
xmlns:c="http://xmlns.jcp.org/jsp/jstl/core"
|
||||
xmlns:libreccm="http://xmlns.jcp.org/jsf/composite/components/libreccm"
|
||||
xmlns:librecms="http://xmlns.jcp.org/jsf/composite/components/librecms"
|
||||
xmlns:ui="http://xmlns.jcp.org/jsf/facelets">
|
||||
<ui:composition template="/WEB-INF/views/org/librecms/ui/contentsection/documents/authoringstep.xhtml">
|
||||
|
||||
<ui:param name="authoringStep"
|
||||
value="/libreccm/@contentsections/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/scidepartment-description" />
|
||||
|
||||
<ui:define name="authoringStep">
|
||||
<h2>#{SciDepartmentMessageBundle['description_step.header']}</h2>
|
||||
|
||||
<c:if test="#{contactableNotFound != null}">
|
||||
<div class="alert alert-warning" role="alert">
|
||||
#{SciDepartmentMessageBundle.getMessage('description_step.errors.contactable_not_found', [contactableNotFound])}
|
||||
</div>
|
||||
</c:if>
|
||||
|
||||
<c:if test="#{personNotFound != null}">
|
||||
<div class="alert alert-warning" role="alert">
|
||||
#{SciDepartmentMessageBundle.getMessage('description_step.errors.person_not_found', [personNotFound])}
|
||||
</div>
|
||||
</c:if>
|
||||
|
||||
<c:if test="#{illegalStatusValue != null}">
|
||||
<div class="alert alert-warning" role="alert">
|
||||
#{SciDepartmentMessageBundle.getMessage('description_step.errors.illegal_member_status_value', [illegalStatusValue])}
|
||||
</div>
|
||||
</c:if>
|
||||
|
||||
<template id="scidepartment-contacts-sort-error-general">
|
||||
<div class="alert alert-danger mt-3" role="alert">
|
||||
#{SciDepartmentMessageBundle['contacts.sort.errors.general']}
|
||||
</div>
|
||||
</template>
|
||||
<template id="scidepartment-contacts-sort-error-save">
|
||||
<div class="alert alert-danger mt-3" role="alert">
|
||||
#{SciDepartmentMessageBundle['contacts.sort.errors.save']}
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<div id="messages"></div>
|
||||
|
||||
<librecms:cmsEditorVariants
|
||||
addButtonLabel="#{SciDepartmentMessageBundle['description.editor.add_variant']}"
|
||||
addDialogLocaleSelectHelp="#{SciDepartmentMessageBundle['description.editor.add.locale.help']}"
|
||||
addMethod="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/description/add"
|
||||
canEdit="#{SciDepartmentDescriptionModel.canEdit}"
|
||||
editorPageUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/description/edit"
|
||||
hasUnusedLocales="#{!SciDepartmentDescriptionModel.unusedLocales.isEmpty()}"
|
||||
headingLevel="3"
|
||||
removeMethod="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/description/remove"
|
||||
sourceEditorPageUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/docuements/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/description/edit-source"
|
||||
title="#{SciDepartmentMessageBundle['description.editor.header']}"
|
||||
unusedLocales="#{SciDepartmentDescriptionModel.unusedLocales}"
|
||||
variants="#{SciDepartmentDescriptionModel.variants}"
|
||||
variantsId="description"
|
||||
viewPageUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/description/view"
|
||||
/>
|
||||
|
||||
<h3>#{SciDepartmentMessageBundle['contacts.header']}</h3>
|
||||
<div class="mb-2">
|
||||
<div class="text-right">
|
||||
<librecms:assetPickerButton
|
||||
assetPickerId="contacts-picker"
|
||||
buttonIcon="plus-circle"
|
||||
buttonText="#{SciDepartmentMessageBundle['contacts.add_button.label']}"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<librecms:assetPicker
|
||||
actionUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/contacts/add"
|
||||
assetType="#{SciDepartmentDescriptionContacts.contactableTypes}"
|
||||
assetPickerId="contacts-picker"
|
||||
baseUrl="#{SciDepartmentDescriptionContacts.baseUrl}"
|
||||
contentSection="#{ContentSectionModel.sectionName}"
|
||||
dialogTitle="#{SciDepartmentMessageBundle['contact.add.title']}"
|
||||
formParamName="contactableUuid">
|
||||
<bootstrap:formGroupSelect
|
||||
help="#{SciDepartmentMessageBundle['contacts.type.help']}"
|
||||
inputId="type"
|
||||
label="#{SciDepartmentMessageBundle['contacts.type.label']}"
|
||||
name="type"
|
||||
options="#{SciDepartmentContactTypes}"
|
||||
/>
|
||||
</librecms:assetPicker>
|
||||
<button class="btn btn-secondary contacts-save-order-button"
|
||||
disabled="disable"
|
||||
type="button">
|
||||
<span class="save-icon">
|
||||
<bootstrap:svgIcon icon="save" />
|
||||
</span>
|
||||
<span class="save-spinner d-none">
|
||||
<span aria-hidden="true"
|
||||
class="spinner-border spinner-border-sm"
|
||||
role="status"></span>
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['contacts.order.save.inprogress']}</span>
|
||||
</span>
|
||||
<span>#{SciDepartmentMessageBundle['contacts.order.save']}</span>
|
||||
</button>
|
||||
<c:choose>
|
||||
<c:when test="#{SciDepartmentDescriptionContacts.contacts.isEmpty()}">
|
||||
<p>#{SciDepartmentMessageBundle['contacts.none']}</p>
|
||||
</c:when>
|
||||
<c:otherwise>
|
||||
<table id="scidepartment-contacts-table"
|
||||
data-saveUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description-contacts/save-order">
|
||||
<thead>
|
||||
<tr>
|
||||
<th scope="col">#{SciDepartmentMessageBundle['contacts.cols.contactable']}</th>
|
||||
<th scope="col">#{SciDepartmentMessageBundle['contacts.cols.type']}</th>
|
||||
<th colspan="2"
|
||||
scope="col"
|
||||
>#{SciDepartmentMessageBundle['contacts.cols.actions']}</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<c:forEach items="#{SciDepartmentDescriptionContacts.contacts}"
|
||||
var="contact">
|
||||
<tr class="scidepartment-contact"
|
||||
id="#{contact.contactId}"
|
||||
data-id="#{contact.contactId}">
|
||||
<td>
|
||||
<c:if test="#{CmsSelectedDocumentModel.canEdit}">
|
||||
<button class="btn btn-secondary cms-sort-handle mr-2"
|
||||
type="button">
|
||||
<bootstrap:svgIcon icon="arrows-move" />
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['contacts.move.button']}</span>
|
||||
</button>
|
||||
</c:if>
|
||||
#{contact.contactable}
|
||||
</td>
|
||||
<td>#{contact.contactType}</td>
|
||||
<td>
|
||||
<button class="btn btn-secondary"
|
||||
data-toggle="modal"
|
||||
data-target="#contact-edit-dialog-#{contact.contactId}"
|
||||
type="button">
|
||||
<bootstrap:svgIcon icon="pen" />
|
||||
<span>#{SciDepartmentMessageBundle['contacts.edit.label']}</span>
|
||||
</button>
|
||||
<div aria-hidden="true"
|
||||
aria-labelledby="contact-edit-dialog-#{contact.contactId}-title"
|
||||
class="modal fade"
|
||||
id="contact-edit-dialog-#{contact.contactId}"
|
||||
tabindex="-1">
|
||||
<div class="modal-dialog">
|
||||
<form action="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/contacts/edit/#{contact.contactId}"
|
||||
method="post">
|
||||
<div class="modal-header">
|
||||
<h4 class="modal-title"
|
||||
id="contact-edit-dialog-#{contact.contactId}-title">
|
||||
#{SciDepartmentMessageBundle['contacts.edit.title']}
|
||||
</h4>
|
||||
<button
|
||||
aria-label="#{SciDepartmentMessageBundle['contacts.edit.cancel']}"
|
||||
class="close"
|
||||
data-dismiss="modal"
|
||||
type="button">
|
||||
<bootstrap:svgIcon icon="x"/>
|
||||
</button>
|
||||
</div>
|
||||
<div class="modal-body">
|
||||
<bootstrap:formGroupSelect
|
||||
help="#{SciDepartmentMessageBundle['contacts.edit.type.help']}"
|
||||
inputId="type-edit"
|
||||
label="#{SciDepartmentMessageBundle['contacts.edit.type.label']}"
|
||||
name="type"
|
||||
options="#{SciDepartmentContactTypes}"
|
||||
selectedOptions="#{[contact.contactType]}"
|
||||
/>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button class="btn btn-warning"
|
||||
data-dismiss="modal"
|
||||
type="button">
|
||||
#{SciDepartmentMessageBundle['contacts.edit.cancel']}
|
||||
</button>
|
||||
<button class="btn btn-success"
|
||||
type="submit">
|
||||
#{SciDepartmentMessageBundle['contacts.edit.submit']}
|
||||
</button>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
<td>
|
||||
<libreccm:deleteDialog
|
||||
actionTarget="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/contacts/#{contact.contactId}/remove"
|
||||
buttonText="#{SciDepartmentMessageBundle['contacts.delete.label']}"
|
||||
cancelLabel="#{SciDepartmentMessageBundle['contacts.delete.cancel']}"
|
||||
confirmLabel="#{SciDepartmentMessageBundle['contacts.delete.confirm']}"
|
||||
dialogId="contact-delete-dialog-#{contact.contactId}"
|
||||
dialogTitle="#{SciDepartmentMessageBundle['contacts.delete.title']}"
|
||||
message="#{SciDepartmentMessageBundle.getMessage('contacts.delete.message', [contact.contactable, contact.contactType])}"
|
||||
|
||||
/>
|
||||
</td>
|
||||
</tr>
|
||||
</c:forEach>
|
||||
</tbody>
|
||||
</table>
|
||||
</c:otherwise>
|
||||
</c:choose>
|
||||
|
||||
<h3>#{SciDepartmentMessageBundle['memberships.header']}</h3>
|
||||
<div class="mb-2">
|
||||
<div class="text-right">
|
||||
<librecms:assetPickerButton
|
||||
assetPickerId="members-picker"
|
||||
buttonIcon="plus-circle"
|
||||
buttonText="#{SciDepartmentMessageBundle['memberships.add_button.label']}"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<librecms:assetPicker
|
||||
actionUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/members/add"
|
||||
assetPickerId="members-picker"
|
||||
assetType="#{SciDepartmentDescriptionMembers.memberType}"
|
||||
baseUrl="#{SciDepartmentDescriptionContacts.baseUrl}"
|
||||
contentSection="#{ContentSectionModel.sectionName}"
|
||||
dialogTitle="#{SciDepartmentMessageBundle['memberships.add.title']}"
|
||||
formParamName="personUuid">
|
||||
|
||||
<bootstrap:formGroupSelect
|
||||
help="#{SciDepartmentMessageBundle['memberships.role.help']}"
|
||||
inputId="type"
|
||||
label="#{SciDepartmentMessageBundle['memberships.role.label']}"
|
||||
name="role"
|
||||
options="#{SciDepartmentRoles}"
|
||||
/>
|
||||
|
||||
<bootstrap:formGroupSelect
|
||||
help="#{SciDepartmentMessageBundle['memberships.status.help']}"
|
||||
inputId="status"
|
||||
label="#{SciDepartmentMessageBundle['memberships.status.label']}"
|
||||
name="status"
|
||||
options="#{SciDepartmentDescriptionMembers.statusValues}"
|
||||
/>
|
||||
|
||||
</librecms:assetPicker>
|
||||
<c:choose>
|
||||
<c:when test="#{SciDepartmentDescriptionMembers.members.isEmpty()}">
|
||||
<p>#{SciDepartmentMessageBundle['memberships.none']}</p>
|
||||
</c:when>
|
||||
<c:otherwise>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th scope="col">#{SciDepartmentMessageBundle['memberships.cols.name']}</th>
|
||||
<th scope="col">#{SciDepartmentMessageBundle['memberships.cols.role']}</th>
|
||||
<th scope="col">#{SciDepartmentMessageBundle['memberships.cols.status']}</th>
|
||||
<th colspan="2"
|
||||
scope="col">#{SciDepartmentMessageBundle['memberships.cols.actions']}</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody id="members-list">
|
||||
<c:forEach items="#{SciDepartmentDescriptionMembers.members}"
|
||||
var="member">
|
||||
<tr>
|
||||
<td>
|
||||
#{member.name}
|
||||
</td>
|
||||
<td>
|
||||
#{SciDepartmentRoles[member.role]}
|
||||
</td>
|
||||
<td>
|
||||
#{member.status}
|
||||
</td>
|
||||
<td>
|
||||
<button class="btn btn-secondary"
|
||||
data-toggle="modal"
|
||||
data-target="#membership-edit-dialog"
|
||||
type="button">
|
||||
<bootstrap:svgIcon icon="pen"/>
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['memberships.edit.label']}</span>
|
||||
</button>
|
||||
<div aria-hidden="true"
|
||||
aria-labelledby="membership-edit-dialog-title"
|
||||
class="modal fade"
|
||||
id="membership-edit-dialog"
|
||||
tabindex="-1">
|
||||
<div class="modal-dialog">
|
||||
<form action="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/members/edit/#{member.membershipId}"
|
||||
class="modal-content"
|
||||
method="post">
|
||||
<div class="modal-header">
|
||||
<h4 class="modal-title"
|
||||
id="membership-edit-dialog-title">
|
||||
</h4>
|
||||
<button
|
||||
aria-label="#{SciDepartmentMessageBundle['memberships.edit.cancel']}"
|
||||
class="close"
|
||||
data-dismiss="modal"
|
||||
type="button">
|
||||
<bootstrap:svgIcon icon="x"/>
|
||||
</button>
|
||||
</div>
|
||||
<div class="modal-body">
|
||||
<bootstrap:formGroupSelect
|
||||
help="#{SciDepartmentMessageBundle['memberships.edit.role.help']}"
|
||||
inputId="role"
|
||||
label="#{SciDepartmentMessageBundle['memberships.edit.role.label']}"
|
||||
name="role"
|
||||
options="#{SciDepartmentRoles}"
|
||||
selectedOptions="#{[member.role]}"
|
||||
/>
|
||||
|
||||
<bootstrap:formGroupSelect
|
||||
help="#{SciDepartmentMessageBundle['memberships.edit.status.help']}"
|
||||
inputId="status"
|
||||
label="#{SciDepartmentMessageBundle['memberships.edit.status.label']}"
|
||||
name="status"
|
||||
options="#{SciDepartmentDescriptionMembers.statusValues}"
|
||||
selectedOptions="#{[member.status]}"
|
||||
/>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button class="btn btn-warning"
|
||||
data-dismiss="modal"
|
||||
type="button">
|
||||
#{SciDepartmentMessageBundle['members.edit.cancel']}
|
||||
</button>
|
||||
<button class="btn btn-success"
|
||||
type="submit">
|
||||
#{SciDepartmentMessageBundle['members.edit.submit']}
|
||||
</button>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
<td>
|
||||
<libreccm:deleteDialog
|
||||
actionTarget="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/members/remove/#{member.membershipId}"
|
||||
buttonText="#{SciDepartmentMessageBundle['>memberships.delete.label']}"
|
||||
cancelLabel="#{SciDepartmentMessageBundle['memberships.delete.cancel']}"
|
||||
confirmLabel="#{SciDepartmentMessageBundle['memberships.delete.confirm']}"
|
||||
dialogId="membership-delete-dialog"
|
||||
dialogTitle="#{SciDepartmentMessageBundle['memberships.delete.title']}"
|
||||
message="#{SciDepartmentMessageBundle.getMessage('memberships.delete.message', [member.name])}"
|
||||
/>
|
||||
</td>
|
||||
</tr>
|
||||
</c:forEach>
|
||||
</tbody>
|
||||
</table>
|
||||
</c:otherwise>
|
||||
</c:choose>
|
||||
|
||||
<h3>
|
||||
#{SciDepartmentMessageBundle['texts.header']}
|
||||
<button class="btn btn-secondary"
|
||||
data-toggle="modal"
|
||||
data-target="#department-text-add-dialog"
|
||||
type="button">
|
||||
<bootstrap:svgIcon icon="plus-circle" />
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['texts.add.label']}</span>
|
||||
</button>
|
||||
<div aria-hidden="true"
|
||||
aria-labelledby="department-text-add-dialog-title"
|
||||
class="modal fade"
|
||||
id="department-text-add-dialog"
|
||||
tabindex="-1">
|
||||
<div class="modal-dialog">
|
||||
<form action="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/texts/add"
|
||||
method="post">
|
||||
<div class="modal-header">
|
||||
<h4 class="modal-title"
|
||||
id="department-text-add-dialog-title">
|
||||
#{SciDepartmentMessageBundle['texts.add.dialog.title']}
|
||||
</h4>
|
||||
<button aria-label="#{SciDepartmentMessageBundle['texts.add.cancel']}"
|
||||
class="close"
|
||||
data-dismiss="modal"
|
||||
type="button">
|
||||
<bootstrap:svgIcon icon="x" />
|
||||
</button>
|
||||
</div>
|
||||
<div class="modal-body">
|
||||
<bootstrap:formGroupSelect
|
||||
help="#{SciDepartmentMessageBundle['texts.add.key.help']}"
|
||||
inputId="text-key"
|
||||
label="#{SciDepartmentMessageBundle['texts.add.key.label']}"
|
||||
name="textKey"
|
||||
options="#{SciDepartmentTextsModel.availableTextKeys}"
|
||||
/>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button class="btn btn-warning"
|
||||
data-dismiss="modal"
|
||||
type="button">
|
||||
#{SciDepartmentMessageBundle['texts.add.cancel']}
|
||||
</button>
|
||||
<button class="btn btn-success"
|
||||
type="submit">
|
||||
#{SciDepartmentMessageBundle['texts.add.submit']}
|
||||
</button>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</h3>
|
||||
<c:choose>
|
||||
<c:when test="#{SciDepartmentTextsModel.texts.isEmpty()}">
|
||||
<p>#{SciDepartmentMessageBundle['texts.none']}</p>
|
||||
</c:when>
|
||||
<c:otherwise>
|
||||
<c:forEach items="#{SciDepartmentTextsModel.texts.entrySet()}"
|
||||
var="text">
|
||||
<h4>
|
||||
#{SciDepartmentTexts[text.key]}
|
||||
<libreccm:deleteDialog
|
||||
actionTarget="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/texts/remove/#{text.key}"
|
||||
buttonText="#{SciDepartmentMessageBundle['texts.delete.label']}"
|
||||
cancelLabel="#{SciDepartmentMessageBundle['texts.delete.cancel']}"
|
||||
confirmLabel="#{SciDepartmentMessageBundle['texts.delete.confirm']}"
|
||||
dialogId="text-#{text.key}-delete-dialog"
|
||||
dialogTitle="#{SciDepartmentMessageBundle['texts.delete.title']}"
|
||||
message="#{SciDepartmentMessageBundle.getMessage('texts.delete.message', [text.key])}"
|
||||
/>
|
||||
</h4>
|
||||
<librecms:cmsEditorVariants
|
||||
addButtonLabel="#{SciDepartmentMessageBundle['texts.editor.add_variant']}"
|
||||
addDialogLocaleSelectHelp="#{SciDepartmentMessageBundle['texts.editor.add.locale.help']}"
|
||||
addMethod="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/texts/add/#{text.eky}"
|
||||
canEdit="#{SciDepartmentDescriptionModel.canEdit}"
|
||||
editorPageUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/texts/edit/#{text.key}"
|
||||
hasUnusedLocales="#{text.value.unusedLocales.isEmpty()}"
|
||||
headingLevel="5"
|
||||
removeMethod="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidpartment-description-texts/remove/#{text.key}"
|
||||
sourceEditorPageUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidpartment-description-texts/edit-source/#{text.key}"
|
||||
title="#{SciDepartmentMessageBundle.getMessage('texts.editor.header', [text.key])}"
|
||||
unusedLocales="#{text.value.unusedLocales}"
|
||||
variants="#{text.value.variants}"
|
||||
variantsId="text-#{text.key}"
|
||||
viewPageUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidpartment-description-texts/view/#{text.key}"
|
||||
/>
|
||||
</c:forEach>
|
||||
</c:otherwise>
|
||||
</c:choose>
|
||||
|
||||
</ui:define>
|
||||
|
||||
<ui:define name="scripts">
|
||||
<script src="#{request.contextPath}/assets/@scidepartment/scidepartment-contacts.js" />
|
||||
</ui:define>
|
||||
|
||||
</ui:composition>
|
||||
</html>
|
||||
|
|
@ -0,0 +1,40 @@
|
|||
<!DOCTYPE html [<!ENTITY times '×'>]>
|
||||
<html xmlns="http://www.w3.org/1999/xhtml"
|
||||
xmlns:bootstrap="http://xmlns.jcp.org/jsf/composite/components/bootstrap"
|
||||
xmlns:c="http://xmlns.jcp.org/jsp/jstl/core"
|
||||
xmlns:libreccm="http://xmlns.jcp.org/jsf/composite/components/libreccm"
|
||||
xmlns:librecms="http://xmlns.jcp.org/jsf/composite/components/librecms"
|
||||
xmlns:ui="http://xmlns.jcp.org/jsf/facelets">
|
||||
<ui:composition template="/WEB-INF/views/org/librecms/ui/contentsection/documents/authoringstep.xhtml">
|
||||
|
||||
<ui:define name="authoringStep">
|
||||
<div class="d-flex">
|
||||
<a class="btn btn-secondary btn-sm align-self-center mr-2"
|
||||
href="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description">
|
||||
<bootstrap:svgIcon icon="caret-left-fill" />
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['description_step.back']}</span>
|
||||
</a>
|
||||
|
||||
<h2>#{SciDepartmentMessageBundle.getMessage('description_step.text.header.edit', [SciDepartmentTextsModel.selectedText])}</h2>
|
||||
</div>
|
||||
|
||||
<c:if test="#{SciDepartmentDescriptionModel.canEdit}">
|
||||
<librecms:cmsEditor
|
||||
backUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description"
|
||||
baseUrl="#{mvc.basePath}"
|
||||
canEdit="#{SciDepartmentDescriptionModel.canEdit}"
|
||||
contentSection="#{ContentSectionModel.sectionName}"
|
||||
editMethod="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-description/texts/edit/#{SciDepartmentTextsModel.selectedText}"
|
||||
editorId="scidepartment-texts-editor"
|
||||
objectIdentifier="#{CmsSelectedDocumentModel.itemPath}"
|
||||
selectedLocale="#{SciDepartmentTextsModel.selectedLocale}"
|
||||
title="#{SciDepartmentMessageBundle['texts.editor.header']}"
|
||||
variantUrl="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@scidepartment-texts-resources/department-texts"
|
||||
/>
|
||||
</c:if>
|
||||
|
||||
</ui:define>
|
||||
|
||||
</ui:composition>
|
||||
</html>
|
||||
|
||||
|
|
@ -0,0 +1,37 @@
|
|||
<!DOCTYPE html [<!ENTITY times '×'>]>
|
||||
<html xmlns="http://www.w3.org/1999/xhtml"
|
||||
xmlns:bootstrap="http://xmlns.jcp.org/jsf/composite/components/bootstrap"
|
||||
xmlns:c="http://xmlns.jcp.org/jsp/jstl/core"
|
||||
xmlns:h="http://xmlns.jcp.org/jsf/html"
|
||||
xmlns:libreccm="http://xmlns.jcp.org/jsf/composite/components/libreccm"
|
||||
xmlns:ui="http://xmlns.jcp.org/jsf/facelets">
|
||||
<ui:composition template="/WEB-INF/views/org/librecms/ui/contentsection/documents/authoringstep.xhtml">
|
||||
|
||||
<ui:define name="authoringStep">
|
||||
<div class="d-flex">
|
||||
<a class="btn btn-secondary btn-sm align-self-center mr-2"
|
||||
href="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemName}/@department-description">
|
||||
<bootstrap:svgIcon icon="caret-left-fill" />
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['description_step.back']}</span>
|
||||
</a>
|
||||
|
||||
<h2>#{SciDepartmentMessageBundle.getMessage('description_step.texts.header.view', [SciDepartmentTextsModel.selectedText])}</h2>
|
||||
</div>
|
||||
|
||||
<c:if test="#{SciDepartmentDescriptionModel.canEdit}">
|
||||
<div class="text-right">
|
||||
<a class="btn btn-secondary"
|
||||
href="#{mvc.basePath}/#{ContentSectionModel.sectionName}/documents/#{CmsSelectedDocumentModel.itemPath}/@sciproject-description/texts/edit/#{SciDepartmentTextsModel.selectedText}">
|
||||
<bootstrap:svgIcon icon="pen" />
|
||||
<span class="sr-only">#{SciDepartmentMessageBundle['description_step.edit']}</span>
|
||||
</a>
|
||||
</div>
|
||||
</c:if>
|
||||
<div class="cms-text-preview article-text border p-2">
|
||||
<h:outputText escape="false"
|
||||
value="#{SciDepartmentTextsModel.texts.get(SciDepartmentTextsModel.selectedText).get(SciDepartmentTextsModel.selectedLocale)}" />
|
||||
</div>
|
||||
</ui:define>
|
||||
|
||||
</ui:composition>
|
||||
</html>
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
|
||||
member=Member
|
||||
head=Department head
|
||||
deputy_head=Deputy department head
|
||||
associated_member=Associated member
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
|
||||
member=Mitglied
|
||||
head=Abteilungsleitung
|
||||
deputy_head=Stellvertretende Abteilungsleitung
|
||||
associated_member=Assoziertes Mitglied
|
||||
|
|
@ -65,3 +65,81 @@ basicproperties.shortdescription.remove.submit=Remove
|
|||
basicproperties.shortdescription.remove.text=Are you sure to remove this localized short description?
|
||||
basicproperties.shortdescription.remove.header=Confirm removal of localized short description
|
||||
basicproperties.shortdescription.header=Short description
|
||||
description_step.header=Department Description
|
||||
description_step.errors.contactable_not_found=The selected contactable entity {0} was not found.
|
||||
description_step.errors.person_not_found=The selected person was not found.
|
||||
description_step.errors.illegal_member_status_value=Illegal member status.
|
||||
contacts.sort.errors.general=Error while sorting contacts.
|
||||
contacts.sort.errors.save=Error while saving contact order.
|
||||
description.editor.add_variant=Add localized description
|
||||
description.editor.add.locale.help=The locale of the localized description.
|
||||
description.editor.header=Description
|
||||
contacts.header=Contacts
|
||||
contacts.add_button.label=Add contact
|
||||
contact.add.title=Add contact
|
||||
contacts.type.help=The type of the contact.
|
||||
contacts.type.label=Type
|
||||
contacts.order.save.inprogress=Saving contacts order...
|
||||
contacts.none=No contacts have been added yet.
|
||||
contacts.cols.contactable=Contact
|
||||
contacts.cols.type=Type
|
||||
contacts.cols.actions=Actions
|
||||
contacts.move.button=Move
|
||||
contacts.edit.label=Edit
|
||||
contacts.edit.title=Edit contact
|
||||
contacts.edit.cancel=Cancel
|
||||
contacts.edit.type.help=The type of the contact.
|
||||
contacts.edit.type.label=Type
|
||||
contacts.edit.submit=Save
|
||||
contacts.delete.label=Remove
|
||||
contacts.delete.cancel=Cancel
|
||||
contacts.delete.confirm=Remove
|
||||
contacts.delete.title=Confirm Removeal of Contact
|
||||
contacts.delete.message=Are you sure to remove the contact {0} with type {1}?
|
||||
memberships.header=Members
|
||||
memberships.add_button.label=Add member
|
||||
memberships.add.title=Add member
|
||||
memberships.role.help=The role of the member.
|
||||
memberships.role.label=Role
|
||||
memberships.status.help=The status of the member.
|
||||
memberships.status.label=Status
|
||||
memberships.none=No member have been added yet.
|
||||
memberships.cols.name=Name
|
||||
memberships.cols.role=Role
|
||||
memberships.cols.status=Status
|
||||
memberships.cols.actions=Actions
|
||||
memberships.edit.label=Edit
|
||||
memberships.edit.cancel=Cancel
|
||||
memberships.edit.role.help=The role of the member.
|
||||
memberships.edit.role.label=Role
|
||||
memberships.edit.status.help=The status of the member.
|
||||
memberships.edit.status.label=Status
|
||||
members.edit.cancel=Cancel
|
||||
members.edit.submit=Save
|
||||
memberships.delete.label=Remove
|
||||
memberships.delete.cancel=Cancel
|
||||
memberships.delete.confirm=Remove
|
||||
memberships.delete.title=Confirm Removal of Member
|
||||
memberships.delete.message=Are you sure to remove the member {0}?
|
||||
texts.header=Additional texts
|
||||
texts.add.label=Add text
|
||||
texts.add.dialog.title=Add text
|
||||
texts.add.cancel=Cancel
|
||||
texts.add.key.help=The identifier of the text.
|
||||
texts.add.key.label=Identifier
|
||||
texts.add.submit=Add text
|
||||
texts.none=No texts have been added yet.
|
||||
texts.delete.label=Remove text
|
||||
texts.delete.cancel=Cancel
|
||||
texts.delete.confirm=Remove text
|
||||
texts.delete.title=Confirm Removal of Text
|
||||
texts.delete.message=Are you sure to remove the text {0}?
|
||||
texts.editor.add_variant=Add localization
|
||||
texts.editor.add.locale.help=The locale of the localized text.
|
||||
texts.editor.header=Edit text {0}
|
||||
description_step.back=Back
|
||||
description_step.description.header.edit=Edit description
|
||||
description_step.text.header.edit=Edit text {0}
|
||||
description_step.texts.header.view=View text {0}
|
||||
description_step.edit=Edit
|
||||
description_step.description.header.view=Description
|
||||
|
|
|
|||
|
|
@ -65,3 +65,81 @@ basicproperties.shortdescription.remove.submit=Entfernen
|
|||
basicproperties.shortdescription.remove.text=Sind Sie sicher, dass Sie diese lokaliserte Kurzbeschreibung entfernen wollen?
|
||||
basicproperties.shortdescription.remove.header=Entfernen einer lokalisierten Kurzbeschreibung best\u00e4tigen
|
||||
basicproperties.shortdescription.header=Kurzbeschreibung
|
||||
description_step.header=Beschreibung der Abteilung
|
||||
description_step.errors.contactable_not_found=Die ausgew\u00e4hlte Person oder Organisation {0} konnte nicht gefunden werden.
|
||||
description_step.errors.person_not_found=Die ausgew\u00e4hlte Person konnte nicht gefunden werden.
|
||||
description_step.errors.illegal_member_status_value=Fehlerhafter Status f\u00fcr Mitglied.
|
||||
contacts.sort.errors.general=Fehler beim Sortieren der Kontakte.
|
||||
contacts.sort.errors.save=Die Sortierung der Kontakte konnte nicht gespeichert werden.
|
||||
description.editor.add_variant=Lokalisierte Beschreibung hinzuf\u00fcgen
|
||||
description.editor.add.locale.help=Die Sprache der lokalisierten Beschreibung.
|
||||
description.editor.header=Beschreibung
|
||||
contacts.header=Kontakte
|
||||
contacts.add_button.label=Kontakt hinzuf\u00fcgen
|
||||
contact.add.title=Kontakt hinzuf\u00fcgen
|
||||
contacts.type.help=Der Typ des Kontakts.
|
||||
contacts.type.label=Typ
|
||||
contacts.order.save.inprogress=Speichere Sortierung der Kontakte...
|
||||
contacts.none=Es wurden noch keine Kontakte hinzugef\u00fcgt.
|
||||
contacts.cols.contactable=Kontakt
|
||||
contacts.cols.type=Typ
|
||||
contacts.cols.actions=Aktionen
|
||||
contacts.move.button=Verschieben
|
||||
contacts.edit.label=Bearbeiten
|
||||
contacts.edit.title=Kontakt bearbeiten
|
||||
contacts.edit.cancel=Abbrechen
|
||||
contacts.edit.type.help=Der Typ des Kontakts.
|
||||
contacts.edit.type.label=Typ
|
||||
contacts.edit.submit=Speichern
|
||||
contacts.delete.label=Entfernen
|
||||
contacts.delete.cancel=Abbrechen
|
||||
contacts.delete.confirm=Entfernen
|
||||
contacts.delete.title=Entfernen des Kontaktes best\u00e4tigen
|
||||
contacts.delete.message=Sind Sie sicher das Sie den Kontakt {0} (Typ: {1}) entfernen wollen?
|
||||
memberships.header=Mitglieder
|
||||
memberships.add_button.label=Mitglied hinzuf\u00fcgen
|
||||
memberships.add.title=Mitglied hinzuf\u00fcgen
|
||||
memberships.role.help=Die Rolle des Mitglieds.
|
||||
memberships.role.label=Rolle
|
||||
memberships.status.help=Der Status des Mitglieds.
|
||||
memberships.status.label=Status
|
||||
memberships.none=Es wurden noch keine Mitglieder hinzugef\u00fcgt.
|
||||
memberships.cols.name=Name
|
||||
memberships.cols.role=Rolle
|
||||
memberships.cols.status=Status
|
||||
memberships.cols.actions=Aktionen
|
||||
memberships.edit.label=Bearbeiten
|
||||
memberships.edit.cancel=Abbrechen
|
||||
memberships.edit.role.help=Die Rolle des Mitglieds.
|
||||
memberships.edit.role.label=Rolle
|
||||
memberships.edit.status.help=Der Status des Mitglieds.
|
||||
memberships.edit.status.label=Status
|
||||
members.edit.cancel=Abbrechen
|
||||
members.edit.submit=Speichern
|
||||
memberships.delete.label=Entfernen
|
||||
memberships.delete.cancel=Abbrechen
|
||||
memberships.delete.confirm=Entfernen
|
||||
memberships.delete.title=Entfernen des Mitglieds best\u00e4tigen
|
||||
memberships.delete.message=Sind Sie sicher, dass Sie das Mitglied {0} entfernen wollen?
|
||||
texts.header=Weitere Texte
|
||||
texts.add.label=Text hinzuf\u00fcgen
|
||||
texts.add.dialog.title=Text hinzuf\u00fcgen
|
||||
texts.add.cancel=Abbrechen
|
||||
texts.add.key.help=Bezeichner des Textes.
|
||||
texts.add.key.label=Bezeichner
|
||||
texts.add.submit=Text hinzuf\u00fcgen
|
||||
texts.none=Es wurden noch keine Texte hinzugef\u00fcgt.
|
||||
texts.delete.label=Text entfernen
|
||||
texts.delete.cancel=Abbrechen
|
||||
texts.delete.confirm=Text entfernen
|
||||
texts.delete.title=Entfernen des Textes best\u00e4tigen
|
||||
texts.delete.message=Sind Sie sicher, dass Sie den Text {0} entfernen wollen?
|
||||
texts.editor.add_variant=\u00dcbersetzung hinzuf\u00fcgen
|
||||
texts.editor.add.locale.help=Die Sprache der \u00dcbersetzung.
|
||||
texts.editor.header=Text {0} bearbeiten
|
||||
description_step.back=Zur\u00fcck
|
||||
description_step.description.header.edit=Beschreibung bearbeiten
|
||||
description_step.text.header.edit=Text {0} bearbeiten
|
||||
description_step.texts.header.view=Text {0}
|
||||
description_step.edit=Bearbeiten
|
||||
description_step.description.header.view=Beschreibung
|
||||
|
|
|
|||
|
|
@ -0,0 +1,152 @@
|
|||
import Sortable, { SortableEvent } from "sortablejs";
|
||||
|
||||
let contactsSortable: Sortable;
|
||||
|
||||
document.addEventListener("DOMContentLoaded", function (event) {
|
||||
const contactsTable = document.querySelector(
|
||||
"#scidepartment-contacts-table tbody"
|
||||
);
|
||||
|
||||
if (contactsTable) {
|
||||
contactsSortable = initContactsTable(contactsTable as HTMLElement);
|
||||
}
|
||||
|
||||
const saveOrderButtons = document.querySelectorAll(
|
||||
".contacts-save-order-button"
|
||||
);
|
||||
for (let i = 0; i < saveOrderButtons.length; i++) {
|
||||
saveOrderButtons[i].addEventListener("click", saveOrder);
|
||||
}
|
||||
});
|
||||
|
||||
function initContactsTable(contactsTable: HTMLElement): Sortable {
|
||||
return new Sortable(contactsTable, {
|
||||
animation: 150,
|
||||
group: "scidepartment-contact",
|
||||
handle: ".cms-sort-handle",
|
||||
onEnd: enableSaveButton,
|
||||
});
|
||||
}
|
||||
|
||||
function enableSaveButton(event: SortableEvent) {
|
||||
const saveOrderButtons = document.querySelectorAll(
|
||||
".contacts-save-order-button"
|
||||
);
|
||||
for (let i = 0; i < saveOrderButtons.length; i++) {
|
||||
const saveOrderButton: HTMLButtonElement = saveOrderButtons[
|
||||
i
|
||||
] as HTMLButtonElement;
|
||||
saveOrderButton.disabled = false;
|
||||
}
|
||||
}
|
||||
|
||||
function saveOrder() {
|
||||
const contactsTable = document.querySelector("#scidepartment-contacts-table");
|
||||
|
||||
if (!contactsTable) {
|
||||
showGeneralError();
|
||||
throw Error("scidepartment-contacts-table not found");
|
||||
}
|
||||
|
||||
const saveUrl = contactsTable.getAttribute("data-saveUrl");
|
||||
if (!saveUrl) {
|
||||
showGeneralError();
|
||||
throw Error(
|
||||
"data-saveUrl on scidepartment-contacts-table container is missing or empty"
|
||||
);
|
||||
}
|
||||
|
||||
const saveOrderButtons = document.querySelectorAll(
|
||||
".contacts-save-order-button"
|
||||
);
|
||||
for (let i = 0; i < saveOrderButtons.length; i++) {
|
||||
const saveOrderButton: HTMLButtonElement = saveOrderButtons[
|
||||
i
|
||||
] as HTMLButtonElement;
|
||||
saveOrderButton.disabled = true;
|
||||
const saveIcon = saveOrderButton.querySelector(".save-icon");
|
||||
const spinner = saveOrderButton.querySelector(".save-spinner");
|
||||
saveIcon?.classList.toggle("d-none");
|
||||
spinner?.classList.toggle("d-none");
|
||||
}
|
||||
|
||||
const headers = new Headers();
|
||||
headers.append("Content-Type", "application/json");
|
||||
fetch(saveUrl, {
|
||||
credentials: "include",
|
||||
body: JSON.stringify(contactsSortable.toArray()),
|
||||
headers,
|
||||
method: "POST",
|
||||
})
|
||||
.then((response) => {
|
||||
if (response.ok) {
|
||||
for (let i = 0; i < saveOrderButtons.length; i++) {
|
||||
const saveOrderButton: HTMLButtonElement = saveOrderButtons[
|
||||
i
|
||||
] as HTMLButtonElement;
|
||||
const saveIcon =
|
||||
saveOrderButton.querySelector(".save-icon");
|
||||
const spinner =
|
||||
saveOrderButton.querySelector(".save-spinner");
|
||||
saveIcon?.classList.toggle("d-none");
|
||||
spinner?.classList.toggle("d-none");
|
||||
}
|
||||
} else {
|
||||
showSaveError();
|
||||
for (let i = 0; i < saveOrderButtons.length; i++) {
|
||||
const saveOrderButton: HTMLButtonElement = saveOrderButtons[
|
||||
i
|
||||
] as HTMLButtonElement;
|
||||
saveOrderButton.disabled = false;
|
||||
const saveIcon =
|
||||
saveOrderButton.querySelector(".save-icon");
|
||||
const spinner =
|
||||
saveOrderButton.querySelector(".save-spinner");
|
||||
saveIcon?.classList.toggle("d-none");
|
||||
spinner?.classList.toggle("d-none");
|
||||
}
|
||||
throw Error(
|
||||
`Failed to save contacts order. Response status: ${response.status}, statusText: ${response.statusText}`
|
||||
);
|
||||
}
|
||||
})
|
||||
.catch((error) => {
|
||||
showSaveError();
|
||||
for (let i = 0; i < saveOrderButtons.length; i++) {
|
||||
const saveOrderButton: HTMLButtonElement = saveOrderButtons[
|
||||
i
|
||||
] as HTMLButtonElement;
|
||||
saveOrderButton.disabled = false;
|
||||
const saveIcon = saveOrderButton.querySelector(".save-icon");
|
||||
const spinner = saveOrderButton.querySelector(".save-spinner");
|
||||
saveIcon?.classList.toggle("d-none");
|
||||
spinner?.classList.toggle("d-none");
|
||||
}
|
||||
throw new Error(`Failed to save contacts order: ${error}`);
|
||||
});
|
||||
}
|
||||
|
||||
function showGeneralError(): void {
|
||||
const alertTemplate = document.querySelector(
|
||||
"#scidepartment-contacts-sort-error-general"
|
||||
) as HTMLTemplateElement;
|
||||
const alert = alertTemplate.content.cloneNode(true) as Element;
|
||||
|
||||
const container = document.querySelector("#messages");
|
||||
if (container) {
|
||||
container.appendChild(alert);
|
||||
}
|
||||
}
|
||||
|
||||
function showSaveError(): void {
|
||||
const alertTemplate = document.querySelector(
|
||||
"#scidepartment-contacts-sort-error-save"
|
||||
) as HTMLTemplateElement;
|
||||
const alert = alertTemplate.content.cloneNode(true) as Element;
|
||||
|
||||
const container = document.querySelector("#messages");
|
||||
if (container) {
|
||||
container.appendChild(alert);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -0,0 +1,20 @@
|
|||
{
|
||||
"compilerOptions": {
|
||||
"allowSyntheticDefaultImports": true,
|
||||
"declaration": true,
|
||||
"lib": [
|
||||
"DOM",
|
||||
"ES2016"
|
||||
],
|
||||
"module": "commonjs",
|
||||
"moduleResolution": "node",
|
||||
"outDir": "target/generated-resources/assets/@scidepartment",
|
||||
"sourceMap": true,
|
||||
"strict": true,
|
||||
"target": "ES6"
|
||||
},
|
||||
"include": [
|
||||
"src/main/typescript/**/*"
|
||||
]
|
||||
}
|
||||
|
||||
|
|
@ -0,0 +1,23 @@
|
|||
module.exports = {
|
||||
mode: "development",
|
||||
devtool: "source-map",
|
||||
optimization: {
|
||||
chunkIds: false
|
||||
},
|
||||
entry: {
|
||||
"scidepartment-contacts": "./src/main/typescript/scidepartment-contacts.ts"
|
||||
},
|
||||
output: {
|
||||
filename: "[name].js",
|
||||
path: __dirname + "/target/generated-resources/assets/@scidepartment"
|
||||
},
|
||||
resolve: {
|
||||
extensions: [".tsx", ".ts", ".js", ".json"]
|
||||
},
|
||||
module: {
|
||||
rules: [
|
||||
// all files with a '.ts' or '.tsx' extension will be handled by 'ts-loader'
|
||||
{ test: /\.tsx?$/, use: ["ts-loader"], exclude: /node_modules/ }
|
||||
]
|
||||
}
|
||||
}
|
||||
Loading…
Reference in New Issue