Skip to content

Commit

Permalink
Event handlers ActiveXObject.on; remove duplicate JsDoc entries
Browse files Browse the repository at this point in the history
  • Loading branch information
zspitz committed Feb 22, 2017
1 parent 0e0a978 commit c56e95d
Show file tree
Hide file tree
Showing 6 changed files with 54 additions and 13 deletions.
4 changes: 3 additions & 1 deletion core/Classes/DataClasses.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
using System.Linq;
using Microsoft.Win32;
using static TsActivexGen.TSParameterType;
using static TsActivexGen.Util.Functions;

namespace TsActivexGen {
public abstract class EqualityBase<T> : IEquatable<T> where T : class {
Expand Down Expand Up @@ -61,6 +62,7 @@ public void AddParameter(string name, ITSType type) {
if (Parameters == null) { Parameters = new List<KeyValuePair<string, TSParameterDescription>>(); }
Parameters.Add(name, new TSParameterDescription() { Type = type });
}
public void AddParameter(string name, string type) => AddParameter(name, new TSSimpleType(type));
public string[] TypeParts() {
var ret = new List<string>();
Parameters.DefaultIfNull().Values().SelectMany(x => x.Type.TypeParts()).AddRangeTo(ret);
Expand Down Expand Up @@ -92,7 +94,7 @@ public class TSNamespace {

public HashSet<string> GetUsedTypes() {
var types = new List<string>();
Interfaces.Values.Concat(GlobalInterfaces.Values).SelectMany(i => i.Members).Values().SelectMany(x => x.TypeParts()).AddRangeTo(types);
Interfaces.Values.Concat(GlobalInterfaces.Values).SelectMany(i => i.Members).Values().SelectMany(x => x.TypeParts()).NamedTypes().AddRangeTo(types);
Aliases.Values().NamedTypes().AddRangeTo(types);
return types.ToHashSet();
}
Expand Down
10 changes: 7 additions & 3 deletions core/Classes/TSBuilder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ private void WriteMemberBase(TSMemberDescription m, string ns, string memberIden

WriteJsDoc(m.JsDoc, indentationLevel, true);

$"{memberIdentifier}{parameterList}: {returnType}{comment}".AppendLineTo(sb, indentationLevel);
$"{memberIdentifier}{parameterList}: {returnType};{comment}".AppendLineTo(sb, indentationLevel);
}

private void WriteMember(KeyValuePair<string, TSMemberDescription> x, string ns, int indentationLevel) {
Expand All @@ -109,8 +109,12 @@ private void WriteMember(KeyValuePair<string, TSMemberDescription> x, string ns,
//go pattern matching!!!
if (ExecIfType<TSSimpleType>(type, x => ret = RelativeName(x.GenericParameter ?? x.FullName, ns))) {
} else if (ExecIfType<TSTupleType>(type, x => ret = $"[{x.Members.Joined(",", y => GetTypeString(y, ns))}]")) {
} else if (ExecIfType<TSObjectType>(type, x => ret = $"{x.Members.JoinedKVP((key, val) => $"{key}: {GetTypeString(val, ns)}")}")) {
} else if (ExecIfType<TSFunctionType>(type, x => ret = $"({x.FunctionDescription.Parameters.Select(y => GetParameterString(y, ns))}: {GetTypeString(x.FunctionDescription.ReturnType, ns)}")) {
} else if (ExecIfType<TSObjectType>(type, x => ret = $"{{{x.Members.JoinedKVP((key, val) => $"{key}: {GetTypeString(val, ns)}")}}}")) {
} else if (ExecIfType<TSFunctionType>(type, x => {
//the only way to define a function type is with the fat arrow
//e.g. () => void and not (): void
ret = $"({x.FunctionDescription.Parameters.Joined(", ", y => GetParameterString(y, ns))}) => {GetTypeString(x.FunctionDescription.ReturnType, ns)}";
})) {
} else {
throw new NotImplementedException();
}
Expand Down
9 changes: 7 additions & 2 deletions core/Classes/TSTypes.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,8 @@
namespace TsActivexGen {
/// <summary>Describes namespace+name types, as well as built-in and literal types</summary>
public class TSSimpleType : EqualityBase<TSSimpleType>, ITSType {
public static TSSimpleType Any = new TSSimpleType { FullName = "any" };
public static TSSimpleType Any = new TSSimpleType("any");
public static TSSimpleType Void = new TSSimpleType("void");
public string FullName { get; set; }
public string Namespace {
get {
Expand Down Expand Up @@ -40,6 +41,10 @@ public TSSimpleType(string fullName = null) {
public class TSTupleType : ITSType {
public List<ITSType> Members { get; } = new List<ITSType>();
public string[] TypeParts() => Members.SelectMany(x => x.TypeParts()).ToArray();
public TSTupleType() {}
public TSTupleType(IEnumerable<string> members) {
members.Select(x => new TSSimpleType(x)).AddRangeTo(Members);
}
}

public class TSObjectType : ITSType {
Expand All @@ -48,7 +53,7 @@ public class TSObjectType : ITSType {
}

public class TSFunctionType : ITSType {
public TSMemberDescription FunctionDescription { get; set; }
public TSMemberDescription FunctionDescription { get; } = new TSMemberDescription();
public string[] TypeParts() => FunctionDescription.TypeParts();
}
}
41 changes: 35 additions & 6 deletions core/Classes/TlbInf32Generator.cs
Original file line number Diff line number Diff line change
Expand Up @@ -130,7 +130,11 @@ private KeyValuePair<string, TSParameterDescription> ToTSParameterDescription(Pa
ret.ParameterType = Standard;
}
if (p.Default) {
jsDoc.Add("param", $"{returnType.FullName} [{name}={AsString(p.DefaultValue)}]");
var defaultValue = p.DefaultValue;
if (defaultValue != null) {
var kvp = KVP("param", $"{returnType.FullName} [{name}={AsString(p.DefaultValue)}]");
if (!jsDoc.Contains(kvp)) { jsDoc.Add(kvp); }
}
}
return KVP(p.Name, ret);
}
Expand Down Expand Up @@ -226,6 +230,8 @@ private KeyValuePair<string, TSInterfaceDescription> ToTSInterfaceDescription(In

private KeyValuePair<string, TSInterfaceDescription> ToTSInterfaceDescription(CoClassInfo c) {
var typename = $"{c.Parent.Name}.{c.Name}";
//scripting environments can only use the default interface, because they don't have variable types
//we can thus ignore everything else in c.Interfaces
return ToTSInterfaceDescriptionBase(c.DefaultInterface.Members, typename,c.HelpString);
}

Expand All @@ -240,11 +246,34 @@ private KeyValuePair<string, TSInterfaceDescription> ToTSInterfaceDescription(Re
private TSMemberDescription ToActiveXObjectConstructorDescription(CoClassInfo c) {
var ret = new TSMemberDescription();
var typename = $"{c.Parent.Name}.{c.Name}";
ret.AddParameter("progid", new TSSimpleType($"'{typename}'")); //note the string literal type
ret.AddParameter("progid", $"'{typename}'"); //note the string literal type
ret.ReturnType = new TSSimpleType(typename);
return ret;
}

//ActiveXObject.on(obj: 'Word.Application', 'BeforeDocumentSave', ['Doc','SaveAsUI','Cancel'], function (params) {});
private TSMemberDescription ToActiveXEventMember(MemberInfo m, CoClassInfo c) {
var args = m.Parameters.Cast().Select(x => KVP<string,ITSType>(x.Name, GetTypeName(x.VarTypeInfo)));
var typename = $"{c.Parent.Name}.{c.Name}";

var ret = new TSMemberDescription();
ret.AddParameter("obj", $"{typename}");
ret.AddParameter("eventName", $"'{m.Name}'");
if (args.Keys().Any()) {ret.AddParameter("eventArgs", new TSTupleType(args.Keys().Select(x => $"'{x}'")));}

var parameterType = new TSObjectType();
args.AddRangeTo(parameterType.Members);
var fnType = new TSFunctionType();
fnType.FunctionDescription.AddParameter("this", typename);
fnType.FunctionDescription.AddParameter("parameter", parameterType);
fnType.FunctionDescription.ReturnType = TSSimpleType.Void;
ret.AddParameter("handler", fnType);

ret.ReturnType = TSSimpleType.Void;

return ret;
}

private TSMemberDescription ToEnumeratorConstructorDescription(KeyValuePair<TSSimpleType,string> kvp) {
var collectionTypeName = kvp.Key;
var itemTypeName = kvp.Value;
Expand All @@ -262,8 +291,6 @@ private TSNamespace ToNamespace(TypeLibInfo tli) {
tli.Constants.Cast().Where(x => x.TypeKind == TKIND_MODULE).Select(ToTSNamespaceDescription).AddRangeTo(ret.Namespaces);
coclasses.Select(ToTSInterfaceDescription).AddRangeTo(ret.Interfaces);

//TODO do we need to look at ImpliedInterfaces? Should we use GetMembers instead of manually iterating over Members?

if (tli.Declarations.Cast().Any()) {
//not sure what these are, if they are accessible from JScript
//there is one in the Excel object library
Expand All @@ -275,8 +302,10 @@ private TSNamespace ToNamespace(TypeLibInfo tli) {

var activex = new TSInterfaceDescription();
coclasses.Where(x => x.IsCreateable()).OrderBy(x => x.Name).Select(ToActiveXObjectConstructorDescription).AddRangeTo(activex.Constructors);

//TODO implement calls to ActiveXObject.on with appropriate parameters
coclasses.Select(x => new {
coclass = x,
eventInterface = x.DefaultEventInterface
}).Where(x => x.eventInterface != null).SelectMany(x => x.eventInterface.Members.Cast().Select(y => KVP("on", ToActiveXEventMember(y, x.coclass)))).AddRangeTo(activex.Members);

if (activex.Constructors.Any()) {
ret.GlobalInterfaces["ActiveXObject"] = activex;
Expand Down
1 change: 1 addition & 0 deletions core/Extensions/Misc.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ public static class MiscExtensions {
static string[] builtins = new[] { "any", "void", "boolean", "string", "number", "undefined", "null", "never", "VarDate" };
public static string[] NamedTypes(this ITSType type) => type.TypeParts().Except(builtins).Where(x => !IsLiteralTypeName(x)).ToArray();
public static HashSet<string> NamedTypes(this IEnumerable<ITSType> types) => types.SelectMany(x => x.NamedTypes()).ToHashSet();
public static string[] NamedTypes(this IEnumerable<string> types) => types.Except(builtins).Where(x => !IsLiteralTypeName(x)).ToArray();
public static bool IsLiteralType(this ITSType type) => IsLiteralTypeName((type as TSSimpleType)?.FullName);
}
}
2 changes: 1 addition & 1 deletion core/Extensions/Type.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ public static Type UnderlyingIfNullable(this Type t) {
return t;
}
public static bool IsNumeric(this Type t) {
return t.UnderlyingIfNullable().In(typeof(int), typeof(short), typeof(decimal), typeof(double), typeof(UInt16)); //other types should be here too
return t.UnderlyingIfNullable().In(typeof(int), typeof(short), typeof(decimal), typeof(double), typeof(ushort), typeof(float)); //other types should be here too
}
}
}

0 comments on commit c56e95d

Please sign in to comment.