/// ------------------------------------------------------------------------------------ private bool CreateWordEntriesFromAllomorphs(IPaLexEntry lxEntry, RecordCacheEntry recCacheEntry) { var skip1 = true; foreach (var allo in lxEntry.Allomorphs.Where(p => p != null)) { if (skip1) { skip1 = false; continue; } var eticValue = allo.GetString(m_phoneticWsId); if (eticValue != null) { var wentry = new WordCacheEntry(recCacheEntry, m_phoneticFieldName); wentry.SetValue(m_phoneticFieldName, eticValue); if (m_audioWsId != null) { string audioFile = allo.GetString(m_audioWsId); if (audioFile != null) { wentry["AudioFile"] = audioFile; } } wentry.Guid = new Guid(lxEntry.Guid.ToString()); recCacheEntry.WordEntries.Add(wentry); } } return(recCacheEntry.WordEntries.Count > 0); }
/// ------------------------------------------------------------------------------------ public bool Matches(WordCacheEntry entry) { bool match = false; foreach (var expression in Expressions) { if (expression.ExpressionType == ExpressionType.PhoneticSrchPtrn && expression.SearchEngine == null) { expression.SearchEngine = entry.Project.FilterHelper.CheckSearchQuery(expression.SearchQuery, false); if (expression.SearchEngine == null) { return(false); } } match = expression.Matches(entry); // If the entry matches and we're logically OR'ing the expressions, // then we're done here. The entry matches the filter. if (match && MatchAny) { return(true); } // If the entry didn't match and the expressions are logically AND'd, // then we're done here. The entry doesn't match the filter. if (!match && !MatchAny) { return(false); } } return(match); }
/// <summary> /// Audio files can be store in special audio writing systems in the LexememForm, the CitationForm or the /// Example field of the pronunciation. /// First field found will be used. /// </summary> private void SearchForAudioWritingSystems(WordCacheEntry wentry, IPaLexEntry lxEntry, IPaLexPronunciation pro) { if (m_audioWsId == null) { return; } string audioFile = null; if (lxEntry.LexemeForm != null) { audioFile = lxEntry.LexemeForm.GetString(m_audioWsId); } if (audioFile == null && lxEntry.CitationForm != null) { audioFile = lxEntry.CitationForm.GetString(m_audioWsId); } // TODO: Should look at examples also, but examples are not part of the data PA can get from FLEx. if (audioFile != null) { wentry["AudioFile"] = audioFile; } }
public void TestSetup() { _entry = new WordCacheEntry( new RecordCacheEntry(_prj) { DataSource = new PaDataSource() }, "Phonetic"); }
/// ------------------------------------------------------------------------------------ public bool MatchesSearchPattern(WordCacheEntry entry) { if (m_searchQuery == null || string.IsNullOrEmpty(m_pattern)) { return(false); } string[][] eticWords = new string[1][]; if (m_searchQuery.IncludeAllUncertainPossibilities && entry.ContiansUncertainties) { // Get a list of all the words (each word being in the form of // an array of phones) that can be derived from all the primary // and non primary uncertainties. eticWords = entry.GetAllPossibleUncertainWords(false); if (eticWords == null) { return(false); } } else { // Not all uncertain possibilities should be included in the search, so // just load up the phones that only include the primary uncertain Phone(s). eticWords[0] = entry.Phones; if (eticWords[0] == null) { return(false); } } // If eticWords.Length = 1 then either the word we're searching doesn't contain // uncertain phones or it does but they are only primary uncertain phones. When // eticWords.Length > 1, we know the uncertain phones in the first word are only // primary uncertainities while at least one phone in the remaining words is a // non primary uncertainy. for (int i = 0; i < eticWords.Length; i++) { // If the search pattern contains the word breaking character, then add a // space at the beginning and end of the array of phones so the word breaking // character has something to match at the extremes of the phonetic values. if (m_patternContainsWordBoundaries) { List <string> tmpChars = new List <string>(eticWords[i]); tmpChars.Insert(0, " "); tmpChars.Add(" "); eticWords[i] = tmpChars.ToArray(); } int[] result; if (SearchEngine.SearchWord(eticWords[i], out result)) { return(true); } } return(false); }
/// ------------------------------------------------------------------------------------ private bool MatchesFilter(WordCacheEntry entry) { if (entry.Project.FilterHelper.Filters != null) { var filter = entry.Project.FilterHelper.GetFilter(m_pattern); if (filter != null) { return(filter.Matches(entry)); } } return(false); }
/// ------------------------------------------------------------------------------------ public bool Read(RecordCache recCache) { var reader = new SaAudioDocumentReader(m_worker); if (!reader.Initialize(m_dataSource.SourceFile) || reader.Words == null) { return(false); } // Make only a single record entry for the entire wave file. var recCacheEntry = new RecordCacheEntry(false, m_project) { DataSource = m_dataSource, NeedsParsing = false, Channels = reader.Channels, BitsPerSample = reader.BitsPerSample, SamplesPerSecond = reader.SamplesPerSecond, }; var audioField = m_project.GetAudioFileField(); recCacheEntry.SetValue(audioField.Name, m_dataSource.SourceFile); m_worker.ReportProgress(0); // Get all the record level fields. foreach (var fname in m_dataSource.FieldMappings.Where(m => !m.IsParsed).Select(m => m.Field.Name)) { SetFieldValueFromObject(typeof(SaAudioDocumentReader), fname, reader, recCacheEntry.SetValue); } int wordIndex = 0; recCacheEntry.WordEntries = new List <WordCacheEntry>(); foreach (var kvp in reader.Words) { var wentry = new WordCacheEntry(recCacheEntry, wordIndex++); foreach (var fname in m_dataSource.FieldMappings.Where(m => m.IsParsed).Select(m => m.Field.Name)) { SetFieldValueFromObject(typeof(AudioDocWords), fname, kvp.Value, wentry.SetValue); } wentry.AudioOffset = kvp.Key; wentry.AudioLength = kvp.Value.AudioLength; recCacheEntry.WordEntries.Add(wentry); } recCache.Add(recCacheEntry); return(true); }
/// ------------------------------------------------------------------------------------ /// <summary> /// /// </summary> /// ------------------------------------------------------------------------------------ private bool MatchesFilter(WordCacheEntry entry) { if (FilterHelper.FilterList != null) { foreach (PaFilter filter in FilterHelper.FilterList) { if (m_pattern == filter.Name) { return(filter.Matches(entry)); } } } return(false); }
/// ------------------------------------------------------------------------------------ private bool CreateWordEntriesFromPronunciations(IPaLexEntry lxEntry, RecordCacheEntry recCacheEntry) { foreach (var pro in lxEntry.Pronunciations.Where(p => p.Form != null)) { var eticValue = pro.Form.GetString(m_phoneticWsId); if (eticValue != null) { var wentry = new WordCacheEntry(recCacheEntry, m_phoneticFieldName); wentry.SetValue(m_phoneticFieldName, eticValue); wentry.Guid = new Guid(lxEntry.Guid.ToString()); ReadSinglePronunciation(pro, wentry); recCacheEntry.WordEntries.Add(wentry); } } return(recCacheEntry.WordEntries.Count > 0); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Constructs a temporary file that contains commands for SA to use for opening /// the specified wave file and zooming to a particular start and stop offset. /// </summary> /// ------------------------------------------------------------------------------------ private string GetSaListFile(WordCacheEntry wcentry, string audioFile, string callingApp) { // Get the utterance's offset. var offset = wcentry.AudioOffset; var length = wcentry.AudioLength; // Create the contents for the SA list file. var saListFileContent = string.Format(kSaListFileContentFmt, new object[] { callingApp, audioFile, offset, offset + length }); saListFileContent = Utils.ConvertLiteralNewLines(saListFileContent); // Write the list file. var lstFile = Path.GetTempFileName(); File.AppendAllText(lstFile, saListFileContent); return(lstFile); }
/// ------------------------------------------------------------------------------------ private void ReadSinglePronunciation(IPaLexPronunciation pro, WordCacheEntry wentry) { var mapping = m_dataSource.FieldMappings.SingleOrDefault(m => m.NameInDataSource == "CV-Pattern-Source"); if (mapping != null) { wentry.SetValue(mapping.NameInDataSource, pro.CVPattern); } mapping = m_dataSource.FieldMappings.SingleOrDefault(m => m.NameInDataSource == "Tone"); if (mapping != null) { wentry.SetValue(mapping.NameInDataSource, pro.Tone); } mapping = m_dataSource.FieldMappings.SingleOrDefault(m => m.NameInDataSource == "Location"); if (mapping != null) { wentry.SetValue(mapping.NameInDataSource, GetPossibilityValue(pro.Location, false)); } if (!pro.MediaFiles.Any()) { return; } // TODO: Verify that the media file is audio. var mediaFile = pro.MediaFiles.ElementAt(0); // TODO: Figure out a way to deal with more than one media file and label. wentry.SetValue("AudioFile", mediaFile.AbsoluteInternalPath); mapping = m_dataSource.FieldMappings.SingleOrDefault(m => m.NameInDataSource == "AudioFileLabel"); if (mapping != null) { wentry.SetValue("AudioFileLabel", GetMultiStringValue(mediaFile.Label, mapping.FwWsId)); } }
/// ------------------------------------------------------------------------------------ /// <summary> /// Constructs a DataSourceEditor object and calls the "owning" application to edit the /// data source from which the specified record originated (e.g. Toolbox, Flex, SA). /// </summary> /// ------------------------------------------------------------------------------------ public DataSourceEditor(WordCacheEntry wcentry, string callingApp, bool showFwUrlDialog) { m_showFwJumpUrlDlg = showFwUrlDialog; var sourceType = wcentry.RecordEntry.DataSource.Type; switch (sourceType) { case DataSourceType.SFM: EditRecordInSFMEditor(wcentry.RecordEntry); break; case DataSourceType.Toolbox: EditRecordInToolbox(wcentry.RecordEntry); break; case DataSourceType.FW: case DataSourceType.FW7: EditRecordInFieldWorks(wcentry.RecordEntry); break; case DataSourceType.SA: EditRecordInSA(wcentry, callingApp); break; default: ErrorReport.NotifyUserOfProblem(LocalizationManager.GetString( "Miscellaneous.Messages.DataSourceEditing.UnableToEditSourceRecordMsg", "There is no source record editor associated with this record.")); break; } }
/// ------------------------------------------------------------------------------------ private void HandleReadingFwData(SqlDataReader reader) { if (reader == null || reader.IsClosed) { return; } // First, get a list of the fields returned from the query // and translate those to their corresponding PA fields. var fieldNames = new Dictionary <int, string>(); for (int i = 0; i < reader.FieldCount; i++) { if (m_dataSource.FieldMappings.Any(m => m.Field.Name == reader.GetName(i))) { fieldNames[i] = reader.GetName(i); } } var eticField = m_dataSource.FieldMappings.FirstOrDefault(m => m.Field.Type == FieldType.Phonetic); var eticFieldName = (eticField != null ? eticField.PaFieldName : null); while (reader.Read()) { // Make a new record entry for each row returned from the query. var recCacheEntry = new RecordCacheEntry(false, m_project) { DataSource = m_dataSource, NeedsParsing = false, WordEntries = new List <WordCacheEntry>(), }; var wentry = new WordCacheEntry(recCacheEntry); // Read the data for all columns having a mapped field. foreach (var kvp in fieldNames) { var dbValue = reader[kvp.Key]; if (dbValue is DBNull) { continue; } // Put the phonetic field in a word entry and all the other data in the // record entry. if (kvp.Value != eticFieldName) { recCacheEntry.SetValue(kvp.Value, dbValue.ToString()); } else { wentry.SetValue(kvp.Value, dbValue.ToString()); } } var guid = reader["Guid"]; if (!(guid is DBNull)) { recCacheEntry.Guid = new Guid(guid.ToString()); } // Add the entries to the caches. recCacheEntry.WordEntries.Add(wentry); m_recCache.Add(recCacheEntry); } }
/// ------------------------------------------------------------------------------------ /// <summary> /// Constructs a DataSourceEditor object and calls the "owning" application to edit the /// data source from which the specified record originated (e.g. Toolbox, Flex, SA). /// </summary> /// ------------------------------------------------------------------------------------ public DataSourceEditor(WordCacheEntry wcentry, string callingApp) : this(wcentry, callingApp, false) { }
/// ------------------------------------------------------------------------------------ public bool Matches(WordCacheEntry entry) { // If this expression is to match the entry against a filter, then find // the filter and return whether or not the entry matches the filter. if (FieldName == OtherFilterField) { return(MatchesFilter(entry)); } if (m_expTypep == Filter.ExpressionType.PhoneticSrchPtrn) { return(MatchesSearchPattern(entry)); } if (!m_fieldTypeDetermined) { var field = entry.Project.GetFieldForName(FieldName); if (field != null) { m_fieldIsDate = (field.Type == FieldType.Date); m_fieldIsNumeric = (field.Type == FieldType.GeneralNumeric); m_fieldTypeDetermined = true; } } string entryValue = (entry[FieldName] ?? string.Empty); if (m_expTypep == Filter.ExpressionType.RegExp) { if (Operator == Filter.Operator.Matches) { return(Regex.IsMatch(entryValue, m_pattern)); } return(!Regex.IsMatch(entryValue, m_pattern)); } if (m_fieldIsNumeric || Operator == Filter.Operator.GreaterThan || Operator == Filter.Operator.GreaterThanOrEqual || Operator == Filter.Operator.LessThan || Operator == Filter.Operator.LessThanOrEqual) { return(MatchesNumeric(entryValue)); } if (m_fieldIsDate) { return(MatchesDate(entryValue)); } if (FieldName == PaField.kAudioFileFieldName) { entryValue = entryValue.ToLowerInvariant(); m_pattern = m_pattern.ToLowerInvariant(); } switch (Operator) { case Filter.Operator.Matches: case Filter.Operator.Equals: return(entryValue.Equals(m_pattern, StringComparison.Ordinal)); case Filter.Operator.NotEquals: return(!entryValue.Equals(m_pattern, StringComparison.Ordinal)); case Filter.Operator.Contains: return(entryValue.Contains(m_pattern)); case Filter.Operator.DoesNotContain: return(!entryValue.Contains(m_pattern)); case Filter.Operator.BeginsWith: return(entryValue.StartsWith(m_pattern, StringComparison.Ordinal)); case Filter.Operator.EndsWith: return(entryValue.EndsWith(m_pattern, StringComparison.Ordinal)); case Filter.Operator.DoesNotBeginsWith: return(!entryValue.StartsWith(m_pattern, StringComparison.Ordinal)); case Filter.Operator.DoesNotEndsWith: return(!entryValue.EndsWith(m_pattern, StringComparison.Ordinal)); case Filter.Operator.PathExists: return(File.Exists(entryValue)); case Filter.Operator.PathDoesNotExist: return(!File.Exists(entryValue)); case Filter.Operator.GreaterThan: case Filter.Operator.GreaterThanOrEqual: case Filter.Operator.LessThan: case Filter.Operator.LessThanOrEqual: return(MatchesNumeric(entryValue)); default: break; } return(false); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Reads all the data for a lex. entry that get written to word cache entries (e.g. /// phonetic, audio file info., etc.) /// </summary> /// ------------------------------------------------------------------------------------ private bool ReadWordEntryFieldsFromLexEntry(IPaLexEntry lxEntry, RecordCacheEntry recCacheEntry) { if (m_fwDsInfo.PhoneticStorageMethod == FwDBUtils.PhoneticStorageMethod.AllPronunciationFields) { return(CreateWordEntriesFromPronunciations(lxEntry, recCacheEntry)); } recCacheEntry.Guid = new Guid(lxEntry.Guid.ToString()); var pro = (!lxEntry.Pronunciations.Any() ? null : lxEntry.Pronunciations.ElementAt(0)); string eticValue = null; if (m_fwDsInfo.PhoneticStorageMethod == FwDBUtils.PhoneticStorageMethod.LexemeForm) { if (m_vernCustom) { var customvalues = m_customfield.CustomValues.FindAll(m => m.Guid == lxEntry.Guid.ToString()); foreach (var nm in customvalues.Select(m => m.CustomFields).Select(value => value.SingleOrDefault(m => m.Name == m_vernPhonetic.Name)).Where(nm => nm != null)) { eticValue = nm.Value; break; } } else { switch (m_vernPhonetic != null ? m_vernPhonetic.Name : "LexemeForm") { case "LexemeForm": eticValue = GetMultiStringValue(lxEntry.LexemeForm, m_phoneticWsId); break; case "Variants": eticValue = lxEntry.Variants.Where(v => v.VariantForm != null).Select(v => v.VariantForm.GetString(m_phoneticWsId)).FirstOrDefault(); break; case "ComplexForms": eticValue = GetCommaDelimitedList(lxEntry.ComplexForms.Select(c => c.GetString(m_phoneticWsId))); break; case "Components": eticValue = lxEntry.ComplexFormInfo.Select(ci => GetCommaDelimitedList(ci.Components)).FirstOrDefault(); break; case "Allomorphs": return(CreateWordEntriesFromAllomorphs(lxEntry, recCacheEntry)); case "CitationForm": eticValue = GetMultiStringValue(lxEntry.CitationForm, m_phoneticWsId); break; } } //if (lxEntry.LexemeForm != null) // eticValue = lxEntry.LexemeForm.GetString(m_phoneticWsId); } else { if (pro != null && pro.Form != null) { eticValue = pro.Form.GetString(m_phoneticWsId); } } if (eticValue == null) { return(false); } var wentry = new WordCacheEntry(recCacheEntry, m_phoneticFieldName); wentry.SetValue(m_phoneticFieldName, eticValue); if (pro != null) { ReadSinglePronunciation(pro, wentry); } if (wentry.GetField("AudioFile", false) == null) { SearchForAudioWritingSystems(wentry, lxEntry, pro); } recCacheEntry.WordEntries.Add(wentry); return(true); }
/// ------------------------------------------------------------------------------------ public bool EntryMatchesCurrentFilter(WordCacheEntry entry) { return(CurrentFilter == null ? true : CurrentFilter.Matches(entry)); }
/// ------------------------------------------------------------------------------------ /// <summary> /// /// </summary> /// ------------------------------------------------------------------------------------ public bool Matches(WordCacheEntry entry) { // If this expression is to match the entry against a filter, then find // the filter and return whether or not the entry matches the filter. if (m_fieldName == OtherFilterField) { return(MatchesFilter(entry)); } if (m_expTypep == ExpressionType.PhoneticSrchPtrn) { return(MatchesSearchPattern(entry)); } if (!m_fieldTypeDetermined) { PaFieldInfo fieldInfo = PaApp.FieldInfo[m_fieldName]; if (fieldInfo != null) { m_fieldIsDate = fieldInfo.IsDate; m_fieldIsNumeric = fieldInfo.IsNumeric || fieldInfo.IsAudioLength || fieldInfo.IsAudioOffset; m_fieldTypeDetermined = true; } } string entryValue = (entry[m_fieldName] ?? string.Empty); if (m_expTypep == ExpressionType.RegExp) { return(Regex.IsMatch(entryValue, m_pattern)); } if (m_fieldIsNumeric || m_operator == FilterOperator.GreaterThan || m_operator == FilterOperator.GreaterThanOrEqual || m_operator == FilterOperator.LessThan || m_operator == FilterOperator.LessThanOrEqual) { return(MatchesNumeric(entryValue)); } if (m_fieldIsDate) { return(MatchesDate(entryValue)); } switch (m_operator) { case FilterOperator.Matches: case FilterOperator.Equals: return(entryValue.Equals(m_pattern, StringComparison.InvariantCulture)); case FilterOperator.NotEquals: return(!entryValue.Equals(m_pattern, StringComparison.InvariantCulture)); case FilterOperator.Contains: return(entryValue.Contains(m_pattern)); case FilterOperator.DoesNotContain: return(!entryValue.Contains(m_pattern)); case FilterOperator.BeginsWith: return(entryValue.StartsWith(m_pattern, StringComparison.InvariantCulture)); case FilterOperator.EndsWith: return(entryValue.EndsWith(m_pattern, StringComparison.InvariantCulture)); case FilterOperator.DoesNotBeginsWith: return(!entryValue.StartsWith(m_pattern, StringComparison.InvariantCulture)); case FilterOperator.DoesNotEndsWith: return(!entryValue.EndsWith(m_pattern, StringComparison.InvariantCulture)); case FilterOperator.PathExists: return(File.Exists(entryValue)); case FilterOperator.PathDoesNotExist: return(!File.Exists(entryValue)); case FilterOperator.GreaterThan: case FilterOperator.GreaterThanOrEqual: case FilterOperator.LessThan: case FilterOperator.LessThanOrEqual: return(MatchesNumeric(entryValue)); default: break; } return(false); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Attempts to edit the specified record in Speech Analyzer. /// </summary> /// ------------------------------------------------------------------------------------ private void EditRecordInSA(WordCacheEntry wcentry, string callingApp) { // Get the audio file field. var field = wcentry.Project.GetAudioFileField(); if (field == null) { ErrorReport.NotifyUserOfProblem(LocalizationManager.GetString( "Miscellaneous.Messages.DataSourceEditing.NoAudioFileFieldMissingMsg", "This project doesn't contain a field definition for an audio file path.")); return; } // Get the audio file and make sure it exists. var audioFile = wcentry[field.Name]; if (string.IsNullOrEmpty(audioFile) || !File.Exists(audioFile)) { ErrorReport.NotifyUserOfProblem(LocalizationManager.GetString( "Miscellaneous.Messages.DataSourceEditing.AudioFileMissingMsg", "The audio file '{0}' is cannot be found."), audioFile); return; } // Make sure SA exists. var saPath = AudioPlayer.GetSaPath(); if (saPath == null || !File.Exists(saPath)) { var msg = LocalizationManager.GetString("Miscellaneous.Messages.DataSourceEditing.AudioEditProblemMsg", "Speech Analyzer 3.1 is required to edit audio data sources, but it " + "is not installed. Please install Speech Analyzer 3.1 and try again.", "Message displayed when SA 3.1 is not installed and the user is attempting to edit an audio file."); using (var dlg = new DownloadSaDlg(msg)) dlg.ShowDialog(); return; } var lstFile = GetSaListFile(wcentry, audioFile, callingApp); // Start SA. var prs = new Process(); prs.StartInfo.UseShellExecute = true; prs.StartInfo.FileName = "\"" + saPath + "\""; prs.StartInfo.Arguments = "-l " + lstFile; prs.EnableRaisingEvents = true; prs.Exited += SA_Exited; // Create a new collection to hold the new process. if (s_saProcesses == null) { s_saProcesses = new List <Process>(); } // Save the process so PA has a record of it. (See CloseSAInstances, below) s_saProcesses.Add(prs); prs.Start(); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Gets the value for the specified field name. /// </summary> /// ------------------------------------------------------------------------------------ public string this[string field] { get { return(WordCacheEntry.GetField(field)); } }
/// ------------------------------------------------------------------------------------ /// <summary> /// /// </summary> /// ------------------------------------------------------------------------------------ internal void Read(RecordCacheEntry recEntry) { if (recEntry == null || !System.IO.File.Exists(recEntry.DataSource.DataSourceFile)) { return; } if (!Initialize(recEntry.DataSource.DataSourceFile)) { return; } m_segments = ReflectionHelper.GetField(m_doc, "m_segments") as SortedDictionary <uint, SegmentData>; if (m_segments == null) { return; } SortedDictionary <uint, AudioDocWords> adWords = GetWords(); if (adWords == null) { return; } int wordIndex = 0; PaFieldInfo fieldInfo; recEntry.WordEntries = new List <WordCacheEntry>(); // Go through each word, adding a word cache entry for each. foreach (KeyValuePair <uint, AudioDocWords> adw in adWords) { WordCacheEntry wentry = new WordCacheEntry(recEntry, wordIndex++, true); Dictionary <string, PaFieldValue> fieldValues = ReflectionHelper.GetField(wentry, "m_fieldValues") as Dictionary <string, PaFieldValue>; if (fieldValues != null) { fieldValues["Reference"] = new PaFieldValue("Reference"); } fieldInfo = PaApp.FieldInfo.PhoneticField; if (fieldInfo != null) { wentry[fieldInfo.FieldName] = adw.Value.Phonetic; } fieldInfo = PaApp.FieldInfo.PhonemicField; if (fieldInfo != null) { wentry[fieldInfo.FieldName] = adw.Value.Phonemic; } fieldInfo = PaApp.FieldInfo.ToneField; if (fieldInfo != null) { wentry[fieldInfo.FieldName] = adw.Value.Tone; } fieldInfo = PaApp.FieldInfo.OrthoField; if (fieldInfo != null) { wentry[fieldInfo.FieldName] = adw.Value.Orthographic; } fieldInfo = PaApp.FieldInfo.GlossField; if (fieldInfo != null) { wentry[fieldInfo.FieldName] = adw.Value.Gloss; } fieldInfo = PaApp.FieldInfo.ReferenceField; if (fieldInfo != null) { wentry[fieldInfo.FieldName] = adw.Value.Reference; } fieldInfo = PaApp.FieldInfo.AudioFileLengthField; if (fieldInfo != null) { wentry[fieldInfo.FieldName] = adw.Value.AudioLength.ToString(); } fieldInfo = PaApp.FieldInfo.AudioFileOffsetField; if (fieldInfo != null) { wentry[fieldInfo.FieldName] = adw.Key.ToString(); } recEntry.WordEntries.Add(wentry); } }