private void MyStruct_AddWithMethod(CsEnumItem enumItem, bool isFirst) { if (isFirst) { var cw = new CsCodeWriter(); const string maskVariable = "value"; const string modifiedValue = "current"; cw.SingleLineIf("add", $"return {modifiedValue} | {maskVariable};", $"return {modifiedValue} & ~{maskVariable};"); var m = ExtensionsClass .AddMethod(SetOrClearMethod, MyEnumTypeName) .WithBody(cw) .WithStatic(); m.AddAggressiveInlining(ExtensionsClass); m.AddParam(modifiedValue, MyEnumTypeName).UseThis = true; m.AddParam(maskVariable, MyEnumTypeName); m.AddParam("add", "bool"); } { var mask = GetMask(MyEnum, enumItem.EnumName); var cw = CsCodeWriter.Create <SingleTaskEnumsGenerator>(); cw.WriteLine($"{flagsPropertyName} = {flagsPropertyName}.{SetOrClearMethod}({mask}, value);"); cw.WriteLine("return this;"); var m = MyStruct.AddMethod("With" + enumItem.EnumName, OptionsClassName) .WithBody(cw); m.AddParam("value", "bool").ConstValue = "true"; m.Description = enumItem.Description; } }
public void Append(CsEnumItem enumItem) { enumItem.EncodedValue = Value.ToInv(); _target.Items.Add(enumItem); _target.UnderlyingType = GetUnderlyingType(); Value *= 2; }
/// <summary> /// Maps a C++ Enum to a C# enum. /// </summary> /// <param name="newEnum">the C# enum.</param> private void Process(CsEnum newEnum) { var cppEnum = (CppEnum)newEnum.CppElement; // Get tag from C++ enum var tag = cppEnum.GetTagOrDefault <MappingRule>(); // Determine enum type. Default is int string typeName = cppEnum.GetTypeNameWithMapping(); switch (typeName) { case "byte": newEnum.Type = typeof(byte); newEnum.SizeOf = 1; break; case "short": newEnum.Type = typeof(short); newEnum.SizeOf = 1; break; case "int": newEnum.Type = typeof(int); newEnum.SizeOf = 4; break; default: Logger.Error("Invalid type [{0}] for enum [{1}]. Types supported are : int, byte, short", typeName, cppEnum); break; } // Find Root Name of this enum // All enum items should start with the same root name and the root name should be at least 4 chars string rootName = cppEnum.Name; string rootNameFound = null; bool isRootNameFound = false; for (int i = rootName.Length; i >= 4 && !isRootNameFound; i--) { rootNameFound = rootName.Substring(0, i); isRootNameFound = true; foreach (var cppEnumItem in cppEnum.EnumItems) { if (!cppEnumItem.Name.StartsWith(rootNameFound)) { isRootNameFound = false; break; } } } if (isRootNameFound) { rootName = rootNameFound; } // Create enum items for enum foreach (var cppEnumItem in cppEnum.EnumItems) { string enumName = NamingRules.Rename(cppEnumItem, rootName); string enumValue = cppEnumItem.Value; var csharpEnumItem = new CsEnumItem(enumName, enumValue) { CppElement = cppEnumItem }; newEnum.Add(csharpEnumItem); if (cppEnumItem.Name != "None") { Manager.BindType(cppEnumItem.Name, csharpEnumItem); } } bool tryToAddNone = tag.EnumHasNone.HasValue ? tag.EnumHasNone.Value : false; // If C++ enum name is ending with FLAG OR FLAGS // Then tag this enum as flags and add None if necessary if (cppEnum.Name.EndsWith("FLAG") || cppEnum.Name.EndsWith("FLAGS")) { newEnum.IsFlag = true; if (!tag.EnumHasNone.HasValue) { tryToAddNone = !newEnum.Items.Cast <CsEnumItem>().Any(item => item.Name == "None"); } } // Add None value if (tryToAddNone) { var csharpEnumItem = new CsEnumItem("None", "0"); csharpEnumItem.CppElement = new CppElement { Description = "None." }; newEnum.Add(csharpEnumItem); } }
private static string GetEnumCondition(string variableName, CsEnum csEnum, CsEnumItem enumItem) { var mask = GetMask(csEnum, enumItem); return($"({variableName} & {mask}) != 0"); }
private bool CreateEnumAndConversionMethods() { var parts = _item.OwnerClasses; var conflictsCodeMethod = Extensions_CheckConflictsCode(_item); var optionsToStringCode = new CsCodeWriter(); optionsToStringCode.WriteLine("// generator : " + GetType().Name); if (!string.IsNullOrEmpty(conflictsCodeMethod)) { optionsToStringCode.WriteLine($"{conflictsCodeMethod}({valueVariable});"); } var fb = new EnumFlagsBuilder(MyEnum); fb.AddFlagsAttribute(MyNamespace); var enumSource = from q in _item.Options.Values where string.IsNullOrEmpty(q.Parameter?.Value) select q; var generate = false; foreach (var option in enumSource) { generate = true; var enumItem = new CsEnumItem(option.GetCsName()) { Description = option.FullDescription, }; var stringValue = GetStringValue(preferLongNameVariable, option, ExtensionsClass); optionsToStringCode.WriteDescriptionComment(option); var condition = GetEnumCondition(valueVariable, MyEnum, enumItem); optionsToStringCode.SingleLineIf(condition, $"yield return {stringValue};"); MyStruct_AddWithMethod(enumItem, fb.Value == 1); fb.Append(enumItem); { apps.Add((w, r) => { var stringValue = GetStringValue(preferLongNameVariable, option, ExtensionsClass); w.WriteDescriptionComment(option); var condition = GetEnumCondition(flagsPropertyName, MyEnum, enumItem); w.SingleLineIf(condition, $"yield return {stringValue};"); }); } } if (!generate) { return(false); } { var m = ExtensionsClass .AddMethod("OptionsToString", MyNamespace.GetTypeName <IEnumerable <string> >()) .WithStatic() .WithBody(optionsToStringCode); m.AddParam(valueVariable, MyEnumTypeName).UseThis = true; m.AddParam <OptionPreference>(preferLongNameVariable, ExtensionsClass).ConstValue = ExtensionsClass.GetEnumValueCode(OptionPreference.Short); } AddEnumToOutput(parts, MyNamespace, MyEnum); return(true); }
/// <summary> /// Maps a C++ Enum to a C# enum. /// </summary> /// <param name="newEnum">the C# enum.</param> public override void Process(CsEnum newEnum) { var cppEnum = (CppEnum)newEnum.CppElement; // Determine enum type. Default is int var typeName = cppEnum.GetTypeNameWithMapping(); switch (typeName) { case "byte": newEnum.UnderlyingType = typeRegistry.ImportType(typeof(byte)); break; case "short": newEnum.UnderlyingType = typeRegistry.ImportType(typeof(short)); break; case "ushort": newEnum.UnderlyingType = typeRegistry.ImportType(typeof(ushort)); break; case "int": newEnum.UnderlyingType = typeRegistry.ImportType(typeof(int)); break; case "uint": newEnum.UnderlyingType = typeRegistry.ImportType(typeof(uint)); break; default: Logger.Error(LoggingCodes.InvalidUnderlyingType, "Invalid type [{0}] for enum [{1}]. Types supported are : int, byte, short", typeName, cppEnum); break; } // Find Root Name of this enum // All enum items should start with the same root name and the root name should be at least 4 chars string rootName = cppEnum.Name; string rootNameFound = null; bool isRootNameFound = false; for (int i = rootName.Length; i >= 4 && !isRootNameFound; i--) { rootNameFound = rootName.Substring(0, i); isRootNameFound = true; foreach (var cppEnumItem in cppEnum.EnumItems) { if (!cppEnumItem.Name.StartsWith(rootNameFound)) { isRootNameFound = false; break; } } } if (isRootNameFound) { rootName = rootNameFound; } // Create enum items for enum foreach (var cppEnumItem in cppEnum.EnumItems) { string enumName = NamingRules.Rename(cppEnumItem, rootName); string enumValue = cppEnumItem.Value; var csharpEnumItem = new CsEnumItem(enumName, enumValue) { CppElement = cppEnumItem }; newEnum.Add(csharpEnumItem); } var rule = cppEnum.GetMappingRule(); bool tryToAddNone = rule.EnumHasNone ?? false; // If C++ enum name is ending with FLAG OR FLAGS // Then tag this enum as flags and add None if necessary if (cppEnum.Name.EndsWith("FLAG") || cppEnum.Name.EndsWith("FLAGS")) { newEnum.IsFlag = true; if (!rule.EnumHasNone.HasValue) { tryToAddNone = !newEnum.EnumItems.Any(item => item.Name == "None"); } } // Add None value if (tryToAddNone) { var csharpEnumItem = new CsEnumItem("None", "0") { CppElementName = "None", Description = "None" }; newEnum.Add(csharpEnumItem); } }