full support interface inheritance

This commit is contained in:
Dima Granetchi
2015-01-02 01:25:45 +02:00
parent 5ab43ca192
commit 5c2df234e0
2 changed files with 26 additions and 14 deletions
+22 -12
View File
@@ -4,11 +4,13 @@ import bindx.GenericError;
import haxe.macro.Type; import haxe.macro.Type;
import haxe.macro.Expr; import haxe.macro.Expr;
import haxe.macro.Context; import haxe.macro.Context;
import haxe.macro.TypeTools;
using haxe.macro.Tools; using haxe.macro.Tools;
using Lambda; using Lambda;
using StringTools; using StringTools;
using bindx.MetaUtils; using bindx.MetaUtils;
using haxe.macro.Tools;
class BindMacros { class BindMacros {
#if macro #if macro
@@ -24,21 +26,25 @@ class BindMacros {
*/ */
static public inline var FORCE = "force"; static public inline var FORCE = "force";
static var processed:Array<Type> = []; static var processed:Array<String> = [];
static var bindingSignalProvider:IBindingSignalProvider; static var bindingSignalProvider:IBindingSignalProvider;
static var interfaceBindableFields:Map<String, Array<String>>;
macro static public function buildIBindable():Array<Field> { macro static public function buildIBindable():Array<Field> {
var type = Context.getLocalType(); var type = Context.getLocalType();
if (processed.indexOf(type) > -1) { var tName = type.toComplexType().toString();
if (processed.indexOf(tName) > -1) {
return null; return null;
} }
processed.push(type); processed.push(tName);
var classType = type.getClass(); var classType = type.getClass();
if (bindingSignalProvider == null) { if (bindingSignalProvider == null) {
bindingSignalProvider = new bindx.BindSignal.BindSignalProvider(); bindingSignalProvider = new bindx.BindSignal.BindSignalProvider();
interfaceBindableFields = new Map();
} }
var fields = Context.getBuildFields(); var fields = Context.getBuildFields();
@@ -47,17 +53,20 @@ class BindMacros {
if (meta != null) injectBindableMeta(fields, meta); if (meta != null) injectBindableMeta(fields, meta);
if (classType.isInterface) { if (classType.isInterface) {
var a = [];
for (f in fields) { for (f in fields) {
for (m in f.meta) if (m.name == MetaUtils.BINDABLE_META) { for (m in f.meta) if (m.name == MetaUtils.BINDABLE_META) {
a.push(f.name);
if (m.params.length > 0) if (m.params.length > 0)
Context.warning('Interface doesn\'t support @:bindable meta params', m.pos); Context.warning('Interface doesn\'t support @:bindable meta params', m.pos);
} }
} }
interfaceBindableFields.set(typeName(classType), a);
return fields; return fields;
} }
var interfaceFields = getBindableFieldsFromInterfaces(classType); var interfaceFields = getBindableFieldsFromInterfaces(classType);
var res = []; var res = [];
for (f in fields) for (f in fields)
if (f.hasBindableMeta()) { if (f.hasBindableMeta()) {
@@ -79,16 +88,17 @@ class BindMacros {
static function getBindableFieldsFromInterfaces(classType:ClassType):Map<String, ClassType> { static function getBindableFieldsFromInterfaces(classType:ClassType):Map<String, ClassType> {
var interfaceFields = new Map(); var interfaceFields = new Map();
for (i in classType.interfaces) {
var t = i.t.get(); function iter(t:ClassType) {
if (@:privateAccess Bind.isBindable(t)) { var a = interfaceBindableFields.get(typeName(t));
for (f in t.fields.get()) { if (a != null) {
if (f.meta.has(MetaUtils.BINDABLE_META)) { for (i in a)
interfaceFields.set(f.name, t); interfaceFields.set(i, t);
}
}
} }
for (it in t.interfaces) iter(it.t.get());
} }
for (i in classType.interfaces) iter(i.t.get());
return interfaceFields; return interfaceFields;
} }
+4 -2
View File
@@ -46,7 +46,9 @@ interface IIBindable extends IBindable {
var i(default, set):Int; var i(default, set):Int;
} }
class BindableParent implements IIBindable { interface IIIBindable extends IIBindable { }
class BindableParent implements IIIBindable {
public function new() {} public function new() {}
@:bindable @:bindable
@@ -54,7 +56,7 @@ class BindableParent implements IIBindable {
} }
@:bindable @:bindable
class BindableChild extends BindableParent { class BindableChild extends BindableParent implements IIBindable {
public var s:String; public var s:String;
} }