Example #1
0
/** Load the event_workspace field
 *
 * @param wksp_cls
 * @param progressStart
 * @param progressRange
 * @return
 */
API::MatrixWorkspace_sptr LoadNexusProcessed::loadEventEntry(NXData & wksp_cls, NXDouble & xbins,
    const double& progressStart, const double& progressRange)
{
  NXDataSetTyped<int64_t> indices_data = wksp_cls.openNXDataSet<int64_t>("indices");
  indices_data.load();
  boost::shared_array<int64_t> indices = indices_data.sharedBuffer();
  int numspec = indices_data.dim0()-1;

  int num_xbins = xbins.dim0();
  if (num_xbins < 2) num_xbins = 2;
  EventWorkspace_sptr ws = boost::dynamic_pointer_cast<EventWorkspace>
  (WorkspaceFactory::Instance().create("EventWorkspace", numspec, num_xbins, num_xbins-1));

  // Set the YUnit label
  ws->setYUnit(indices_data.attributes("units"));
  std::string unitLabel = indices_data.attributes("unit_label");
  if (unitLabel.empty()) unitLabel = indices_data.attributes("units");
  ws->setYUnitLabel(unitLabel);

  //Handle optional fields.
  // TODO: Handle inconsistent sizes
  boost::shared_array<int64_t> pulsetimes;
  if (wksp_cls.isValid("pulsetime"))
  {
    NXDataSetTyped<int64_t> pulsetime = wksp_cls.openNXDataSet<int64_t>("pulsetime");
    pulsetime.load();
    pulsetimes = pulsetime.sharedBuffer();
  }

  boost::shared_array<double> tofs;
  if (wksp_cls.isValid("tof"))
  {
    NXDouble tof = wksp_cls.openNXDouble("tof");
    tof.load();
    tofs = tof.sharedBuffer();
  }

  boost::shared_array<float> error_squareds;
  if (wksp_cls.isValid("error_squared"))
  {
    NXFloat error_squared = wksp_cls.openNXFloat("error_squared");
    error_squared.load();
    error_squareds = error_squared.sharedBuffer();
  }

  boost::shared_array<float> weights;
  if (wksp_cls.isValid("weight"))
  {
    NXFloat weight = wksp_cls.openNXFloat("weight");
    weight.load();
    weights = weight.sharedBuffer();
  }

  // What type of event lists?
  EventType type = TOF;
  if (tofs && pulsetimes && weights && error_squareds)
    type = WEIGHTED;
  else if ((tofs && weights && error_squareds))
    type = WEIGHTED_NOTIME;
  else if (pulsetimes && tofs)
    type = TOF;
  else
    throw std::runtime_error("Could not figure out the type of event list!");

  // Create all the event lists
  PARALLEL_FOR_NO_WSP_CHECK()
  for (int wi=0; wi < numspec; wi++)
  {
    PARALLEL_START_INTERUPT_REGION
    int64_t index_start = indices[wi];
    int64_t index_end = indices[wi+1];
    if (index_end >= index_start)
    {
      EventList & el = ws->getEventList(wi);
      el.switchTo(type);

      // Allocate all the required memory
      el.reserve(index_end - index_start);
      el.clearDetectorIDs();

      for (long i=index_start; i<index_end; i++)
      switch (type)
      {
      case TOF:
        el.addEventQuickly( TofEvent( tofs[i], DateAndTime(pulsetimes[i])) );
        break;
      case WEIGHTED:
        el.addEventQuickly( WeightedEvent( tofs[i], DateAndTime(pulsetimes[i]), weights[i], error_squareds[i]) );
        break;
      case WEIGHTED_NOTIME:
        el.addEventQuickly( WeightedEventNoTime( tofs[i], weights[i], error_squareds[i]) );
        break;
      }

      // Set the X axis
      if (this->m_shared_bins)
        el.setX(this->m_xbins);
      else
      {
        MantidVec x;
        x.resize(xbins.dim0());
        for (int i=0; i < xbins.dim0(); i++)
          x[i] = xbins(wi, i);
        el.setX(x);
      }
    }

    progress(progressStart + progressRange*(1.0/numspec));
    PARALLEL_END_INTERUPT_REGION
  }
  PARALLEL_CHECK_INTERUPT_REGION

  // Clean up some stuff
  ws->doneAddingEventLists();

  return ws;
}