public void Execute(object sender, DoWorkEventArgs e) { bw = (BackgroundWorker)sender; bw.ReportProgress(0, "Starting BDFConverter"); CCIUtilities.Log.writeToLog("Starting BDFConverter on records in " + directory); /***** Read electrode file *****/ ElectrodeInputFileStream etrFile = new ElectrodeInputFileStream( new FileStream(Path.Combine(directory, eventHeader.ElectrodeFile), FileMode.Open, FileAccess.Read)); /***** Open BDF file *****/ Microsoft.Win32.SaveFileDialog dlg = new Microsoft.Win32.SaveFileDialog(); dlg.Title = "Save as BDF file ..."; dlg.AddExtension = true; dlg.DefaultExt = ".bdf"; // Default file extension dlg.Filter = "BDF Files (.bdf)|*.bdf"; // Filter files by extension dlg.FileName = Path.GetFileNameWithoutExtension(eventHeader.BDFFile); bool? result = dlg.ShowDialog(); if (result == false) { e.Result = new int[] { 0, 0 }; return; } samplingRate = BDF.NSamp / BDF.RecordDuration; //Old sampling rate; exact as number of samples and duration are always an exact multiple oldOffsetInPts = Convert.ToInt32(offset * samplingRate); int newSamplingRate = (int)((double)samplingRate / (double)decimation + 0.5); //Make best estimate possible with integers newOffsetInPts = Convert.ToInt32(offset * newSamplingRate); newRecordLength = length * newSamplingRate; //new record length must be exact multiple of the sampling rate in BDF newStatus = new int[newRecordLength]; status = new int[BDF.NSamp]; GV0 = GV[0]; BDFWriter = new BDFEDFFileWriter(File.Open(dlg.FileName, FileMode.Create, FileAccess.ReadWrite), channels.Count + 1, /* Extra channel will have group variable value in it */ length, /* Record length in seconds, must be integer */ newSamplingRate, true); log = new LogFile(dlg.FileName + ".log.xml"); bigBuff = new float[BDF.NumberOfChannels - 1, newRecordLength]; //have to dimension to old channels rather than new //in case we need for reference calculations later /***** Create BDF header record *****/ BDFWriter.LocalRecordingId = BDF.LocalRecordingId; BDFWriter.LocalSubjectId = BDF.LocalSubjectId; int chan; for (int i = 0; i < channels.Count; i++) { chan = channels[i]; BDFWriter.channelLabel(i, BDF.channelLabel(chan)); BDFWriter.transducer(i, BDF.transducer(chan)); BDFWriter.dimension(i, BDF.dimension(chan)); BDFWriter.pMax(i, BDF.pMax(chan)); BDFWriter.pMin(i, BDF.pMin(chan)); BDFWriter.dMax(i, BDF.dMax(chan)); BDFWriter.dMin(i, BDF.dMin(chan)); BDFWriter.prefilter(i, BDF.prefilter(chan)); } chan = channels.Count; BDFWriter.channelLabel(chan, GV0.Name); //Make entries for old Status channel BDFWriter.transducer(chan, "None"); BDFWriter.dimension(chan, ""); BDFWriter.pMax(chan, 262143); BDFWriter.pMin(chan, -262144); BDFWriter.dMax(chan, 262143); BDFWriter.dMin(chan, -262144); BDFWriter.prefilter(chan, "None"); log.registerHeader(this); /***** Open Event file for reading *****/ EventFactory.Instance(eventHeader.Events); // set up the factory EventFileReader EventFR = new EventFileReader( new FileStream(Path.Combine(directory, eventHeader.EventFile), FileMode.Open, FileAccess.Read)); BDFLoc stp = BDF.LocationFactory.New(); BDFLoc lastEvent = BDF.LocationFactory.New(); if (!EDE.intrinsic) //set threshold if (risingEdge) threshold = EDE.channelMin + (EDE.channelMax - EDE.channelMin) * threshold; else threshold = EDE.channelMax - (EDE.channelMax - EDE.channelMin) * threshold; nominalT = BDF.LocationFactory.New(); //nominal Event time based on Event.Time actualT = BDF.LocationFactory.New(); //actual Event time in Status channel //Note: these should be the same if the two clocks run the same rate (DAQ and computer) /***** MAIN LOOP *****/ foreach (InputEvent ie in EventFR) //Loop through Event file { bw.ReportProgress(0, "Processing event " + ie.Index.ToString("0")); //Report progress if (ie.Name == EDE.Name) // Event match found in Event file { if(findEvent(ref stp, ie)) if (allSamps) //this is a continuous copy, not Event generated episodic conversion { runBDFtoEvent(lastEvent, ref stp, ie); lastEvent = BDF.LocationFactory.New(); } else createBDFRecord(stp, ie); //Create BDF recordset around this point; i.e. Event generated episodic conversion } } if (allSamps) //copy out to end of file { stp.Rec = BDF.NumberOfRecords; stp.Pt = 0; runBDFtoEvent(lastEvent, ref stp, null); } e.Result = new int[] { BDFWriter.NumberOfRecords, BDFWriter.NumberOfRecords }; BDFWriter.Close(); EventFR.Close(); log.Close(); }
public void Execute(object sender, DoWorkEventArgs e) { bw = (BackgroundWorker)sender; bw.ReportProgress(0, "Starting FMConverter"); CCIUtilities.Log.writeToLog("Starting FMConverter on records in " + directory); /***** Read electrode file *****/ ElectrodeInputFileStream etrFile = new ElectrodeInputFileStream( new FileStream(Path.Combine(directory, eventHeader.ElectrodeFile), FileMode.Open, FileAccess.Read)); /***** Open FILMAN file *****/ SaveFileDialog dlg = new SaveFileDialog(); dlg.Title = "Save as FILMAN file ..."; dlg.AddExtension = true; dlg.DefaultExt = ".fmn"; // Default file extension dlg.Filter = "FILMAN Files (.fmn)|*.fmn"; // Filter files by extension dlg.FileName=Path.GetFileNameWithoutExtension(eventHeader.BDFFile); Nullable<bool> result = dlg.ShowDialog(); if (result == null || !(bool)result) { e.Result = new int[] { 0, 0 }; return; } samplingRate = BDF.NSamp / BDF.RecordDuration; offsetInPts = Convert.ToInt32(offset * samplingRate); newRecordLength = Convert.ToInt32(Math.Ceiling(length * samplingRate / (float)decimation)); FMStream = new FILMANOutputStream( File.Open(dlg.FileName, FileMode.Create, FileAccess.ReadWrite), GV.Count + 2, EDE.ancillarySize, channels.Count, newRecordLength, FILMANFileStream.FILMANFileStream.Format.Real); log = new LogFile(dlg.FileName + ".log.xml"); FMStream.IS = Convert.ToInt32( (double)samplingRate/(double)decimation); bigBuff = new float[BDF.NumberOfChannels - 1, FMStream.ND]; //have to dimension to BDF rather than FMStream //in case we need for reference calculations /***** Create FILMAN header records *****/ FMStream.GVNames(0, "Channel"); FMStream.GVNames(1, "Montage"); int i = 2; foreach (GVEntry gv in GV) FMStream.GVNames(i++, gv.Name); //generate group variable names for (i = 0; i < FMStream.NC; i++) //generate channel labels { string s = BDF.channelLabel(channels[i]); ElectrodeFileStream.ElectrodeRecord p; if (etrFile.etrPositions.TryGetValue(s, out p)) //add electrode location information, if available FMStream.ChannelNames(i, s.PadRight(16, ' ') + p.projectPhiTheta().ToString("0")); else FMStream.ChannelNames(i, s); } FMStream.Description(0, eventHeader.Title + " Date: " + eventHeader.Date + " " + eventHeader.Time); FMStream.Description(1, "File: " + Path.Combine(directory, Path.GetFileNameWithoutExtension(eventHeader.BDFFile))); StringBuilder sb = new StringBuilder("Subject: " + eventHeader.Subject.ToString()); if (eventHeader.Agent != 0) sb.Append(" Agent: " + eventHeader.Agent); sb.Append(" Tech:"); foreach (string s in eventHeader.Technician) sb.Append(" " + s); FMStream.Description(2, sb.ToString()); sb = new StringBuilder("Event="+EDE.Name); sb.Append(" Offset=" + offset.ToString("0.00")); sb.Append(" Length=" + length.ToString("0.00")); if (referenceGroups == null || referenceGroups.Count == 0) sb.Append(" No reference"); else if (referenceGroups.Count == 1) { sb.Append(" Single ref group with"); if (referenceGroups[0].Count >= FMStream.NC) if (referenceChannels[0].Count == BDF.NumberOfChannels) sb.Append(" common average ref"); else if (referenceChannels[0].Count == 1) sb.Append(" ref channel " + referenceChannels[0][0].ToString("0") + "=" + BDF.channelLabel(referenceChannels[0][0])); else sb.Append(" multiple ref channels=" + referenceChannels[0].Count.ToString("0")); } else // complex reference expression { sb.Append(" Multiple reference groups=" + referenceGroups.Count.ToString("0")); } FMStream.Description(3, sb.ToString()); sb = new StringBuilder("#Group vars=" + GV.Count.ToString("0")); if (anc) sb.Append(" Ancillary=" + FMStream.NA.ToString("0")); sb.Append(" #Channels=" + FMStream.NC.ToString("0")); sb.Append(" #Samples=" + FMStream.ND.ToString("0")); sb.Append(" Samp rate=" + FMStream.IS.ToString("0")); FMStream.Description(4, sb.ToString()); FMStream.Description(5, BDF.LocalRecordingId); FMStream.writeHeader(); log.registerHeader(this); /***** Open Event file for reading *****/ EventFactory.Instance(eventHeader.Events); // set up the factory EventFileReader EventFR = new EventFileReader( new FileStream(Path.Combine(directory, eventHeader.EventFile), FileMode.Open, FileAccess.Read)); BDFLoc stp = BDF.LocationFactory.New(); if (!EDE.intrinsic) if (risingEdge) threshold = EDE.channelMin + (EDE.channelMax - EDE.channelMin) * threshold; else threshold = EDE.channelMax - (EDE.channelMax - EDE.channelMin) * threshold; nominalT = BDF.LocationFactory.New(); //nominal Event time based on Event.Time actualT = BDF.LocationFactory.New(); //actual Event time in Status channel //Note: these should be the same if the two clocks run the same rate (BioSemi DAQ and computer) /***** MAIN LOOP *****/ foreach (InputEvent ie in EventFR) //Loop through Event file { bw.ReportProgress(0, "Processing event " + ie.Index.ToString("0")); //Report progress if (ie.Name == EDE.Name) // Event match found in Event file { if (findEvent(ref stp, ie)) createFILMANRecord(stp, ie); //Create FILMAN recordset around this found point } } e.Result = new int[] { FMStream.NR, FMStream.NR / FMStream.NC }; FMStream.Close(); EventFR.Close(); log.Close(); }