public static IEnumerable <TranslationGroup> GetGroups(Type type, TranslationBase original, TranslationBase translation) { var dic = new Dictionary <object, TranslationGroup>(); TranslationGroup ungrouped = null; getGroups(null, type, original, translation, original.Language.GetNumberSystem(), translation.Language.GetNumberSystem(), dic, ref ungrouped, new object[0], ""); var enumTypes = dic.Keys.Select(k => k.GetType()).Distinct().OrderBy(t => t.Name).ToArray(); var enumValues = enumTypes.SelectMany(t => Enum.GetValues(t).Cast <object>()).ToArray(); foreach (var key in enumValues) { if (dic.ContainsKey(key)) { yield return(dic[key]); } } if (ungrouped != null) { yield return(ungrouped); } }
private static void getGroups(FieldInfo field, Type type, object original, object translation, NumberSystem originalNumSys, NumberSystem translationNumSys, Dictionary <object, TranslationGroup> dic, ref TranslationGroup ungrouped, IEnumerable <object> classGroups, string path) { if (!type.IsDefined <LingoStringClassAttribute>(true)) { if (field == null) { throw new ArgumentException($@"Type ""{type.FullName}"" must be marked with the [LingoStringClass] attribute.", nameof(type)); } else { throw new ArgumentException($@"Field ""{field.DeclaringType.FullName}.{field.Name}"" must either be marked with the [LingoIgnore] attribute, or be of type TrString, TrStringNumbers, or a type with the [LingoStringClass] attribute.", nameof(type)); } } var thisClassGroups = type.GetCustomAttributes(true).OfType <LingoInGroupAttribute>().Select(attr => attr.Group); if (classGroups != null) { thisClassGroups = thisClassGroups.Concat(classGroups); } foreach (var f in type.GetFields(BindingFlags.Public | BindingFlags.Instance)) { if (f.FieldType == typeof(TrString) || f.FieldType == typeof(TrStringNum)) { string notes = f.GetCustomAttributes <LingoNotesAttribute>().Select(lna => lna.Notes).FirstOrDefault(); var trInfo = f.FieldType == typeof(TrString) ? (TranslationInfo) new TrStringInfo { Label = path + f.Name, Notes = notes, NewOriginal = ((TrString)f.GetValue(original)).Translation, TranslationTr = (TrString)f.GetValue(translation) } : (TranslationInfo) new TrStringNumInfo((TrStringNum)f.GetValue(original), (TrStringNum)f.GetValue(translation), originalNumSys, translationNumSys) { Label = path + f.Name, Notes = notes }; var groups = f.GetCustomAttributes <LingoInGroupAttribute>().Select(attr => attr.Group).Concat(thisClassGroups); if (!groups.Any()) { if (ungrouped == null) { ungrouped = new TranslationGroup { Label = "Ungrouped strings", Notes = "This group contains strings not found in any other group." } } ; ungrouped.Infos.Add(trInfo); } else { foreach (var group in groups) { TranslationGroup grp; if (!dic.TryGetValue(group, out grp)) { grp = createGroup(group); dic[group] = grp; } grp.Infos.Add(trInfo); } } } else if (!f.IsDefined <LingoIgnoreAttribute>(true)) { getGroups(f, f.FieldType, f.GetValue(original), f.GetValue(translation), originalNumSys, translationNumSys, dic, ref ungrouped, thisClassGroups, path + f.Name + " / "); } } }