/*- * Copyright 2016 Diamond Light Source Ltd. * * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html */ package uk.ac.diamond.scisoft.analysis.processing.metadata; import org.apache.commons.beanutils.BeanUtils; import org.eclipse.dawnsci.analysis.api.processing.IOperation; import org.eclipse.dawnsci.analysis.api.processing.IOperationContext; import org.eclipse.dawnsci.analysis.api.processing.IOperationService; import org.eclipse.dawnsci.analysis.api.processing.model.IOperationModel; import org.eclipse.dawnsci.analysis.dataset.slicer.SliceFromSeriesMetadata; import org.eclipse.dawnsci.analysis.dataset.slicer.SourceInformation; import org.eclipse.january.dataset.Dataset; import org.eclipse.january.dataset.ILazyDataset; import org.eclipse.january.dataset.SliceND; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import uk.ac.diamond.scisoft.analysis.processing.LocalServiceManager; import uk.ac.diamond.scisoft.analysis.processing.operations.externaldata.DataUtils; import uk.ac.diamond.scisoft.analysis.processing.operations.utils.ProcessingUtils; import uk.ac.diamond.scisoft.analysis.processing.visitor.AveragingOutputExecutionVisitor; @SuppressWarnings("rawtypes") public class OperationMetadataImpl implements OperationMetadata { private static final long serialVersionUID = 1L; private final static Logger logger = LoggerFactory.getLogger(OperationMetadataImpl.class); private String filename; private IOperation current; private IOperation[] operations; public OperationMetadataImpl(String filename, IOperation[] operations, IOperation current) { this.filename = filename; this.operations = operations; this.current = current; } @Override public String getOutputFilename() { return filename; } @Override public Dataset process(String filename, String datasetName, SliceFromSeriesMetadata metadata) { return process(filename, datasetName, metadata, null, null); } public Dataset process(String filename, String datasetName, SliceFromSeriesMetadata metadata, Integer start, Integer stop) { SliceND sampling = null; ILazyDataset lz = ProcessingUtils.getLazyDataset(current, filename, datasetName); lz = lz.getSliceView(); IOperation[] pOps = getPreviousOperations(); SourceInformation si = new SourceInformation(filename, datasetName, lz); lz.setMetadata(new SliceFromSeriesMetadata(si)); AveragingOutputExecutionVisitor vis = new AveragingOutputExecutionVisitor(); IOperationService opServ = LocalServiceManager.getOperationService(); IOperationContext context = opServ.createContext(); context.setData(lz); int[] dataDims = updateDataDimensions(metadata.getDataDimensions(), metadata.getSourceInfo().getParent().getRank(), lz.getRank()); context.setDataDimensions(dataDims); context.setVisitor(vis); context.setSeries(pOps); if (start != null || stop != null) { int fd = DataUtils.calculateFastestDimension(dataDims, lz.getShape()); if (fd != -1) { sampling = new SliceND(lz.getShape()); sampling.setSlice(fd, start, stop, 1); } } context.setSlicing(sampling); opServ.execute(context); return vis.getAverage(); } @Override public OperationMetadata clone() { return new OperationMetadataImpl(filename, operations, current); } private int[] updateDataDimensions(int[] dataDimensions, int initRank, int newRank) { //assume c style NDarrays, i.e. fastest dimension is last dimension if (initRank == newRank) return dataDimensions.clone(); if (dataDimensions.length > newRank) throw new RuntimeException("Data dimensions larger than dataset rank!"); int[] dd = new int[dataDimensions.length]; for (int i = 0; i < dd.length; i++) dd[i] = dataDimensions[i] - (newRank - initRank); return dd; } private IOperation[] getPreviousOperations(){ int i = 0; for (;i<operations.length;i++) if (operations[i] == current) break; IOperation[] ops = new IOperation[i]; for (int j = 0 ; j < ops.length; j++) ops[j] = cloneOperation(operations[j]); return ops; } private IOperation cloneOperation(IOperation op) { IOperation clone = null; try { clone= LocalServiceManager.getOperationService().create(op.getId()); IOperationModel model = clone.getModel(); BeanUtils.copyProperties(model, op.getModel()); } catch (Exception e) { logger.error("TODO put description of error here", e); return null; } return clone; } }