Skip to content
Snippets Groups Projects
film_gls.cc 4.47 KiB
Newer Older
Stephen Smith's avatar
Stephen Smith committed
/*  film_gls.cc

    Mark Woolrich, FMRIB Image Analysis Group

    Copyright (C) 1999-2000 University of Oxford  */

Stephen Smith's avatar
Stephen Smith committed
/*  CCOPYRIGHT  */
Stephen Smith's avatar
Stephen Smith committed

#include <iostream>
#include <fstream>
#include <strstream>
#define WANT_STREAM
#define WANT_MATH

#include "newmatap.h"
#include "newmatio.h"
#include "VolumeSeries.h"
#include "Volume.h"
#include "glim.h"
#include "sigproc.h"
#include "miscmaths.h"
#include "gaussComparer.h"
#include "Log.h"
#include "AutoCorrEstimator.h"
#include "paradigm.h"
#include "FilmGlsOptions.h"
#include "glimGls.h"

#include <string>

#ifndef NO_NAMESPACE
using namespace NEWMAT;
using namespace SIGPROC;
using namespace TACO;
using namespace UTILS;
#endif

int main(int argc, char *argv[])
{
  try{
    rand();
    // parse command line to find out directory name for logging:
    ofstream out2;
    FilmGlsOptions& globalopts = FilmGlsOptions::getInstance();
    globalopts.parse_command_line(argc, argv, out2);

    // Setup logging:
    Log& logger = Log::getInstance();
    logger.setLogFile("glslogfile");
    logger.establishDir(globalopts.datadir);

    // parse command line again to output arguments to logfile
    globalopts.parse_command_line(argc, argv, logger.str());

    // load non-temporally filtered data
    VolumeSeries x;
    x.read(globalopts.inputfname);

    // if needed output the 12th volume for use later
    Volume epivol;
    if(globalopts.smoothACEst)
      {
	epivol = x.getVolume(12).AsColumn();
	epivol.setDims(x.getDims());
	
	epivol.writeAsInt(logger.getDir() + "/" + globalopts.epifname);
      }

    // This also removes the mean from each of the time series:
    x.thresholdSeries(globalopts.thresh, true);

    // if needed later also threshold the epi volume
    if(globalopts.smoothACEst)
      {
	epivol.setPreThresholdPositions(x.getPreThresholdPositions());
	epivol.threshold();
      }

    int sizeTS = x.getNumVolumes();
    int numTS = x.getNumSeries();
    
    // Load paradigm: 
    Paradigm parad;
    parad.load(globalopts.paradigmfname, "", false, sizeTS);

    // Sort out detrending:
    if(globalopts.detrend)
      {
	SIGPROC::Detrend(x, false);
      }

    if(globalopts.verbose)
      {
	logger.out("Gc", parad.getDesignMatrix());
      }

    // Set up OLS GLM for non-whitened data 
    Glim glim(x, parad.getDesignMatrix());
	    
    cerr << "Computing residuals for non-whitened data... ";
    const VolumeSeries& rnotw = glim.ComputeResids();
    cerr << "Completed" << endl;
    
    if(globalopts.verbose)
      {
	logger.out("rnotw", rnotw);
      }
    
    // Estimate Autocorrelations:
    AutoCorrEstimator acEst(rnotw);

    if(globalopts.fitAutoRegressiveModel)
      {
	acEst.fitAutoRegressiveModel();
	if(globalopts.verbose)
	  {
	    AutoCorrEstimator acEstForLogging(rnotw);
	    acEstForLogging.calcRaw();
	    logger.out("rawac", acEstForLogging.getEstimates());
	    logger.out("autoregac", acEst.getEstimates());
	  }
      }
    else
      {
	acEst.calcRaw();
	    
	if(globalopts.verbose)
	  {
	    logger.out("rawac", acEst.getEstimates());
	  }
	    
	// Smooth raw estimates:
	if(globalopts.smoothACEst)
	  { 
	    acEst.spatiallySmooth(logger.getDir() + "/" + globalopts.epifname, epivol, globalopts.ms, globalopts.epifname, globalopts.susanpath);
	    
	  }
	
	// Apply constraints to estimate autocorr:
	acEst.pava();
	    
	if(globalopts.verbose)
	  {
	    logger.out("threshac", acEst.getEstimates());
	  }
      }
    
    ColumnVector I(sizeTS);
    I = 0;
    I(1) = 1;
    
    // Setup OLS GLM for temporally filtered data:
    int numParams = parad.getDesignMatrix().Ncols();
    GlimGls glimGls(numTS, sizeTS, numParams);
    
    ColumnVector xw(sizeTS);
    ColumnVector xprew(sizeTS);

    acEst.setDesignMatrix(parad.getDesignMatrix());
    int co = 1;
    
    // Loop through voxels:
    cerr << "Calculating params..." << endl;

    for(int i = 1; i <= numTS; i++)
      {	
	// Use autocorr estimate to prewhiten data:
	xprew = x.getSeries(i);
	    
	Matrix designmattw;
	acEst.preWhiten(xprew, xw, i, designmattw);

	if(co > 1000 || i == 5618 || i == 5582)
	  {
	    co = 1;
	    cerr << (float)i/(float)numTS << ",";
	  }
	else
	  co++;
	    
	glimGls.setData(xw, designmattw, i);   
      }
    cerr << "Completed" << endl;

    // Write out necessary data:
    cerr << "Saving results... ";
    glimGls.Save(x.getDims(), x.getPreThresholdPositions());
    cerr << "Completed" << endl;
  }  
  catch(Exception p_excp) 
    {
      cerr << p_excp.what() << endl;
    }
  catch(...) 
    {
      cerr << "Image error" << endl;
    } 
  return 0;
}