From 31e2804b820eae7c19313c97e51c6e9859c5bb76 Mon Sep 17 00:00:00 2001 From: srosse <none@none> Date: Thu, 29 Aug 2013 10:57:23 +0200 Subject: [PATCH] OO-691: allow essay in test with a lot of warnings and messages --- .../course/nodes/iq/IQEditController.java | 29 +++++++++- .../nodes/iq/_i18n/LocalStrings_de.properties | 3 +- .../nodes/iq/_i18n/LocalStrings_en.properties | 1 + .../ims/qti/QTI12ResultDetailsController.java | 31 ++++++++++- .../org/olat/ims/qti/_content/qtires.html | 3 ++ .../ims/qti/_i18n/LocalStrings_de.properties | 1 + .../ims/qti/_i18n/LocalStrings_en.properties | 1 + .../olat/ims/qti/container/ItemContext.java | 4 ++ .../org/olat/ims/qti/container/Variables.java | 10 ++-- .../ims/qti/editor/ChoiceItemController.java | 16 +++--- .../ims/qti/editor/EssayItemController.java | 16 +++++- .../editor/ItemMetadataFormController.java | 9 ++-- .../editor/ItemNodeTabbedFormController.java | 5 +- .../olat/ims/qti/editor/QTIEditHelper.java | 4 +- .../qti/editor/QTIEditorMainController.java | 54 +++++++++++++------ .../olat/ims/qti/editor/_content/index.html | 3 ++ .../qti/editor/_content/tab_essayItem.html | 5 ++ .../editor/_i18n/LocalStrings_de.properties | 3 ++ .../editor/_i18n/LocalStrings_en.properties | 3 ++ .../editor/beecom/objects/ChoiceQuestion.java | 2 +- .../editor/beecom/objects/EssayQuestion.java | 21 +++++++- .../beecom/objects/OutcomesProcessing.java | 5 +- .../qti/editor/tree/QTIEditorTreeModel.java | 4 +- 23 files changed, 187 insertions(+), 46 deletions(-) diff --git a/src/main/java/org/olat/course/nodes/iq/IQEditController.java b/src/main/java/org/olat/course/nodes/iq/IQEditController.java index 19342beb76a..1f588601b1b 100644 --- a/src/main/java/org/olat/course/nodes/iq/IQEditController.java +++ b/src/main/java/org/olat/course/nodes/iq/IQEditController.java @@ -81,6 +81,11 @@ import org.olat.course.tree.CourseInternalLinkTreeModel; import org.olat.fileresource.FileResourceManager; import org.olat.ims.qti.QTIResult; import org.olat.ims.qti.QTIResultManager; +import org.olat.ims.qti.editor.QTIEditorPackage; +import org.olat.ims.qti.editor.QTIEditorPackageImpl; +import org.olat.ims.qti.editor.beecom.objects.Assessment; +import org.olat.ims.qti.editor.beecom.objects.Item; +import org.olat.ims.qti.editor.beecom.objects.Section; import org.olat.ims.qti.fileresource.SurveyFileResource; import org.olat.ims.qti.fileresource.TestFileResource; import org.olat.ims.qti.process.AssessmentInstance; @@ -566,6 +571,7 @@ public class IQEditController extends ActivateableTabbableDefaultController impl /** * @see org.olat.core.gui.control.DefaultController#event(org.olat.core.gui.UserRequest, org.olat.core.gui.control.Controller, org.olat.core.gui.control.Event) */ + @Override public void event(UserRequest urequest, Controller source, Event event) { if (source.equals(searchController)) { if (event == ReferencableEntriesSearchController.EVENT_REPOSITORY_ENTRY_SELECTED) { @@ -573,7 +579,8 @@ public class IQEditController extends ActivateableTabbableDefaultController impl cmc.deactivate(); RepositoryEntry re = searchController.getSelectedEntry(); doIQReference(urequest, re); - this.updateEditController(urequest); + updateEditController(urequest); + checkEssay(re); } } else if (source == accessibilityCondContr) { if (event == Event.CHANGED_EVENT) { @@ -629,6 +636,26 @@ public class IQEditController extends ActivateableTabbableDefaultController impl } } + private void checkEssay(RepositoryEntry re) { + TestFileResource fr = new TestFileResource(); + fr.overrideResourceableId(re.getOlatResource().getResourceableId()); + QTIEditorPackage qtiPackage = new QTIEditorPackageImpl(getIdentity(), fr, getTranslator()); + Assessment ass = qtiPackage.getQTIDocument().getAssessment(); + + //Sections with their Items + List<Section> sections = ass.getSections(); + for (Section section:sections) { + List<Item> items = section.getItems(); + for (Item item:items) { + String ident = item.getIdent(); + if(ident != null && ident.startsWith("QTIEDIT:ESSAY")) { + showWarning("warning.test.with.essay"); + break; + } + } + } + } + private void doModOnyxConfigForm(IQEditForm modConfigForm) { String qtiType = null; if (moduleConfiguration.get(IQEditController.CONFIG_KEY_TYPE_QTI) != null) { diff --git a/src/main/java/org/olat/course/nodes/iq/_i18n/LocalStrings_de.properties b/src/main/java/org/olat/course/nodes/iq/_i18n/LocalStrings_de.properties index 12d4b747331..33764945283 100644 --- a/src/main/java/org/olat/course/nodes/iq/_i18n/LocalStrings_de.properties +++ b/src/main/java/org/olat/course/nodes/iq/_i18n/LocalStrings_de.properties @@ -230,4 +230,5 @@ command.editRepFile = Editieren help.select.file.test=Hilfe zur Auswahl eines Tests help.select.file.self=Hilfe zur Auswahl eines Selbsttests -help.select.file.surv=Hilfe zur Auswahl eines Fragebogens \ No newline at end of file +help.select.file.surv=Hilfe zur Auswahl eines Fragebogens +warning.test.with.essay=$org.olat.ims.qti.editor\:warning.test.with.essay \ No newline at end of file diff --git a/src/main/java/org/olat/course/nodes/iq/_i18n/LocalStrings_en.properties b/src/main/java/org/olat/course/nodes/iq/_i18n/LocalStrings_en.properties index f898075a970..a7ccf50ff17 100644 --- a/src/main/java/org/olat/course/nodes/iq/_i18n/LocalStrings_en.properties +++ b/src/main/java/org/olat/course/nodes/iq/_i18n/LocalStrings_en.properties @@ -196,3 +196,4 @@ showResults.detailed=Results showResults.title=Results showResults.visibility=Your results will be displayed from "{0}" until "{1}" start=Start +warning.test.with.essay=$org.olat.ims.qti.editor\:warning.test.with.essay diff --git a/src/main/java/org/olat/ims/qti/QTI12ResultDetailsController.java b/src/main/java/org/olat/ims/qti/QTI12ResultDetailsController.java index c858187128c..5c83a3e578a 100644 --- a/src/main/java/org/olat/ims/qti/QTI12ResultDetailsController.java +++ b/src/main/java/org/olat/ims/qti/QTI12ResultDetailsController.java @@ -53,6 +53,12 @@ import org.olat.course.nodes.AssessableCourseNode; import org.olat.course.run.scoring.ScoreEvaluation; import org.olat.course.run.userview.UserCourseEnvironment; import org.olat.ims.qti.container.AssessmentContext; +import org.olat.ims.qti.editor.QTIEditorPackage; +import org.olat.ims.qti.editor.QTIEditorPackageImpl; +import org.olat.ims.qti.editor.beecom.objects.Assessment; +import org.olat.ims.qti.editor.beecom.objects.Item; +import org.olat.ims.qti.editor.beecom.objects.Section; +import org.olat.ims.qti.fileresource.TestFileResource; import org.olat.ims.qti.process.AssessmentFactory; import org.olat.ims.qti.process.AssessmentInstance; import org.olat.ims.qti.process.FilePersister; @@ -110,14 +116,37 @@ public class QTI12ResultDetailsController extends BasicController { String resourcePath = courseResourceableId + File.separator + nodeIdent; qtiPersister = new FilePersister(assessedIdentity, resourcePath); - + init(ureq); } + private boolean checkEssay() { + TestFileResource fr = new TestFileResource(); + fr.overrideResourceableId(repositoryEntry.getOlatResource().getResourceableId()); + QTIEditorPackage qtiPackage = new QTIEditorPackageImpl(getIdentity(), fr, getTranslator()); + Assessment ass = qtiPackage.getQTIDocument().getAssessment(); + + //Sections with their Items + List<Section> sections = ass.getSections(); + for (Section section:sections) { + List<Item> items = section.getItems(); + for (Item item:items) { + String ident = item.getIdent(); + if(ident != null && ident.startsWith("QTIEDIT:ESSAY")) { + return true; + } + } + } + return false; + } + private void init(UserRequest ureq) { main = createVelocityContainer("qtires"); details = createVelocityContainer("qtires_details"); + boolean hasEssay = checkEssay(); + main.contextPut("warningEssay", new Boolean(hasEssay)); + TableGuiConfiguration tableConfig = new TableGuiConfiguration(); tableCtr = new TableController(tableConfig, ureq, getWindowControl(), getTranslator()); tableCtr.addColumnDescriptor(new DefaultColumnDescriptor("column.header.date", 0, null, ureq.getLocale())); diff --git a/src/main/java/org/olat/ims/qti/_content/qtires.html b/src/main/java/org/olat/ims/qti/_content/qtires.html index 62644395557..91d1faed4c6 100644 --- a/src/main/java/org/olat/ims/qti/_content/qtires.html +++ b/src/main/java/org/olat/ims/qti/_content/qtires.html @@ -1 +1,4 @@ +#if($warningEssay) + <div class="b_warning">$r.translate("warning.test.with.essay")</div> +#end $r.render("qtirestable") diff --git a/src/main/java/org/olat/ims/qti/_i18n/LocalStrings_de.properties b/src/main/java/org/olat/ims/qti/_i18n/LocalStrings_de.properties index 3de4cc7c03d..d488fa5b925 100644 --- a/src/main/java/org/olat/ims/qti/_i18n/LocalStrings_de.properties +++ b/src/main/java/org/olat/ims/qti/_i18n/LocalStrings_de.properties @@ -68,3 +68,4 @@ score.val=Erreichte Punktzahl sec=Sektion secs=Sekunden time=Zeit +warning.test.with.essay=$org.olat.ims.qti.editor\:warning.test.with.essay diff --git a/src/main/java/org/olat/ims/qti/_i18n/LocalStrings_en.properties b/src/main/java/org/olat/ims/qti/_i18n/LocalStrings_en.properties index c9c7993e7da..50c2678201e 100644 --- a/src/main/java/org/olat/ims/qti/_i18n/LocalStrings_en.properties +++ b/src/main/java/org/olat/ims/qti/_i18n/LocalStrings_en.properties @@ -65,3 +65,4 @@ score.val=Achieved score sec=Section secs=Seconds time=Time +warning.test.with.essay=$org.olat.ims.qti.editor\:warning.test.with.essay diff --git a/src/main/java/org/olat/ims/qti/container/ItemContext.java b/src/main/java/org/olat/ims/qti/container/ItemContext.java index d82ebcc83c8..2a72e44b262 100644 --- a/src/main/java/org/olat/ims/qti/container/ItemContext.java +++ b/src/main/java/org/olat/ims/qti/container/ItemContext.java @@ -409,6 +409,10 @@ public class ItemContext implements Serializable { public float getScore() { Variable var = getVariables().getSCOREVariable(); if (var == null) { + if(ident.startsWith("QTIEDIT:ESSAY")) { + return 0.0f; + } + // we demand that a SCORE variable must always exist throw new RuntimeException("no SCORE def for " + getIdent()); } else { diff --git a/src/main/java/org/olat/ims/qti/container/Variables.java b/src/main/java/org/olat/ims/qti/container/Variables.java index a48d53e402e..bdf0b20f35a 100644 --- a/src/main/java/org/olat/ims/qti/container/Variables.java +++ b/src/main/java/org/olat/ims/qti/container/Variables.java @@ -32,16 +32,18 @@ import java.util.Map; /** */ public class Variables implements Serializable{ - Map vars; + + private static final long serialVersionUID = 4599004441875604671L; + private final Map<String,Variable> vars; public Variables() { super(); - vars = new HashMap(3); + vars = new HashMap<String,Variable>(3); } public Variable getVariable(String varName) { - return (Variable)vars.get(varName); + return vars.get(varName); } public Variable getSCOREVariable() { @@ -60,7 +62,7 @@ public class Variables implements Serializable{ vars.put(var.getVarName(),var); } - + @Override public String toString() { return vars.toString()+"="+super.toString(); } diff --git a/src/main/java/org/olat/ims/qti/editor/ChoiceItemController.java b/src/main/java/org/olat/ims/qti/editor/ChoiceItemController.java index b6931087359..d0f37769d76 100644 --- a/src/main/java/org/olat/ims/qti/editor/ChoiceItemController.java +++ b/src/main/java/org/olat/ims/qti/editor/ChoiceItemController.java @@ -108,14 +108,14 @@ public class ChoiceItemController extends DefaultController implements Controlle if (sPosid != null) posid = Integer.parseInt(sPosid); if (cmd.equals("up")) { if (posid > 0) { - List elements = item.getQuestion().getResponses(); - Object obj = elements.remove(posid); + List<Response> elements = item.getQuestion().getResponses(); + Response obj = elements.remove(posid); elements.add(posid - 1, obj); } } else if (cmd.equals("down")) { - List elements = item.getQuestion().getResponses(); + List<Response> elements = item.getQuestion().getResponses(); if (posid < elements.size() - 1) { - Object obj = elements.remove(posid); + Response obj = elements.remove(posid); elements.add(posid + 1, obj); } } else if (cmd.equals("editq")) { @@ -129,7 +129,7 @@ public class ChoiceItemController extends DefaultController implements Controlle } else if (cmd.equals("addchoice")) { ChoiceQuestion question = (ChoiceQuestion) item.getQuestion(); - List choices = question.getResponses(); + List<Response> choices = question.getResponses(); ChoiceResponse newChoice = new ChoiceResponse(); newChoice.getContent().add(new Mattext(trnsltr.translate("newresponsetext"))); newChoice.setCorrect(false); @@ -142,7 +142,7 @@ public class ChoiceItemController extends DefaultController implements Controlle getWindowControl().pushAsModalDialog( delYesNoCtrl.getInitialComponent()); } else if (cmd.equals("ssc")) { // submit sc ChoiceQuestion question = (ChoiceQuestion) item.getQuestion(); - List q_choices = question.getResponses(); + List<Response> q_choices = question.getResponses(); String correctChoice = ureq.getParameter("correctChoice"); for (int i = 0; i < q_choices.size(); i++) { ChoiceResponse choice = (ChoiceResponse) q_choices.get(i); @@ -169,7 +169,7 @@ public class ChoiceItemController extends DefaultController implements Controlle } else if (cmd.equals("smc")) { // submit mc ChoiceQuestion question = (ChoiceQuestion) item.getQuestion(); - List choices = question.getResponses(); + List<Response> choices = question.getResponses(); boolean hasZeroPointChoice = false; for (int i = 0; i < choices.size(); i++) { ChoiceResponse choice = (ChoiceResponse) choices.get(i); @@ -201,7 +201,7 @@ public class ChoiceItemController extends DefaultController implements Controlle // invalid input, set maxValue 0 } ChoiceQuestion question = (ChoiceQuestion) item.getQuestion(); - List q_choices = question.getResponses(); + List<Response> q_choices = question.getResponses(); for (int i = 0; i < q_choices.size(); i++) { String correctChoice = ureq.getParameter("correctChoice_q" + i); ChoiceResponse choice = (ChoiceResponse) q_choices.get(i); diff --git a/src/main/java/org/olat/ims/qti/editor/EssayItemController.java b/src/main/java/org/olat/ims/qti/editor/EssayItemController.java index 87673329a05..a4dd74647f1 100644 --- a/src/main/java/org/olat/ims/qti/editor/EssayItemController.java +++ b/src/main/java/org/olat/ims/qti/editor/EssayItemController.java @@ -35,7 +35,6 @@ import org.olat.core.gui.control.Event; import org.olat.core.gui.control.WindowControl; import org.olat.core.gui.control.generic.closablewrapper.CloseableModalController; import org.olat.core.gui.translator.Translator; -import org.olat.core.util.Formatter; import org.olat.core.util.Util; import org.olat.ims.qti.editor.beecom.objects.EssayQuestion; import org.olat.ims.qti.editor.beecom.objects.Item; @@ -82,6 +81,8 @@ public class EssayItemController extends DefaultController implements Controller main.contextPut("response", essayQuestion.getEssayResponse()); main.contextPut("mediaBaseURL", qtiPackage.getMediaBaseURL()); main.contextPut("isRestrictedEdit", restrictedEdit ? Boolean.TRUE : Boolean.FALSE); + main.contextPut("isSurveyMode", qtiPackage.getQTIDocument().isSurvey() ? "true" : "false"); + setInitialComponent(main); } @@ -115,6 +116,19 @@ public class EssayItemController extends DefaultController implements Controller iRows = 5; getWindowControl().setWarning(trnsltr.translate("error.rows")); } + + + try { + String score = ureq.getParameter("single_score"); + float sc = Float.parseFloat(score); + if(sc <= 0.0001f) { + getWindowControl().setWarning(trnsltr.translate("editor.info.mc.zero.points")); + } + essayQuestion.setMinValue(0.0f); + essayQuestion.setMaxValue(sc); + } catch(Exception e) { + getWindowControl().setWarning(trnsltr.translate("editor.info.mc.zero.points")); + } if (restrictedEdit) { boolean hasChange = false; diff --git a/src/main/java/org/olat/ims/qti/editor/ItemMetadataFormController.java b/src/main/java/org/olat/ims/qti/editor/ItemMetadataFormController.java index 6466328a32d..79a295fd84e 100644 --- a/src/main/java/org/olat/ims/qti/editor/ItemMetadataFormController.java +++ b/src/main/java/org/olat/ims/qti/editor/ItemMetadataFormController.java @@ -166,14 +166,17 @@ public class ItemMetadataFormController extends FormBasicController { * org.olat.core.gui.control.Controller, org.olat.core.gui.UserRequest) */ protected void initForm(FormItemContainer formLayout, Controller listener, UserRequest ureq) { - this.setFormTitle("fieldset.legend.metadata"); + setFormTitle("fieldset.legend.metadata"); int t = item.getQuestion().getType(); + if(!isSurvey && t == Question.TYPE_ESSAY) { + setFormWarning("warning.essay.test"); + } if (isSurvey) { - this.setFormContextHelp("org.olat.ims.qti.editor", "qed-meta-surv-"+t+".html", "help.hover.qti-meta-"+t); + setFormContextHelp("org.olat.ims.qti.editor", "qed-meta-surv-"+t+".html", "help.hover.qti-meta-"+t); } else { - this.setFormContextHelp("org.olat.ims.qti.editor", "qed-meta-test-"+t+".html", "help.hover.qti-meta-"+t); + setFormContextHelp("org.olat.ims.qti.editor", "qed-meta-test-"+t+".html", "help.hover.qti-meta-"+t); } // Title diff --git a/src/main/java/org/olat/ims/qti/editor/ItemNodeTabbedFormController.java b/src/main/java/org/olat/ims/qti/editor/ItemNodeTabbedFormController.java index 92404558187..69045374942 100644 --- a/src/main/java/org/olat/ims/qti/editor/ItemNodeTabbedFormController.java +++ b/src/main/java/org/olat/ims/qti/editor/ItemNodeTabbedFormController.java @@ -60,7 +60,6 @@ public class ItemNodeTabbedFormController extends TabbableDefaultController { * @param wControl * @param trnsltr */ - @SuppressWarnings("unused") public ItemNodeTabbedFormController(Item item, QTIEditorPackage qtiPackage, UserRequest ureq, WindowControl wControl, Translator trnsltr, boolean restrictedEdit) { super(ureq, wControl); @@ -148,8 +147,8 @@ public class ItemNodeTabbedFormController extends TabbableDefaultController { } if (ctrl != null) { // if item was identified tabbedPane.addTab(translate("tab.question"), ctrl.getInitialComponent()); - this.listenTo(ctrl); - if (!isSurvey) { + listenTo(ctrl); + if (!isSurvey && questionType != Question.TYPE_ESSAY) { tabbedPane.addTab(translate("tab.feedback"), feedbackPanel); } Controller itemPreviewController = new ItemPreviewController(getWindowControl(), item, qtiPackage, getTranslator()); diff --git a/src/main/java/org/olat/ims/qti/editor/QTIEditHelper.java b/src/main/java/org/olat/ims/qti/editor/QTIEditHelper.java index 3519db6be06..9de4b52d1e2 100644 --- a/src/main/java/org/olat/ims/qti/editor/QTIEditHelper.java +++ b/src/main/java/org/olat/ims/qti/editor/QTIEditHelper.java @@ -460,8 +460,8 @@ public class QTIEditHelper { * @param response_labels * @return Map of choices. */ - public static List fetchChoices(List response_labels) { - List choices = new ArrayList(); + public static List<Response> fetchChoices(List response_labels) { + List<Response> choices = new ArrayList<Response>(); for (Iterator i = response_labels.iterator(); i.hasNext();) { ChoiceResponse choice = new ChoiceResponse(); Element response_label = (Element) i.next(); diff --git a/src/main/java/org/olat/ims/qti/editor/QTIEditorMainController.java b/src/main/java/org/olat/ims/qti/editor/QTIEditorMainController.java index afacd0e07ad..b42ce1fc9a9 100644 --- a/src/main/java/org/olat/ims/qti/editor/QTIEditorMainController.java +++ b/src/main/java/org/olat/ims/qti/editor/QTIEditorMainController.java @@ -25,6 +25,7 @@ package org.olat.ims.qti.editor; +import java.util.ArrayList; import java.util.Collection; import java.util.Date; import java.util.HashMap; @@ -75,6 +76,7 @@ import org.olat.core.util.mail.ContactList; import org.olat.core.util.mail.ContactMessage; import org.olat.core.util.memento.Memento; import org.olat.core.util.nodes.INode; +import org.olat.core.util.tree.TreeHelper; import org.olat.core.util.tree.TreeVisitor; import org.olat.core.util.tree.Visitor; import org.olat.core.util.vfs.VFSContainer; @@ -216,7 +218,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement private InsertItemTreeModel insertTreeModel; private LockResult lockEntry; private boolean restrictedEdit; - private Map history = null; + private Map<String, Memento> history = null; private String startedWithTitle; private List<ReferenceImpl> referencees; private ChangeMessageForm chngMsgFrom; @@ -274,6 +276,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement } // init(ureq); // initialize the gui + updateWarning(); } else { String fullName = userManager.getUserDisplayName(lockEntry.getOwner()); wControl.setWarning( getTranslator().translate("error.lock", new String[] { fullName, @@ -326,7 +329,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement } else { // start with a fresh history. Editor is resumed but no changes were made // so far. - history = new HashMap(); + history = new HashMap<String, Memento>(); } if (restrictedEdit) { @@ -337,7 +340,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement mainToolC.setEnabled(CMD_TOOLS_ADD_FIB, false); if (!qtiPackage.getQTIDocument().isSurvey()) mainToolC.setEnabled(CMD_TOOLS_ADD_KPRIM, false); - if (qtiPackage.getQTIDocument().isSurvey()) mainToolC.setEnabled(CMD_TOOLS_ADD_FREETEXT, false); + mainToolC.setEnabled(CMD_TOOLS_ADD_FREETEXT, false); } mainToolC.setEnabled(CMD_TOOLS_CHANGE_DELETE, false); mainToolC.setEnabled(CMD_TOOLS_CHANGE_MOVE, false); @@ -383,6 +386,23 @@ public class QTIEditorMainController extends MainLayoutBasicController implement columnLayoutCtr.hideCol2(true); } } + + private void updateWarning() { + boolean warningEssay = false; + if(!qtiPackage.getQTIDocument().isSurvey()) { + //check if the test contains some essay + List<TreeNode> flattedTree = new ArrayList<TreeNode>(); + TreeHelper.makeTreeFlat(menuTreeModel.getRootNode(), flattedTree); + for(TreeNode node:flattedTree) { + Object uo = node.getUserObject(); + if(uo instanceof String && ((String)uo).startsWith("QTIEDIT:ESSAY")) { + warningEssay = true; + break; + } + } + } + main.contextPut("warningEssay", new Boolean(warningEssay)); + } /** @@ -454,6 +474,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement parentTargetNode.insertQTIObjectAt(subject, targetPos); qtiPackage.serializeQTIDocument(); menuTree.setDirty(true); //force rerendering for ajax mode + updateWarning(); } } else if (source == copyTree) { // catch copy operations cmc.deactivate(); @@ -503,6 +524,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement menuTree.setSelectedNodeId(newNode.getIdent()); event(ureq, menuTree, new Event(MenuTree.COMMAND_TREENODE_CLICKED)); qtiPackage.serializeQTIDocument(); + updateWarning(); } } else if (source == insertTree) { // catch insert operations cmc.deactivate(); @@ -512,6 +534,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement TreeEvent te = (TreeEvent) event; if (te.getCommand().equals(TreeEvent.COMMAND_TREENODE_CLICKED)) { // insert doInsert(ureq, te.getNodeId(), insertTree.getUserObject()); + updateWarning(); } } else if (source == exitVC) { if (event.getCommand().equals(CMD_EXIT_SAVE)) { @@ -695,7 +718,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement } else if (CMD_TOOLS_ADD_QPOOL.equals(cmd)) { doSelectQItem(ureq); } else if (CMD_TOOLS_EXPORT_QPOOL.equals(cmd)) { - doExportQItem(ureq); + doExportQItem(); } else if (cmd.startsWith(CMD_TOOLS_ADD_PREFIX)) { // add new object // fetch new object GenericQtiNode insertObject = null; @@ -741,7 +764,8 @@ public class QTIEditorMainController extends MainLayoutBasicController implement if(deletableMediaFiles!=null && deletableMediaFiles.size()>0) { String msg = translate("delete.item.media", deletableMediaFiles.toString()); deleteMediaDialog = activateYesNoDialog(ureq, null, msg, deleteMediaDialog); - } + } + updateWarning(); } // cleanup controller removeAsListenerAndDispose(deleteDialog); @@ -811,7 +835,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement QTIChangeLogMessage clm = new QTIChangeLogMessage(changeLog, chngMsgFrom.hasInformLearners()); qtiPackage.commitChangelog(clm); StringBuilder traceMsg = new StringBuilder(chngMsgFrom.hasInformLearners() ? "Visible for ALL \n" : "Visible for GROUP only \n"); - Tracing.logAudit(traceMsg.append(changeLog).toString(), QTIEditorMainController.class); + logAudit(traceMsg.append(changeLog).toString(), null); // save, remove locks and tmp files saveAndExit(ureq); } @@ -896,6 +920,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement event(ureq, menuTree, new Event(MenuTree.COMMAND_TREENODE_CLICKED)); qtiPackage.serializeQTIDocument(); + updateWarning(); } private void doInsert(GenericQtiNode parentTargetNode, GenericQtiNode insertNode, int position) { @@ -926,7 +951,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement listenTo(cmc); } - private void doExportQItem(UserRequest ureq) { + private void doExportQItem() { GenericQtiNode selectedNode = menuTreeModel.getQtiNode(menuTree.getSelectedNodeId()); if(selectedNode instanceof ItemNode) { ItemNode itemNode = (ItemNode)selectedNode; @@ -1005,8 +1030,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement if (!qtiPackage.getQTIDocument().isSurvey()) tc.addLink(CMD_TOOLS_ADD_KPRIM, translate("tools.add.kprim"), CMD_TOOLS_ADD_KPRIM, "o_mi_qtikprim"); tc.addLink(CMD_TOOLS_ADD_FIB, translate("tools.add.cloze"), CMD_TOOLS_ADD_FIB, "o_mi_qtifib"); - if (qtiPackage.getQTIDocument().isSurvey()) tc.addLink(CMD_TOOLS_ADD_FREETEXT, translate("tools.add.freetext"), - CMD_TOOLS_ADD_FREETEXT, "o_mi_qtiessay"); + tc.addLink(CMD_TOOLS_ADD_FREETEXT, translate("tools.add.freetext"), CMD_TOOLS_ADD_FREETEXT, "o_mi_qtiessay"); // change tc.addHeader(translate("tools.change.header")); // change actions @@ -1059,8 +1083,8 @@ public class QTIEditorMainController extends MainLayoutBasicController implement StringBuilder result = new StringBuilder(); result.append(translate("qti.restricted.leading")); - for (Iterator iter = referencees.iterator(); iter.hasNext();) { - ReferenceImpl element = (ReferenceImpl) iter.next(); + for (Iterator<ReferenceImpl> iter = referencees.iterator(); iter.hasNext();) { + ReferenceImpl element = iter.next(); // FIXME:discuss:possible performance/cache problem if ("CourseModule".equals(element.getSource().getResourceableTypeName())) { ICourse course = CourseFactory.loadCourse(element.getSource().getResourceableId()); @@ -1154,7 +1178,7 @@ public class QTIEditorMainController extends MainLayoutBasicController implement Memento respMem = null; if (history.containsKey(key)) { // question changed! - questMem = (Memento) history.get(key); + questMem = history.get(key); hasChanges = true; } // if(!hasChanges){ @@ -1162,11 +1186,11 @@ public class QTIEditorMainController extends MainLayoutBasicController implement // new prefix for responses prefixKey += "/null/"; // list contains org.olat.ims.qti.editor.beecom.objects.Response - List responses = question != null ? question.getResponses() : null; + List<Response> responses = question != null ? question.getResponses() : null; if (responses != null && responses.size() > 0) { // check for changes in each response - for (Iterator iter = responses.iterator(); iter.hasNext();) { - Response resp = (Response) iter.next(); + for (Iterator<Response> iter = responses.iterator(); iter.hasNext();) { + Response resp = iter.next(); if (history.containsKey(prefixKey + resp.getIdent())) { // this response changed! Memento tmpMem = (Memento) history.get(prefixKey + resp.getIdent()); diff --git a/src/main/java/org/olat/ims/qti/editor/_content/index.html b/src/main/java/org/olat/ims/qti/editor/_content/index.html index 0e533d59dd6..38d3706ba70 100644 --- a/src/main/java/org/olat/ims/qti/editor/_content/index.html +++ b/src/main/java/org/olat/ims/qti/editor/_content/index.html @@ -1,2 +1,5 @@ <h4>$qtititle</h4> +#if($warningEssay) + <div class="b_warning">$r.translate("warning.test.with.essay")</div> +#end $r.render("tabbedPane") diff --git a/src/main/java/org/olat/ims/qti/editor/_content/tab_essayItem.html b/src/main/java/org/olat/ims/qti/editor/_content/tab_essayItem.html index 616d4ce6301..7d78c014301 100644 --- a/src/main/java/org/olat/ims/qti/editor/_content/tab_essayItem.html +++ b/src/main/java/org/olat/ims/qti/editor/_content/tab_essayItem.html @@ -58,6 +58,11 @@ </tbody> </table> <br><br> +#if($isSurveyMode.equals("false") && !$isRestrictedEdit) + $r.translate("score") + <input type="text" name="single_score" value="$question.getMaxValue()" size="4" onchange="return setFormDirty('ofo_tab_scitem')" onclick="return setFormDirty('ofo_tab_scitem')"/> + <br /> +#end <div class="b_button_group"><input type="submit" value="$r.translateInAttribute("submit")" class="b_button" name="olat_fosm" /></div> </form> </fieldset> diff --git a/src/main/java/org/olat/ims/qti/editor/_i18n/LocalStrings_de.properties b/src/main/java/org/olat/ims/qti/editor/_i18n/LocalStrings_de.properties index 3295c388fe0..6fd74557976 100644 --- a/src/main/java/org/olat/ims/qti/editor/_i18n/LocalStrings_de.properties +++ b/src/main/java/org/olat/ims/qti/editor/_i18n/LocalStrings_de.properties @@ -391,3 +391,6 @@ tools.tools.preview=Vorschau valuation_method=Bewertungsmethode valuation_method_multi=Punkte pro Antwort valuation_method_single=Alle korrekten Antworten +warning.essay.test=Diese Frage muss manuell bewertet werden. +warning.test.with.essay=Dieser enth?lt ein Freitext Frage. Die Freitext Fragen m?ssen manuell bewertet werden und der End Score manuell angepasst. + diff --git a/src/main/java/org/olat/ims/qti/editor/_i18n/LocalStrings_en.properties b/src/main/java/org/olat/ims/qti/editor/_i18n/LocalStrings_en.properties index b7d10faa5a1..cf6564468fc 100644 --- a/src/main/java/org/olat/ims/qti/editor/_i18n/LocalStrings_en.properties +++ b/src/main/java/org/olat/ims/qti/editor/_i18n/LocalStrings_en.properties @@ -340,3 +340,6 @@ tools.tools.preview=Preview valuation_method=Method of assessment valuation_method_multi=Score per answer valuation_method_single=All correct answers +warning.essay.test=This question muss be manually corrected. +warning.test.with.essay=This test contains question of type essay. The essay has to be corrected manually and the final score after the test does not reflect the correction of the essay type and might be adjusted manually later. + diff --git a/src/main/java/org/olat/ims/qti/editor/beecom/objects/ChoiceQuestion.java b/src/main/java/org/olat/ims/qti/editor/beecom/objects/ChoiceQuestion.java index 54a36675115..13517e3f6c6 100644 --- a/src/main/java/org/olat/ims/qti/editor/beecom/objects/ChoiceQuestion.java +++ b/src/main/java/org/olat/ims/qti/editor/beecom/objects/ChoiceQuestion.java @@ -113,7 +113,7 @@ public class ChoiceQuestion extends Question implements QTIObject { if (flow_label != null) instance.setFlowLabelClass(flow_label.attributeValue("class")); List response_lables = response_lid.selectNodes(".//response_label"); - List choices = QTIEditHelper.fetchChoices(response_lables); + List<Response> choices = QTIEditHelper.fetchChoices(response_lables); instance.setResponses(choices); Element resprocessingXML = item.element("resprocessing"); diff --git a/src/main/java/org/olat/ims/qti/editor/beecom/objects/EssayQuestion.java b/src/main/java/org/olat/ims/qti/editor/beecom/objects/EssayQuestion.java index 3cec74c5f8f..301f71681b8 100644 --- a/src/main/java/org/olat/ims/qti/editor/beecom/objects/EssayQuestion.java +++ b/src/main/java/org/olat/ims/qti/editor/beecom/objects/EssayQuestion.java @@ -29,6 +29,7 @@ import java.util.Iterator; import java.util.List; import org.dom4j.Element; +import org.olat.ims.qti.editor.QTIEditHelper; import org.olat.ims.qti.editor.beecom.parser.ParserManager; /** @@ -72,7 +73,7 @@ public class EssayQuestion extends Question implements QTIObject { instance.setQuestion(matQuestion); // Response - List responses = instance.getResponses(); + List<Response> responses = instance.getResponses(); EssayResponse response = new EssayResponse(); Element response_str = (Element)presentationXML.selectSingleNode(".//response_str"); // export uses flow @@ -116,6 +117,22 @@ public class EssayQuestion extends Question implements QTIObject { response_label.addAttribute("rshuffle", "Yes"); // QTI default // No resprocessing since only used in survey mode + + Element resprocessingXML = root.addElement("resprocessing"); + resprocessingXML.addAttribute("scoremodel","HumanRater"); + + Element outcomes = resprocessingXML.addElement("outcomes"); + Element decvar = outcomes.addElement("decvar"); + decvar.addAttribute("varname", "SCORE"); + decvar.addAttribute("vartype", "Decimal"); + decvar.addAttribute("defaultval", "0"); + decvar.addAttribute("minvalue", "" + getMinValue()); + float maxScore = QTIEditHelper.calculateMaxScore(this); + maxScore = maxScore > getMaxValue() ? getMaxValue() : maxScore; + decvar.addAttribute("maxvalue", "" + maxScore); + decvar.addAttribute("cutvalue", "" + maxScore); + + Element procExtension = resprocessingXML.addElement("itemproc_extension"); } @@ -126,7 +143,7 @@ public class EssayQuestion extends Question implements QTIObject { */ public EssayResponse getEssayResponse(){ EssayResponse response = null; - for (Iterator iter = getResponses().iterator(); iter.hasNext();){ + for (Iterator<Response> iter = getResponses().iterator(); iter.hasNext();){ response = (EssayResponse) iter.next(); } return response; diff --git a/src/main/java/org/olat/ims/qti/editor/beecom/objects/OutcomesProcessing.java b/src/main/java/org/olat/ims/qti/editor/beecom/objects/OutcomesProcessing.java index 002be0e487e..083678a5105 100644 --- a/src/main/java/org/olat/ims/qti/editor/beecom/objects/OutcomesProcessing.java +++ b/src/main/java/org/olat/ims/qti/editor/beecom/objects/OutcomesProcessing.java @@ -26,6 +26,7 @@ package org.olat.ims.qti.editor.beecom.objects; import java.util.HashMap; +import java.util.Map; import org.dom4j.Element; @@ -42,7 +43,7 @@ import org.dom4j.Element; */ public class OutcomesProcessing implements QTIObject { - private HashMap outcomesProcessing = new HashMap(); + private Map<String,String> outcomesProcessing = new HashMap<String,String>(); // Strings used in outcomes processing // public static final String DEFAULTVAL = "defaultval"; @@ -68,7 +69,7 @@ public class OutcomesProcessing implements QTIObject { decvar.addAttribute(CUTVALUE, (String)outcomesProcessing.get(CUTVALUE)); } - public String getField(String key) { return (String)outcomesProcessing.get(key); } + public String getField(String key) { return outcomesProcessing.get(key); } public void setField(String key, String value) { outcomesProcessing.put(key, value); } diff --git a/src/main/java/org/olat/ims/qti/editor/tree/QTIEditorTreeModel.java b/src/main/java/org/olat/ims/qti/editor/tree/QTIEditorTreeModel.java index 61e787b7288..739ec288ef8 100644 --- a/src/main/java/org/olat/ims/qti/editor/tree/QTIEditorTreeModel.java +++ b/src/main/java/org/olat/ims/qti/editor/tree/QTIEditorTreeModel.java @@ -75,10 +75,10 @@ public class QTIEditorTreeModel extends GenericTreeModel { GenericQtiNode rootNode = new AssessmentNode(ass, qtiPackage); this.setRootNode(rootNode); //Sections with their Items - List sections = ass.getSections(); + List<Section> sections = ass.getSections(); for (int i=0; i < sections.size(); i++) { //get section data - Section elem = (Section)sections.get(i); + Section elem = sections.get(i); GenericQtiNode sectionNode = new SectionNode(elem, qtiPackage); List<Item> items = elem.getItems(); for (int j=0; j < items.size(); j++) { -- GitLab