Browse Source

[cs] Only use native properties for interacting with CsNative

Cauê Waneck 11 years ago
parent
commit
652a94d737
4 changed files with 58 additions and 7 deletions
  1. 1 0
      ast.ml
  2. 1 0
      common.ml
  3. 51 0
      gencommon.ml
  4. 5 7
      gencs.ml

+ 1 - 0
ast.ml

@@ -110,6 +110,7 @@ module Meta = struct
 		| Optional
 		| Overload
 		| PrivateAccess
+		| Property
 		| Protected
 		| Public
 		| PublicFields

+ 1 - 0
common.ml

@@ -405,6 +405,7 @@ module MetaInfo = struct
 		| PublicFields -> ":publicFields",("Forces all class fields of inheriting classes to be public",[UsedOn TClass])
 		| PrivateAccess -> ":privateAccess",("Allow private access to anything for the annotated expression",[UsedOn TExpr])
 		| Protected -> ":protected",("Marks a class field as being protected",[UsedOn TClassField])
+		| Property -> ":property",("Marks a property field to be compiled as a native C# property",[UsedOn TClassField;Platform Cs])
 		| ReadOnly -> ":readOnly",("Generates a field with the 'readonly' native keyword",[Platform Cs; UsedOn TClassField])
 		| RealPath -> ":realPath",("Internally used on @:native types to retain original path information",[Internal])
 		| Remove -> ":remove",("Causes an interface to be removed from all implementing classes before generation",[UsedOn TClass])

+ 51 - 0
gencommon.ml

@@ -9838,6 +9838,57 @@ struct
 
 end;;
 
+(* ******************************************* *)
+(* InterfaceProps *)
+(* ******************************************* *)
+
+(*
+
+  This module filter will go through all declared properties, and see if they are conforming to a native interface.
+  If they are, it will add Meta.Property to it
+
+  dependencies:
+
+*)
+
+module InterfaceProps =
+struct
+  let name = "interface_props"
+
+  let priority = solve_deps name []
+
+  let run gen =
+    let run md = match md with
+      | TClassDecl ( { cl_interface = false; cl_extern = false } as cl ) ->
+        let vars = List.fold_left (fun acc (iface,_) ->
+          if Meta.has Meta.CsNative iface.cl_meta then
+            List.filter (fun cf -> match cf.cf_kind with
+              | Var { v_read = AccCall } | Var { v_write = AccCall } ->
+                true
+              | _ -> false
+            ) iface.cl_ordered_fields @ acc
+          else
+            acc
+        ) [] cl.cl_implements in
+        let vars = List.map (fun cf -> cf.cf_name) vars in
+        if vars <> [] then
+          List.iter (fun cf -> match cf.cf_kind with
+            | Var { v_read = AccCall } | Var { v_write = AccCall } when List.mem cf.cf_name vars ->
+              cf.cf_meta <- (Meta.Property, [], Ast.null_pos) :: cf.cf_meta
+            | _ -> ()
+          ) cl.cl_ordered_fields;
+
+        md
+      | _ -> md
+    in
+    run
+
+  let configure gen =
+    let run = run gen in
+    let map md = Some(run md) in
+    gen.gmodule_filters#add ~name:name ~priority:(PCustom priority) map
+end;;
+
 (* ******************************************* *)
 (* Int Division Synf *)
 (* ******************************************* *)

+ 5 - 7
gencs.ml

@@ -632,10 +632,7 @@ let configure gen =
   let change_id name = try
 			Hashtbl.find reserved name
 		with | Not_found ->
-			if String.starts_with name "get_" || String.starts_with name "set_" then
-				"_" ^ name
-			else
-				name
+      name
 	in
 
   let change_ns md = if no_root then
@@ -981,7 +978,7 @@ let configure gen =
 
 	let is_extern_prop t name = match field_access gen t name with
 		| FClassField(_,_,decl,v,_,t,_) ->
-			Type.is_extern_field v && decl.cl_extern && not (is_hxgen (TClassDecl decl))
+			Type.is_extern_field v && (Meta.has Meta.Property v.cf_meta || (decl.cl_extern && not (is_hxgen (TClassDecl decl))))
 		| _ -> false
 	in
 
@@ -1876,7 +1873,7 @@ let configure gen =
 			(* first get all vars declared as properties *)
 			let props, nonprops = List.partition (fun v -> match v.cf_kind with
 				| Var { v_read = AccCall } | Var { v_write = AccCall } ->
-					Type.is_extern_field v
+					Type.is_extern_field v && Meta.has Meta.Property v.cf_meta
 				| _ -> false
 			) cflist in
 			let props = ref (List.map (fun v -> (v.cf_name, ref (v,v.cf_type,None,None))) props) in
@@ -1884,7 +1881,7 @@ let configure gen =
 			let find_prop name = try
 					List.assoc name !props
 				with | Not_found -> match field_access gen t name with
-					| FClassField (_,_,decl,v,_,t,_) when Type.is_extern_field v && decl.cl_extern && not (is_hxgen (TClassDecl decl)) ->
+					| FClassField (_,_,decl,v,_,t,_) when is_extern_prop (TInst(cl,List.map snd cl.cl_types)) name ->
 						let ret = ref (v,t,None,None) in
 						props := (name, ret) :: !props;
 						ret
@@ -2112,6 +2109,7 @@ let configure gen =
   EnumToClass.configure gen (Some (fun e -> mk_cast gen.gcon.basic.tint e)) false true (get_cl (get_type gen (["haxe";"lang"],"Enum")) ) true false;
 
   InterfaceVarsDeleteModf.configure gen;
+  InterfaceProps.configure gen;
 
   let dynamic_object = (get_cl (get_type gen (["haxe";"lang"],"DynamicObject")) ) in