From 1a891ef85ff92fc6c65090145d7a4d8f99eebb95 Mon Sep 17 00:00:00 2001
From: Greg <gchristian@gc-master.cyclotron.tamu.edu>
Date: Thu, 6 Sep 2018 12:38:26 -0500
Subject: [PATCH] Added menate_R source files and updates CMakeLists.txt file
 to compile and install them.

menate_R is a special neutron interaction library that uses correct carbon inelastic cross
sections (important for simulating organic scintillator neutron detectors)
---
 NPSimulation/Process/CMakeLists.txt |    2 +-
 NPSimulation/Process/menate_R.cc    | 2525 +++++++++++++++++++++++++++
 NPSimulation/Process/menate_R.hh    |  339 ++++
 3 files changed, 2865 insertions(+), 1 deletion(-)
 create mode 100644 NPSimulation/Process/menate_R.cc
 create mode 100644 NPSimulation/Process/menate_R.hh

diff --git a/NPSimulation/Process/CMakeLists.txt b/NPSimulation/Process/CMakeLists.txt
index 8eeaa7c33..acf8bfe48 100644
--- a/NPSimulation/Process/CMakeLists.txt
+++ b/NPSimulation/Process/CMakeLists.txt
@@ -1,2 +1,2 @@
-add_library(NPSProcess SHARED Decay.cc BeamReaction.cc FastDriftElectron.cc NPIonIonInelasticPhysic.cc PhysicsList.cc G4DriftElectron.cc G4IonizationWithDE.cc G4DriftElectronPhysics.cc G4DEAbsorption.cc G4DEAmplification.cc G4DETransport.cc )
+add_library(NPSProcess SHARED Decay.cc BeamReaction.cc FastDriftElectron.cc NPIonIonInelasticPhysic.cc PhysicsList.cc G4DriftElectron.cc G4IonizationWithDE.cc G4DriftElectronPhysics.cc G4DEAbsorption.cc G4DEAmplification.cc G4DETransport.cc menate_R.cc)
 target_link_libraries(NPSProcess ${ROOT_LIBRARIES} ${Geant4_LIBRARIES} ${NPLib_LIBRARIES} -lNPInitialConditions -lNPInteractionCoordinates -lNPReactionConditions)
diff --git a/NPSimulation/Process/menate_R.cc b/NPSimulation/Process/menate_R.cc
new file mode 100644
index 000000000..38cdf914b
--- /dev/null
+++ b/NPSimulation/Process/menate_R.cc
@@ -0,0 +1,2525 @@
+//--------------------------------------------------------------------
+//--------------------------------------------------------------------
+//
+// menate_R.cc 
+//
+// Description - contains member functions declared in menate_R.hh
+//
+// started on 6 May 2008
+//
+// Written by: Brian Roeder, Postdoc, LPC Caen, Texas A&M Univ. 
+// email - broeder@comp.tamu.edu
+//
+// -Kinematics processes in PostStepDoIt translated from FORTRAN code
+//  "MENATE" by P. Desesquelles et al., NIM A 307 (1991) 366.
+// -MeanFreePath and Reaction Selection based on discussions with JL Lecouey
+// -Uses cross sections from MENATE, but these can be modified by changing
+//  the data files.
+// -Modifications : Uses non-isotropic angular distributions for
+//                  other processes.
+//---------------------------------------------------------------------
+// Version Comments - (other changes/fixes noted in menate_R.hh)
+//  
+// 23 April 2008 - version 1.0 -> working version -> by Brian Roeder
+// modified functions and cross section read-in functions
+// added all reactions considered in original MENATE including:
+// n+H -> n+p elastic
+// n+12C -> n+12C elastic
+// n+12C -> n'+12C+gamma(4.4MeV)
+// n+12C -> a+9Be
+// n+12C -> n'+ 3a
+// n+12C -> p + 12B
+// n+12C -> n' + p + 11B (breakup)
+// n+12C -> n' + n + 11C (breakup)
+// All reactions considered together for MeanFreePath and
+// reaction probability consideration
+// **** This version includes fix in "Available_Eng" for
+// Alpha2 in process 12C(n,n')3a (bug in FORTRAN version of MENATE)
+//-----------------------------------------------------------------
+//-----------------------------------------------------------------
+// 19 May 2008 - new version with modifications - BTR
+//             - Modified angular distributions for n+p, n+12C elastic
+// other changes listed in menate_R.hh.
+//------------------------------------------------------------------
+// 2011-2012 Zach Kohley Modifications
+// To allow for the Sweeper magnet and sweeper chamber to be included
+// in the simulation needed to add Al and Fe materials into Menate_R
+// only elastic and non-elastic process are included.  Non-elastic are
+// essentially absorption (neutron is killed).
+// Angular distribution for 30, 50 and 70 MeV are included for the elastic
+// scattering of neutron off Fe and Al.
+//-----------------------------------------------------------------------
+//
+// 6 Sept 2018
+// Added to NPTool package by Greg Christian (TAMU), gchristian@tamu.edu
+// Code inherited from MoNA-simulation package,
+// https://github.com/baumann3141/MoNA-simulation (cloned 6 Sept 2018, 10:20 AM CDT
+//
+// Changes Made w.r.t. MoNA-simulation version.  Changes were required to make menate_R.cc
+// compile within the NPSimulation framework
+//    1.  Added "using namespace CLHEP" to top of file
+//    2.  Added explicit std:: before call to std::isnan
+//    3.  Changed G4ParticleTable::GetParticleTable()->GetIon(...) to
+//        G4IonTable::GetIonTable()->GetIon(...).  The former is not any
+//        longer available for GEANT v10.0 and up.  Also required adding
+//        #include "G4IonTable.hh" to menate_R.hh
+//    4.  Changed menate_R::ReadCrossSectionFile() to look in
+//        $NPTOOL/Inputs/CrossSection/MENATE_R
+//    5.  Local variable ElementName changed to ElementName_ to get rid of warning
+//    6.  Commented declaration of DiffNorm variable (use was already commented)
+//    7.  Changed inner XEV -> XEV1 in Evaporate_Eng, to get rid of compiler warning
+//    8.  Got rid of previousStepSize in GetMeanFreePath (remove unused variable warning)
+//    9.  Got rid of declaration of unused T_Feel variable (in 2 places)
+//    10. Using Thomass Baumann's / Nathan Frank's modified 12C(n,np)11Be cross section file
+//        (fixes mistake in the original)
+//
+
+#include "menate_R.hh"
+#include <cmath>
+#include <iomanip>
+using namespace CLHEP;
+
+menate_R::menate_R(const G4String& processName) : G4VDiscreteProcess(processName)
+{
+  Pi = CLHEP::pi;
+  Two_Pi = 2.*Pi;
+
+  AMass_Material = 12.; // Atomic Mass of C12 for certain inelastic reactions
+                        // If Used with materials other than C12, need to
+                        // give atomic Mass here or in PostStepDoIt Method (as for NE213)
+
+  CalcMeth="ORIGINAL";
+
+  G4cout << "Constructor for menate_R process was called! " << G4endl;
+  G4cout << "A non-relativistic model for n - scattering ";
+  G4cout << "on carbon and hydrogen or materials composed of it (e.g. NE213)" << G4endl;
+  G4cout << "You are using MENATE_R version 1.4, finished 19 May 2008 - BTR" << G4endl;
+
+  Setup_FeElastic_AngDist();
+  Setup_AlElastic_AngDist();
+  
+  const G4MaterialTable* theMaterialList = G4Material::GetMaterialTable();
+  G4int NumberOfMaterials = G4Material::GetNumberOfMaterials(); 
+
+  // Read Each Material to get List of Elements
+  H_Switch = false;
+  C_Switch = false;
+  Fe_Switch = false;
+  Al_Switch = false;
+
+  for(G4int i=0; i<NumberOfMaterials; i++)
+    {
+      // Searches to see if Carbon and Hydrogen defined.
+      // Can add other elements to this process later if needed.  
+
+      const G4Material* theMaterial = (*theMaterialList)[i];
+      G4String MaterialName = theMaterial->GetName();
+      const G4ElementVector* theElementList = theMaterial->GetElementVector();
+      G4int NumberOfElements = theMaterial->GetNumberOfElements();
+
+      for(G4int j=0;j<NumberOfElements; j++)
+	{
+	  if(j == 0)
+	    {G4cout << "Reading Elements in Material : " << MaterialName << G4endl;}
+
+	  const G4Element* theElement = (*theElementList)[j];
+	  G4String theElementName = theElement->GetName();
+
+	  if(theElementName == "Hydrogen" || theElementName == "H")
+	    { H_Switch = true; } // Hydrogen defined 
+	  else if(theElementName == "Carbon" || theElementName == "C")
+	    { C_Switch = true; } // Carbon defined
+	  else if(theElementName == "Iron" || theElementName == "Fe")
+	    { Fe_Switch = true; } // Iron defined
+	  else if(theElementName == "Aluminum" || theElementName == "Al")
+	    { Al_Switch = true; } // Al defined
+	}
+    }
+
+  // Load Cross Sections if Element is Found
+
+	  if(H_Switch == true)
+	    { ReadCrossSectionFile("Hydrogen1_el.dat",theHydrogenXS);}
+	  
+	  if(C_Switch == true)
+	    { 
+	      // Load all Carbon Elastic and Inelastic Cross Sections
+	      ReadCrossSectionFile("Carbon12_el.dat",theCarbonXS); 
+	      ReadCrossSectionFile("Carbon12_nng4_4.dat",theC12NGammaXS);
+	      ReadCrossSectionFile("Carbon12_na9Be.dat",theC12ABe9XS);
+	      ReadCrossSectionFile("Carbon12_np12B.dat",theC12NPB12XS);
+//	      ReadCrossSectionFile("Carbon12_nnp11B.dat",theC12NNPB11XS);
+				ReadCrossSectionFile("MODIFIED_12Cnnp11B.dat",theC12NNPB11XS);
+	      ReadCrossSectionFile("Carbon12_2n11C.dat",theC12N2NC11XS);
+	      ReadCrossSectionFile("Carbon12_nn3a.dat",theC12NN3AlphaXS);
+	    }
+
+	  if(Fe_Switch == true){
+	    ReadCrossSectionFile("Iron56_el.dat",theIronElasXS);
+	    ReadCrossSectionFile("Iron56_nonel.dat",theIronNonelasXS);
+	  }
+
+	  if(Al_Switch == true){
+	    ReadCrossSectionFile("Al27_el.dat",theAlElasXS);
+	    ReadCrossSectionFile("Al27_nonel.dat",theAlNonelasXS);
+	  }
+	    
+  G4cout << "Finished Building Cross Section Table! " << G4endl;
+}
+
+
+menate_R::~menate_R()
+{;}
+
+
+G4double menate_R::Absolute(G4double Num)
+{
+  if(Num < 0.)
+    { Num *= -1.;}
+
+  return Num;
+}
+
+G4double menate_R::SIGN(G4double A1, G4double B2)
+{
+  // Does FORTRAN sign command
+  // Return "A1" with the sign of B2
+
+  if(B2 >= 0.)
+    {A1 = Absolute(A1);}
+  else
+    {A1 = -1.*Absolute(A1);}
+  return A1;
+}
+
+void menate_R::ReadCrossSectionFile(G4String FileName, CrossSectionClass* theReactionXS)
+{
+  if(!getenv("NPTOOL")) 
+	{
+		G4cerr << "Please set NPTOOL environment variable!" << G4endl;
+		exit(1);
+	}
+  G4String  DirName = G4String(getenv("NPTOOL")) + "/Inputs/CrossSection/MENATE_R";
+
+  FileName = DirName+"/"+FileName;
+
+  G4String ElementName_;
+  G4int NumberOfLines = 0;
+
+  std::fstream theFile;
+  theFile.open(FileName, std::fstream::in );
+  theFile >> NumberOfLines; 
+
+  if(theFile.good())
+    {
+      theFile >> ElementName_;
+
+      G4cout << "Loading Data For : " << ElementName_ << " , FileName = " << FileName << G4endl;
+      for(G4int k=0; k<NumberOfLines; k++)
+	{
+	  G4double theEnergy;
+	  G4double theCrossSection;
+	  theFile >> theEnergy >> theCrossSection;
+	  
+	  if(FileName.contains("Iron") || FileName.contains("Al27") ){
+	    theReactionXS[k].SetNumberOfLines(NumberOfLines);
+	    theReactionXS[k].SetElementName(ElementName_);
+	    theReactionXS[k].SetKinEng(theEnergy*eV);
+	    theReactionXS[k].SetTotalCrossSection(theCrossSection*barn);
+	    //G4cout << theReactionXS[k].GetKinEng()/MeV << "  " << theReactionXS[k].GetTotalCrossSection()/barn << G4endl;
+	  } else{
+	    theReactionXS[k].SetNumberOfLines(NumberOfLines);
+	    theReactionXS[k].SetElementName(ElementName_);
+	    theReactionXS[k].SetKinEng(theEnergy*MeV);
+	    theReactionXS[k].SetTotalCrossSection(theCrossSection*barn);
+	  }
+
+	  /*//zwk adjusting cross sections
+	  if(FileName.contains("nng4")){
+	    theReactionXS[k].SetTotalCrossSection(50*theCrossSection*barn);
+	    G4cout << "nng4 cross section enhanced :) !!" << G4endl;
+	  }
+	  else theReactionXS[k].SetTotalCrossSection(theCrossSection*barn); */
+	  //theReactionXS[k].DumpData();
+	}
+      G4cout << "Successfully Loaded !" << G4endl;
+      theFile.close();
+    }
+  else
+    {
+      G4cerr << "File = " << FileName << " not found or in improper format." << G4endl;
+      enum G4ExceptionSeverity severity;
+      severity = JustWarning;
+      G4Exception("Program aborted in menate::ReadCrossSectionFile() method!","",severity,"");
+    }
+} 
+
+
+G4double menate_R::GetCrossSection(G4double KinEng, CrossSectionClass* theReactionXS)
+{
+  G4double CrossSection=0.;
+  G4int NumberOfLines;
+
+      NumberOfLines = theReactionXS[0].GetNumberOfLines();	
+      
+      if(KinEng > (theReactionXS[NumberOfLines-1].GetKinEng()))
+	{ 
+        G4cout << "The Neutron Energy is higher than the Total Cross Section DataFile!" << G4endl;
+	G4cout << "Using last cross section available!!!!!!!!" << G4endl;
+	G4cout << "  Name: " << theReactionXS[0].GetElementName() << G4endl;
+	G4cout << "  Max XS Energy: " << theReactionXS[NumberOfLines-1].GetKinEng() << G4endl;
+	//G4cerr << "Setting Cross Section = 0 !!!!!!!!!!!!!!!!!!!!!!!" << G4endl;
+	//return 0.;
+	//zwk use last cross section rather than nothing
+	return theReactionXS[NumberOfLines-1].GetTotalCrossSection();
+	}
+  
+      for(G4int k=0; k<NumberOfLines; k++)
+	{
+	  if((theReactionXS[k].GetKinEng()) == KinEng)
+	  { 
+	    CrossSection = theReactionXS[k].GetTotalCrossSection();
+	    //G4cout << CrossSection/barn << " barn" << G4endl;
+	    return CrossSection;
+	  }
+	  else if ((theReactionXS[k].GetKinEng()) > KinEng)
+	  {
+	    //G4cout << "Calculating average Cross Section (no exact match)" << G4endl;
+	    //G4cout << KinEng/MeV << G4endl;
+	    G4double LowEng = (theReactionXS[k-1].GetKinEng());
+	    G4double HighEng = (theReactionXS[k].GetKinEng());
+	    G4double LowerXS = (theReactionXS[k-1].GetTotalCrossSection());
+	    G4double UpperXS = (theReactionXS[k].GetTotalCrossSection()); 
+	    CrossSection = GetXSInterpolation(KinEng,LowEng,HighEng,LowerXS,UpperXS);
+	    //G4cout << CrossSection/barn << " barn" << G4endl;
+	    return CrossSection;
+	  }
+	}
+	 
+  return CrossSection;
+}
+
+G4double menate_R::GetXSInterpolation(G4double KinEng, G4double LowEng, G4double HighEng, 
+                                         G4double LowXS, G4double HighXS)
+{
+  G4double slope = (HighXS-LowXS)/(HighEng-LowEng);
+  G4double y_inter = HighXS-(slope*HighEng);
+
+  G4double Interpol_XS = y_inter + (slope*KinEng);
+
+  return Interpol_XS;
+}
+
+G4ThreeVector menate_R::GenMomDir(G4ThreeVector MomDirIn, G4double theta, G4double phi)
+{
+  // Generates final momentum direction in frame of initial particle
+  // follows routine of "MEN_COMPUTE_DIRECTION"
+  // Accounts for initial direction of neutron not parallel to z-axis
+
+  // Variables used in calculation
+
+  G4double SinTh = sin(theta);
+  G4double CosTh = cos(theta);
+  G4double SinPh = sin(phi);
+  G4double CosPh = cos(phi);
+  G4double CONS = sqrt( Absolute((1. - pow(MomDirIn[2],2))) );
+
+  G4ThreeVector MomDirOut;
+  MomDirOut[0] = SinTh*CosPh;
+  MomDirOut[1] = SinTh*SinPh;
+  MomDirOut[2] = CosTh;
+
+  if(CONS > 1e-8)
+    {
+      // If CONS > 1e-8, not on z-axis, so need to change frames as below:
+      MomDirOut[0] = (SinTh*CosPh*MomDirIn[0]*MomDirIn[2]/CONS) +
+	             (SinTh*SinPh*MomDirIn[1]/CONS) +
+	             (CosTh*MomDirIn[0]);
+      MomDirOut[1] = (SinTh*CosPh*MomDirIn[1]*MomDirIn[2]/CONS) -
+	             (SinTh*SinPh*MomDirIn[0]/CONS) +
+	             (CosTh*MomDirIn[1]);
+      MomDirOut[2] = -(SinTh*CosPh*CONS) + CosTh*MomDirIn[2];
+    }
+
+  G4double Norm = sqrt(pow(MomDirOut[0],2)+pow(MomDirOut[1],2)+pow(MomDirOut[2],2));
+  // G4double DiffNorm = Absolute(1.-Norm);
+
+  if(Norm != 1.)
+    {
+      //zwk commented out
+      //only occured once when running millions of events
+      // if(DiffNorm >= 1e-6)
+      // {G4Exception(" Momentum Direction not a unit vector in menate_R::GenMomDir(): Aborted!");}
+
+      // Fixes slight norm diff due to rounding to avoid G4 error
+
+      MomDirOut[0] /= Norm;
+      MomDirOut[1] /= Norm;
+      MomDirOut[2] /= Norm;
+
+    }
+
+  return MomDirOut;
+}
+
+G4double menate_R::ShareGammaEngC12(G4double Available_Eng)
+{
+  // 24 Apr. 2008 - This function translated from original FORTRAN "MENATE_R"
+  // Bleeds excitation energy of C12* into 400 keV gamma rays unless there
+  // is enough energy to create the 4.439 MeV (2+->g.s.) gamma. 
+  // Addition of this function effects neutron det. efficiency in region
+  // between 5-11 MeV (lowers eff. by a few percent).
+
+  // 19 May 2008 - Removed counter for 400 keV gamma rays - BTR
+
+  Num_gamma_4439k = 0;
+
+  G4double Remaining_Eng = Available_Eng;
+
+  while(Remaining_Eng > 4.439*MeV)
+    {
+      Num_gamma_4439k++;
+      Remaining_Eng -= 4.439*MeV;
+    }
+
+ G4double Tot_Gamma_Eng = static_cast<G4double>(Num_gamma_4439k)*4.439*MeV;
+
+ return Tot_Gamma_Eng;
+}
+
+
+G4double menate_R::Evaporate_Eng(G4double AMass,G4double Available_Eng)
+{
+  // Calculate an energy included between 0 and Available_Eng following a probability
+  // density dp/de = e/n*exp(-e/t) --- copied from MENATE_R fortran code
+  
+  G4double Evap_Eng = 0.;
+
+  G4double Temperature = sqrt(8.*Available_Eng/AMass);
+
+  if(Temperature == 0.)
+	{ 
+		Evap_Eng = 0.;
+		return Evap_Eng; 
+	}
+
+  G4double ALEA = G4UniformRand();
+  G4double XEV = Available_Eng/Temperature;
+
+  if(XEV < 1e-4)
+	{ Evap_Eng = 0.; }
+  else
+	{
+		G4double ZNORM = 1. - (1.-(1.+XEV)*exp(-XEV))*ALEA;
+		if(ZNORM == 0.)
+		{
+			Evap_Eng = 0.;
+			return Evap_Eng;
+		} 
+		G4double YEV = XEV*ALEA;
+		G4double XEV1;
+
+		do{
+			XEV1 = YEV;
+			YEV = log((1.+XEV1)/ZNORM);
+			if( XEV1 == 0.)
+	    {
+	      Evap_Eng = 0.;
+	      return Evap_Eng;
+	    }
+		}
+		while(Absolute((YEV/XEV1)-1.) > 1e-6);
+
+		Evap_Eng = YEV*Temperature;
+	}
+
+  if(Evap_Eng >= Available_Eng)
+	{ Evap_Eng = Available_Eng; }
+
+  return Evap_Eng;
+}
+
+
+void menate_R::SetMeanFreePathCalcMethod(G4String Method)
+{
+  CalcMeth = Method;
+  G4cout << "The MeanFreePath and Reaction Calculations method is set to : " << CalcMeth << G4endl;
+}
+
+
+G4String menate_R::ChooseReaction()
+{
+  // Chooses Reaction that is used in PostStepDoIt 
+  G4String theReaction = "NoReaction";
+
+  if(H_Switch == true && C_Switch == false && Fe_Switch==false && Al_Switch==false)
+    { theReaction = "N_P_elastic"; }
+  else if(C_Switch == true || Fe_Switch == true || Al_Switch==true)
+    {
+     // Get number of probabilities considered
+     // Only include if Cross Section > 0 !
+     G4double ProbSigma[12];
+     G4double ProbLimit[12];
+     if(H_Switch == false){
+       ProbSigma[0] = 0.;
+       ProbLimit[0] = 0.;
+     }
+     if(C_Switch == false){
+       for(int p=1; p<8; p++){ProbSigma[p]=0.; ProbLimit[0]=0.;}
+     }
+     if(Fe_Switch == false){
+       ProbSigma[8]=0; ProbLimit[8]=0;
+       ProbSigma[9]=0; ProbLimit[9]=0;
+     }
+     if(Al_Switch == false){
+       ProbSigma[10]=0; ProbLimit[10]=0;
+       ProbSigma[11]=0; ProbLimit[11]=0;
+     }
+
+     for(G4int i=0; i<12; i++)
+       {
+	 ProbSigma[i] = ProbDistPerReaction[i]/ProbTot;
+	 
+	 if( i == 0 )
+	   { ProbLimit[i] = ProbSigma[i]; }
+	 else
+	   { ProbLimit[i] = ProbLimit[i-1] + ProbSigma[i]; }
+	 //G4cout << "ProbSigma " << i << " is : " << ProbSigma[i] << " ProbLimit = " << ProbLimit[i] << G4endl;
+       }
+
+    // Set Reaction Type
+    // H(n,np) - N_P_elastic
+    // 12C(n,n) - N_C12_elastic
+    // 12C(n,n'gamma)12C - N_C12_NGamma
+    // 12C(n,alpha)9Be - N_C12_A_Be9
+    // 12C(n,p)12B     - N_C12_P_B12
+    // 12C(n,np)11B    - N_C12_NNP_B11
+    // 12C(n,2n)11C    - N_C12_N2N_C11
+    // 12C(n,n')3alpha - N_C12_NN3Alpha
+     //Fe (n,n) - N_Fe_elastic
+     //Fe (n,x) - N_Fe_nonelastic
+     //Al (n,n) - N_Al_elastic
+     //Al (n,x) - N_Al_nonelastic
+
+     while(theReaction == "NoReaction")
+       {
+	 // Loop through reactions until one is chosen.
+	 // If Prob = 0. for a Reaction, disregarded
+	 G4double RecRandnum = G4UniformRand();
+	 if(RecRandnum < ProbLimit[0] && ProbSigma[0] > 0.)
+	   { theReaction = "N_P_elastic"; }
+	 if(RecRandnum >= ProbLimit[0] && RecRandnum < ProbLimit[1] && ProbSigma[1] > 0.)
+	   { theReaction = "N_C12_elastic"; }
+	 if(RecRandnum >= ProbLimit[1] && RecRandnum < ProbLimit[2] && ProbSigma[2] > 0.)
+	   { theReaction = "N_C12_NGamma"; }
+	 if(RecRandnum >= ProbLimit[2] && RecRandnum < ProbLimit[3] && ProbSigma[3] > 0.)
+	   { theReaction = "N_C12_A_Be9"; } 
+	 if(RecRandnum >= ProbLimit[3] && RecRandnum < ProbLimit[4] && ProbSigma[4] > 0.)
+	   { theReaction = "N_C12_P_B12"; }
+	 if(RecRandnum >= ProbLimit[4] && RecRandnum < ProbLimit[5] && ProbSigma[5] > 0.)
+	   { theReaction = "N_C12_NNP_B11"; } 
+	 if(RecRandnum >= ProbLimit[5] && RecRandnum < ProbLimit[6] && ProbSigma[6] > 0.)
+	   { theReaction = "N_C12_N2N_C11"; } 
+	 if(RecRandnum >= ProbLimit[6] && RecRandnum < ProbLimit[7] && ProbSigma[7] > 0.)
+	   { theReaction = "N_C12_NN3Alpha"; }
+	 if(RecRandnum >= ProbLimit[7] && RecRandnum < ProbLimit[8] && ProbSigma[8] > 0.)
+	   { theReaction = "N_Fe_elastic"; }
+	 if(RecRandnum >= ProbLimit[8] && RecRandnum < ProbLimit[9] && ProbSigma[9] > 0.)
+	   { theReaction = "N_Fe_nonelastic"; }
+	 if(RecRandnum >= ProbLimit[9] && RecRandnum < ProbLimit[10] && ProbSigma[10] > 0.)
+	   { theReaction = "N_Al_elastic"; }
+	 if(RecRandnum >= ProbLimit[10] && RecRandnum < ProbLimit[11] && ProbSigma[11] > 0.)
+	   { theReaction = "N_Al_nonelastic"; }
+       }
+
+ 
+     //     G4cout << "***************Reaction Chosen was : " << theReaction << G4endl;
+   }
+ return theReaction;
+}
+
+//-----------------------------------------------------------
+// Angular Distribution generators - Added 6 May 2008 BTR
+//-----------------------------------------------------------
+G4double menate_R::NP_AngDist(G4double NEng)
+{
+  //NP scattering from DEMONS by Reese, Yariv and Sailor et al.
+  //originally written by Stanton
+  //based on equation - a + 3b cos(theta)
+  // adjusted "30." in original routine with "29.", including
+  // minimum energy for "dip" to 29 MeV - BTR 7 May 2008.
+
+  G4double CosCM = 0.;
+
+  if(NEng < 29.*MeV)
+    {
+      CosCM = 2.*G4UniformRand()-1.;
+      return CosCM;
+    }
+
+ //      a = 3.0/(3.0+rMax)
+ //      b = rMax*a/3.0
+ //      RAT = a/(a+b)
+
+  G4double rMax = NEng/29.-1.;
+  G4double RAT = 1./(1.+(rMax/3.));
+  G4double ran1, ran2, absRan2;
+
+  ran1 = G4UniformRand();
+  ran2 = 2.*G4UniformRand()-1.;
+  absRan2 = Absolute(ran2);
+
+   if(absRan2 < RAT)
+    {CosCM = 2.0*ran1-1.0;}
+  else
+    {CosCM = SIGN(pow(ran1,(1./3.)),ran2);}
+
+ return CosCM;
+}
+
+G4double menate_R::NC12_DIFF(G4double NEng)
+{
+  // Generates Angular Distribution for n+12C scattering
+  // in center of mass system. Kinematics in PostStepDoIt
+  // convert result to lab angle. 
+
+  // Uses parameterization in DEMONS by Reese, Yariv and Sailor et al.
+
+  // n+12C cross section is considered isotropic for NEng < 7.35 MeV.
+  // The orignal "FitParam" was tweaked to 0.5 to provide a better fit
+  // to the C12 diffractive peak at forward angles between 7.3 and 70 MeV.
+  // For NEng>70MeV, FitParam is returned to original value 
+  // (1.17 fits 96 MeV) with a linear increase (shown below).
+  // Fits ang dist data up to 150 MeV.
+  // Assume a "global" split between diffractive and non-diffractive
+  // cross sections at 0.9.
+
+  // References for n+12C angular distributions (elastic) include :
+  // Z.P Chen et al. - J. Phys. G: Nucl. Part. Phys. 31, 1249 (2005).
+  // T. Kaneko et al. - Phys. Rev. C 46, 298 (1992).   
+  // Z.M. Chen et al. - J. Phys. G: Nucl. Part. Phys. 19, 877 (1993).
+  // J.S. Petler et al. - Phys. Rev. C 32, 673 (1985).
+  // P. Mermod et al. - Phys. Rev. C 74, 054002 (2006).
+  // J.H. Osborne et al. - Phys. Rev. C 70, 054613 (2004).
+
+  // Modifications added by Brian Roeder, LPC Caen, 19 May 2008.
+
+  G4double CosCM = 0.;
+  G4double DiffSigma;
+  G4double FitParam = 0.5;
+  if(NEng >= 70.*MeV)
+    {FitParam = 0.021613*NEng-0.90484;} // Fit to AngDist Data
+
+  if(NEng < 7.35*MeV)
+    {
+      CosCM = 1.-2.*G4UniformRand();
+      return CosCM;
+    }
+  else
+    {
+      G4double rand = G4UniformRand();
+      if(rand > 0.9)
+	{CosCM = 1.-2.*G4UniformRand();}
+      else
+	{
+	  DiffSigma = GetCrossSection(NEng,theCarbonXS)/barn;	  
+	  do
+	    {
+	      G4double rand2 = 0.;
+	      rand2 = G4UniformRand();
+	      //CosCM = 1.0+log(rand2)/1.17/DiffSigma/NEng;
+	      CosCM = 1.0+log(rand2)/FitParam/DiffSigma/NEng;
+	    }
+	  while(CosCM < -1. || CosCM > 1.);	 	  
+	}
+    }
+
+  return CosCM;
+}
+
+
+void menate_R::Setup_AlElastic_AngDist(){
+
+
+  const int num = 146;
+
+  //30MeV-------
+  double dist_30[num]={
+    -1.000000+0, 1.143092e-2, -9.990482e-1, 1.124223e-2, -9.961947e-1, 1.069678e-2,
+    -9.914449e-1, 9.853178e-3, -9.848078e-1, 8.801133e-3, -9.762960e-1, 7.649630e-3,
+    -9.659258e-1, 6.513742e-3, -9.537170e-1, 5.500872e-3, -9.396926e-1, 4.698089e-3,
+    -9.238795e-1, 4.163449e-3, -9.063078e-1, 3.920835e-3, -8.870108e-1, 3.959841e-3,
+    -8.660254e-1, 4.239958e-3, -8.433914e-1, 4.698323e-3, -8.191520e-1, 5.259733e-3,
+    -7.933533e-1, 5.847400e-3, -7.660444e-1, 6.392955e-3, -7.372773e-1, 6.844546e-3,
+    -7.071068e-1, 7.172467e-3, -6.755902e-1, 7.371493e-3, -6.427876e-1, 7.460832e-3,
+    -6.087614e-1, 7.481616e-3, -5.735764e-1, 7.493423e-3, -5.372996e-1, 7.569377e-3,
+    -5.000000e-1, 7.791201e-3, -4.617486e-1, 8.243935e-3, -4.226183e-1, 9.009845e-3,
+    -3.826834e-1, 1.016157e-2, -3.420201e-1, 1.175351e-2, -3.007058e-1, 1.381233e-2,
+    -2.588190e-1, 1.632611e-2, -2.164396e-1, 1.923550e-2, -1.736482e-1, 2.242820e-2,
+    -1.305262e-1, 2.574168e-2, -8.715574e-2, 2.897774e-2, -4.361939e-2, 3.193267e-2,
+    0.000000+0, 3.444537e-2, 4.361939e-2, 3.646164e-2, 8.715574e-2, 3.811006e-2,
+    1.305262e-1, 3.977790e-2, 1.736482e-1, 4.217155e-2, 2.164396e-1, 4.633969e-2,
+    2.588190e-1, 5.363686e-2, 3.007058e-1, 6.560642e-2, 3.420201e-1, 8.376855e-2,
+    3.826834e-1, 1.093183e-1, 4.226183e-1, 1.427545e-1, 4.617486e-1, 1.834979e-1,
+    5.000000e-1, 2.295749e-1, 5.372996e-1, 2.774898e-1, 5.735764e-1, 3.224090e-1,
+    6.087614e-1, 3.587789e-1, 6.427876e-1, 3.814766e-1, 6.755902e-1, 3.875034e-1,
+    7.071068e-1, 3.781310e-1, 7.372773e-1, 3.612692e-1, 7.660444e-1, 3.536586e-1,
+    7.933533e-1, 3.823776e-1, 8.191520e-1, 4.850586e-1, 8.433914e-1, 7.082584e-1,
+    8.660254e-1, 1.103586+0, 8.870108e-1, 1.721515+0, 9.063078e-1, 2.603299+0,
+    9.238795e-1, 3.771875+0, 9.396926e-1, 5.223208+0, 9.537170e-1, 6.919739+0,
+    9.659258e-1, 8.787858+0, 9.762960e-1, 1.072018+1, 9.848078e-1, 1.258416+1,
+    9.914449e-1, 1.423525+1, 9.961947e-1, 1.553436+1, 9.990482e-1, 1.636534+1,
+    1.000000+0, 1.665131+1 };
+
+  hAl_AngDist_30MeV = new TH1F("hAl_AngDist_30MeV","hAl_AngDist_30MeV",300, -1.1, 1.1);
+  for(int i=0; i<num; i++){
+    double angle = dist_30[i];
+    double prob = dist_30[i+1];
+    //G4cout << i << " " << angle << " " << prob << G4endl;
+    i++;
+    double bin = hAl_AngDist_30MeV->FindBin(angle);
+    hAl_AngDist_30MeV->SetBinContent(bin, prob);
+  }
+
+
+  //50MeV-----
+  double dist_50[num]={
+    -1.000000+0, 6.709124e-4, -9.990482e-1, 6.603906e-4, -9.961947e-1, 6.304766e-4,
+    -9.914449e-1, 5.858351e-4, -9.848078e-1, 5.332814e-4, -9.762960e-1, 4.805843e-4,
+    -9.659258e-1, 4.350849e-4, -9.537170e-1, 4.024467e-4, -9.396926e-1, 3.857654e-4,
+    -9.238795e-1, 3.852123e-4, -9.063078e-1, 3.982495e-4, -8.870108e-1, 4.203689e-4,
+    -8.660254e-1, 4.461890e-4, -8.433914e-1, 4.707079e-4, -8.191520e-1, 4.904874e-4,
+    -7.933533e-1, 5.045640e-4, -7.660444e-1, 5.149420e-4, -7.372773e-1, 5.265894e-4,
+    -7.071068e-1, 5.469609e-4, -6.755902e-1, 5.851284e-4, -6.427876e-1, 6.506459e-4,
+    -6.087614e-1, 7.522636e-4, -5.735764e-1, 8.966486e-4, -5.372996e-1, 1.087158e-3,
+    -5.000000e-1, 1.322876e-3, -4.617486e-1, 1.598021e-3, -4.226183e-1, 1.902000e-3,
+    -3.826834e-1, 2.220344e-3, -3.420201e-1, 2.536745e-3, -3.007058e-1, 2.836444e-3,
+    -2.588190e-1, 3.110933e-3, -2.164396e-1, 3.363524e-3, -1.736482e-1, 3.614936e-3,
+    -1.305262e-1, 3.907434e-3, -8.715574e-2, 4.305532e-3, -4.361939e-2, 4.891377e-3,
+    0.000000+0, 5.753370e-3, 4.361939e-2, 6.967889e-3, 8.715574e-2, 8.576699e-3,
+    1.305262e-1, 1.056473e-2, 1.736482e-1, 1.284832e-2, 2.164396e-1, 1.528370e-2,
+    2.588190e-1, 1.770778e-2, 3.007058e-1, 2.001875e-2, 3.420201e-1, 2.229245e-2,
+    3.826834e-1, 2.491798e-2, 4.226183e-1, 2.871318e-2, 4.617486e-1, 3.496300e-2,
+    5.000000e-1, 4.531408e-2, 5.372996e-1, 6.146544e-2, 5.735764e-1, 8.463770e-2,
+    6.087614e-1, 1.148850e-1, 6.427876e-1, 1.504327e-1, 6.755902e-1, 1.873634e-1,
+    7.071068e-1, 2.201177e-1, 7.372773e-1, 2.432984e-1, 7.660444e-1, 2.551966e-1,
+    7.933533e-1, 2.630871e-1, 8.191520e-1, 2.897874e-1, 8.433914e-1, 3.801505e-1,
+    8.660254e-1, 6.053457e-1, 8.870108e-1, 1.062217+0, 9.063078e-1, 1.865062+0,
+    9.238795e-1, 3.128298+0, 9.396926e-1, 4.940641+0, 9.537170e-1, 7.334422+0,
+    9.659258e-1, 1.025697+1, 9.762960e-1, 1.355285+1, 9.848078e-1, 1.696543+1,
+    9.914449e-1, 2.016259+1, 9.961947e-1, 2.278521+1, 9.990482e-1, 2.450986+1,
+    1.000000+0, 2.511166+1 };
+
+  hAl_AngDist_50MeV = new TH1F("hAl_AngDist_50MeV","hAl_AngDist_50MeV",300, -1.1, 1.1);
+  for(int i=0; i<num; i++){
+    double angle = dist_50[i];
+    double prob = dist_50[i+1];
+    //G4cout << i << " " << angle << " " << prob << G4endl;
+    i++;
+    double bin = hAl_AngDist_50MeV->FindBin(angle);
+    hAl_AngDist_50MeV->SetBinContent(bin, prob);
+  }
+
+
+  //70MeV-----
+  double dist_70[num]={
+    -1.000000+0, 3.282137e-6, -9.990482e-1, 3.320258e-6, -9.961947e-1, 3.435988e-6,
+    -9.914449e-1, 3.627566e-6, -9.848078e-1, 3.879130e-6, -9.762960e-1, 4.156161e-6,
+    -9.659258e-1, 4.410307e-6, -9.537170e-1, 4.586605e-6, -9.396926e-1, 4.627784e-6,
+    -9.238795e-1, 4.480618e-6, -9.063078e-1, 4.114588e-6, -8.870108e-1, 3.553527e-6,
+    -8.660254e-1, 2.905423e-6, -8.433914e-1, 2.372443e-6, -8.191520e-1, 2.238375e-6,
+    -7.933533e-1, 2.843672e-6, -7.660444e-1, 4.551534e-6, -7.372773e-1, 7.691386e-6,
+    -7.071068e-1, 1.246622e-5, -6.755902e-1, 1.883831e-5, -6.427876e-1, 2.643986e-5,
+    -6.087614e-1, 3.455596e-5, -5.735764e-1, 4.220604e-5, -5.372996e-1, 4.833323e-5,
+    -5.000000e-1, 5.212627e-5, -4.617486e-1, 5.349607e-5, -4.226183e-1, 5.366340e-5,
+    -3.826834e-1, 5.568937e-5, -3.420201e-1, 6.468955e-5, -3.007058e-1, 8.747101e-5,
+    -2.588190e-1, 1.314276e-4, -2.164396e-1, 2.026794e-4, -1.736482e-1, 3.036667e-4,
+    -1.305262e-1, 4.308042e-4, -8.715574e-2, 5.733049e-4, -4.361939e-2, 7.146489e-4,
+    0.000000+0, 8.379677e-4, 4.361939e-2, 9.356725e-4, 8.715574e-2, 1.021972e-3,
+    1.305262e-1, 1.144510e-3, 1.736482e-1, 1.389505e-3, 2.164396e-1, 1.873184e-3,
+    2.588190e-1, 2.714392e-3, 3.007058e-1, 3.989167e-3, 3.420201e-1, 5.679383e-3,
+    3.826834e-1, 7.640669e-3, 4.226183e-1, 9.625927e-3, 4.617486e-1, 1.139963e-2,
+    5.000000e-1, 1.295828e-2, 5.372996e-1, 1.482605e-2, 5.735764e-1, 1.832085e-2,
+    6.087614e-1, 2.561511e-2, 6.427876e-1, 3.937859e-2, 6.755902e-1, 6.185808e-2,
+    7.071068e-1, 9.347093e-2, 7.372773e-1, 1.313941e-1, 7.660444e-1, 1.691515e-1,
+    7.933533e-1, 1.987067e-1, 8.191520e-1, 2.166963e-1, 8.433914e-1, 2.358658e-1,
+    8.660254e-1, 3.010805e-1, 8.870108e-1, 5.064869e-1, 9.063078e-1, 1.006997+0,
+    9.238795e-1, 2.014608+0, 9.396926e-1, 3.770019+0, 9.537170e-1, 6.484900+0,
+    9.659258e-1, 1.026029+1, 9.762960e-1, 1.500126+1, 9.848078e-1, 2.035945+1,
+    9.914449e-1, 2.573888+1, 9.961947e-1, 3.038484+1, 9.990482e-1, 3.354666+1,
+    1.000000+0, 3.466892+1 };
+
+  hAl_AngDist_70MeV = new TH1F("hAl_AngDist_70MeV","hAl_AngDist_70MeV",300, -1.1, 1.1);
+  for(int i=0; i<num; i++){
+    double angle = dist_70[i];
+    double prob = dist_70[i+1];
+    //G4cout << i << " " << angle << " " << prob << G4endl;
+    i++;
+    double bin = hAl_AngDist_70MeV->FindBin(angle);
+    hAl_AngDist_70MeV->SetBinContent(bin, prob);
+  }
+
+
+
+}
+
+void menate_R::Setup_FeElastic_AngDist(){
+
+  const int num = 146;
+
+  //30MeV-------
+  double dist_30[num]={
+    -1.000000e+0, 6.864330e-2, -9.990482e-1, 6.799924e-2, -9.961947e-1, 6.606658e-2,
+    -9.914449e-1, 6.285744e-2, -9.848078e-1, 5.841792e-2, -9.762960e-1, 5.286584e-2,
+    -9.659258e-1, 4.642469e-2, -9.537170e-1, 3.944496e-2, -9.396926e-1, 3.240171e-2,
+    -9.238795e-1, 2.585606e-2, -9.063078e-1, 2.038231e-2, -8.870108e-1, 1.646921e-2,
+    -8.660254e-1, 1.441510e-2, -8.433914e-1, 1.424461e-2, -8.191520e-1, 1.567324e-2,
+    -7.933533e-1, 1.813968e-2, -7.660444e-1, 2.090887e-2, -7.372773e-1, 2.322993e-2,
+    -7.071068e-1, 2.451358e-2, -6.755902e-1, 2.448392e-2, -6.427876e-1, 2.326010e-2,
+    -6.087614e-1, 2.133853e-2, -5.735764e-1, 1.947210e-2, -5.372996e-1, 1.847261e-2,
+    -5.000000e-1, 1.898707e-2, -4.617486e-1, 2.130970e-2, -4.226183e-1, 2.528576e-2,
+    -3.826834e-1, 3.033819e-2, -3.420201e-1, 3.561518e-2, -3.007058e-1, 4.022124e-2,
+    -2.588190e-1, 4.346884e-2, -2.164396e-1, 4.508347e-2, -1.736482e-1, 4.530519e-2,
+    -1.305262e-1, 4.486399e-2, -8.715574e-2, 4.483712e-2, -4.361939e-2, 4.643046e-2,
+    0.000000e+0, 5.073712e-2, 4.361939e-2, 5.852223e-2, 8.715574e-2, 7.006881e-2,
+    1.305262e-1, 8.508392e-2, 1.736482e-1, 1.026739e-1, 2.164396e-1, 1.213783e-1,
+    2.588190e-1, 1.392980e-1, 3.007058e-1, 1.543629e-1, 3.420201e-1, 1.647997e-1,
+    3.826834e-1, 1.698153e-1, 4.226183e-1, 1.704198e-1, 4.617486e-1, 1.701846e-1,
+    5.000000e-1, 1.755779e-1, 5.372996e-1, 1.954684e-1, 5.735764e-1, 2.394566e-1,
+    6.087614e-1, 3.149690e-1, 6.427876e-1, 4.235233e-1, 6.755902e-1, 5.571453e-1,
+    7.071068e-1, 6.964176e-1, 7.372773e-1, 8.118647e-1, 7.660444e-1, 8.699422e-1,
+    7.933533e-1, 8.440213e-1, 8.191520e-1, 7.290353e-1, 8.433914e-1, 5.566144e-1,
+    8.660254e-1, 4.061517e-1, 8.870108e-1, 4.064349e-1, 9.063078e-1, 7.237915e-1,
+    9.238795e-1, 1.535223e+0, 9.396926e-1, 2.989307e+0, 9.537170e-1, 5.162009e+0,
+    9.659258e-1, 8.018149e+0, 9.762960e-1, 1.139005e+1, 9.848078e-1, 1.498265e+1,
+    9.914449e-1, 1.840853e+1, 9.961947e-1, 2.124884e+1, 9.990482e-1, 2.312784e+1,
+    1.000000e+0, 2.378523e+1};
+
+  hFe_AngDist_30MeV = new TH1F("hFe_AngDist_30MeV","hFe_AngDist_30MeV",300, -1.1, 1.1);
+  for(int i=0; i<num; i++){
+    double angle = dist_30[i];
+    double prob = dist_30[i+1];
+    //G4cout << i << " " << angle << " " << prob << G4endl;
+    i++;
+    double bin = hFe_AngDist_30MeV->FindBin(angle);
+    hFe_AngDist_30MeV->SetBinContent(bin, prob);
+  }
+
+
+  //50MeV-----
+  double dist_50[num]={
+    -1.000000e+0, 3.691942e-3, -9.990482e-1, 3.578426e-3, -9.961947e-1, 3.262122e-3,
+    -9.914449e-1, 2.808433e-3, -9.848078e-1, 2.304621e-3, -9.762960e-1, 1.835324e-3,
+    -9.659258e-1, 1.461301e-3, -9.537170e-1, 1.208336e-3, -9.396926e-1, 1.068867e-3,
+    -9.238795e-1, 1.014110e-3, -9.063078e-1, 1.010602e-3, -8.870108e-1, 1.034141e-3,
+    -8.660254e-1, 1.076051e-3, -8.433914e-1, 1.140557e-3, -8.191520e-1, 1.236001e-3,
+    -7.933533e-1, 1.364980e-3, -7.660444e-1, 1.518547e-3, -7.372773e-1, 1.677278e-3,
+    -7.071068e-1, 1.818750e-3, -6.755902e-1, 1.928005e-3, -6.427876e-1, 2.006146e-3,
+    -6.087614e-1, 2.073045e-3, -5.735764e-1, 2.162751e-3, -5.372996e-1, 2.313195e-3,
+    -5.000000e-1, 2.554042e-3, -4.617486e-1, 2.896975e-3, -4.226183e-1, 3.331733e-3,
+    -3.826834e-1, 3.829010e-3, -3.420201e-1, 4.349491e-3, -3.007058e-1, 4.856640e-3,
+    -2.588190e-1, 5.330337e-3, -2.164396e-1, 5.777631e-3, -1.736482e-1, 6.238028e-3,
+    -1.305262e-1, 6.779185e-3, -8.715574e-2, 7.482344e-3, -4.361939e-2, 8.417194e-3,
+    0.000000e+0, 9.613124e-3, 4.361939e-2, 1.103728e-2, 8.715574e-2, 1.259760e-2,
+    1.305262e-1, 1.418379e-2, 1.736482e-1, 1.574889e-2, 2.164396e-1, 1.740999e-2,
+    2.588190e-1, 1.951995e-2, 3.007058e-1, 2.264527e-2, 3.420201e-1, 2.739634e-2,
+    3.826834e-1, 3.411133e-2, 4.226183e-1, 4.249017e-2, 4.617486e-1, 5.138349e-2,
+    5.000000e-1, 5.900207e-2, 5.372996e-1, 6.375657e-2, 5.735764e-1, 6.569038e-2,
+    6.087614e-1, 6.807300e-2, 6.427876e-1, 7.826655e-2, 6.755902e-1, 1.067589e-1,
+    7.071068e-1, 1.635344e-1, 7.372773e-1, 2.520196e-1, 7.660444e-1, 3.625788e-1,
+    7.933533e-1, 4.694480e-1, 8.191520e-1, 5.360762e-1, 8.433914e-1, 5.328226e-1,
+    8.660254e-1, 4.670148e-1, 8.870108e-1, 4.188167e-1, 9.063078e-1, 5.690737e-1,
+    9.238795e-1, 1.200984e+0, 9.396926e-1, 2.659844e+0, 9.537170e-1, 5.266500e+0,
+    9.659258e-1, 9.198724e+0, 9.762960e-1, 1.437487e+1, 9.848078e-1, 2.038495e+1,
+    9.914449e-1, 2.650916e+1, 9.961947e-1, 3.183898e+1, 9.990482e-1, 3.547902e+1,
+    1.000000e+0, 3.677275e+1};
+
+  hFe_AngDist_50MeV = new TH1F("hFe_AngDist_50MeV","hFe_AngDist_50MeV",300, -1.1, 1.1);
+  for(int i=0; i<num; i++){
+    double angle = dist_50[i];
+    double prob = dist_50[i+1];
+    //G4cout << i << " " << angle << " " << prob << G4endl;
+    i++;
+    double bin = hFe_AngDist_50MeV->FindBin(angle);
+    hFe_AngDist_50MeV->SetBinContent(bin, prob);
+  }
+
+
+  //70MeV-----
+  double dist_70[num]={
+    -1.000000e+0, 1.983425e-6, -9.990482e-1, 1.965798e-6, -9.961947e-1, 1.905855e-6,
+    -9.914449e-1, 1.789217e-6, -9.848078e-1, 1.608414e-6, -9.762960e-1, 1.374194e-6,
+    -9.659258e-1, 1.121800e-6, -9.537170e-1, 9.156061e-7, -9.396926e-1, 8.487982e-7,
+    -9.238795e-1, 1.028369e-6, -9.063078e-1, 1.543452e-6, -8.870108e-1, 2.426820e-6,
+    -8.660254e-1, 3.620830e-6, -8.433914e-1, 4.955293e-6, -8.191520e-1, 6.152640e-6,
+    -7.933533e-1, 6.884876e-6, -7.660444e-1, 6.894530e-6, -7.372773e-1, 6.152684e-6,
+    -7.071068e-1, 5.003299e-6, -6.755902e-1, 4.240556e-6, -6.427876e-1, 5.065765e-6,
+    -6.087614e-1, 8.855034e-6, -5.735764e-1, 1.670012e-5, -5.372996e-1, 2.880136e-5,
+    -5.000000e-1, 4.395150e-5, -4.617486e-1, 5.943709e-5, -4.226183e-1, 7.165837e-5,
+    -3.826834e-1, 7.762420e-5, -3.420201e-1, 7.715392e-5, -3.007058e-1, 7.507574e-5,
+    -2.588190e-1, 8.212670e-5, -2.164396e-1, 1.131184e-4, -1.736482e-1, 1.816766e-4,
+    -1.305262e-1, 2.925482e-4, -8.715574e-2, 4.346801e-4, -4.361939e-2, 5.800715e-4,
+    0.000000e+0, 6.933060e-4, 4.361939e-2, 7.530309e-4, 8.715574e-2, 7.790938e-4,
+    1.305262e-1, 8.502975e-4, 1.736482e-1, 1.093673e-3, 2.164396e-1, 1.633476e-3,
+    2.588190e-1, 2.510481e-3, 3.007058e-1, 3.613760e-3, 3.420201e-1, 4.690171e-3,
+    3.826834e-1, 5.484783e-3, 4.226183e-1, 5.996965e-3, 4.617486e-1, 6.725686e-3,
+    5.000000e-1, 8.681963e-3, 5.372996e-1, 1.297100e-2, 5.735764e-1, 1.997476e-2,
+    6.087614e-1, 2.857775e-2, 6.427876e-1, 3.626075e-2, 6.755902e-1, 4.084107e-2,
+    7.071068e-1, 4.379671e-2, 7.372773e-1, 5.349841e-2, 7.660444e-1, 8.508892e-2,
+    7.933533e-1, 1.537562e-1, 8.191520e-1, 2.613914e-1, 8.433914e-1, 3.833791e-1,
+    8.660254e-1, 4.699469e-1, 8.870108e-1, 4.791521e-1, 9.063078e-1, 4.493164e-1,
+    9.238795e-1, 5.943887e-1, 9.396926e-1, 1.373549e+0, 9.537170e-1, 3.465226e+0,
+    9.659258e-1, 7.589794e+0, 9.762960e-1, 1.418895e+1, 9.848078e-1, 2.306574e+1,
+    9.914449e-1, 3.316772e+1, 9.961947e-1, 4.268799e+1, 9.990482e-1, 4.953558e+1,
+    1.000000e+0, 5.203243e+1 };
+
+  hFe_AngDist_70MeV = new TH1F("hFe_AngDist_70MeV","hFe_AngDist_70MeV",300, -1.1, 1.1);
+  for(int i=0; i<num; i++){
+    double angle = dist_70[i];
+    double prob = dist_70[i+1];
+    //G4cout << i << " " << angle << " " << prob << G4endl;
+    i++;
+    double bin = hFe_AngDist_70MeV->FindBin(angle);
+    hFe_AngDist_70MeV->SetBinContent(bin, prob);
+  }
+
+
+  //+++ ---
+}
+
+
+G4double menate_R:: AlElastic_AngDist(G4double NEng){
+  double ang_CM = 0;
+
+  if(NEng<=15*MeV) ang_CM = G4UniformRand();
+  else if(NEng<=40*MeV ) ang_CM = hAl_AngDist_30MeV->GetRandom();
+  else if(NEng<=60*MeV ) ang_CM = hAl_AngDist_50MeV->GetRandom();
+  else if(NEng>60*MeV ) ang_CM = hAl_AngDist_70MeV->GetRandom();
+
+  return ang_CM;
+}
+
+G4double menate_R:: FeElastic_AngDist(G4double NEng){
+  double ang_CM = 0;
+
+  if(NEng<=15*MeV) ang_CM = G4UniformRand();
+  else if(NEng<=40*MeV ) ang_CM = hFe_AngDist_30MeV->GetRandom();
+  else if(NEng<=60*MeV ) ang_CM = hFe_AngDist_50MeV->GetRandom();
+  else if(NEng>60*MeV ) ang_CM = hFe_AngDist_70MeV->GetRandom();
+
+  return ang_CM;
+}
+//e-e-e-e-e------------------------------------------------------------------
+//----------------------------------------------------------------------
+// The Below are the GEANT4:: G4VDiscreteProcess class methods that must
+// be overridden to run this process in G4.
+//----------------------------------------------------------------------
+//----------------------------------------------------------------------
+
+ 
+G4bool menate_R::IsApplicable(const G4ParticleDefinition& particle)
+{ 
+// returns "true" if this model can be applied to the particle-type
+  //G4cout << "IsApplicable loaded!" << G4endl;
+
+  if (particle == *(       G4Neutron::Neutron()       )) 
+    {
+      //G4cout << "Found the Neutron ! " << G4endl;
+      return true;
+    }
+  else
+    {   enum G4ExceptionSeverity severity;
+        severity = JustWarning;
+        G4Exception("Model \"menate_R\" can only be used for neutron scattering!","",severity,"");}
+  return false;
+}
+
+
+G4double menate_R::GetMeanFreePath(const G4Track& aTrack, G4double, // previousStepSize, 
+                                      G4ForceCondition* condition) 
+{
+  //G4cout << "menate_R GetMeanFreePath called!" << G4endl;
+  
+  const G4Step* theStep = aTrack.GetStep();
+  G4StepPoint* thePoint = theStep->GetPreStepPoint();
+  G4String theVolume =  thePoint->GetPhysicalVolume()->GetName();
+ 
+  /*
+  if(theVolume == "target")  
+    {*condition = Forced;}
+  else
+    {*condition = NotForced;}
+  */  
+
+  *condition = NotForced;
+  
+//  G4double previousStepSize = 0.1*mm;
+
+  const G4DynamicParticle* projectile = aTrack.GetDynamicParticle();
+  G4double theKinEng = projectile->GetKineticEnergy();
+
+  if(theKinEng < 1e-4*MeV)
+  {return DBL_MAX;} // Energy too low for this model!
+
+  // Now read the medium to get mean free path at this energy!
+
+ const G4Material* theMaterial = aTrack.GetMaterial();
+
+ // GetVecNbOfAtomsPerVolume() returns (NumberOfAtoms/mm3)! 
+ const G4double* N_Per_Volume = theMaterial->GetVecNbOfAtomsPerVolume();
+
+ // Get List of Elements in Material, also get number!
+ const G4ElementVector* theElementList = theMaterial->GetElementVector();
+ G4int NumberOfElements = theMaterial->GetNumberOfElements();
+
+ // Only do MeanFreePath calculation if in a material
+ // that has Hydrogen or Carbon !
+ H_Switch = false;
+ C_Switch = false;
+ Fe_Switch = false;
+ Al_Switch = false;
+
+ for(G4int ne=0;ne<NumberOfElements;ne++)
+   {
+     G4Element* theElement = (*theElementList)[ne];
+
+     //G4cout << "The Element is : " << theElement->GetName() << G4endl;
+     Z = static_cast<int>(theElement->GetZ());
+     A = static_cast<int>(theElement->GetN());  // returns Atomic Weight
+     //G4cout << Z << " " << A << G4endl;
+
+     //G4cout << theMaterial->GetName() << G4endl;
+     if(Z == 1 && A == 1)
+       { 
+	 H_Switch = true; 
+	 Num_H = N_Per_Volume[ne];
+       }
+     else if(Z == 6 && A == 12)
+       { 
+	 C_Switch = true; 
+	 Num_C = N_Per_Volume[ne];
+       }
+     else if(Z == 26){
+       Fe_Switch = true;
+       //G4cout << "Inside IRON !!" << G4endl;
+       Num_Fe = N_Per_Volume[ne];
+     }
+     else if(Z == 13){
+       Al_Switch = true;
+       //G4cout << "Inside IRON !!" << G4endl;
+       Num_Al = N_Per_Volume[ne];
+     }
+   }
+
+ if(H_Switch == false && C_Switch == false && Fe_Switch == false && Al_Switch == false)
+   { return DBL_MAX; }
+
+ // Calculate Total Mean Free Path (From Total Cross Section and Density)
+ // Does not decide reaction --- PostStepDoIt decides reaction if n-scattering occurs
+
+ if(CalcMeth == "ORIGINAL")
+   {
+     G4int k_tot = 0;
+
+     if(H_Switch == true)
+       {
+	 // Returns Cross Section in Barns, pre-loaded in constructor
+	 Sigma = GetCrossSection(theKinEng,theHydrogenXS);
+	 //G4cout << "Sigma =  " << Sigma/barn << G4endl; 
+	 ProbDistPerReaction[0] = Sigma*Num_H;
+	 k_tot = 1;
+       }
+     else
+       {
+	 // Clears array element
+	 ProbDistPerReaction[0] = 0.;
+       }
+
+     if(C_Switch == true)
+       {
+	 Sigma = GetCrossSection(theKinEng,theCarbonXS);
+	 ProbDistPerReaction[1] = Sigma*Num_C;	
+	 Sigma = GetCrossSection(theKinEng,theC12NGammaXS);
+	 ProbDistPerReaction[2] = Sigma*Num_C;
+	 Sigma = GetCrossSection(theKinEng,theC12ABe9XS);
+	 ProbDistPerReaction[3] = Sigma*Num_C;
+	 Sigma = GetCrossSection(theKinEng,theC12NPB12XS);
+	 ProbDistPerReaction[4] = Sigma*Num_C;
+	 Sigma = GetCrossSection(theKinEng,theC12NNPB11XS);
+	 ProbDistPerReaction[5] = Sigma*Num_C;
+	 Sigma = GetCrossSection(theKinEng,theC12N2NC11XS);
+	 ProbDistPerReaction[6] = Sigma*Num_C;
+	 Sigma = GetCrossSection(theKinEng,theC12NN3AlphaXS);
+	 ProbDistPerReaction[7] = Sigma*Num_C;
+
+	 k_tot = 8;
+       }
+     else
+       {
+	 // Clears array element
+	 for(G4int i=1;i<8;i++)
+	   { ProbDistPerReaction[i] = 0.; }
+       }
+
+     if(Fe_Switch == true)
+       {
+	 Sigma = GetCrossSection(theKinEng,theIronElasXS);
+	 ProbDistPerReaction[8] = Sigma*Num_Fe;	
+	 Sigma = GetCrossSection(theKinEng,theIronNonelasXS);
+	 ProbDistPerReaction[9] = Sigma*Num_Fe;       
+
+	 k_tot = 10;
+       }
+     else
+       {
+	 // Clears array element
+	 for(G4int i=8;i<10;i++)
+	   { ProbDistPerReaction[i] = 0.; }
+       }
+
+     if(Al_Switch == true)
+       {
+	 Sigma = GetCrossSection(theKinEng,theAlElasXS);
+	 ProbDistPerReaction[10] = Sigma*Num_Al;	
+	 Sigma = GetCrossSection(theKinEng,theAlNonelasXS);
+	 ProbDistPerReaction[11] = Sigma*Num_Al;       
+
+	 k_tot = 12;
+       }
+     else
+       {
+	 // Clears array element
+	 for(G4int i=10;i<12;i++)
+	   { ProbDistPerReaction[i] = 0.; }
+       }
+
+
+     ProbTot = 0.;  // Reset Probtot
+
+     for(G4int k=0; k<k_tot; k++)
+       {ProbTot += ProbDistPerReaction[k];}
+    
+     if(ProbTot > 1.e-6)
+       {
+	 G4double total_mean_free_path = 1/(ProbTot);
+	 //G4cout << "The mean free path was : " << total_mean_free_path/cm << " cm" << G4endl; 
+	 return total_mean_free_path;
+       }
+   }
+ else if(CalcMeth == "MENATE")
+   {
+     // MENATE MeanFreePath method is as follows:
+     // Adds up total cross section for hydrogen and carbon and then uses molecular weight,
+     // density of NE213 to calculate MeanFreePath
+
+     // 30 April 2008 - BTR - After comparison with program DECOI, determined the difference
+     // between the ORIGINAL mean free path calculation above and the MENATE calculation
+     // is that the MENATE calculation lacks a factor 1.213 that is multiplied to the n-p
+     // total cross section. The 1.213 factor comes from the ratio of Carbon to Hydrogen in 
+     // NE213. This disagreement is "fixed" in the original MENATE FORTRAN code by mulitiplying
+     // the Hydrogren cross sections in the data file by a factor of 1.2. 
+     // I have left here the original method in the FORTRAN MENATE code for mean free path
+     // calculation for comparison with the ORIGINAL (standard) method. Note that the methods
+     // do not agree unless the n-p total cross sections in the data file are muliplied by 1.2
+     // as in the FORTRAN version data files. 
+
+     G4String MaterialName = theMaterial->GetName();
+     if(MaterialName == "NE213")
+       { AMass_Material = 13.213; }
+     else
+       { AMass_Material = theMaterial->GetA(); }
+
+     // Get Cross Section Sum at this energy
+     ProbDistPerReaction[0] = (GetCrossSection(theKinEng,theHydrogenXS))/barn;
+     ProbDistPerReaction[1] = (GetCrossSection(theKinEng,theCarbonXS))/barn;	
+     ProbDistPerReaction[2] = (GetCrossSection(theKinEng,theC12NGammaXS))/barn;
+     ProbDistPerReaction[3] = (GetCrossSection(theKinEng,theC12ABe9XS))/barn;
+     ProbDistPerReaction[4] = (GetCrossSection(theKinEng,theC12NPB12XS))/barn;
+     ProbDistPerReaction[5] = (GetCrossSection(theKinEng,theC12NNPB11XS))/barn;
+     ProbDistPerReaction[6] = (GetCrossSection(theKinEng,theC12N2NC11XS))/barn;
+     ProbDistPerReaction[7] = (GetCrossSection(theKinEng,theC12NN3AlphaXS))/barn;
+
+     // Add up Cross Sections
+     ProbTot = 0.;  // Reset Probtot
+
+     for(G4int k=0; k<8; k++)
+       {ProbTot += ProbDistPerReaction[k];}
+
+     G4double NE213dens = 0.874;
+     G4double NumAvagadro = 0.60221367;   // Num Avagadro*conversion to barns
+     G4double Constant = 10.*AMass_Material/NumAvagadro/NE213dens;    
+     G4double total_mean_free_path = Constant/ProbTot;
+     //G4cout << "The mean free path was : " << total_mean_free_path/cm << " cm" << G4endl; 
+	
+     if(total_mean_free_path < DBL_MAX)
+       {return total_mean_free_path;}
+      
+   }
+ else if(CalcMeth == "carbon_el_only" && C_Switch == true)
+   {
+     // Added 7 May 2007 - For carbon elastic scattering only
+      // Clears array elements
+	 for(G4int i=0;i<8;i++)
+	   { ProbDistPerReaction[i] = 0.; }
+	 Sigma = GetCrossSection(theKinEng,theCarbonXS);
+	 ProbDistPerReaction[1] = Sigma*Num_C;
+	 ProbTot = ProbDistPerReaction[1];
+	 if(ProbTot > 1.e-6)
+	   {
+	     G4double total_mean_free_path = 1/(ProbTot);
+	     //G4cout << "The mean free path was : " << total_mean_free_path/cm << " cm" << G4endl; 
+	     return total_mean_free_path;
+	   }
+   }
+
+ return DBL_MAX;
+}
+
+
+G4VParticleChange* menate_R::PostStepDoIt(const G4Track& aTrack, const G4Step& aStep)
+{
+  // Now we tell GEANT what to do if MeanFreePath condition is satisfied!
+  // Overrides PostStepDoIt function in G4VDiscreteProcess
+
+  const G4DynamicParticle* projectile = aTrack.GetDynamicParticle();
+  //const G4ParticleDefinition* particle = projectile->GetDefinition();
+
+  const G4Material* theMaterial = aTrack.GetMaterial();
+  G4String MaterialName = theMaterial->GetName();
+
+  G4double KinEng_Int = projectile->GetKineticEnergy();
+  G4ThreeVector MomDir_Int = projectile->GetMomentumDirection();
+  G4double GlobalTime = aTrack.GetGlobalTime(); 
+  G4ThreeVector thePosition = aTrack.GetPosition();
+  G4TouchableHandle theTouchable = aTrack.GetTouchableHandle();
+
+
+  //zwk Found that Genat4 gets hung up randomly with a position of (nan,nan,nan)
+  //Therefore if this happens reset position to previous set
+  if(std::isnan(thePosition.x())||std::isnan(thePosition.y())||std::isnan(thePosition.z())){ 
+    //G4cout << "MENATE_R: Current position is (nan,nan,nan): resetting to presteppoint" << G4endl;
+    G4cout << aTrack.GetMaterial()->GetName() << G4endl;
+    G4cout << aTrack.GetNextMaterial()->GetName() << G4endl;
+    G4cout << aStep.GetPreStepPoint()->GetPosition().z()/cm << G4endl;
+    G4cout << aStep.GetPostStepPoint()->GetPosition().z()/cm << G4endl;
+    G4cout << aStep.GetPreStepPoint()->GetMaterial()->GetName() << G4endl;
+    G4cout << aStep.GetPostStepPoint()->GetMaterial()->GetName() << G4endl;
+
+    thePosition = aStep.GetPreStepPoint()->GetPosition();
+
+  }
+
+  /*
+  // These variables not used...
+  G4double LocalTime = aTrack.GetLocalTime();
+  G4double ProperTime = aTrack.GetProperTime();
+  G4double theProjMass = projectile->GetMass();
+  */
+
+  //zwk changed from 10-5 MeV
+ if(KinEng_Int < 0.5e-3*MeV)
+   {
+     //G4cout << "Neutron Energy = " << KinEng_Int << G4endl;
+     //G4cout << "Do Nothing, Kill Event! " << G4endl;
+    aParticleChange.ProposeTrackStatus(fStopAndKill);
+    aParticleChange.ProposeEnergy(0.);
+    aParticleChange.ProposePosition(thePosition);
+    return pParticleChange;
+   } 
+
+ if(MaterialName == "NE213")
+   { AMass_Material = 13.213; }
+
+  // Define Reaction -
+  // Chooses Reaction based on ProbDistPerReaction Vector defined in GetMeanFreePath()
+
+ G4String ReactionName = ChooseReaction();
+
+  //
+  //*******MENATE Reaction Kinematics*************
+  //
+    
+      //zwk modification  Bool_t fwrdANGLES = true means use cos_theta_iso=pow(G4uniformRand,1/4), so becomes very forward focused rather than isotropic
+      G4bool fwrdANGLES = false;
+
+if(ReactionName == "N_P_elastic")
+  {
+
+    G4double mass_ratio = 939.6/938.3;  // Mass ratio N/P
+
+    G4double cos_theta = 0.;
+    G4double theta_cm = 0.;
+    G4double theta_N  = 0.;
+    G4double phi_N = 0.;
+    G4double T_N = 0.;
+    G4ThreeVector MomDir_N;
+
+    G4double cos_theta_P = 0.;
+    G4double theta_P = 0.;
+    G4double phi_P = 0.;
+    G4double T_P = 0.;
+    G4ThreeVector MomDir_P;
+
+    // *** 6 May 2008 - Added n-p angular distribution as in DEMONS - BTR
+    // Made slight adjustment to routine (changed "30" to "29") to improve 
+    // agreement with data.
+    // Calculate recoil energy as in Knoll          
+
+    cos_theta = NP_AngDist(KinEng_Int); // cosine of cm_angle
+    theta_cm = acos(cos_theta);
+
+    // Following Knoll, calculate energy for proton first
+    cos_theta_P = sqrt((1.-cos_theta)/2.);
+    theta_P = acos(cos_theta_P);
+    phi_P = 2.*Pi*G4UniformRand();
+
+    T_P = KinEng_Int*pow(cos_theta_P,2);
+
+    MomDir_P = GenMomDir(MomDir_Int,theta_P,phi_P);
+
+    // scattered neutron ----------------
+    // angles changed from cm to lab as in Marian and Young
+    theta_N = atan(sin(theta_cm)/(cos_theta+mass_ratio));
+    phi_N = phi_P+Pi;
+
+    T_N = KinEng_Int - T_P;    
+
+    MomDir_N = GenMomDir(MomDir_Int,theta_N,phi_N);
+  
+    // Generate a Secondary Neutron
+    G4DynamicParticle* theSecNeutron = new G4DynamicParticle;
+    G4ParticleDefinition* theSecNeutronDefinition = G4Neutron::Neutron();
+    theSecNeutron->SetDefinition(theSecNeutronDefinition);
+    theSecNeutron->SetKineticEnergy(T_N);
+    theSecNeutron->SetMomentumDirection(MomDir_N);
+
+    // Generate a Secondary Proton
+    G4DynamicParticle* theSecProton = new G4DynamicParticle;
+    G4ParticleDefinition* theSecProtonDefinition = G4Proton::Proton();
+    theSecProton->SetDefinition(theSecProtonDefinition);
+    theSecProton->SetKineticEnergy(T_P);
+    theSecProton->SetMomentumDirection(MomDir_P);
+   
+    // Kill the Parent Neutron -----------------------
+    aParticleChange.ProposeTrackStatus(fStopAndKill);
+    aParticleChange.ProposeEnergy(0.);
+    aParticleChange.ProposePosition(thePosition);
+  
+ // Set final tracks in motion!
+    G4Track* theNTrack = new G4Track(theSecNeutron,GlobalTime,thePosition);
+    theNTrack->SetTouchableHandle(theTouchable);
+    G4Track* thePTrack = new G4Track(theSecProton,GlobalTime,thePosition);
+    thePTrack->SetTouchableHandle(theTouchable);
+
+    aParticleChange.SetNumberOfSecondaries(2);
+    aParticleChange.AddSecondary(theNTrack);
+    aParticleChange.AddSecondary(thePTrack);
+  
+    // G4cout << "Made it to the end ! " << G4endl;
+  
+  }
+ else if(ReactionName == "N_C12_elastic")
+   {
+     G4double theta_N  = 0.;
+     G4double phi_N = 0.;
+
+     G4double T_N = 0.;
+     G4double T_C12el = 0.;
+     G4ThreeVector MomDir_N;
+     G4ThreeVector MomDir_C12;
+
+     // For n,12C elastic scattering, follows model of Knoll
+     // Original MENATE distribution was isotropic in CM
+     // G4double cos_sq_theta = G4UniformRand(); 
+
+     // Calls diffractive angular distribution as in DEMONS
+     G4double cos_theta_cm = NC12_DIFF(KinEng_Int);
+
+     // Convert according to Knoll
+     G4double cos_theta_lab = sqrt((1.-cos_theta_cm)/2.);
+
+     G4double cos_sq_theta = pow(cos_theta_lab,2);
+    
+     // .2840237              =4*Mc12*Mn/(Mc12+Mn)^2
+     T_C12el = 0.2840237*KinEng_Int*cos_sq_theta;
+
+     T_N = KinEng_Int - T_C12el;
+
+     if(T_N > 1.e-5)
+       {
+	 G4double arg = (sqrt(KinEng_Int)-sqrt(12.*T_C12el*cos_sq_theta))/sqrt(T_N);
+	 if(arg > 1.)
+	   {arg = 1.;}
+	 theta_N = acos(arg);
+         phi_N = 2.*Pi*G4UniformRand();
+       }
+
+     MomDir_N = GenMomDir(MomDir_Int,theta_N,phi_N);
+
+     // Carbon angles
+     G4double theta_C12 = acos(sqrt(cos_sq_theta));
+     G4double phi_C12 = phi_N+Pi;
+
+     MomDir_C12 = GenMomDir(MomDir_Int,theta_C12,phi_C12);
+    
+     // Generate a Secondary Neutron
+     G4DynamicParticle* theSecNeutron = new G4DynamicParticle;
+     G4ParticleDefinition* theSecNeutronDefinition = G4Neutron::Neutron();
+     theSecNeutron->SetDefinition(theSecNeutronDefinition);
+     theSecNeutron->SetKineticEnergy(T_N);
+     theSecNeutron->SetMomentumDirection(MomDir_N);
+
+     // Generate a Secondary C12
+     G4DynamicParticle* theSecC12 = new G4DynamicParticle;
+     // GetIon() Method works whether particle exists in physicslist or not. 
+     // Arguements are GetIon(Charge,Mass,ExcitationEng)
+     G4ParticleDefinition* theSecC12Definition = G4IonTable::GetIonTable()->GetIon(6,12,0.);
+     theSecC12->SetDefinition(theSecC12Definition);
+     theSecC12->SetKineticEnergy(T_C12el);
+     theSecC12->SetMomentumDirection(MomDir_C12);
+   
+     // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     // Set final tracks in motion!
+     G4Track* theNTrack = new G4Track(theSecNeutron,GlobalTime,thePosition);
+     theNTrack->SetTouchableHandle(theTouchable);
+     G4Track* theC12Track = new G4Track(theSecC12,GlobalTime,thePosition);
+     theC12Track->SetTouchableHandle(theTouchable);
+
+     aParticleChange.SetNumberOfSecondaries(2);
+     aParticleChange.AddSecondary(theNTrack);
+     aParticleChange.AddSecondary(theC12Track);
+  
+    // G4cout << "Made it to the end ! " << G4endl;
+   }
+ else if(ReactionName == "N_C12_NGamma")
+   {
+     // 24 Apr. 2008 - BTR - This version replaces version in previous
+     // menate.cc to 12C(n,n'gamma) reaction in orig FORTRAN MENATE
+
+     G4double Available_Eng;
+
+     if(KinEng_Int >= 8.5*MeV)
+       { Available_Eng = 8.5*MeV*(G4UniformRand()); } // Max available Eng = 8.5 MeV ?
+     else
+       { Available_Eng = KinEng_Int*G4UniformRand(); }
+     
+
+     //G4double Total_Gamma_Eng = ShareGammaEngC12(Available_Eng);
+     //Changed such that one 4.4 MeV gamma is always produced if the
+     //nng4 reaction is called.
+     //if the energy is >4.43 MeV then 1 gamma is produced.
+     G4double enough_gamma_eng=0*MeV;
+     if(KinEng_Int >= 4.5*MeV) enough_gamma_eng = 5.0*MeV;
+     G4double Total_Gamma_Eng = ShareGammaEngC12(enough_gamma_eng);
+
+     G4ThreeVector MomDir_N;
+     G4ThreeVector MomDir_C12;
+
+     // N'
+
+     Available_Eng = 0.9230769*KinEng_Int-Total_Gamma_Eng;
+     if(Available_Eng <= 0.)
+       {Available_Eng = 0.;} // = 0 in Fortran code - BTR 
+
+     G4double cos_theta_iso = 1.-(2.*G4UniformRand());
+     //zwk
+     if(fwrdANGLES) cos_theta_iso = pow(G4UniformRand(),1./4.0);
+
+     G4double T_N = KinEng_Int/169.+0.9230769*Available_Eng + 
+                    (0.1478106*sqrt(KinEng_Int*Available_Eng))*cos_theta_iso;
+     G4double theta_N = acos(cos_theta_iso);
+     G4double phi_N = 2.*Pi*G4UniformRand();
+
+     MomDir_N = GenMomDir(MomDir_Int,theta_N,phi_N);
+ 
+     // C12*
+
+     G4double T_C12 = KinEng_Int - T_N - Total_Gamma_Eng;
+     if(T_C12 <= 0.)
+       {T_C12 = 0.;}
+     G4double theta_C12 = Pi - theta_N;
+     G4double phi_C12 = Pi + phi_N;
+
+     MomDir_C12 = GenMomDir(MomDir_Int,theta_C12,phi_C12);
+
+     // Generate a Secondary Neutron
+     G4DynamicParticle* theSecNeutron = new G4DynamicParticle;
+     G4ParticleDefinition* theSecNeutronDefinition = G4Neutron::Neutron();
+     theSecNeutron->SetDefinition(theSecNeutronDefinition);
+     theSecNeutron->SetKineticEnergy(T_N);
+     theSecNeutron->SetMomentumDirection(MomDir_N);
+
+     // Generate a Secondary C12*
+     G4DynamicParticle* theSecC12 = new G4DynamicParticle;
+     // GetIon() Method works whether particle exists in physicslist or not. 
+     // Arguements are GetIon(Charge,Mass,ExcitationEng)
+     G4ParticleDefinition* theSecC12Definition = G4IonTable::GetIonTable()->GetIon(6,12,0.);
+     theSecC12->SetDefinition(theSecC12Definition);
+     theSecC12->SetKineticEnergy(T_C12);
+     theSecC12->SetMomentumDirection(MomDir_C12);
+
+     // 4.439 MeV Gamma - emitted isotropically from reaction point..
+     // -- 24 Apr 2008 - BTR - With 8.5 MeV limit given at start of 
+     //    MENATE function for this reaction, can not produce more
+     //    than one 4.439 MeV gamma. 
+     // - 19 May 2008 - BTR
+     // --- Removed 400 keV gamma ray counter from original MENATE code
+
+     G4int NumberOfSec = 2+Num_gamma_4439k;
+     aParticleChange.SetNumberOfSecondaries(NumberOfSec);
+
+     //G4cout << Available_Eng/MeV << G4endl;
+     //G4cout << "Num gammas: " << Num_gamma_4439k << G4endl;
+	 if(Num_gamma_4439k > 0)
+	   {	     
+	     G4double T_Gamma = 4.439*MeV;
+	     G4double theta_Gamma = acos(1.-(2.*G4UniformRand()));
+	     G4double phi_Gamma = 2.*Pi*G4UniformRand();
+	     
+	     G4ThreeVector MomDir_Gamma;
+	     MomDir_Gamma = GenMomDir(MomDir_Int,theta_Gamma,phi_Gamma);
+
+	     // Generate a Secondary Gamma (4.439 MeV)
+	     G4DynamicParticle* theSecGamma = new G4DynamicParticle;
+	     G4ParticleDefinition* theGammaDefinition = G4Gamma::Gamma();
+	     theSecGamma->SetDefinition(theGammaDefinition);
+	     theSecGamma->SetKineticEnergy(T_Gamma);
+	     theSecGamma->SetMomentumDirection(MomDir_Gamma);
+
+	     aParticleChange.SetNumberOfSecondaries(2+Num_gamma_4439k);
+
+	     G4Track* theGammaTrack = new G4Track(theSecGamma,GlobalTime,thePosition);
+	     theGammaTrack->SetTouchableHandle(theTouchable);
+	     aParticleChange.AddSecondary(theGammaTrack);
+	   }
+    
+     // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     // Set final tracks in motion!
+     G4Track* theNTrack = new G4Track(theSecNeutron,GlobalTime,thePosition);
+     theNTrack->SetTouchableHandle(theTouchable);
+     G4Track* theC12Track = new G4Track(theSecC12,GlobalTime,thePosition);
+     theC12Track->SetTouchableHandle(theTouchable);
+     
+     aParticleChange.AddSecondary(theNTrack);
+     aParticleChange.AddSecondary(theC12Track);
+     
+    // G4cout << "Made it to the end ! " << G4endl;
+ 
+   }
+ else if(ReactionName == "N_C12_A_Be9")
+   {
+     // Copied from MENATE
+     // Reaction can not occur if incoming neutron energy is below 6.176 MeV
+     // Q Value = - 5.701 MeV
+
+     // Uses formula for C12 recoil to calculate direction of 9Be
+
+     G4ThreeVector MomDir_Alpha;
+     G4ThreeVector MomDir_Be9;
+
+     G4double Q_value = -5.701*MeV;
+     // 0.9230769 = Mass_C12/(Mass_N+Mass_C12) - converts to CM frame energy
+     G4double Available_Eng = 0.9230769*KinEng_Int+Q_value;
+
+     if(Available_Eng <= 0.)
+       { Available_Eng = 0.; }
+
+     // the alpha
+
+     G4double cos_theta_iso = 1.-(2.*G4UniformRand());
+     //zwk
+     if(fwrdANGLES) cos_theta_iso = pow(G4UniformRand(),1./4.0);
+
+     // 0.0236686 = Malpha*MassN/(MassC12+MassN)^2
+     // 0.6923077 = MBe9/(MassN+MassC12)
+     // 0.2560155 = 2.*sqrt(Mn*MBe9*Malpha/(MassC12+MassN)^3)
+
+     G4double T_Alpha = 0.0236686*KinEng_Int+0.6923077*Available_Eng+
+                        (0.2560155*sqrt(KinEng_Int*Available_Eng))*cos_theta_iso;
+
+     G4double theta_Alpha = 0.;
+     G4double phi_Alpha = 0.;
+
+     if(T_Alpha > 1.e-5)
+       {
+	 // 0.1538462 = sqrt(Malpha*Mn)/(Mn+Mc12)
+	 // 0.8320503 = sqrt(MBe9/(MassC12+MassN))
+
+	 G4double Arg = (0.1538462*sqrt(KinEng_Int)+0.8320503*sqrt(Available_Eng)*cos_theta_iso)/(sqrt(T_Alpha));
+
+	 if(Arg > 1.)
+	   { Arg = 1.; }
+
+	 theta_Alpha = acos(Arg);
+	 phi_Alpha = 2.*Pi*G4UniformRand();
+       }
+  
+     MomDir_Alpha = GenMomDir(MomDir_Int,theta_Alpha,phi_Alpha);
+ 
+     // Be9 - Need to check kinematics - maybe not right - 18 Apr 2008, BTR
+
+     G4double T_Be9 = KinEng_Int + Q_value - T_Alpha;
+     G4double theta_Be9 = Pi - theta_Alpha;
+     G4double phi_Be9 = Pi + phi_Alpha;
+
+     MomDir_Be9 = GenMomDir(MomDir_Int,theta_Be9,phi_Be9);
+
+     // Generate a Secondary Alpha
+     G4DynamicParticle* theSecAlpha = new G4DynamicParticle;
+     G4ParticleDefinition* theSecAlphaDefinition = G4Alpha::Alpha();
+     theSecAlpha->SetDefinition(theSecAlphaDefinition);
+     theSecAlpha->SetKineticEnergy(T_Alpha);
+     theSecAlpha->SetMomentumDirection(MomDir_Alpha);
+
+     // Generate a Secondary Be9
+     G4DynamicParticle* theSecBe9 = new G4DynamicParticle;
+     // GetIon() Method works whether particle exists in physicslist or not. 
+     // Arguements are GetIon(Charge,Mass,ExcitationEng)
+     G4ParticleDefinition* theSecBe9Definition = G4IonTable::GetIonTable()->GetIon(4,9,0.);
+     theSecBe9->SetDefinition(theSecBe9Definition);
+     theSecBe9->SetKineticEnergy(T_Be9);
+     theSecBe9->SetMomentumDirection(MomDir_Be9);
+
+    // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     // Set final tracks in motion!
+     G4Track* theAlphaTrack = new G4Track(theSecAlpha,GlobalTime,thePosition);
+     theAlphaTrack->SetTouchableHandle(theTouchable);
+     G4Track* theBe9Track = new G4Track(theSecBe9,GlobalTime,thePosition);
+     theBe9Track->SetTouchableHandle(theTouchable);
+
+     aParticleChange.SetNumberOfSecondaries(2);
+     aParticleChange.AddSecondary(theAlphaTrack);
+     aParticleChange.AddSecondary(theBe9Track);
+  
+     /*
+     //---Test Momentum Conservation----
+     G4cout << "\n\n------------------"<< G4endl;
+
+     //incoming neutron
+     G4DynamicParticle *p1 = (G4DynamicParticle*) aTrack.GetDynamicParticle();
+     G4ThreeVector vec1 = p1->GetMomentum();
+     G4cout << "p1, px: " << vec1.x()/MeV << "  py: " << vec1.y()/MeV << " pz: " << vec1.z()/MeV << "  mag: " << vec1.mag()/MeV << G4endl;
+     G4cout << "  Total Mom: " << p1 ->GetTotalMomentum()/MeV << "  TotalE: " << p1->GetTotalEnergy()/MeV << "  KE: " << p1->GetKineticEnergy()/MeV << G4endl;
+
+
+     G4DynamicParticle *p2 = (G4DynamicParticle*) theAlphaTrack->GetDynamicParticle();
+     G4ThreeVector vec2 = p2->GetMomentum();
+     G4cout << "p2, px: " << vec2.x()/MeV << "  py: " << vec2.y()/MeV << " pz: " << vec2.z()/MeV << "  mag: " << vec2.mag()/MeV << G4endl;
+     G4cout << "  Total Mom: " << p2->GetTotalMomentum()/MeV << "  TotalE: " << p2->GetTotalEnergy()/MeV << "  KE: " << p2->GetKineticEnergy()/MeV << G4endl;
+
+
+     G4DynamicParticle *p3 = (G4DynamicParticle*) theBe9Track->GetDynamicParticle();
+     G4ThreeVector vec3 = p3->GetMomentum();
+     G4cout << "p3, px: " << vec3.x()/MeV << "  py: " << vec3.y()/MeV << " pz: " << vec3.z()/MeV << "  mag: " << vec3.mag()/MeV << G4endl;
+     G4cout << "  Total Mom: " << p3->GetTotalMomentum()/MeV << "  TotalE: " << p3->GetTotalEnergy()/MeV << "  KE: " << p3->GetKineticEnergy()/MeV << G4endl;
+     //-----------
+     */
+
+    // G4cout << "Made it to the end ! " << G4endl;
+   }
+ else if(ReactionName == "N_C12_P_B12")
+   {
+     // Charge exchange Reaction copied from MENATE
+     G4double Q_value = -12.587*MeV;
+
+     G4ThreeVector MomDir_P;
+     G4ThreeVector MomDir_B12;
+
+     G4double Available_Eng = 0.9230769*KinEng_Int+Q_value;
+
+     if(Available_Eng < 0.)
+       { Available_Eng = 0.; }
+
+     // the proton
+
+     G4double cos_theta_iso = 1.-(2.*G4UniformRand());
+     //zwk
+     if(fwrdANGLES) cos_theta_iso = pow(G4UniformRand(),1./4.0);
+
+     //1/169. = Mp*Mn/(Mn+MC12)^2
+     // .9230769 = MB12/(Mn+MC12)
+     // .1478106 = 2*sqrt(Mn*MB12*Mp/(Mc12+Mn)^3)
+
+     G4double T_P = KinEng_Int/169. + 0.9230769*Available_Eng + 
+                    (0.1478106*sqrt(KinEng_Int*Available_Eng))*cos_theta_iso;
+     
+     G4double theta_P = 0.;
+     G4double phi_P = 0.;
+
+     if(T_P > 1.e-5)
+       {
+	 // 1/13. = sqrt(Mp*Mn)/(Mn+Mc)
+	 // 0.9607689 = sqrt(MB12/(Mn+MC12))
+
+	 G4double Arg = (sqrt(KinEng_Int)/13. + 0.9607689*sqrt(Available_Eng)*cos_theta_iso)/(sqrt(T_P)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_P = acos(Arg);
+	 phi_P = 2.*Pi*G4UniformRand();
+       }
+
+     MomDir_P = GenMomDir(MomDir_Int,theta_P,phi_P);
+
+ // B12 - Need to check kinematics - maybe not right - 18 Apr 2008, BTR
+
+     G4double T_B12 = KinEng_Int + Q_value - T_P;
+     G4double theta_B12 = Pi - theta_P;
+     G4double phi_B12 = Pi + phi_P;
+
+     MomDir_B12 = GenMomDir(MomDir_Int,theta_B12,phi_B12);
+
+     // Generate a Secondary Proton
+     G4DynamicParticle* theSecProton = new G4DynamicParticle;
+     G4ParticleDefinition* theSecPDefinition = G4Proton::Proton();
+     theSecProton->SetDefinition(theSecPDefinition);
+     theSecProton->SetKineticEnergy(T_P);
+     theSecProton->SetMomentumDirection(MomDir_P);
+
+     // Generate a Secondary B12
+     G4DynamicParticle* theSecB12 = new G4DynamicParticle;
+     // GetIon() Method works whether particle exists in physicslist or not. 
+     // Arguements are GetIon(Charge,Mass,ExcitationEng)
+     G4ParticleDefinition* theSecB12Definition = G4IonTable::GetIonTable()->GetIon(5,12,0.);
+     theSecB12->SetDefinition(theSecB12Definition);
+     theSecB12->SetKineticEnergy(T_B12);
+     theSecB12->SetMomentumDirection(MomDir_B12);
+
+    // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     // Set final tracks in motion!
+     G4Track* thePTrack = new G4Track(theSecProton,GlobalTime,thePosition);
+     thePTrack->SetTouchableHandle(theTouchable);
+     G4Track* theB12Track = new G4Track(theSecB12,GlobalTime,thePosition);
+     theB12Track->SetTouchableHandle(theTouchable);
+
+     aParticleChange.SetNumberOfSecondaries(2);
+     aParticleChange.AddSecondary(thePTrack);
+     aParticleChange.AddSecondary(theB12Track);
+  
+    // G4cout << "Made it to the end ! " << G4endl;
+   }
+ else if(ReactionName == "N_C12_NNP_B11")
+   {
+     // Reaction copied from MENATE
+     // Treated as :
+     // n + 12C ---> 12C* + n'
+     // 12C*    ---> 11B + p
+
+     G4double Q_value = -15.956*MeV;
+
+     G4ThreeVector MomDir_N;
+     G4ThreeVector MomDir_P;
+     G4ThreeVector MomDir_B11;
+
+     // Scattered neutron (n')
+     G4double Available_Eng = 0.9230769*KinEng_Int+Q_value;
+
+     if(Available_Eng < 0.)
+       { Available_Eng = 1.e-3; }
+
+     G4double Eng_Evap1 = Evaporate_Eng(AMass_Material,Available_Eng);
+
+     G4double cos_theta_iso = 1.-2.*G4UniformRand();
+     //zwk
+     if(fwrdANGLES) cos_theta_iso = pow(G4UniformRand(),1./4.0);
+
+     // 1/169. = (Mn/(Mn+Mc))^2
+     // 0.1538462 = 2Mn/(Mn+Mc)
+
+     G4double T_N = KinEng_Int/169. + Eng_Evap1 + (0.1538462*sqrt(KinEng_Int*Eng_Evap1))*cos_theta_iso;
+     
+     G4double theta_N = 0.;
+     G4double phi_N = 0.;
+
+     if(T_N > 1.e-5)
+       {
+	 // 1/13. = Mn/(Mn+Mc)
+
+	 G4double Arg = (sqrt(KinEng_Int)/13. + (sqrt(Eng_Evap1)*cos_theta_iso))/(sqrt(T_N)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_N = acos(Arg);
+	 phi_N = 2.*Pi*G4UniformRand();
+	 //G4cout << "12C(n,np)11B angle of neutron: " << theta_N*180/3.14 << G4endl;
+       }
+
+     MomDir_N = GenMomDir(MomDir_Int,theta_N,phi_N);
+
+     // Scattered 12C*
+     // 1/13. = Mn(Mc+Mn)
+     // 1.0833333 = (Mc+Mn)/Mc
+
+     G4double T_C12Star = KinEng_Int/13. + 1.0833333*Eng_Evap1 - T_N;
+
+     G4double theta_C12Star = 0.;
+     G4double phi_C12Star = phi_N+Pi;
+
+     if(T_C12Star > 1.e-5)
+       {
+	 // 0.2664694 = sqrt(Mn*Mc)/(Mn+Mc)
+	 // 0.2886751 = sqrt(Mn/Mc)
+	 G4double Arg = (0.2664694*sqrt(KinEng_Int) - (0.2886751*sqrt(Eng_Evap1)*cos_theta_iso))/(sqrt(T_C12Star)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_C12Star = acos(Arg);
+       }
+     
+     // Now the proton is emitted in the frame of the scattered C12*
+     // At the end, the angles are put back into the frame of the original neutron
+ 
+     Available_Eng = KinEng_Int + Q_value - T_N - T_C12Star;
+
+     if(Available_Eng < 0.)
+       { Available_Eng = 0.; }
+
+     cos_theta_iso = 1.-(2.*G4UniformRand());
+
+     // 1/12. = Mp/MC12
+     // .9166667 = MB11/MC12
+     // .5527708 = 2*sqrt(MB11*Mp)/Mc
+
+     G4double T_P = T_C12Star/12. + 0.9166667*Available_Eng + 
+                    (0.5527708*sqrt(Available_Eng*T_C12Star))*cos_theta_iso;
+     
+     G4double theta_C12_P = 0.;
+     G4double phi_C12_P = 0.;
+
+     if(T_P > 1.e-5)
+       {
+	 // 0.2886751 = sqrt(Mp/Mc)
+	 // 0.9574271 = sqrt((MB11)/(MC12))
+
+	 G4double Arg = (0.2886751*sqrt(T_C12Star) + 0.9574271*sqrt(Available_Eng)*cos_theta_iso)/(sqrt(T_P)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_C12_P = acos(Arg);
+	 phi_C12_P = 2.*Pi*G4UniformRand();
+       }
+
+     // Now Start With Z-Axis and then go to incoming neutron frame ?
+     //G4ThreeVector MomDir_ZAxis = G4ThreeVector(0.,0.,1.);
+
+     G4ThreeVector MomDir_ZAxis = MomDir_Int;
+     G4ThreeVector MomDir_C12Star = GenMomDir(MomDir_ZAxis,theta_C12Star,phi_C12Star);
+
+     MomDir_P = GenMomDir(MomDir_C12Star,theta_C12_P,phi_C12_P);
+
+     // B11 - Need to check kinematics - maybe not right - 18 Apr 2008, BTR
+
+     G4double T_B11 = KinEng_Int + Q_value - T_N - T_P; // Remaining Eng
+     if(T_B11 < 0.)
+       {T_B11 = 1e-9;}
+
+     G4double theta_B11 = Pi - theta_C12_P;
+     G4double phi_B11 = Pi + phi_C12_P;
+
+     MomDir_B11 = GenMomDir(MomDir_Int,theta_B11,phi_B11);
+
+// Generate a Secondary Neutron
+     G4DynamicParticle* theSecNeutron = new G4DynamicParticle;
+     G4ParticleDefinition* theSecNDefinition = G4Neutron::Neutron();
+     theSecNeutron->SetDefinition(theSecNDefinition);
+     theSecNeutron->SetKineticEnergy(T_N);
+     theSecNeutron->SetMomentumDirection(MomDir_N);
+
+// Generate a Secondary Proton
+     G4DynamicParticle* theSecProton = new G4DynamicParticle;
+     G4ParticleDefinition* theSecPDefinition = G4Proton::Proton();
+     theSecProton->SetDefinition(theSecPDefinition);
+     theSecProton->SetKineticEnergy(T_P);
+     theSecProton->SetMomentumDirection(MomDir_P);
+
+     // Generate a Secondary B11
+     G4DynamicParticle* theSecB11 = new G4DynamicParticle;
+     // GetIon() Method works whether particle exists in physicslist or not. 
+     // Arguements are GetIon(Charge,Mass,ExcitationEng)
+     G4ParticleDefinition* theSecB11Definition = G4IonTable::GetIonTable()->GetIon(5,11,0.);
+     theSecB11->SetDefinition(theSecB11Definition);
+     theSecB11->SetKineticEnergy(T_B11);
+     theSecB11->SetMomentumDirection(MomDir_B11);
+
+    // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     // Set final tracks in motion!
+     G4Track* theNTrack = new G4Track(theSecNeutron,GlobalTime,thePosition);
+     theNTrack->SetTouchableHandle(theTouchable);
+     G4Track* thePTrack = new G4Track(theSecProton,GlobalTime,thePosition);
+     thePTrack->SetTouchableHandle(theTouchable);
+     G4Track* theB11Track = new G4Track(theSecB11,GlobalTime,thePosition);
+     theB11Track->SetTouchableHandle(theTouchable);
+
+     aParticleChange.SetNumberOfSecondaries(3);
+     aParticleChange.AddSecondary(theNTrack);
+     aParticleChange.AddSecondary(thePTrack);
+     aParticleChange.AddSecondary(theB11Track);
+  
+    // G4cout << "Made it to the end ! " << G4endl;
+   }
+ else if(ReactionName == "N_C12_N2N_C11")
+   {
+     // Reaction copied from MENATE
+     // Treated as :
+     // n + 12C ---> 12C* + n'
+     // 12C*    ---> 11C + n
+
+     G4double Q_value = -18.721*MeV;
+
+     G4ThreeVector MomDir_N1;
+     G4ThreeVector MomDir_N2;
+     G4ThreeVector MomDir_C11;
+
+     // Scattered neutron (n')
+     G4double Available_Eng = 0.9230769*KinEng_Int+Q_value;
+
+     if(Available_Eng < 0.)
+       { Available_Eng = 1.e-3; }
+
+     G4double Eng_Evap1 = Evaporate_Eng(AMass_Material,Available_Eng);
+
+     G4double cos_theta_iso = 1.-(2.*G4UniformRand());
+     //zwk
+     if(fwrdANGLES) cos_theta_iso = pow(G4UniformRand(),1./4.0);
+
+     // 1/169. = (Mn/(Mn+Mc))^2
+     // 0.1538462 = 2Mn/(Mn+Mc)
+
+     G4double T_N1 = KinEng_Int/169. + Eng_Evap1 + (0.1538462*sqrt(KinEng_Int*Eng_Evap1))*cos_theta_iso;
+     
+     G4double theta_N1 = 0.;
+     G4double phi_N1 = 0.;
+
+     if(T_N1 > 1.e-5)
+       {
+	 // 1/13. = Mn/(Mn+Mc)
+
+	 G4double Arg = (sqrt(KinEng_Int)/13. + (sqrt(Eng_Evap1)*cos_theta_iso))/(sqrt(T_N1)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_N1 = acos(Arg);
+	 phi_N1 = 2.*Pi*G4UniformRand();
+       }
+
+     MomDir_N1 = GenMomDir(MomDir_Int,theta_N1,phi_N1);
+
+     // Scattered 12C*
+     // 1/13. = Mn(Mc+Mn)
+     // 1.0833333 = (Mc+Mn)/Mc
+
+     G4double T_C12Star = KinEng_Int/13. + 1.0833333*Eng_Evap1 - T_N1;
+
+     G4double theta_C12Star = 0.;
+     G4double phi_C12Star = phi_N1+Pi;
+
+     if(T_C12Star > 1.e-5)
+       {
+	 // 0.2664694 = sqrt(Mn*Mc)/(Mn+Mc)
+	 // 0.2886751 = sqrt(Mn/Mc)
+	 G4double Arg = (0.2664694*sqrt(KinEng_Int) - (0.2886751*sqrt(Eng_Evap1)*cos_theta_iso))/(sqrt(T_C12Star)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_C12Star = acos(Arg);
+       }
+     
+     // Now neutron2 is emitted in the frame of the scattered C12*
+     // At the end, the angles are put back into the frame of the original neutron
+ 
+     Available_Eng = KinEng_Int + Q_value - T_N1 - T_C12Star;
+
+     if(Available_Eng < 0.)
+       { Available_Eng = 1.e-3; }
+
+     G4double Eng_Evap2 = Evaporate_Eng(AMass_Material,Available_Eng);
+
+     cos_theta_iso = 1.-(2.*G4UniformRand());
+
+     // .5773503 = 2*sqrt(Mn/Mc)
+
+     G4double T_N2 = T_C12Star/12. + Eng_Evap2 + 
+                    (0.5773503*sqrt(T_C12Star*Eng_Evap2))*cos_theta_iso;
+     
+     G4double theta_C12_N2 = acos(cos_theta_iso);
+     G4double phi_C12_N2 = 2.*Pi*G4UniformRand();
+	 
+     // Now Start With Z-Axis and then go to incoming neutron frame ?
+     //G4ThreeVector MomDir_ZAxis = G4ThreeVector(0.,0.,1.);
+    
+     G4ThreeVector MomDir_ZAxis = MomDir_Int;
+     G4ThreeVector MomDir_C12Star = GenMomDir(MomDir_ZAxis,theta_C12Star,phi_C12Star);
+
+     MomDir_N2 = GenMomDir(MomDir_C12Star,theta_C12_N2,phi_C12_N2);
+
+     // C11 - Need to check kinematics - maybe not right - 18 Apr 2008, BTR
+
+     G4double T_C11 = KinEng_Int + Q_value - T_N1 - T_N2; // Remaining Eng
+     if(T_C11 <= 0.)
+       {T_C11 = 1e-9;}
+
+     G4double theta_C11 = Pi - theta_C12_N2;
+     G4double phi_C11 = Pi + phi_C12_N2;
+
+     MomDir_C11 = GenMomDir(MomDir_Int,theta_C11,phi_C11);
+
+// Generate a Secondary Neutron1
+     G4DynamicParticle* theSecNeutron1 = new G4DynamicParticle;
+     G4ParticleDefinition* theSecN1Definition = G4Neutron::Neutron();
+     theSecNeutron1->SetDefinition(theSecN1Definition);
+     theSecNeutron1->SetKineticEnergy(T_N1);
+     theSecNeutron1->SetMomentumDirection(MomDir_N1);
+
+// Generate a Secondary Neutron2
+     G4DynamicParticle* theSecNeutron2 = new G4DynamicParticle;
+     G4ParticleDefinition* theSecN2Definition = G4Neutron::Neutron();
+     theSecNeutron2->SetDefinition(theSecN2Definition);
+     theSecNeutron2->SetKineticEnergy(T_N2);
+     theSecNeutron2->SetMomentumDirection(MomDir_N2);
+
+     // Generate a Secondary C11
+     G4DynamicParticle* theSecC11 = new G4DynamicParticle;
+     // GetIon() Method works whether particle exists in physicslist or not. 
+     // Arguements are GetIon(Charge,Mass,ExcitationEng)
+     G4ParticleDefinition* theSecC11Definition = G4IonTable::GetIonTable()->GetIon(6,11,0.);
+     theSecC11->SetDefinition(theSecC11Definition);
+     theSecC11->SetKineticEnergy(T_C11);
+     theSecC11->SetMomentumDirection(MomDir_C11);
+
+    // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     // Set final tracks in motion!
+     G4Track* theN1Track = new G4Track(theSecNeutron1,GlobalTime,thePosition);
+     theN1Track->SetTouchableHandle(theTouchable);
+     G4Track* theN2Track = new G4Track(theSecNeutron2,GlobalTime,thePosition);
+     theN2Track->SetTouchableHandle(theTouchable);
+     G4Track* theC11Track = new G4Track(theSecC11,GlobalTime,thePosition);
+     theC11Track->SetTouchableHandle(theTouchable);
+
+     aParticleChange.SetNumberOfSecondaries(3);
+     aParticleChange.AddSecondary(theN1Track);
+     aParticleChange.AddSecondary(theN2Track);
+     aParticleChange.AddSecondary(theC11Track);
+
+     /*
+     G4double T_N_Sum = T_N1+T_N2;
+     G4cout << "n, 2n C11 event! " << G4endl;
+     G4cout << "T_N1 = " << T_N1 << "T_N2 = " << T_N2 << " , T_Sum = " << T_N_Sum << G4endl;
+     G4cout << "Total Eng Final State : " << T_N_Sum+T_C11 << " , Eng_Int+Qvalue = " << KinEng_Int+Q_value << G4endl; 
+     */     
+    // G4cout << "Made it to the end ! " << G4endl;
+   }
+else if(ReactionName == "N_C12_NN3Alpha")
+   {
+     // Reaction copied from MENATE
+     // Treated as :
+     // n + 12C ---> 12C* + n'
+     // 12C*    ---> 8Be + alpha1
+     // 8Be*    ---> alpha2+alpha3
+
+     G4double Q_value = -7.275*MeV;
+
+     G4ThreeVector MomDir_N;
+     G4ThreeVector MomDir_Alpha1;
+     G4ThreeVector MomDir_Alpha2;
+     G4ThreeVector MomDir_Alpha3;
+
+     // Scattered neutron (n')
+     G4double Available_Eng = 0.9230769*KinEng_Int+Q_value;
+
+     if(Available_Eng < 0.)
+       { Available_Eng = 1.e-3; }
+
+     G4double Eng_Evap1 = Evaporate_Eng(AMass_Material,Available_Eng);
+
+     G4double cos_theta_iso = 1.-(2.*G4UniformRand());
+     //zwk
+     if(fwrdANGLES) cos_theta_iso = pow(G4UniformRand(),1./4.0);
+
+     // 1/169. = (Mn/(Mn+Mc))^2
+     // 0.1538462 = 2Mn/(Mn+Mc)
+
+     G4double T_N = KinEng_Int/169. + Eng_Evap1 + (0.1538462*sqrt(KinEng_Int*Eng_Evap1))*cos_theta_iso;
+     
+     G4double theta_N = 0.;
+     G4double phi_N = 0.;
+
+     if(T_N > 1.e-5)
+       {
+	 // 1/13. = Mn/(Mn+Mc)
+
+	 G4double Arg = (sqrt(KinEng_Int)/13. + (sqrt(Eng_Evap1)*cos_theta_iso))/(sqrt(T_N)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_N = acos(Arg);
+	 phi_N = 2.*Pi*G4UniformRand();
+       }
+
+     MomDir_N = GenMomDir(MomDir_Int,theta_N,phi_N);
+
+     // Scattered 12C*
+     // 1/13. = Mn(Mc+Mn)
+     // 1.0833333 = (Mc+Mn)/Mc
+
+     G4double T_C12Star = KinEng_Int/13. + 1.0833333*Eng_Evap1 - T_N;
+
+     G4double theta_C12Star = 0.;
+     G4double phi_C12Star = phi_N+Pi;
+
+     if(T_C12Star > 1.e-5)
+       {
+	 // 0.2664694 = sqrt(Mn*Mc)/(Mn+Mc)
+	 // 0.2886751 = sqrt(Mn/Mc)
+	 G4double Arg = (0.2664694*sqrt(KinEng_Int) - (0.2886751*sqrt(Eng_Evap1)*cos_theta_iso))/(sqrt(T_C12Star)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_C12Star = acos(Arg);
+       }
+     
+     // Now Alpha1 is emitted in the frame of the scattered C12*
+     // At the end, the angles are put back into the frame of the original neutron
+ 
+     Available_Eng = (KinEng_Int + Q_value - T_N - T_C12Star)*G4UniformRand();
+
+     if(Available_Eng < 0.)
+       { Available_Eng = 0.; }
+
+     cos_theta_iso = 1.-(2.*G4UniformRand());
+
+     // 1./3. = MA1/MC12
+     // 0.6666667 = MBe8/MC12
+     // 0.9428090 = 2*sqrt(Malpha*M8Be)/Mc12)
+
+     G4double T_Alpha1 = T_C12Star/3. + 0.6666667*Available_Eng + 
+                    (0.9428090*sqrt(Available_Eng*T_C12Star))*cos_theta_iso;
+     
+     G4double theta_Alpha1 = 0.;
+     G4double phi_Alpha1 = 0.;
+
+     if(T_Alpha1 > 1.e-5)
+       {
+	 // 0.5773503 = sqrt(Malpha/MC12)
+	 // 0.8164966 = sqrt((MBe8)/(MC12))
+
+	 G4double Arg = (0.5773503*sqrt(T_C12Star) + 0.8164966*sqrt(Available_Eng)*cos_theta_iso)/(sqrt(T_Alpha1)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_Alpha1 = acos(Arg);
+	 phi_Alpha1 = 2.*Pi*G4UniformRand();
+       }
+
+     // Now Start With Z-Axis and then go to incoming neutron frame ?
+     //  G4ThreeVector MomDir_ZAxis = G4ThreeVector(0.,0.,1.);
+     G4ThreeVector MomDir_ZAxis = MomDir_Int;
+     G4ThreeVector MomDir_C12Star = GenMomDir(MomDir_ZAxis,theta_C12Star,phi_C12Star);
+
+     MomDir_Alpha1 = GenMomDir(MomDir_C12Star,theta_Alpha1,phi_Alpha1);
+
+     // Be8* Kinematics --- Particle decayed into the other alphas
+     // Angles in frame of scattered C12*
+
+     G4double T_Be8Star = T_C12Star + Available_Eng - T_Alpha1; // Remaining Eng
+    
+     G4double theta_Be8Star = 0.;
+     G4double phi_Be8Star = phi_Alpha1+Pi;
+
+     if(T_Be8Star > 1.e-5)
+       {
+	 // 0.5773503 = sqrt(Malpha/MC12)
+	 // 0.8164966 = sqrt(M8Be/MC12)
+	 G4double Arg = (0.8164966*sqrt(T_C12Star) - (0.5773503*sqrt(Available_Eng)*cos_theta_iso))/(sqrt(T_Be8Star)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_Be8Star = acos(Arg);
+       }
+
+     G4ThreeVector MomDir_Be8Star = GenMomDir(MomDir_C12Star,theta_Be8Star,phi_Be8Star);
+
+     // Now Decay 8Be g.s. into 2 Alphas
+     // Q_value = 0.092*MeV
+
+     G4double Q_valueBe8 = 0.092*MeV;
+     Available_Eng = KinEng_Int+Q_value+Q_valueBe8-T_N-T_Alpha1-T_Be8Star; // Changed 23 Apr 2008 - BTR
+
+     if(Available_Eng < 0.)
+       {Available_Eng = 0.;}
+
+     cos_theta_iso = 1.-(2.*G4UniformRand());
+
+     // 0.5 = MA2/Be8
+ 
+     G4double T_Alpha2 = 0.5*(T_Be8Star+Available_Eng) + 
+                    (sqrt(Available_Eng*T_Be8Star))*cos_theta_iso;
+      if(T_Alpha2 < 0.)
+       {T_Alpha2 = 1e-9;}
+
+     G4double theta_Alpha2 = 0.;
+     G4double phi_Alpha2 = 0.;
+
+     if(T_Alpha2 > 1.e-5)
+       {
+	 // 0.7071068 = sqrt(Malpha/MBe8)
+	
+	 G4double Arg = (0.7071068*(sqrt(T_Be8Star) + sqrt(Available_Eng)*cos_theta_iso))/(sqrt(T_Alpha2)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_Alpha2 = acos(Arg);
+	 phi_Alpha2 = 2.*Pi*G4UniformRand();
+       }
+
+     MomDir_Alpha2 = GenMomDir(MomDir_Be8Star,theta_Alpha2,phi_Alpha2);
+
+     // Alpha3 emitted in frame of Be8
+
+     G4double T_Alpha3 = T_Be8Star + Available_Eng - T_Alpha2;
+    if(T_Alpha3 < 0.)
+       {T_Alpha3 = 1e-9;}
+  
+     G4double theta_Alpha3 = 0.;
+     G4double phi_Alpha3 = phi_Alpha2+Pi;
+
+     if(T_Alpha3 > 1.e-5)
+       {
+	 // 0.7071068 = sqrt(Malpha/MBe8)
+	
+	 G4double Arg = (0.7071068*(sqrt(T_Be8Star) - sqrt(Available_Eng)*cos_theta_iso))/(sqrt(T_Alpha3)); 
+	 if( Arg > 1.)
+	   { Arg = 1.; }
+	 theta_Alpha3 = acos(Arg);
+       }
+
+     MomDir_Alpha3 = GenMomDir(MomDir_Be8Star,theta_Alpha3,phi_Alpha3);
+
+// Generate a Secondary Neutron
+     G4DynamicParticle* theSecNeutron = new G4DynamicParticle;
+     G4ParticleDefinition* theSecNDefinition = G4Neutron::Neutron();
+     theSecNeutron->SetDefinition(theSecNDefinition);
+     theSecNeutron->SetKineticEnergy(T_N);
+     theSecNeutron->SetMomentumDirection(MomDir_N);
+
+// Generate a Secondary Alpha1
+     G4DynamicParticle* theSecAlpha1 = new G4DynamicParticle;
+     G4ParticleDefinition* theSecA1Definition = G4Alpha::Alpha();
+     theSecAlpha1->SetDefinition(theSecA1Definition);
+     theSecAlpha1->SetKineticEnergy(T_Alpha1);
+     theSecAlpha1->SetMomentumDirection(MomDir_Alpha1);
+
+// Generate a Secondary Alpha2
+     G4DynamicParticle* theSecAlpha2 = new G4DynamicParticle;
+     G4ParticleDefinition* theSecA2Definition = G4Alpha::Alpha();
+     theSecAlpha2->SetDefinition(theSecA2Definition);
+     theSecAlpha2->SetKineticEnergy(T_Alpha2);
+     theSecAlpha2->SetMomentumDirection(MomDir_Alpha2);
+
+// Generate a Secondary Alpha3
+     G4DynamicParticle* theSecAlpha3 = new G4DynamicParticle;
+     G4ParticleDefinition* theSecA3Definition = G4Alpha::Alpha();
+     theSecAlpha3->SetDefinition(theSecA3Definition);
+     theSecAlpha3->SetKineticEnergy(T_Alpha3);
+     theSecAlpha3->SetMomentumDirection(MomDir_Alpha3);
+
+    
+    // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     // Set final tracks in motion!
+     G4Track* theNTrack = new G4Track(theSecNeutron,GlobalTime,thePosition);
+     theNTrack->SetTouchableHandle(theTouchable);
+     G4Track* theA1Track = new G4Track(theSecAlpha1,GlobalTime,thePosition);
+     theA1Track->SetTouchableHandle(theTouchable);
+     G4Track* theA2Track = new G4Track(theSecAlpha2,GlobalTime,thePosition);
+     theA2Track->SetTouchableHandle(theTouchable);
+     G4Track* theA3Track = new G4Track(theSecAlpha3,GlobalTime,thePosition);
+     theA3Track->SetTouchableHandle(theTouchable);
+
+     aParticleChange.SetNumberOfSecondaries(4);
+     aParticleChange.AddSecondary(theNTrack);
+     aParticleChange.AddSecondary(theA1Track);
+     aParticleChange.AddSecondary(theA2Track);
+     aParticleChange.AddSecondary(theA3Track);
+
+     /*
+     G4double T_A_Sum = T_Alpha1+T_Alpha2+T_Alpha3;
+
+     G4cout << "n, n'3alpha event! " << G4endl;
+     G4cout << "T_N = " << T_N << G4endl;
+     G4cout << "A1 = " << T_Alpha1 << " ,A2 = " << T_Alpha2 << " , A3 = " << T_Alpha3 << ", A_Sum = " << T_A_Sum << G4endl;
+     G4cout << "Total Eng Final State : " << T_A_Sum+T_N << " , Eng_Int-Qvalue = " << KinEng_Int-7.275+0.092 << G4endl; 
+     */
+    // G4cout << "Made it to the end ! " << G4endl;
+   }
+ else if(ReactionName == "N_Fe_elastic")
+   {
+     G4double theta_N  = 0.;
+     G4double phi_N = 0.;
+
+     G4double T_N = 0.;
+//     G4double T_Feel = 0.;
+     G4ThreeVector MomDir_N;
+     G4ThreeVector MomDir_Fe;
+
+     /*
+     //Just going to use isotropic distribution in CM
+     //However good consider using C12 elastic scattering, may be similar
+     G4double cos_sq_theta = G4UniformRand(); 
+
+     // Calls diffractive angular distribution as in DEMONS
+     //G4double cos_theta_cm = NC12_DIFF(KinEng_Int);
+     // Convert according to Knoll
+     //G4double cos_theta_lab = sqrt((1.-cos_theta_cm)/2.);
+     //G4double cos_sq_theta = pow(cos_theta_lab,2);
+    
+     // .070177              =4*Mfe*Mn/(Mfe+Mn)^2
+     T_Feel = 0.07017*KinEng_Int*cos_sq_theta;
+
+     T_N = KinEng_Int - T_Feel;
+
+     if(T_N > 1.e-5)
+       {
+	 G4double arg = (sqrt(KinEng_Int)-sqrt(12.*T_Feel*cos_sq_theta))/sqrt(T_N);
+	 if(arg > 1.)
+	   {arg = 1.;}
+	 theta_N = acos(arg);
+         phi_N = 2.*Pi*G4UniformRand();
+       }
+
+     MomDir_N = GenMomDir(MomDir_Int,theta_N,phi_N);
+
+     // Carbon angles
+     G4double theta_Fe = acos(sqrt(cos_sq_theta));
+     G4double phi_Fe = phi_N+Pi;
+
+     MomDir_Fe = GenMomDir(MomDir_Int,theta_Fe,phi_Fe);
+     */
+
+
+     double cos_theta_cm = FeElastic_AngDist(KinEng_Int); // cosine of cm_angle
+     if(cos_theta_cm > 1) cos_theta_cm = 1;
+     double theta_cm = acos(cos_theta_cm); // of neutron
+     
+     // Following Knoll, calculate energy for proton first
+     double cos_theta_lab_Fe = sqrt((1.-cos_theta_cm)/2.);
+     double theta_lab_Fe = acos(cos_theta_lab_Fe);
+     double phi_Fe = 2.*Pi*G4UniformRand();
+     
+     double T_Fe = KinEng_Int*pow(cos_theta_lab_Fe,2)*4*56/pow(57.,2.);
+     
+     MomDir_Fe = GenMomDir(MomDir_Int,theta_lab_Fe,phi_Fe);
+     
+     // scattered neutron ----------------
+     // angles changed from cm to lab as in Marian and Young
+     theta_N = atan(sin(theta_cm)/(cos_theta_cm+(1/56)) );
+     phi_N = phi_Fe+Pi;
+     
+     T_N = KinEng_Int - T_Fe;    
+     
+     MomDir_N = GenMomDir(MomDir_Int,theta_N,phi_N);
+     
+     // Generate a Secondary Neutron
+     G4DynamicParticle* theSecNeutron = new G4DynamicParticle;
+     G4ParticleDefinition* theSecNeutronDefinition = G4Neutron::Neutron();
+     theSecNeutron->SetDefinition(theSecNeutronDefinition);
+     theSecNeutron->SetKineticEnergy(T_N);
+     theSecNeutron->SetMomentumDirection(MomDir_N);
+
+     // This is where you would generate the recoil Fe nucleus
+     //However for our purpose (Fe is only in sweeper) we don't
+     //need to keep track.
+     //G4DynamicParticle* theSecC12 = new G4DynamicParticle;
+     // GetIon() Method works whether particle exists in physicslist or not. 
+     // Arguements are GetIon(Charge,Mass,ExcitationEng)
+     //G4ParticleDefinition* theSecC12Definition = G4IonTable::GetIonTable()->GetIon(6,12,0.);
+     //theSecC12->SetDefinition(theSecC12Definition);
+     //theSecC12->SetKineticEnergy(T_C12el);
+     //theSecC12->SetMomentumDirection(MomDir_C12);
+   
+     // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     // Set final tracks in motion!
+     G4Track* theNTrack = new G4Track(theSecNeutron,GlobalTime,thePosition);
+     theNTrack->SetTouchableHandle(theTouchable);
+     //G4Track* theC12Track = new G4Track(theSecC12,GlobalTime,thePosition);
+     //theC12Track->SetTouchableHandle(theTouchable);
+
+     aParticleChange.SetNumberOfSecondaries(1);
+     aParticleChange.AddSecondary(theNTrack);
+     //aParticleChange.AddSecondary(theC12Track);
+  
+    // G4cout << "Made it to the end ! " << G4endl;
+     //G4cout << "Finished Elastic Scatter of Fe" << G4endl;
+   }
+ else if(ReactionName == "N_Fe_nonelastic")
+   {
+
+     //For our purposes we are going to treat the non-elastic Fe interactions as absorption of the neutrons
+     //the idea is that after the interaction the neutron would be slowed and may not make it into the timing gate
+     //furthermore we don't have enought information (beyond the cross sections) to know how to handle the 
+     //non-elastic processes.
+
+   
+     // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     aParticleChange.SetNumberOfSecondaries(0);
+     //aParticleChange.AddSecondary(theNTrack);
+     //aParticleChange.AddSecondary(theC12Track);
+  
+    // G4cout << "Made it to the end ! " << G4endl;
+     //G4cout << "Finished Fe Non-Elastic Process" << G4endl;
+   }
+ else if(ReactionName == "N_Al_elastic")
+   {
+
+    G4double theta_N  = 0.;
+     G4double phi_N = 0.;
+
+     G4double T_N = 0.;
+//     G4double T_Feel = 0.;
+     G4ThreeVector MomDir_N;
+     G4ThreeVector MomDir_Al;
+
+     /*
+     //Just going to use isotropic distribution in CM
+     //However good consider using C12 elastic scattering, may be similar
+     G4double cos_sq_theta = G4UniformRand(); 
+
+     // Calls diffractive angular distribution as in DEMONS
+     //G4double cos_theta_cm = NC12_DIFF(KinEng_Int);
+     // Convert according to Knoll
+     //G4double cos_theta_lab = sqrt((1.-cos_theta_cm)/2.);
+     //G4double cos_sq_theta = pow(cos_theta_lab,2);
+    
+     // .070177              =4*Mfe*Mn/(Mfe+Mn)^2
+     T_Feel = 0.07017*KinEng_Int*cos_sq_theta;
+
+     T_N = KinEng_Int - T_Feel;
+
+     if(T_N > 1.e-5)
+       {
+	 G4double arg = (sqrt(KinEng_Int)-sqrt(12.*T_Feel*cos_sq_theta))/sqrt(T_N);
+	 if(arg > 1.)
+	   {arg = 1.;}
+	 theta_N = acos(arg);
+         phi_N = 2.*Pi*G4UniformRand();
+       }
+
+     MomDir_N = GenMomDir(MomDir_Int,theta_N,phi_N);
+
+     // Carbon angles
+     G4double theta_Fe = acos(sqrt(cos_sq_theta));
+     G4double phi_Fe = phi_N+Pi;
+
+     MomDir_Fe = GenMomDir(MomDir_Int,theta_Fe,phi_Fe);
+     */
+
+
+     double cos_theta_cm = AlElastic_AngDist(KinEng_Int); // cosine of cm_angle
+     if(cos_theta_cm > 1) cos_theta_cm = 1;
+     double theta_cm = acos(cos_theta_cm); // of neutron
+     
+     // Following Knoll, calculate energy for proton first
+     double cos_theta_lab_Al = sqrt((1.-cos_theta_cm)/2.);
+     double theta_lab_Al = acos(cos_theta_lab_Al);
+     double phi_Al = 2.*Pi*G4UniformRand();
+     
+     double T_Al = KinEng_Int*pow(cos_theta_lab_Al,2)*4*27/pow(28.,2);
+
+     //G4cout << "Al theta: " << cos_theta_cm << " " << theta_cm << " " << cos_theta_lab_Al << " " << theta_lab_Al << G4endl;
+     //G4cout << "Al KE: " << T_Al/MeV << " Init_N KE: " << KinEng_Int/MeV << G4endl;
+     
+     MomDir_Al = GenMomDir(MomDir_Int,theta_lab_Al,phi_Al);
+     
+     // scattered neutron ----------------
+     // angles changed from cm to lab as in Marian and Young
+     theta_N = atan(sin(theta_cm)/(cos_theta_cm+(1/27)) );
+     phi_N = phi_Al+Pi;
+     
+     T_N = KinEng_Int - T_Al;    
+     
+     MomDir_N = GenMomDir(MomDir_Int,theta_N,phi_N);
+     
+     // Generate a Secondary Neutron
+     G4DynamicParticle* theSecNeutron = new G4DynamicParticle;
+     G4ParticleDefinition* theSecNeutronDefinition = G4Neutron::Neutron();
+     theSecNeutron->SetDefinition(theSecNeutronDefinition);
+     theSecNeutron->SetKineticEnergy(T_N);
+     theSecNeutron->SetMomentumDirection(MomDir_N);
+
+     // This is where you would generate the recoil Fe nucleus
+     //However for our purpose (Fe is only in sweeper) we don't
+     //need to keep track.
+     //G4DynamicParticle* theSecC12 = new G4DynamicParticle;
+     // GetIon() Method works whether particle exists in physicslist or not. 
+     // Arguements are GetIon(Charge,Mass,ExcitationEng)
+     //G4ParticleDefinition* theSecC12Definition = G4IonTable::GetIonTable()->GetIon(6,12,0.);
+     //theSecC12->SetDefinition(theSecC12Definition);
+     //theSecC12->SetKineticEnergy(T_C12el);
+     //theSecC12->SetMomentumDirection(MomDir_C12);
+   
+     // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     // Set final tracks in motion!
+     G4Track* theNTrack = new G4Track(theSecNeutron,GlobalTime,thePosition);
+     theNTrack->SetTouchableHandle(theTouchable);
+     //G4Track* theC12Track = new G4Track(theSecC12,GlobalTime,thePosition);
+     //theC12Track->SetTouchableHandle(theTouchable);
+
+     aParticleChange.SetNumberOfSecondaries(1);
+     aParticleChange.AddSecondary(theNTrack);
+     //aParticleChange.AddSecondary(theC12Track);
+  
+    // G4cout << "Made it to the end ! " << G4endl;
+     //G4cout << "Finished Elastic Scatter of Fe" << G4endl;
+   }
+ else if(ReactionName == "N_Al_nonelastic")
+   {
+
+     //For our purposes we are going to treat the non-elastic Fe interactions as absorption of the neutrons
+     //the idea is that after the interaction the neutron would be slowed and may not make it into the timing gate
+     //furthermore we don't have enought information (beyond the cross sections) to know how to handle the 
+     //non-elastic processes.
+
+   
+     // Kill the Parent Neutron -----------------------
+     aParticleChange.ProposeTrackStatus(fStopAndKill);
+     aParticleChange.ProposeEnergy(0.);
+     aParticleChange.ProposePosition(thePosition);
+  
+     aParticleChange.SetNumberOfSecondaries(0);
+     //aParticleChange.AddSecondary(theNTrack);
+     //aParticleChange.AddSecondary(theC12Track);
+  
+    // G4cout << "Made it to the end ! " << G4endl;
+     //G4cout << "Finished Fe Non-Elastic Process" << G4endl;
+   }
+
+
+ return pParticleChange;
+}
diff --git a/NPSimulation/Process/menate_R.hh b/NPSimulation/Process/menate_R.hh
new file mode 100644
index 000000000..a21ae0723
--- /dev/null
+++ b/NPSimulation/Process/menate_R.hh
@@ -0,0 +1,339 @@
+//----------------------------------------------------------------------
+//----------------------------------------------------------------------
+//
+// menate_R.hh 
+//
+// Description - a GEANT4 discrete process that models neutron
+// elastic scattering with non-relativistic kinematics.
+//
+// started on 6 May 2008
+//
+// a class derived from G4VDiscreteProcess
+// - Includes all processes (elastic and inelastic) from original
+// menate program, including kinematics
+//
+// Written by: Brian Roeder, Postdoc - LPC Caen, Texas A&M Univ. 
+// email - broeder@comp.tamu.edu
+//
+// Translated from Fortran program menates.for by P. Desesquelles et al.
+// Nucl. Instr. and Meths. A 307 Pg. 366 (1991)
+// Uses cross sections from A. Del Geuerra et al., NIM 135 Pg. 337 (1976).
+// except for n-p and n-12C elastic scattering total cross sections 
+// that come from MCNPx.
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// To include in physics list :
+//  #include "menate_R.hh"
+//  pManager = G4Neutron::Neutron()->GetProcessManager();
+// 	
+//    G4String NeutronProcessName = "menateR_neutron";
+//    menate_R* theMenate = new menate_R(NeutronProcessName);
+//    theMenate->SetMeanFreePathCalcMethod("ORIGINAL");
+//
+//  pManager->AddDiscreteProcess(theMenate);
+// 
+// -> Need also to set an environment variable called: MENATEG4XS
+//    to point towards the total cross section data file directory.
+//-----------------------------------------------------------------------
+//-----------------------------------------------------------------------
+// version comments
+//----------------------------------------------------------------------
+// version 0.1 - 18 Apr. 2008
+// added elastic scattering and kinetmatics from :
+// n+H1 -> n + p out (elastic)
+// n+12C -> n + 12C (elastic)
+//------------------------------------------------------------
+// version 1.0 - 23 Apr 2008 -> working version
+// modified functions and cross section read-in functions
+// added all reactions considered in original MENATE including:
+// n+H -> n+p elastic
+// n+12C -> n+12C elastic
+// n+12C -> n'+12C+gamma(4.4MeV)
+// n+12C -> a+9Be
+// n+12C -> n'+ 3a
+// n+12C -> p + 12B
+// n+12C -> n' + p + 11B (breakup)
+// n+12C -> n' + n + 11C (breakup)
+// All reactions considered together for MeanFreePath and
+// reaction probability consideration
+// MeanFreePath considers only total reaction probability
+// PostStepDoIt chooses reaction
+// **** This version includes fix in "Available_Eng" for
+// Alpha2 in process 12C(n,n')3a (bug in FORTRAN version of MENATE)
+//-------------------------------------------------------------------------
+//-------------------------------------------------------------------------
+// version 1.1 - 24 Apr 2008 -> working version
+// added function "ShareGammaEngC12()" to kinematics for 12C(n,n'g)12C*
+// process as in original MENATE FORTRAN code. This change effects NE213
+// efficiency in DEMON module between about 5-11 MeV, making the result
+// of the GEANT+MENATE efficiency calc. closer to that obtained by original
+// MENATE code. Efficiency below 5 MeV in GEANT code not changed.
+//-------------------------------------------------------------------------
+//-------------------------------------------------------------------------
+// 25 April 2008 - version 1.2 BTR
+// ---- Add Normalization of Momentum ThreeVector in GenMomDir to avoid
+// G4 Error Message. Noted that Norm diff from 1 is always less then 1e-7, so 
+// error is probably due to slight rounding error.
+//-------------------------------------------------------------------------
+// 28 April 2008 - version 1.2b BTR
+// ---- Added getenv command to ReadCrossSectionFile() Function
+// Program looks for environment variable MENATEG4XS to find cross sections
+// for use with menate.cc, otherwise throws exception.
+//-------------------------------------------------------------------------
+// 29 April 2008 - version 1.3 BTR
+// --- Noted that MeanFreePath and reaction selection calculations are 
+// different from method used in previous version. Added function
+// SetMeanFreePathCalcMethod() to switch between calc in previous
+// version and that method used specifically by MENATE
+// Modified GetMeanFreePath() and ChooseReaction() part of PostStepDoIt to add
+// MENATE original method.
+//---------------------------------------------------------------------------
+// 6 May 2008 - version 1.4 BTR
+// --- Begin modification to original MENATE code. Remove parts with no sense
+// (such as 400 keV gammas from 12C). Include angular distributions.
+//
+// 19 May 2008 - Finished revisions to version 1.4 BTR
+// --- Added parameterizations of angular distributions for n+p elastic
+// and n+12C elastic. (n+p, DEMONS), (n+12C, modified DEMONS). 
+// Now using ENDF cross sections for n+p and n+12C elastic
+// scattering. Extended total cross sections out to 999 MeV using total cross
+// sections from DEMONS (Los Alamos) program. 
+// Note : This version leaves the inelastic 12C(n,n') processes as isotropic.
+// in the center of mass cross section.
+// -------------------------------------------------------------------------- 
+// 2011-2012 Zach Kohley, see .hh file for detials of modification and addition
+// of Al and Fe material
+//--------------------------------------------------------------------------
+//
+// 6 Sept 2018
+// Added to NPTool package by Greg Christian (TAMU), gchristian@tamu.edu
+// Code inherited from MoNA-simulation package,
+// https://github.com/baumann3141/MoNA-simulation
+//
+// See menate_R.cc for list of changes made w.r.t. the
+// MoNA-simulation version
+
+#ifndef menate_R_hh 
+#define menate_R_hh
+
+#include "globals.hh"
+#include "G4VDiscreteProcess.hh"
+#include "G4ios.hh"
+#include "Randomize.hh" 
+#include "G4Track.hh"
+#include "G4Step.hh"
+#include "G4ParticleTypes.hh"
+#include "G4ParticleTable.hh"
+#include "G4IonTable.hh"
+#include "G4ParticleDefinition.hh"
+#include "G4DynamicParticle.hh"
+#include "G4ThreeVector.hh"
+#include "G4LorentzVector.hh"
+#include "G4VParticleChange.hh"
+
+#include "G4Material.hh"
+#include "G4UnitsTable.hh"
+
+#include "TH1F.h"
+
+#ifndef CS_Class
+#define CS_Class
+
+class CrossSectionClass
+{
+private:
+  // Data Members - each data member has one part of datafile!
+ 
+  G4String ElementName;
+
+  G4int NumberOfLines;
+  G4double KinEng;
+  G4double TotalCrossSection;
+
+public:
+
+  // constructor
+  CrossSectionClass()
+  {
+   NumberOfLines = 0;
+   ElementName = "Nothing";
+   KinEng = 0;
+   TotalCrossSection = 0;
+  }
+
+  // destructor
+  ~CrossSectionClass() 
+  {;}
+
+public:
+  // Setting and Access Functions
+
+  void SetNumberOfLines(G4int Lines)
+  { NumberOfLines = Lines; }
+
+  void SetElementName(G4String ElName)
+  { ElementName = ElName; }
+
+  void SetKinEng(G4double Energy)
+  { KinEng = Energy; }
+
+  void SetTotalCrossSection(G4double CrossSection)
+  { TotalCrossSection = CrossSection; }
+
+  G4int GetNumberOfLines()
+  { return NumberOfLines; }
+
+  G4String GetElementName()
+  { return ElementName; }
+
+  G4double GetKinEng()
+  { return KinEng; }
+
+  G4double GetTotalCrossSection()
+  { return TotalCrossSection; } 
+
+  void DumpData()
+  {
+    G4cout << "Number of Lines Total " << NumberOfLines
+           << ", Element Name = " << ElementName
+           << ", KinEng = " << KinEng
+           << " , CrossSection = " << TotalCrossSection << G4endl;
+  }
+
+}; 
+#endif 
+
+class menate_R : public G4VDiscreteProcess
+{
+public:
+
+  // constructor
+  menate_R(const G4String& processName="menate_R");
+
+  // destructor
+  ~menate_R();
+
+public:
+  // These are the functions in the Process: Derived from G4VDiscreteProcess.hh
+
+  G4bool IsApplicable(const G4ParticleDefinition& aParticle);
+  // Decides if process applicable or not. Only valid for Neutrons
+  // at some energy.
+
+  G4double GetMeanFreePath(const G4Track& aTrack, G4double previousStepSize,
+                           G4ForceCondition* condition); 
+  // Returns MeanFreePath for a particle in a given material in mm
+
+  G4VParticleChange* PostStepDoIt(const G4Track &aTrack, const G4Step &aStep);
+  // This is the important function where you define the process
+  // Returns steps, track and secondary particles
+
+  void SetMeanFreePathCalcMethod(G4String Method);
+
+private:
+
+ // Hide assignment operator as private 
+  menate_R& operator=(const menate_R &right);
+
+  // Copy constructor
+  menate_R(const menate_R&);
+
+  // Chooses Reaction in PostStepDoIt
+
+  G4String ChooseReaction();
+
+  // Other Pre-Defined Class Variables and Functions are below!
+
+  G4double Absolute(G4double Num);
+  G4double SIGN(G4double A1, G4double B2);
+ 
+  // Returns Cross Section for a given element, energy
+  G4double GetCrossSection(G4double KinEng, CrossSectionClass* theXS);
+
+  void ReadCrossSectionFile(G4String FileName, CrossSectionClass* theXS);
+
+  G4double GetXSInterpolation(G4double KinEng, G4double LEng, G4double HEng, 
+                               G4double LXS, G4double HXS);
+
+  // Functions translated from FORTRAN "MENATE" code 
+
+  G4ThreeVector GenMomDir(G4ThreeVector MomIn, G4double theta, G4double phi);
+
+  G4double ShareGammaEngC12(G4double A_Eng);
+
+  G4double Evaporate_Eng(G4double AMass, G4double Avail_Eng);
+
+  // Angular Distribution Generators
+
+  G4double NP_AngDist(G4double NEng);
+  G4double NC12_DIFF(G4double NEng);
+  void Setup_AlElastic_AngDist(); 
+  void Setup_FeElastic_AngDist(); 
+  G4double AlElastic_AngDist(G4double NEng); 
+  G4double FeElastic_AngDist(G4double NEng); 
+ 
+private:
+
+  // Class Variables
+
+  TH1F *hFe_AngDist_30MeV;
+  TH1F *hFe_AngDist_50MeV;
+  TH1F *hFe_AngDist_70MeV;
+  TH1F *hAl_AngDist_30MeV;
+  TH1F *hAl_AngDist_50MeV;
+  TH1F *hAl_AngDist_70MeV;
+
+
+
+  G4bool H_Switch;
+  G4bool C_Switch; 
+  G4bool Fe_Switch;
+  G4bool Al_Switch;
+
+  // Hold Number Density for H or C
+  G4double Num_H;  
+  G4double Num_C;
+  G4double Num_Fe;
+  G4double Num_Al;
+
+  // Variables used in MENATE functions above
+
+  G4double AMass_Material;  // Atomic Mass NE213 (according to MENATE)
+  G4String CalcMeth;
+
+  // integers for ShareGammaEngC12 Function
+  G4int Num_gamma_4439k;  // Num of 4.4MeV gammas
+
+  G4double Sigma;
+  G4double ProbDistPerReaction[12];
+  G4double ProbTot;
+
+  CrossSectionClass theHydrogenXS[181];
+  CrossSectionClass theCarbonXS[852];
+
+  CrossSectionClass theC12NGammaXS[37];
+  CrossSectionClass theC12ABe9XS[32];
+  CrossSectionClass theC12NPB12XS[15];
+
+  CrossSectionClass theC12NNPB11XS[10];
+  CrossSectionClass theC12N2NC11XS[11];
+  CrossSectionClass theC12NN3AlphaXS[35];
+
+  CrossSectionClass theIronElasXS[1040];
+  CrossSectionClass theIronNonelasXS[278];
+
+  CrossSectionClass theAlElasXS[380];
+  CrossSectionClass theAlNonelasXS[325];
+
+
+  // for storing current scattering element
+
+  G4String ElementName;
+  G4int A;             // Integer Mass of Recoil (from GetN())
+  G4int Z;             // Integer Charge of Recoil (from GetZ())
+
+  G4double Pi;
+  G4double Two_Pi;
+
+};
+#endif
-- 
GitLab