/**
 * Populate this object with the data from the file
 */
void FileBackedExperimentInfo::populateFromFile() const {
  try {
    ::NeXus::File nxFile(m_filename);
    nxFile.openPath(m_nxpath);
    // The loadExperimentInfo calls things such as mutableSample()
    // and if m_loaded is not true then this function is
    // will be called recursively.
    m_loaded = true;

    std::string parameterStr;
    const_cast<FileBackedExperimentInfo *>(this)
        ->loadExperimentInfoNexus(m_filename, &nxFile, parameterStr);
    const_cast<FileBackedExperimentInfo *>(this)
        ->readParameterMap(parameterStr);
  } catch (::NeXus::Exception &exc) {
    std::ostringstream os;
    os << "Unable to load experiment information from NeXus file: "
       << exc.what() << "\n";
    throw std::runtime_error(os.str());
  }
}
Пример #2
0
/**
 * Creates the format for the output file if it doesn't exist
 * @returns the structured nexus file to write the data to
 *
 * @throw runtime_error Thrown if nexus file cannot be opened or created
 */
::NeXus::File SaveNXTomo::setupFile() {
  // Try and open the file, if it doesn't exist, create it.
  NXhandle fileHandle;
  NXstatus status = NXopen(this->m_filename.c_str(), NXACC_RDWR, &fileHandle);

  if (status != NX_ERROR && !m_overwriteFile) {
    // Appending to an existing file, return reference to the file
    ::NeXus::File nxFile(fileHandle);
    return nxFile;
  }

  // Either overwriting the file or creating a new one now
  if (status != NX_ERROR) {
    ::NeXus::File f(fileHandle);
    f.close();
  }

  // If not overwriting, ensure it has a .nxs extension
  if ((!m_overwriteFile || status == NX_ERROR) &&
      !boost::ends_with(this->m_filename, ".nxs"))
    m_filename = m_filename + ".nxs";

  status = NXopen(this->m_filename.c_str(), NXACC_CREATE5, &fileHandle);

  if (status == NX_ERROR)
    throw std::runtime_error("Unable to open or create nexus file.");

  // *********************************
  // Now genererate file and structure

  ::NeXus::File nxFile(fileHandle);

  // Make the top level entry (and open it)
  nxFile.makeGroup("entry1", "NXentry", true);

  // Make an entry to store log values from the original files.
  nxFile.makeGroup("log_info", "NXsubentry", false);

  // Make a sub-group for the entry to work with DAWN software (and open it)
  nxFile.makeGroup("tomo_entry", "NXsubentry", true);

  // Title
  nxFile.writeData("title", this->m_filename);

  // Definition name and version
  nxFile.writeData("definition", "NXtomo");
  nxFile.openData("definition");
  nxFile.putAttr("version", NXTOMO_VER);
  nxFile.closeData();

  // Originating program name and version
  nxFile.writeData("program_name", "mantid");
  nxFile.openData("program_name");
  nxFile.putAttr("version", Mantid::Kernel::MantidVersion::version());
  nxFile.closeData();

  // ******************************************
  // NXinstrument
  nxFile.makeGroup("instrument", "NXinstrument", true);
  // Write the instrument name | could add short_name attribute to name
  nxFile.writeData("name", m_workspaces[0]->getInstrument()->getName());

  // detector group - diamond example file contains
  // {data,distance,image_key,x_pixel_size,y_pixel_size}
  nxFile.makeGroup("detector", "NXdetector", true);

  std::vector<int64_t> infDim;
  infDim.push_back(NX_UNLIMITED);

  nxFile.makeData("image_key", ::NeXus::FLOAT64, infDim, false);
  nxFile.closeGroup(); // detector

  // source group // from diamond file contains {current,energy,name,probe,type}
  // - probe = [neutron | x-ray | electron]

  nxFile.closeGroup(); // NXinstrument

  // ******************************************
  // NXsample
  nxFile.makeGroup("sample", "NXsample", true);

  nxFile.makeData("rotation_angle", ::NeXus::FLOAT64, infDim, true);
  // Create a link object for rotation_angle to use later
  NXlink rotationLink = nxFile.getDataID();
  nxFile.closeData();
  nxFile.closeGroup(); // NXsample

  // ******************************************
  // Make the NXmonitor group - Holds base beam intensity for each image

  nxFile.makeGroup("control", "NXmonitor", true);
  nxFile.makeData("data", ::NeXus::FLOAT64, infDim, false);
  nxFile.closeGroup(); // NXmonitor

  nxFile.makeGroup("data", "NXdata", true);
  nxFile.putAttr<int>("NumFiles", 0);

  nxFile.makeLink(rotationLink);

  nxFile.makeData("data", ::NeXus::FLOAT64, m_infDimensions, true);
  // Create a link object for the data
  NXlink dataLink = nxFile.getDataID();
  nxFile.closeData();

  if (m_includeError)
    nxFile.makeData("error", ::NeXus::FLOAT64, m_infDimensions, false);

  nxFile.closeGroup(); // Close Data group

  // Put a link to the data in instrument/detector
  nxFile.openGroup("instrument", "NXinstrument");
  nxFile.openGroup("detector", "NXdetector");
  nxFile.makeLink(dataLink);
  nxFile.closeGroup();
  nxFile.closeGroup();

  nxFile.closeGroup(); // tomo_entry sub-group
  nxFile.closeGroup(); // Top level NXentry

  return nxFile;
}