diff --git a/modules/bibedit/etc/Makefile.am b/modules/bibedit/etc/Makefile.am index c946f81ca..26ffcca59 100644 --- a/modules/bibedit/etc/Makefile.am +++ b/modules/bibedit/etc/Makefile.am @@ -1,27 +1,31 @@ ## This file is part of CDS Invenio. ## Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008 CERN. ## ## CDS Invenio is free software; you can redistribute it and/or ## modify it under the terms of the GNU General Public License as ## published by the Free Software Foundation; either version 2 of the ## License, or (at your option) any later version. ## ## CDS Invenio is distributed in the hope that it will be useful, but ## WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ## General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with CDS Invenio; if not, write to the Free Software Foundation, Inc., ## 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. etcdir = $(sysconfdir)/bibedit/ etc_DATA = MARC21slim.dtd refextract-journal-titles.kb refextract-report-numbers.kb rectmpldir = $(etcdir)/record_templates/ rectmpl_DATA = poem.xml +fldtmpldir = $(etcdir)/field_templates/ +fldtmpl_DATA = firstauthor.xml + EXTRA_DIST = $(etc_DATA) \ - $(rectmpl_DATA) + $(rectmpl_DATA) \ + $(fldtmpl_DATA) CLEANFILES = *~ *.tmp \ No newline at end of file diff --git a/modules/bibedit/etc/firstauthor.xml b/modules/bibedit/etc/firstauthor.xml new file mode 100644 index 000000000..ff3301e09 --- /dev/null +++ b/modules/bibedit/etc/firstauthor.xml @@ -0,0 +1,8 @@ + + + + + VOLATILE: Familyname, Firstname + VOLATILE: Affiliation + + diff --git a/modules/bibedit/lib/bibedit_config.py b/modules/bibedit/lib/bibedit_config.py index 3d5e6e54a..0efd91e26 100644 --- a/modules/bibedit/lib/bibedit_config.py +++ b/modules/bibedit/lib/bibedit_config.py @@ -1,143 +1,145 @@ ## This file is part of CDS Invenio. ## Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008 CERN. ## ## CDS Invenio is free software; you can redistribute it and/or ## modify it under the terms of the GNU General Public License as ## published by the Free Software Foundation; either version 2 of the ## License, or (at your option) any later version. ## ## CDS Invenio is distributed in the hope that it will be useful, but ## WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ## General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with CDS Invenio; if not, write to the Free Software Foundation, Inc., ## 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. """BibEdit Configuration.""" __revision__ = "$Id$" from invenio.config import CFG_ETCDIR import os ## CFG_BIBEDIT_FILENAME - default filename for BibEdit files. CFG_BIBEDIT_FILENAME = "bibedit_record" ## The CFG_BIBEDIT_JS_* constants are passed on and used by the BibEdit ## Javascript engine. ## CFG_BIBEDIT_JS_HASH_CHECK_INTERVAL - interval (in ms) between checking if ## hash has changed. CFG_BIBEDIT_JS_HASH_CHECK_INTERVAL = 250 ## CFG_BIBEDIT_JS_CHECK_SCROLL_INTERVAL - interval (in ms) between menu ## repositioning. CFG_BIBEDIT_JS_CHECK_SCROLL_INTERVAL = 250 ## CFG_BIBEDIT_JS_STATUS_INFO_TIME - display status info messages for how long ## (in ms). CFG_BIBEDIT_JS_STATUS_INFO_TIME = 1000 ## CFG_BIBEDIT_JS_STATUS_ERROR_TIME - display status error messages for how long ## (in ms). CFG_BIBEDIT_JS_STATUS_ERROR_TIME = 2000 ## CFG_BIBEDIT_JS_CLONED_RECORD_COLOR - Color of cloned record ID highlighting. CFG_BIBEDIT_JS_CLONED_RECORD_COLOR = 'yellow' ## CFG_BIBEDIT_JS_CLONED_RECORD_COLOR_FADE_DURATION - Duration (in ms) for the ## fading of cloned record ID highlighting. CFG_BIBEDIT_JS_CLONED_RECORD_COLOR_FADE_DURATION = 5000 ## CFG_BIBEDIT_JS_NEW_ADD_FIELD_FORM_COLOR - Color of new field forms' ## highlighting. CFG_BIBEDIT_JS_NEW_ADD_FIELD_FORM_COLOR = 'lightblue' ## CFG_BIBEDIT_JS_NEW_ADD_FIELD_FORM_COLOR_FADE_DURATION - Duration (in ms) for ## the fading of new field forms' highlighting. CFG_BIBEDIT_JS_NEW_ADD_FIELD_FORM_COLOR_FADE_DURATION = 2000 ## CFG_BIBEDIT_JS_NEW_FIELDS_COLOR - Color of new fields' highlighting CFG_BIBEDIT_JS_NEW_FIELDS_COLOR = 'lightgreen' ## CFG_BIBEDIT_JS_NEW_FIELDS_COLOR_FADE_DURATION - Duration (in ms) for the ## fading of new fields' highlighting. CFG_BIBEDIT_JS_NEW_FIELDS_COLOR_FADE_DURATION = 2000 ## CFG_BIBEDIT_JS_NEW_CONTENT_HIGHLIGHT_DELAY - Duration (in ms) before ## highlighting newly modified content. ## WARNING: If set to low, the Jeditable plugin won't have time to update the ## cell with the new content (recommended: >50). CFG_BIBEDIT_JS_NEW_CONTENT_HIGHLIGHT_DELAY = 50 ## CFG_BIBEDIT_JS_NEW_FIELDS_COLOR - Color of new fields' highlighting CFG_BIBEDIT_JS_NEW_CONTENT_COLOR = 'lightgreen' ## CFG_BIBEDIT_JS_NEW_FIELDS_COLOR_FADE_DURATION - Duration (in ms) for the ## fading of new fields' highlighting. CFG_BIBEDIT_JS_NEW_CONTENT_COLOR_FADE_DURATION = 2000 ## CFG_BIBEDIT_JS_TICKET_REFRESH_DELAY - Duration (in ms) before refreshing ## a record's tickets after the user clicks on the link to create a new one. ## WARNING: If set to low, the request for RT to generate the ticket won't have ## time to finish (recommended: >2000). CFG_BIBEDIT_JS_TICKET_REFRESH_DELAY = 5000 ## CFG_BIBEDIT_AJAX_RESULT_CODES - dictionary of result codes and messages used ## by the Ajax engine. CFG_BIBEDIT_AJAX_RESULT_CODES = { 0: '', 1: 'Search completed', 2: 'Tag format changed', 3: 'Record loaded', 4: 'Record submitted', 5: 'Cancelled', 6: 'Record created (new)', 7: 'Record created (from template)', 8: 'Record created (from existing)', 9: 'Record cloned', 10: 'Record deleted', 11: 'Cache deleted', 12: 'Record ready for merge', 20: 'Added controlfield', 21: 'Added field', 22: 'Added subfield', 23: 'Added subfields', 24: 'Content modified', 25: 'Subfield moved', 26: 'Field deleted', 27: 'Fields deleted', 28: 'Subfield deleted', 29: 'Subfields deleted', 30: 'Selection deleted', 31: 'Tickets retrieved', 32: 'Field moved', 100: 'Error: Not logged in', 101: 'Error: Permission denied', 102: 'Error: Non-existent record', 103: 'Error: Deleted record', 104: 'Error: Record locked by user', 105: 'Error: Record locked by queue', 106: 'Error: Cache file missing', 107: 'Error: Cache file changed', 108: 'Error: Template file missing', 109: 'Error: Invalid template file', 110: 'Error: Invalid content in record' } ## CFG_BIBEDIT_MAX_SEARCH_RESULTS CFG_BIBEDIT_MAX_SEARCH_RESULTS = 99 ## CFG_BIBEDIT_TAG_FORMAT - default format to use when displaying MARC tags. CFG_BIBEDIT_TAG_FORMAT = 'MARC' ## CFG_BIBEDIT_TO_MERGE_SUFFIX - default filename suffix for XML file to be ## merged. Filename will then be constructed like this: ## ___.xml CFG_BIBEDIT_TO_MERGE_SUFFIX = 'merge' # CFG_BIBEDIT_RECORD_TEMPLATES_PATH - path to record template directory + CFG_BIBEDIT_RECORD_TEMPLATES_PATH = "%s%sbibedit%srecord_templates" % (CFG_ETCDIR, os.sep, os.sep) +CFG_BIBEDIT_FIELD_TEMPLATES_PATH = "%s%sbibedit%sfield_templates" % (CFG_ETCDIR, os.sep, os.sep) diff --git a/modules/bibedit/lib/bibedit_display.js b/modules/bibedit/lib/bibedit_display.js index 981be5a76..194d442a6 100644 --- a/modules/bibedit/lib/bibedit_display.js +++ b/modules/bibedit/lib/bibedit_display.js @@ -1,591 +1,642 @@ /* * This file is part of CDS Invenio. * Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008 2009 CERN. * * CDS Invenio is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 2 of the * License, or (at your option) any later version. * * CDS Invenio is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with CDS Invenio; if not, write to the Free Software Foundation, Inc., * 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * This is the BibEdit Javascript for generation of webpage elements and HTML. */ function displayRecord(){ /* * Create the main content table. */ var table = '' + '' + '' + '' + '' + '' + '' + '' + // Create a dummy row to hack layout in like FF.. '' + '' + '' + '' + '' + '' + '' + '' + '' + ''; var tags = getTagsSorted(), tag, fields; // For each controlfield, create row. for (var i=0, n=tags.length; i' + '' + '' + '' + '' + '' + '' + '' + ''; } function createField(tag, field, fieldPosition){ /* * Create field row(s). */ var subfields = field[0], ind1 = field[1], ind2 = field[2]; var fieldID = tag + '_' + fieldPosition; ind1 = (ind1 != ' ' && ind1 != '') ? ind1 : '_'; ind2 = (ind2 != ' ' && ind2 != '') ? ind2 : '_'; var protectedField = fieldIsProtected(tag + ind1 + ind2); var subfieldsLength = subfields.length; var result = ''; for (var i=0, n=subfields.length; i'; } function createRow(tag, ind1, ind2, subfieldCode, subfieldValue, fieldID, subfieldIndex, subfieldsLength, protectedField){ /* * Create single row (not controlfield). */ var MARC = tag + ind1 + ind2 + subfieldCode; var protectedSubfield = (protectedField) ? true : fieldIsProtected(MARC); var subfieldID = fieldID + '_' + subfieldIndex; var boxField = '', cellFieldTagAttrs = 'class="bibEditCellField"', fieldTagToPrint = '', cellContentClass = 'bibEditCellContentProtected', cellContentTitle='', cellContentOnClick = ''; if (!protectedField){ // Enable features for unprotected fields. if (!protectedSubfield){ cellContentClass = 'bibEditCellContent'; cellContentTitle = 'title="Click to edit" '; cellContentOnClick = 'onclick="onContentClick(this)" '; } } cellContentAdditionalClass = ""; if (subfieldValue.substring(0,9) == "VOLATILE:"){ subfieldValue = subfieldValue.substring(9); cellContentAdditionalClass += " bibEditVolatileSubfield"; } var boxSubfield = input('checkbox', 'boxSubfield_' + subfieldID, 'bibEditBoxSubfield', {onclick: 'onSubfieldBoxClick(this)', tabindex: -1}); var subfieldTagToPrint = getSubfieldTag(MARC); var btnAddSubfield = ''; // If first subfield, add tag and selection box, remove up arrow. if (subfieldIndex == 0){ boxField = input('checkbox', 'boxField_' + fieldID, 'bibEditBoxField', {onclick: 'onFieldBoxClick(this)', tabindex: -1}); cellFieldTagAttrs = 'id="fieldTag_' + fieldID + '" class="bibEditCellFieldTag"'; fieldTagToPrint = getFieldTag(MARC); } // If last subfield, remove down arrow, add 'Add subfield' button. if (subfieldIndex == subfieldsLength - 1){ if (!protectedField) btnAddSubfield = img('/img/add.png', 'btnAddSubfield_' + fieldID, '', {title: 'Add subfield', onclick: 'onAddSubfieldsClick(this)'}); } return '' + '' + '' + '' + '' + '' + '' + '' + ''; } function redrawFields(tag){ /* * Redraw all fields for a given tag. */ var rowGroup = $('#rowGroup_' + tag + '_0'), prevRowGroup; if (rowGroup.length){ // Remove the fields from view. prevRowGroup = rowGroup.prev(); prevRowGroup.nextAll('[id^=rowGroup_' + tag + ']').remove(); } else{ // New tag. Determine previous sibling. var prevTag = getPreviousTag(tag); prevRowGroup = $('#rowGroup_' + prevTag + '_0'); } // Redraw all fields and append to table. if (gRecord[tag]){ var fields = gRecord[tag]; var result = '', i, n; if (validMARC.reControlTag.test(tag)){ for (i=0, n=fields.length; i' + '' + '' + '' + '' + '' + + '' + '' + - '' + '' + createAddFieldRow(fieldTmpNo, 0) + + // adding a row used to insert at the end without repositioning the tag and indicators '' + - '' + - '' + - '' + - '' + - '' + - '' + + '' + + '' + + '' + + '' + + '' + + '' + '' + ''; } -function createAddFieldRow(fieldTmpNo, subfieldTmpNo){ +function createAddFieldRow(fieldTmpNo, subfieldTmpNo, defaultCode, defaultValue){ /* * Create a row in the 'Add field' form. + * optional parameters: + * defaultCode - the subfield code displayed by default + * defaultValue - the subfield value displayed by default */ + var fieldCode = ""; + var fieldValue = ""; + if (defaultCode != undefined && defaultCode != " "){ + fieldCode = defaultCode; + } + if (defaultValue != undefined && defaultValue != " "){ + fieldValue = defaultValue; + } + + var isVolatile = (defaultValue != undefined && defaultValue.substring(0, 9) == "VOLATILE:"); + var additionalClass = ""; + if (isVolatile){ + additionalClass = " bibEditVolatileSubfield"; + fieldValue = fieldValue.substring(9); + } + var txtAddFieldTag = '', txtAddFieldInd1 = '', txtAddFieldInd2 = '', btnAddFieldRemove = ''; if (subfieldTmpNo == 0){ txtAddFieldTag = input('text', 'txtAddFieldTag_' + fieldTmpNo, 'bibEditTxtTag', {maxlength: 3}); txtAddFieldInd1 = input('text', 'txtAddFieldInd1_' + fieldTmpNo, 'bibEditTxtInd', {maxlength: 1}); txtAddFieldInd2 = input('text', 'txtAddFieldInd2_' + fieldTmpNo, 'bibEditTxtInd', {maxlength: 1}); } else btnAddFieldRemove = img('/img/delete.png', 'btnAddFieldRemove_' + fieldTmpNo + '_' + subfieldTmpNo, '', {title: 'Remove subfield'}); return '' + '' + '' + '' + '' + '' + '' + '' + ''; } function createAddSubfieldsForm(fieldID){ /* * Create an 'Add subfields' form. */ return '' + createAddSubfieldsRow(fieldID, 0) + '' + '' + '' + '' + '' + '' + '' + ''; } function createAddSubfieldsRow(fieldID, subfieldTmpNo){ /* * Create a row in the 'Add subfields' form. */ var subfieldID = fieldID + '_' + subfieldTmpNo; var btnRemove = (subfieldTmpNo == 0) ? '' : img('/img/delete.png', 'btnAddSubfieldsRemove_' + subfieldID, '', {title: 'Remove subfield'}); return '' + '' + '' + '' + '' + '' + '' + '' + ''; } function displayMessage(msgCode, keepContent, args){ /* * Display message in the main work area. Messages codes returned from the * server (positive integers) are as specified in the BibEdit configuration. */ var msg; switch (msgCode){ case -1: msg = 'Search term did not match any records.'; break; case 0: msg = 'A server error has occured. Please contact your system ' + 'administrator.
' + 'Error code: ' + msgCode + ''; break; case 4: msg = 'Your modifications have now been submitted. ' + 'They will be processed as soon as the task queue is empty.'; break; case 6: msg = 'The record will be deleted as soon as the task queue is empty.'; break; case 101: msg = 'Could not access record. Permission denied.'; break; case 102: msg = 'This record does not exist. Please try another record ID.'; break; case 103: msg = 'Cannot edit deleted record.'; break; case 104: msg = 'This record is currently being edited by another user. Please ' + 'try again later.'; break; case 105: msg = 'This record cannot be safely edited at the moment. Please ' + 'try again in a few minutes.'; break; case 106: msg = 'A server error has occured. You may have lost your changes to ' + 'this record.
' + 'Error code: ' + msgCode + ' (missing cache file)'; break; case 107: msg = 'It appears that you have opened this record in another editor, ' + 'perhaps in a different window or on a different computer. A record ' + 'can only be edited in one place at the time.
' + 'Do you want to ' + 'reopen the record here?'; break; case 108: msg = 'Could not find record template file. Please notify your system ' + 'administrator.'; break; case 109: msg = 'The record template file is invalid. Please notify your system ' + 'administrator'; break; case 110: msg = 'The record contains invalid content. Remove the invalid content ' + 'and resubmit the record.
' + 'Errors: ' + args[0] + '

'; break; default: msg = 'Result code: ' + msgCode + ''; } if (!keepContent) $('#bibEditContent').html('
' + msg + '
'); else $('#bibEditContent').prepend('
' + msg + '
'); } function displayNewRecordScreen(){ /* * Display options for creating a new record: An empty record or a template * selected from a list of templates. */ var msg = '
' + input('checkbox', 'boxField_' + fieldID, 'bibEditBoxField', {onclick: 'onFieldBoxClick(this)', tabindex: -1}) + '' + getFieldTag(tag) + '' + escapeHTML(field[3]) + '
' + boxField + '' + fieldTagToPrint + '' + boxSubfield + '' + subfieldTagToPrint + '' + subfieldValue + '' + btnAddSubfield + '
New
Add field: ' + + select('selectAddFieldTemplate_' + fieldTmpNo, fieldTemplatesData, fieldTemplateNo) + + '
Add ' + + input('text', 'selectAddFieldTemplateTimes_' + fieldTmpNo, "addFieldAddSimilarInput", {"maxlength" : 4, "size": 1}) + + button('similar', 'selectAddSimilarFields_' + fieldTmpNo, "", {}) + + '
' + - 'Controlfield ' + input('checkbox', 'chkAddFieldControlfield_' + - fieldTmpNo) + - '' + - img('/img/add.png', 'btnAddFieldAddSubfield_' + fieldTmpNo, '', { + img('/img/add.png', 'btnAddFieldAddSubfield_' + fieldTmpNo, '', { title: 'Add subfield'}) + '
' + - button('Save', 'btnAddFieldSave_' + fieldTmpNo, 'bibEditBtnBold') + - button('Cancel', 'btnAddFieldCancel_' + fieldTmpNo, '') + - button('Clear', 'btnAddFieldClear_' + fieldTmpNo, 'bibEditBtnClear') + - '' + + '
' + txtAddFieldTag + txtAddFieldInd1 + txtAddFieldInd2 + '' + input('text', 'txtAddFieldSubfieldCode_' + fieldTmpNo + '_' + - subfieldTmpNo, 'bibEditTxtSubfieldCode', {maxlength: 1}) + + subfieldTmpNo, 'bibEditTxtSubfieldCode', {maxlength: 1, value: fieldCode}) + '' + input('text', 'txtAddFieldValue_' + fieldTmpNo + '_' + - subfieldTmpNo, 'bibEditTxtValue') + + subfieldTmpNo, 'bibEditTxtValue' + additionalClass, {value : fieldValue}) + '' + btnAddFieldRemove + '
' + - button('Save', 'btnAddSubfieldsSave_' + fieldID, 'bibEditBtnBold') + - button('Cancel', 'btnAddSubfieldsCancel_' + fieldID, '') + - button('Clear', 'btnAddSubfieldsClear_' + fieldID, 'bibEditBtnClear') + '
' + input('text', 'txtAddSubfieldsCode_' + subfieldID, 'bibEditTxtSubfieldCode', {maxlength: 1}) + '' + input('text', 'txtAddSubfieldsValue_' + subfieldID, 'bibEditTxtValue') + '' + btnRemove + '
'; var templatesCount = gRECORD_TEMPLATES.length; if (!templatesCount) msg += ''; else{ for (var i=0, n=templatesCount; i' + '' + gRECORD_TEMPLATES[i][1] + '' + ''; } msg += '
No record templates found' + '
' + '' + gRECORD_TEMPLATES[i][2] + '
'; $('#bibEditContent').html(msg); } function displayCacheOutdatedScreen(requestType){ /* * Display options to resolve the outdated cache scenario (DB record updated * during editing). Options differ depending on wether the situation was * discovered when fetching or when submitting the record. */ $('#bibEditMessage').remove(); var recordURL = gSITE_URL + '/record/' + gRecID + '/'; var viewMARCURL = recordURL + '?of=hm'; var viewMARCXMLURL = recordURL + '?of=xm'; var msg = ''; if (requestType == 'submit') msg = 'Someone has changed this record while you were editing. ' + 'You can:
    ' + '
  • View (HTML,' + ' MARC,' + ' MARCXML' + ') the latest version
  • ' + '
  • Merge your changes ' + 'with the latest version by using the merge interface
  • ' + '
  • Force your changes ' + '(Warning: overwrites the latest version)
  • ' + '
  • HTML,' + ' MARC,' + ' MARCXML' + ') the latest version
  • ' + '
  • Merge your changes ' + 'with the latest version by using the merge interface
  • ' + '
  • Get the latest version' + ' (Warning: discards your changes)
  • ' + '
  • Keep editing. When submitting you will be offered to overwrite ' + 'the latest version. Click here' + ' to remove this message.
  • ' + '
'; $('#bibEditContent').prepend('
' + msg + '
'); } function displayAlert(msgType, args){ /* * Display pop-up of type alert or confirm. * args can be an array with additional arguments. */ var msg; var popUpType = 'alert'; switch (msgType){ case 'confirmClone': msg = 'Clone this record?\n\n'; popUpType = 'confirm'; break; case 'confirmSubmit': msg = 'Submit your changes to this record?\n\n'; popUpType = 'confirm'; break; case 'confirmCancel': msg = 'You have unsubmitted changes to this record.\n\n' + 'Discard your changes?'; popUpType = 'confirm'; break; case 'confirmDeleteRecord': msg = 'Really delete this record?\n\n'; popUpType = 'confirm'; break; case 'confirmInvalidOrEmptyInput': msg = 'WARNING: Some subfields contain invalid MARC or are empty. \n' + 'Click Cancel to go back and correct. \n' + 'Click OK to ignore and continue (only valid subfields will be saved).'; popUpType = 'confirm'; break; case 'confirmLeavingChangedRecord': msg = '******************** WARNING ********************\n' + ' You have unsubmitted changes.\n\n' + 'You should go back to the record and click either:\n' + ' * Submit (to save your changes permanently)\n or\n' + ' * Cancel (to discard your changes)\n\n' + 'Press OK to continue, or Cancel to stay on the current record.'; popUpType = 'confirm'; break; case 'alertCriticalInput': msg = 'ERROR: Your input had critical errors. Please go back and ' + 'correct any fields with invalid MARC (red border) or fields that ' + 'should not be empty.'; break; case 'alertAddProtectedField': msg = 'ERROR: Cannot add protected field ' + args[0] + '.'; break; case 'alertAddProtectedSubfield': msg = 'ERROR: Cannot add protected subfield ' + args[0] + '.'; break; + case 'alertEmptySubfieldsList': + msg = "The field has to contain at least one non-empty subfield."; + break; case 'alertDeleteProtectedField': msg = 'ERROR: Cannot delete protected field ' + args[0] + '.'; break; default: msg = msgType; } if (popUpType == 'confirm') return confirm(msg); else alert(msg); } function notImplemented(event){ /* * Handle unimplemented function. */ alert('Sorry, this function is not implemented yet!'); event.preventDefault(); } function button(value, id, _class, attrs){ /* * Create a button tag with specified attributes. */ value = (value != undefined) ? value : ''; id = id ? 'id="' + id + '" ' : ''; _class = _class ? 'class="' + _class + '" ' : ''; var strAttrs = ''; for (var attr in attrs){ strAttrs += attr + '="' + attrs[attr] + '" '; } return ''; } function img(src, id, _class, attrs){ /* * Create an image tag with specified attributes. */ src = 'src="' + src + '" '; id = id ? 'id="' + id + '" ' : ''; _class = _class ? 'class="' + _class + '" ' : ''; var strAttrs = ''; for (var attr in attrs){ strAttrs += attr + '="' + attrs[attr] + '" '; } return ''; } function input(type, id, _class, attrs){ /* * Create an input tag with specified attributes. */ type = 'type="' + type + '" '; id = id ? 'id="' + id + '" ' : ''; _class = _class ? 'class="' + _class + '" ' : ''; var strAttrs = ''; for (var attr in attrs){ strAttrs += attr + '="' + attrs[attr] + '" '; } return ''; } +function select(id, options, selectedOption){ + /* + * Create the select input -> it has a different structure than most of the + * inputs + * options: a list of options appearing under the same id. Each option is a + * dictionary describing the value associated and the description + * a sample entry of the options : {value: "1", description: "option1"} + */ + + optionsHTML = ""; + + for (optionNr in options){ + optionsHTML += "