diff --git a/src/main/java/org/olat/course/assessment/bulk/BulkAssessmentOverviewController.java b/src/main/java/org/olat/course/assessment/bulk/BulkAssessmentOverviewController.java index eed01634d787f97100b2734b3865ad8b53d173e5..e17beede64f42b0bfb54ce20d65950bd1746dffa 100644 --- a/src/main/java/org/olat/course/assessment/bulk/BulkAssessmentOverviewController.java +++ b/src/main/java/org/olat/course/assessment/bulk/BulkAssessmentOverviewController.java @@ -270,6 +270,7 @@ public class BulkAssessmentOverviewController extends FormBasicController { AssessableCourseNode courseNode = data.getCourseNode(); final Task editableTask = taskManager.pickTaskForEdition(data.getTask()); + editedTask = editableTask; if(editableTask == null) { showWarning("task.edited"); } else { diff --git a/src/main/java/org/olat/course/assessment/bulk/BulkAssessment_2_DatasStep.java b/src/main/java/org/olat/course/assessment/bulk/BulkAssessment_2_DatasStep.java index db1206b100cfb2c33c8dc6a9b89984c8442f1335..7ee64f8fdc7d0b210d8bb8693efc8fb4c09196b0 100644 --- a/src/main/java/org/olat/course/assessment/bulk/BulkAssessment_2_DatasStep.java +++ b/src/main/java/org/olat/course/assessment/bulk/BulkAssessment_2_DatasStep.java @@ -41,6 +41,7 @@ public class BulkAssessment_2_DatasStep extends BasicStep { private final Task task; private final BulkAssessmentDatas datas; private final AssessableCourseNode courseNode; + private boolean hasPreviousStep = true; public BulkAssessment_2_DatasStep(UserRequest ureq) { this(ureq, null, null, null); @@ -48,6 +49,7 @@ public class BulkAssessment_2_DatasStep extends BasicStep { public BulkAssessment_2_DatasStep(UserRequest ureq, AssessableCourseNode courseNode) { this(ureq, courseNode, null, null); + hasPreviousStep = false; } /** @@ -64,11 +66,12 @@ public class BulkAssessment_2_DatasStep extends BasicStep { this.courseNode = courseNode; setI18nTitleAndDescr("data.title", "data.title"); setNextStep(new BulkAssessment_3_ValidationStep(ureq)); + hasPreviousStep = false; } @Override public PrevNextFinishConfig getInitialPrevNextFinishConfig() { - return new PrevNextFinishConfig(true, true, false); + return new PrevNextFinishConfig(hasPreviousStep, true, false); } @Override diff --git a/src/main/java/org/olat/course/assessment/bulk/DataStepForm.java b/src/main/java/org/olat/course/assessment/bulk/DataStepForm.java index ac2bea728a710351cbf3201fe491d9ca924a909e..40415b26dbefec5b95098551f6890dcccacc2600 100644 --- a/src/main/java/org/olat/course/assessment/bulk/DataStepForm.java +++ b/src/main/java/org/olat/course/assessment/bulk/DataStepForm.java @@ -60,8 +60,8 @@ import org.olat.core.util.vfs.VFSLeaf; import org.olat.core.util.vfs.VFSManager; import org.olat.course.assessment.model.BulkAssessmentDatas; import org.olat.course.assessment.model.BulkAssessmentRow; +import org.olat.course.assessment.model.BulkAssessmentSettings; import org.olat.course.nodes.AssessableCourseNode; -import org.olat.course.nodes.TACourseNode; /** * @@ -91,7 +91,7 @@ public class DataStepForm extends StepFormBasicController { public DataStepForm(UserRequest ureq, WindowControl wControl, AssessableCourseNode courseNode, BulkAssessmentDatas datas, StepsRunContext runContext, Form rootForm) { - super(ureq, wControl, rootForm, runContext, LAYOUT_DEFAULT, null); + super(ureq, wControl, rootForm, runContext, LAYOUT_VERTICAL, null); this.datas = datas; this.courseNode = courseNode; @@ -123,10 +123,18 @@ public class DataStepForm extends StepFormBasicController { String[] values = new String[] {translate("form.step3.delimiter.tab"),translate("form.step3.delimiter.comma")}; delimiter = uifactory.addRadiosVertical("delimiter", "form.step3.delimiter", formLayout, keys, values); - delimiter.select("tab", true); - - if(courseNode instanceof TACourseNode) { - //return files + // preset delimiter type to first appearance of either tab or comma when data is available, default to tab for no data + int firstComma = dataVal.indexOf(","); + int firstTab = dataVal.indexOf("\t"); + if (firstComma > -1 && (firstTab == -1 || firstTab > firstComma )) { + delimiter.select("comma", true); + } else { + delimiter.select("tab", true); + } + + BulkAssessmentSettings settings = new BulkAssessmentSettings(courseNode); + // return files only when configured + if(settings.isHasReturnFiles()) { returnFileEl = uifactory.addFileElement("returnfiles", "return.files", formLayout); Set<String> mimes = new HashSet<String>(); mimes.add(WebappHelper.getMimeType("file.zip")); @@ -136,7 +144,7 @@ public class DataStepForm extends StepFormBasicController { if(targetArchive.exists()) { returnFileEl.setInitialFile(targetArchive.getBasefile()); } - } + } } } @@ -344,17 +352,15 @@ public class DataStepForm extends StepFormBasicController { if(valuesLength > 1) { String scoreStr = values[1]; Float score; - if("".equals(scoreStr)) { - score = null; - } else if("\"\"".equals(scoreStr) || "''".equals(scoreStr)) { - score = new Float(0.0f); - } else if (StringHelper.containsNonWhitespace(scoreStr)) { + if (StringHelper.containsNonWhitespace(scoreStr)) { try { - score = Float.parseFloat(scoreStr); + // accept writing with , or . + score = Float.parseFloat(scoreStr.replace(',', '.')); } catch (NumberFormatException e) { score = null; } } else { + // only set new numbers, ignore everything else score = null; } row.setScore(score); @@ -363,15 +369,20 @@ public class DataStepForm extends StepFormBasicController { if(valuesLength > 2) { String passedStr = values[2]; Boolean passed; - if("\"\"".equals(passedStr) || "''".equals(passedStr)) { - passed = Boolean.FALSE; - } else if("y".equalsIgnoreCase(passedStr) || "yes".equalsIgnoreCase(passedStr) - || "true".equalsIgnoreCase(passedStr) || "1".equalsIgnoreCase(passedStr)) { + if ("y".equalsIgnoreCase(passedStr) + || "yes".equalsIgnoreCase(passedStr) + || "passed".equalsIgnoreCase(passedStr) + || "true".equalsIgnoreCase(passedStr) + || "1".equalsIgnoreCase(passedStr)) { passed = Boolean.TRUE; - } else if("n".equalsIgnoreCase(passedStr) || "no".equalsIgnoreCase(passedStr) - || "false".equalsIgnoreCase(passedStr) || "0".equalsIgnoreCase(passedStr)) { + } else if ("n".equalsIgnoreCase(passedStr) + || "no".equalsIgnoreCase(passedStr) + || "false".equalsIgnoreCase(passedStr) + || "failed".equalsIgnoreCase(passedStr) + || "0".equalsIgnoreCase(passedStr)) { passed = Boolean.FALSE; } else { + // only set defined values, ignore everything else passed = null; } row.setPassed(passed); @@ -380,12 +391,13 @@ public class DataStepForm extends StepFormBasicController { if(valuesLength > 3) { String commentStr = values[3]; if(commentStr.isEmpty()) { + // ignore empty values row.setComment(null); } else if("\"\"".equals(commentStr) || "''".equals(commentStr)) { row.setComment(""); } else { row.setComment(commentStr); - } + } } return row; diff --git a/src/main/java/org/olat/course/assessment/bulk/TaskData.java b/src/main/java/org/olat/course/assessment/bulk/TaskData.java index 40441b4162f03e80f2aa8ca0f8a4866a7443654f..f93ed4753a1a90bddad62a6fd5611eccb15c1e46 100644 --- a/src/main/java/org/olat/course/assessment/bulk/TaskData.java +++ b/src/main/java/org/olat/course/assessment/bulk/TaskData.java @@ -47,7 +47,7 @@ public class TaskData { this.ownerFullName = ownerFullName; hasScore = runnable.getSettings().isHasScore(); - hasPassed = runnable.getSettings().isHasPassed(); + hasPassed = runnable.getSettings().isHasPassed() && runnable.getSettings().getCut() == null; hasUserComment = runnable.getSettings().isHasUserComment(); hasReturnFiles = runnable.getSettings().isHasReturnFiles(); numOfAssessedIds = runnable.getDatas().getRowsSize(); diff --git a/src/main/java/org/olat/course/assessment/bulk/ValidationStepForm.java b/src/main/java/org/olat/course/assessment/bulk/ValidationStepForm.java index 692b4804ca41e97b14b13d86a7a623a2870377e9..fad90ad2a32af379f622454150d7cba296bbc43c 100644 --- a/src/main/java/org/olat/course/assessment/bulk/ValidationStepForm.java +++ b/src/main/java/org/olat/course/assessment/bulk/ValidationStepForm.java @@ -84,9 +84,15 @@ public class ValidationStepForm extends StepFormBasicController { tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.identifier", Cols.identifier.ordinal())); tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.lastName", Cols.lastName.ordinal())); tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.firstName", Cols.firstName.ordinal())); - tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.score", Cols.score.ordinal(), new ScoreCellRenderer(settings))); - tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.passed", Cols.passed.ordinal(), new PassedCellRenderer())); - tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.comment", Cols.comment.ordinal())); + if(settings.isHasScore()) { + tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.score", Cols.score.ordinal(), new ScoreCellRenderer(settings))); + } + if(settings.isHasPassed() && settings.getCut() == null) { + tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.passed", Cols.passed.ordinal(), new PassedCellRenderer())); + } + if(settings.isHasUserComment()) { + tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.comment", Cols.comment.ordinal())); + } if(settings.isHasReturnFiles()) { tableColumnModel.addFlexiColumnModel(new DefaultFlexiColumnModel("table.header.numOfReturnFiles", Cols.numOfReturnFiles.ordinal())); } @@ -98,6 +104,8 @@ public class ValidationStepForm extends StepFormBasicController { invalidModel = new ValidDataModel(Collections.<UserData>emptyList()); invalidModel.setTableColumnModel(tableColumnModel); invalidTableEl = uifactory.addTableElement(ureq, getWindowControl(), "notFoundList", invalidModel, formLayout); + + flc.contextPut("settings", settings); } @Override diff --git a/src/main/java/org/olat/course/assessment/bulk/_content/validation.html b/src/main/java/org/olat/course/assessment/bulk/_content/validation.html index 3f8c1f166f0278a0184324adf1caaa809be586e8..34f1f84c9cc7e03b287217ea7c12e32972c1fe6e 100644 --- a/src/main/java/org/olat/course/assessment/bulk/_content/validation.html +++ b/src/main/java/org/olat/course/assessment/bulk/_content/validation.html @@ -3,6 +3,37 @@ $r.translate("validation.error") </p> #else + <fieldset> + <legend> + $r.translate("validation.features.title") + </legend> + <p> + $r.translate("validation.features") + </p> + <ul> + #if($settings.isHasScore()) + <li>$r.translate("table.header.score")</li> + #end + #if($settings.isHasPassed() && !$settings.getCut()) + <li> + $r.translate("table.header.passed") + </li> + #end + #if($settings.isHasUserComment()) + <li>$r.translate("table.header.comment")</li> + #end + #if($settings.isHasReturnFiles()) + <li>$r.translate("table.header.returnFiles")</li> + #end + </ul> + #if($settings.isHasPassed() && $settings.getCut()) + <p> + $r.translate("validation.passed.cut", "$settings.getCut()") + </p> + #end + + </fieldset> + #if ($hasValidItems) <fieldset> <legend>$r.translate("validation.ok.title")</legend> diff --git a/src/main/java/org/olat/course/assessment/bulk/_i18n/LocalStrings_de.properties b/src/main/java/org/olat/course/assessment/bulk/_i18n/LocalStrings_de.properties index ed0e953ba3be62404e36ea57a5e1bfd02805ba95..42f558f89bd7676f6bba85f862740265ebdf2a9c 100644 --- a/src/main/java/org/olat/course/assessment/bulk/_i18n/LocalStrings_de.properties +++ b/src/main/java/org/olat/course/assessment/bulk/_i18n/LocalStrings_de.properties @@ -66,6 +66,9 @@ validation.error=Es wurden keine Bewertungsdaten gefunden. Das Datenformat ist e validation.ok.title=Überprüfung erfolgreich validation.nok.title=Überprüfung fehlgeschlagen validation.nok.desc=Bei den folgenden Einträgen wurden Fehler entdeckt (z.B. Benutzer existiert nicht). Sie werden bei der Ausführung ignoriert. +validation.features.title=Konfiguration Kursbaustein +validation.features=Die folgende Bewertungsfunktionen sind beim gewählten Kursbaustein konfiguiert. Andere Daten die in den Bewertungsdaten enthalten sind werden ignoriert. +validation.passed.cut=Auf diesem Baustein wird die Bestanden Information automatisch über Punkteschwelle {0} berechnet. Es ist daher ist kein Import der Bestanden Information möglich. confirmation.mail.subject=Geplante Massenbewertung {0} {1} ausgeführt confirmation.mail.body=Ihre Massenbewertung des Kursbausteins {1} im Kurs {0} wurde wie geplant für {3} Benutzer am {4} ausgeführt.\n\n{2} diff --git a/src/main/java/org/olat/course/assessment/bulk/_i18n/LocalStrings_en.properties b/src/main/java/org/olat/course/assessment/bulk/_i18n/LocalStrings_en.properties index f9f8870bfd9aea6e3396c4a75e69dbe50bd3b5a4..589eb5cdbbb6a007e8416344b81316d99b1a53df 100644 --- a/src/main/java/org/olat/course/assessment/bulk/_i18n/LocalStrings_en.properties +++ b/src/main/java/org/olat/course/assessment/bulk/_i18n/LocalStrings_en.properties @@ -69,5 +69,8 @@ validation.error=No assessment data has been found. Either the file format is wr validation.ok.title=Validation of data successful validation.nok.title=Validation of data failed validation.nok.desc=The following entries contain errors (e.g. user does not exist). They will be ignored during execution. +validation.features.title=Configuration course element +validation.features=The following assessment features are configured for the selected course element. Other data contained in the bulk assessment will be ignored. +validation.passed.cut=For this course element the passed information is calculated using the cut value {}. Import for passed information is not possible. help.hover.bulkassessment=Help for bulk assessment diff --git a/src/main/java/org/olat/course/assessment/model/BulkAssessmentSettings.java b/src/main/java/org/olat/course/assessment/model/BulkAssessmentSettings.java index 91d18b02bc50bad328f0c630b61e77d84f9977d8..c681dcd79add7b4786e596df18b5ba3f450069b9 100644 --- a/src/main/java/org/olat/course/assessment/model/BulkAssessmentSettings.java +++ b/src/main/java/org/olat/course/assessment/model/BulkAssessmentSettings.java @@ -45,7 +45,13 @@ public class BulkAssessmentSettings implements Serializable { hasUserComment = courseNode.hasCommentConfigured(); hasScore = courseNode.hasScoreConfigured(); hasPassed = courseNode.hasPassedConfigured(); - hasReturnFiles = (courseNode instanceof TACourseNode); + + if (courseNode instanceof TACourseNode) { + Boolean hasReturnBox = (Boolean)courseNode.getModuleConfiguration().get(TACourseNode.CONF_RETURNBOX_ENABLED); + hasReturnFiles = hasReturnBox.booleanValue(); + } else { + hasReturnFiles = false; + } if (hasScore) { min = courseNode.getMinScoreConfiguration();