Ignore:
Timestamp:
Nov 11, 2013, 10:48:59 AM (8 years ago)
Author:
Nicklas Nordborg
Message:

References #489: Histology scoring wizard

Several improvements to saving and error handling:

  • Support for 'keep session alive' to reduce the risk of automatic logout during data entry
  • Warning about unsaved data should now work for all cases when navigating to another page
  • Using local storage to temporary store info on the local computer. Useful if computer/browser crashes and it is possible to restore all entered information.



File:
1 edited

Legend:

Unmodified
Added
Removed
  • extensions/net.sf.basedb.reggie/branches/ticket-489/resources/sampleproc/histology_score.jsp

    r2125 r2128  
    4040var heGlass;
    4141
     42var disableModificationCheck = false;
     43
    4244var SCORES = ['ScoreInvasiveCancer', 'ScoreInsituCancer', 'ScoreLymphocytes', 'ScoreNormal', 'ScoreStroma', 'ScoreFat'];
    4345var FIELDS = ['score_invasive_cancer', 'score_insitu_cancer', 'score_lymphocytes', 'score_normal', 'score_stroma', 'score_fat'];
     
    7274       
    7375        saveOriginalProperties(sample);
     76        restoreFromLocalStorage(sample);
    7477       
    7578        // Save ID of HE glass since we need that later
     
    105108    Main.show('gocreate');
    106109    window.addEventListener('beforeunload', confirmIfModified);
    107 
     110   
     111    keepSessionAlive('<%=ID%>', debug && false, '../');
    108112  }
    109113  else
     
    143147  o.GoodStain = sample.GoodStain;
    144148  o.ScoreComplete = sample.ScoreComplete;
     149  o.comments = sample.comments;
    145150  sample.o = o;
    146151  sample.isModified = false;
     
    152157function isModified(sample, useCache)
    153158{
    154   if (useCache)
    155   {
    156     return sample.isModified;
    157   }
    158   var o = sample.o;
    159   for (var p in o)
    160   {
    161     if (o[p] != sample[p]) return true;
    162   }
    163   return false;
     159  if (!useCache)
     160  {
     161    var o = sample.o;
     162    sample.isModified = false;
     163    for (var p in o)
     164    {
     165      if (o[p] != sample[p])
     166      {
     167        sample.isModified = true;
     168        break;
     169      }
     170    }
     171  }
     172  return sample.isModified;
    164173}
    165174
     
    170179  {
    171180    glassName = frm.findGlassName.value;
     181    if (!glassName) return;
     182   
    172183    if (glassName.match(/^\d+$/))
    173184    {
     
    185196  }
    186197 
    187   location.href = url;
     198  location.replace(url);
    188199}
    189200
    190201function selectHeGlass()
    191202{
     203  if (!confirmIfModified()) return;
     204 
    192205  var url = getRoot() + 'biomaterials/bioplates/index.jsp?ID=<%=ID%>&cmd=UpdateContext&mode=selectone';
    193206  url += '&resetTemporary=1';
     
    199212function setSelectedHeGlass(id, name)
    200213{
     214  disableModificationCheck = true;
    201215  findHeGlass(name);
    202216}
     
    352366 
    353367  // Comments
    354   frm.comments.value = sample.comments;
     368  frm.comments.value = sample.comments || '';
    355369 
    356370  // Class name of selected table cell
     
    416430    frm.score_complete.disabled = true;
    417431    frm.score_complete.checked = false;
    418    
    419     if (selectedSample.ScoreTotal != null)
    420     {
    421       selectedSample.ScoreComplete = false;
    422       setInputStatus('score_total', 'Not 100%', 'warning');
    423     }
    424     else
    425     {
    426       selectedSample.ScoreComplete = null;
    427       setInputStatus('score_total', '', '');
    428     }
     432
     433    setInputStatus('score_total', 'Not 100%', 'warning');
     434    selectedSample.ScoreComplete = selectedSample.ScoreTotal == null ? null : false;
    429435  }
    430436
    431437  setSampleClassName(selectedSample);
     438  saveToLocalStorage(selectedSample);
    432439}
    433440
     
    464471  selectedSample.ScoreComplete = frm.score_complete.checked;
    465472  setSampleClassName(selectedSample);
     473  saveToLocalStorage(selectedSample);
    466474}
    467475
     
    482490        sample.GoodStain = null;
    483491        setSampleClassName(sample);
     492        saveToLocalStorage(sample);
    484493      }
    485494    }
     
    489498  frm.good_stain.disabled = true;
    490499  setSampleClassName(selectedSample);
     500  saveToLocalStorage(selectedSample);
    491501}
    492502
     
    495505  var frm = document.forms['reggie'];
    496506  selectedSample.comments = frm.comments.value;
     507  setSampleClassName(selectedSample);
     508  saveToLocalStorage(selectedSample);
    497509}
    498510
     
    564576function confirmIfModified(event)
    565577{
     578  if (disableModificationCheck) return;
     579 
    566580  var numModified = 0;
    567581  for (var glassNo = 0; glassNo < heGlass.length; glassNo++)
     
    578592  }
    579593 
    580   var okToContinue = true;
    581   if (numModified > 0)
    582   {
    583     if (event)
     594  if (event)
     595  {
     596    if (numModified > 0)
    584597    {
    585598      event.returnValue = 'There are unsaved modifications. Continue?';
    586     }
    587     else
    588     {
    589       if (!confirm('There are unsaved modifications. Continue?'))
    590       {
    591         okToContinue = false;
    592       }
    593     }
    594   }
    595  
    596   return okToContinue;
     599      return event.returnValue;
     600    }
     601  }
     602  else
     603  {
     604    return confirm('There are unsaved modifications. Continue?');
     605  }
     606 
    597607}
    598608
     
    667677  }
    668678 
     679  // Reset changed properties and remove saved info
     680  for (var sampleNo = 0; sampleNo < samples.length; sampleNo++)
     681  {
     682    var sample = samples[sampleNo];
     683    saveOriginalProperties(sample);
     684    setSampleClassName(sample);
     685    removeFromLocalStorage(sample);
     686  }
     687
     688 
    669689  var msg = '<ul>';
    670690  for (var i = 0; i < response.messages.length; i++)
     
    679699  Main.hide('gocreate');
    680700
     701}
     702
     703
     704/**
     705  Save score information to the local storage.
     706*/
     707function saveToLocalStorage(sample)
     708{
     709  if (window.localStorage && isModified(sample, true))
     710  {
     711    var storeKey = getStoreKey(sample);
     712    window.localStorage.setItem(storeKey, JSON.stringify(sample));
     713    if (debug)
     714    {
     715      Main.debug('saveToLocalStorage: ' + sample.name + '=' + window.localStorage.getItem(storeKey));
     716    }
     717  }
     718}
     719
     720function removeFromLocalStorage(sample)
     721{
     722  if (!window.localStorage) return;
     723  if (debug) Main.debug('removeFromLocalStorage:' + sample.name);
     724  window.localStorage.removeItem(getStoreKey(sample));
     725}
     726
     727function restoreFromLocalStorage(sample)
     728{
     729  if (!window.localStorage) return;
     730  try
     731  {
     732    var stored = window.localStorage.getItem(getStoreKey(sample));
     733    if (!stored) return;
     734   
     735    if (debug) Main.debug(stored);
     736    var tmp = JSON.parse(stored);
     737    if (!tmp) return;
     738   
     739    // Check that all original scores are the same, or someone has modified
     740    // this sample from another computer
     741    for (var p in sample.o)
     742    {
     743      if (sample.o[p] != tmp.o[p])
     744      {
     745        return;
     746      }
     747    }
     748   
     749    // Ok, copy stored info to the current sample
     750    for (var i = 0; i < SCORES.length; i++)
     751    {
     752      sample[SCORES[i]] = tmp[SCORES[i]];
     753    }
     754    sample.ScoreComplete = tmp.ScoreComplete;
     755    sample.GoodStain = tmp.GoodStain;
     756    sample.comments = tmp.comments;
     757  }
     758  catch (e)
     759  {
     760    Main.debug('Could not load stored information for sample ' + sample.name + ': ' + e);
     761  }
     762}
     763
     764function getStoreKey(sample)
     765{
     766  return 'reggie.histology.' + sample.id + '.scoreInfo';
    681767}
    682768
Note: See TracChangeset for help on using the changeset viewer.