diff options
author | Dominic Letz <dominic@diode.io> | 2021-01-17 03:21:43 +0100 |
---|---|---|
committer | Dominic Letz <dominic@diode.io> | 2021-02-19 12:20:55 +0100 |
commit | b9702ca17cbe8f1443b0eb0952981e190ed4cf16 (patch) | |
tree | 40bb88bcd1f263b4c1cde63c43408cdf7e9bab83 /lib/wx/api_gen | |
parent | 5722b2b1da3b713bbd190810ff2f96ba7c5b9ace (diff) | |
download | erlang-b9702ca17cbe8f1443b0eb0952981e190ed4cf16.tar.gz |
Add wxWebView
This patch adds support for the wxWebView component of wxWidgets. This finally enables Erlang developers to write modern desktop applications comparable in look and feel with state of the art applications.
The patchset ships with an addition of the demo application and adds a sample component in examples/demo/
This patchset also depends on adding libwxgtk-webveiw3.0-gtk3-dev to the base images for the CI builds to succeed.
Diffstat (limited to 'lib/wx/api_gen')
-rw-r--r-- | lib/wx/api_gen/Makefile | 2 | ||||
-rwxr-xr-x | lib/wx/api_gen/interface/wx/webview.h | 10 | ||||
-rw-r--r-- | lib/wx/api_gen/wx_extra/wx_misc.erl | 23 | ||||
-rw-r--r-- | lib/wx/api_gen/wx_gen_cpp.erl | 1452 | ||||
-rw-r--r-- | lib/wx/api_gen/wx_gen_erl.erl | 7 | ||||
-rw-r--r-- | lib/wx/api_gen/wx_gen_nif.erl | 58 | ||||
-rw-r--r-- | lib/wx/api_gen/wxapi.conf | 67 |
7 files changed, 143 insertions, 1476 deletions
diff --git a/lib/wx/api_gen/Makefile b/lib/wx/api_gen/Makefile index 0905e0de20..3f54dfff46 100644 --- a/lib/wx/api_gen/Makefile +++ b/lib/wx/api_gen/Makefile @@ -26,7 +26,7 @@ GL_DIR = /usr/include/GL ERL_COMPILE_FLAGS=+debug_info +warn_unused_vars -COMPILER = gen_util wx_gen wx_gen_erl wx_gen_cpp wx_gen_nif wx_gen_doc +COMPILER = gen_util wx_gen wx_gen_erl wx_gen_nif wx_gen_doc COMPILER_T = $(COMPILER:%=$(EBIN)/%.beam) GL_COMP = gl_gen gl_gen_erl gl_gen_nif gl_gen_doc gl_scan_doc diff --git a/lib/wx/api_gen/interface/wx/webview.h b/lib/wx/api_gen/interface/wx/webview.h index b2a05d1c26..897bbcb7c7 100755 --- a/lib/wx/api_gen/interface/wx/webview.h +++ b/lib/wx/api_gen/interface/wx/webview.h @@ -280,6 +280,7 @@ public: custom schemes and virtual file systems. @par wxWEBVIEW_BACKEND_EDGE (MSW) + @anchor wxWEBVIEW_BACKEND_EDGE The Edge (Chromium) backend uses Microsoft's <a href="https://docs.microsoft.com/en-us/microsoft-edge/hosting/webview2">Edge WebView2</a>. @@ -305,7 +306,8 @@ public: - Make sure to add a note about using the WebView2 SDK to your application documentation, as required by its licence - @par wxWEBVIEW_WEBKIT (GTK) + @par wxWEBVIEW_BACKEND_WEBKIT (GTK) + @anchor wxWEBVIEW_BACKEND_WEBKIT Under GTK the WebKit backend uses <a href="http://webkitgtk.org/">WebKitGTK+</a>. The current minimum version @@ -315,14 +317,16 @@ public: resources such as images and stylesheets are currently loaded using the data:// scheme. - @par wxWEBVIEW_WEBKIT2 (GTK3) + @par wxWEBVIEW_BACKEND_WEBKIT2 (GTK3) + @anchor wxWEBVIEW_BACKEND_WEBKIT2 Under GTK3 the WebKit2 version of <a href="http://webkitgtk.org/">WebKitGTK+</a> is used. In Ubuntu the required package name is libwebkit2gtk-4.0-dev and under Fedora it is webkitgtk4-devel. All wxWEBVIEW_WEBKIT features are supported except for clearing and enabling / disabling the history. - @par wxWEBVIEW_WEBKIT (OSX) + @par wxWEBVIEW_BACKEND_WEBKIT (OSX) + @anchor wxWEBVIEW_BACKEND_WEBKIT The macOS WebKit backend uses Apple's <a href="http://developer.apple.com/library/mac/#documentation/Cocoa/Reference/WebKit/Classes/WebView_Class/Reference/Reference.html#//apple_ref/doc/uid/20001903">WebView</a> diff --git a/lib/wx/api_gen/wx_extra/wx_misc.erl b/lib/wx/api_gen/wx_extra/wx_misc.erl new file mode 100644 index 0000000000..eb105dbd52 --- /dev/null +++ b/lib/wx/api_gen/wx_extra/wx_misc.erl @@ -0,0 +1,23 @@ +-export([mSWSetEmulationLevel/1, mSWSetEmulationLevel/2]). + +%% @doc See <a href="https://docs.wxwidgets.org/3.1.4/classwx_web_view_i_e.html#a7a45d02cb7dd6dbfcc09566449a1f3bd">external documentation</a>. +%%<br /> Level = ?wxWEBVIEWIE_EMU_DEFAULT | ?wxWEBVIEWIE_EMU_IE7 | ?wxWEBVIEWIE_EMU_IE8 | ?wxWEBVIEWIE_EMU_IE8_FORCE | ?wxWEBVIEWIE_EMU_IE9 | ?wxWEBVIEWIE_EMU_IE9_FORCE | ?wxWEBVIEWIE_EMU_IE10 | ?wxWEBVIEWIE_EMU_IE10_FORCE | ?wxWEBVIEWIE_EMU_IE11 | ?wxWEBVIEWIE_EMU_IE11_FORCE +-spec mSWSetEmulationLevel(Level) -> boolean() when + Level :: wx:wx_enum(). +mSWSetEmulationLevel(Level) when is_integer(Level) -> + mSWSetEmulationLevel(Level, "erl.exe"), + mSWSetEmulationLevel(Level, "werl.exe"), + true. + +%% @doc See <a href="https://docs.wxwidgets.org/3.1.4/classwx_web_view_i_e.html#a7a45d02cb7dd6dbfcc09566449a1f3bd">external documentation</a>. +%%<br /> Level = ?wxWEBVIEWIE_EMU_DEFAULT | ?wxWEBVIEWIE_EMU_IE7 | ?wxWEBVIEWIE_EMU_IE8 | ?wxWEBVIEWIE_EMU_IE8_FORCE | ?wxWEBVIEWIE_EMU_IE9 | ?wxWEBVIEWIE_EMU_IE9_FORCE | ?wxWEBVIEWIE_EMU_IE10 | ?wxWEBVIEWIE_EMU_IE10_FORCE | ?wxWEBVIEWIE_EMU_IE11 | ?wxWEBVIEWIE_EMU_IE11_FORCE +-spec mSWSetEmulationLevel(Level, Executable) -> boolean() when + Level :: wx:wx_enum(), + Executable :: string(). +mSWSetEmulationLevel(Level, Executable) -> + {ok, Reg} = win32reg:open([write]), + ok = win32reg:change_key(Reg, "\\hkey_current_user\\software\\microsoft\\internet explorer\\main\\featurecontrol\\"), + ok = win32reg:change_key_create(Reg, "FEATURE_BROWSER_EMULATION"), + ok = win32reg:set_value(Reg, Executable, Level), + ok = win32reg:close(Reg), + true. diff --git a/lib/wx/api_gen/wx_gen_cpp.erl b/lib/wx/api_gen/wx_gen_cpp.erl deleted file mode 100644 index 356ebfe127..0000000000 --- a/lib/wx/api_gen/wx_gen_cpp.erl +++ /dev/null @@ -1,1452 +0,0 @@ -%% -%% %CopyrightBegin% -%% -%% Copyright Ericsson AB 2008-2018. All Rights Reserved. -%% -%% Licensed under the Apache License, Version 2.0 (the "License"); -%% you may not use this file except in compliance with the License. -%% You may obtain a copy of the License at -%% -%% http://www.apache.org/licenses/LICENSE-2.0 -%% -%% Unless required by applicable law or agreed to in writing, software -%% distributed under the License is distributed on an "AS IS" BASIS, -%% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -%% See the License for the specific language governing permissions and -%% limitations under the License. -%% -%% %CopyrightEnd% -%% -%%%------------------------------------------------------------------- -%%% File : wx_gen_cpp.erl -%%% Author : Dan Gudmundsson <dgud@erix.ericsson.se> -%%% Description : -%%% -%%% Created : 19 Feb 2007 by Dan Gudmundsson <dgud@erix.ericsson.se> -%%%------------------------------------------------------------------- --module(wx_gen_cpp). - --include("wx_gen.hrl"). - --compile(export_all). - --import(lists, [foldl/3,foldr/3,reverse/1, keysearch/3, map/2, filter/2]). --import(gen_util, [lowercase/1, lowercase_all/1, uppercase/1, uppercase_all/1, - open_write/1, close/0, c_copyright/0, w/2, w/1, - args/3, strip_name/2]). --import(wx_gen, [next_id/1]). - -gen(Defs) -> - open_write("../c_src/gen/wxe_derived_dest.h"), - c_copyright(), - w("~n/***** This file is generated do not edit ****/~n~n", []), - gen_derived_dest(Defs), - close(), - - open_write("../c_src/gen/wxe_funcs.cpp"), - c_copyright(), - Res = gen_funcs(Defs), - close(), - - open_write("../c_src/gen/wxe_macros.h"), - c_copyright(), - gen_macros(), - close(), - - open_write("../c_src/gen/wxe_init.cpp"), - c_copyright(), - build_enums(), - close(), - - build_events(), - Res. - -gen_derived_dest(Defs) -> - [gen_derived_dest_2(Class) || Class <- Defs], - ok. - -gen_derived_dest_2(C=#class{name=Class, options=Opts}) -> - ?WTC("gen_derived_dest_2"), - Derived = is_derived(C), - TaylorMade = taylormade_class(C), - - if Derived andalso (TaylorMade =:= false) -> - case lists:keysearch(ifdef,1,Opts) of - {value, {ifdef, What}} when is_list(What)-> w("#if ~s~n",[What]); - {value, {ifdef, What}} when is_atom(What) -> w("#if ~p~n",[What]); - _ -> ok - end, - w("class E~s : public ~s {~n",[Class,Class]), - case Class of - "wxGLCanvas" -> %% Special for cleaning up gl context - w(" public: ~~E~s() {deleteActiveGL(this);" - "((WxeApp *)wxTheApp)->clearPtr(this);};~n", [Class]); - _ -> - w(" public: ~~E~s() {((WxeApp *)wxTheApp)->clearPtr(this);};~n", [Class]) - end, - gen_constructors(C), - case lists:keysearch(ifdef,1,Opts) of - {value, {ifdef, Endif}} -> - w("};~n", []), - w("#endif // ~p~n~n",[Endif]); - _ -> - w("};~n~n", []) - end; - TaylorMade /= false -> - w("~s~n", [TaylorMade]); - true -> - ignore - end. - -taylormade_class(#class{name=CName, methods=Ms}) -> - TaylorMade = lists:any(fun([#method{where=taylormade}|_]) -> true; - (_) -> false - end, Ms), - case TaylorMade of - false -> false; - true -> - {ok, Bin} = file:read_file(filename:join([wx_extra, CName ++".c_src"])), - Src = binary_to_list(Bin), - case gen_util:get_taylor_made(Src, CName ++ "_class") of - nomatch -> false; - {match, [Str0]} -> Str0 - end - end. - -gen_constructors(#class{name=Class, methods=Ms0}) -> - Ms = lists:append(Ms0), - Cs = lists:filter(fun(#method{method_type=MT}) -> MT =:= constructor end, Ms), - [gen_constructor(Class, Const) || Const <- Cs], - case need_copy_constr(Class) of - true -> - w(" E~s(~s copy) : ~s(copy) {};~n", [Class, Class, Class]); - false -> - ignore - end. -gen_constructor(_Class, #method{where=merged_c}) -> ok; -gen_constructor(_Class, #method{where=erl_no_opt}) -> ok; -gen_constructor(_Class, #method{where=erl_alias}) -> ok; -gen_constructor(Class, _M=#method{params=Ps, opts=FOpts}) -> - Gen = fun(#param{name=N, type=T}, Id) -> gen_type(T,Id) ++ N end, - CallA = fun(#param{name=N}) -> N end, - MergedType = fun(#param{type={merged,L}}) -> length(L); (_) -> 0 end, - ?WTC("gen_constructor"), - Endif = case lists:keysearch(deprecated, 1, FOpts) of - {value, {deprecated, IfDef}} -> - w("#if ~s~n", [IfDef]), - true; - _ -> false - end, - case lists:max([0|[MergedType(P) || P <- Ps]]) of - 0 -> - w(" E~s(~s) : ~s(~s) {};~n", - [Class,args(fun(P) -> Gen(P,1) end,",",Ps),Class,args(CallA,",",Ps)]); - Max -> - [w(" E~s(~s) : ~s(~s) {};~n", - [Class,args(fun(P) -> Gen(P,Id) end,",",Ps),Class,args(CallA,",",Ps)]) - || Id <- lists:seq(1,Max)] - end, - Endif andalso w("#endif~n", []), - ok. - - -%% need_copy_constr("wxFont") -> true; -%% need_copy_constr("wxIcon") -> true; -need_copy_constr("wxImage") -> true; -%%need_copy_constr("wxBitmap") -> true; -%%need_copy_constr("wxGraphics" ++ _) -> true; -need_copy_constr(_) -> false. - -gen_type(#type{name=Type, ref={pointer,1}, mod=Mod},_) -> - mods(Mod) ++ to_string(Type) ++ " * "; -gen_type(#type{name=Type, ref={pointer,2}, mod=Mod},_) -> - mods(Mod) ++ to_string(Type) ++ " ** "; -gen_type(#type{name=Type, ref=reference, mod=Mod},_) -> - mods(Mod) ++ to_string(Type) ++ "& "; -gen_type(#type{name=Type, ref=undefined, base=binary, mod=Mod},_) -> - mods(Mod) ++ to_string(Type) ++ " * "; -gen_type(#type{name=Type, ref=undefined, single=array, mod=Mod},_) -> - mods(Mod) ++ to_string(Type) ++ " * "; -gen_type(#type{name=Type, ref=undefined, mod=Mod},_) -> - mods(Mod) ++ to_string(Type) ++ " "; -gen_type({merged, MTs}, N) when is_integer(N) -> - {_, T, _} = lists:nth(N, MTs), - gen_type(T,error); -gen_type(voidp, _) -> - "void ** ". - -gen_funcs(Defs) -> - w("~n/***** This file is generated do not edit ****/~n~n"), - w("#include <wx/wx.h>~n"), - w("#include \"../wxe_impl.h\"~n"), - w("#include \"../wxe_events.h\"~n"), - w("#include \"../wxe_return.h\"~n"), - w("#include \"../wxe_gl.h\"~n"), - w("#include \"wxe_macros.h\"~n"), - w("#include \"wxe_derived_dest.h\"~n~n"), - - w("#if !wxCHECK_VERSION(2,9,0)~n", []), - [w("#define ~p int~n", [Enum]) || - Enum <- [wxPenJoin, wxPenCap, wxImageResizeQuality, %%wxBitmapType, - wxPolygonFillMode, wxMappingMode, wxRasterOperationMode, - wxFloodFillStyle - ]], - w("#endif~n",[]), - - w("void WxeApp::wxe_dispatch(wxeCommand& Ecmd)~n{~n"), - w(" char * bp = Ecmd.buffer;~n"), - w(" int op = Ecmd.op;~n"), - w(" Ecmd.op = -1;~n"), - w(" wxeMemEnv *memenv = getMemEnv(Ecmd.port);~n"), -%% w(" wxMBConvUTF32 UTFconverter;~n"), - w(" wxeReturn rt = wxeReturn(WXE_DRV_PORT, Ecmd.caller, true);~n"), - w(" try {~n"), - w(" switch (op)~n{~n"), -%% w(" case WXE_CREATE_PORT:~n", []), -%% w(" { newMemEnv(Ecmd.port); } break;~n", []), -%% w(" case WXE_REMOVE_PORT:~n", []), -%% w(" { destroyMemEnv(Ecmd.port); } break;~n", []), - w(" case DESTROY_OBJECT: {~n"), - w(" void *This = getPtr(bp,memenv);~n"), - w(" wxeRefData *refd = getRefData(This);~n"), - w(" if(This && refd) {~n"), - w(" if(recurse_level > 1 && refd->type != 8) {~n"), - w(" delayed_delete->Append(Ecmd.Save(op));~n"), - w(" } else {~n"), - w(" delete_object(This, refd);~n"), - w(" ((WxeApp *) wxTheApp)->clearPtr(This);}~n"), - w(" } } break;~n"), - w(" case WXE_REGISTER_OBJECT: {~n" - " registerPid(bp, Ecmd.caller, memenv);~n" - " rt.addAtom(\"ok\");~n" - " break;~n" - " }~n"), - w(" case WXE_BIN_INCR:~n driver_binary_inc_refc(Ecmd.bin[0].bin);~n break;~n",[]), - w(" case WXE_BIN_DECR:~n driver_binary_dec_refc(Ecmd.bin[0].bin);~n break;~n",[]), - w(" case WXE_INIT_OPENGL:~n wxe_initOpenGL(&rt, bp);~n break;~n",[]), - - Res = [gen_class(Class) || Class <- Defs], - - w(" default: {~n"), - w(" wxeReturn error = wxeReturn(WXE_DRV_PORT, Ecmd.caller, false);"), - w(" error.addAtom(\"_wxe_error_\");~n"), - w(" error.addInt((int) op);~n"), - w(" error.addAtom(\"not_supported\");~n"), - w(" error.addTupleCount(3);~n"), - w(" error.send();~n"), - w(" return ;~n"), - w(" }~n"), - w("} // switch~n"), - w(" rt.send();~n"), - w("} catch (wxe_badarg badarg) { // try~n"), - w(" wxeReturn error = wxeReturn(WXE_DRV_PORT, Ecmd.caller, false);"), - w(" error.addAtom(\"_wxe_error_\");~n"), - w(" error.addInt((int) op);~n"), - w(" error.addAtom(\"badarg\");~n"), - w(" error.addInt((int) badarg.ref);~n"), - w(" error.addTupleCount(2);~n"), - w(" error.addTupleCount(3);~n"), - w(" error.send();~n"), - w("}} /* The End */~n~n~n"), - - UglySkipList = ["wxCaret", "wxCalendarDateAttr", - "wxFileDataObject", "wxTextDataObject", "wxBitmapDataObject", - "wxAuiSimpleTabArt" - ], - - w("bool WxeApp::delete_object(void *ptr, wxeRefData *refd) {~n", []), - w(" if(wxe_debug) {\n" - " wxString msg;\n" - " const wxChar *class_info = wxT(\"unknown\");\n" - " if(refd->type < 10) {\n" - " wxClassInfo *cinfo = ((wxObject *)ptr)->GetClassInfo();\n" - " class_info = cinfo->GetClassName();\n" - " }\n" - " msg.Printf(wxT(\"Deleting {wx_ref, %d, %s} at %p \"), refd->ref, class_info, ptr);\n" - " send_msg(\"debug\", &msg);\n" - " };\n"), - - w(" switch(refd->type) {~n", []), - w("#if wxUSE_GRAPHICS_CONTEXT~n", []), - w(" case 4: delete (wxGraphicsObject *) ptr; break;~n", []), - w("#endif~n", []), - Case = fun(C=#class{name=Class, id=Id, abstract=IsAbs, parent=P}) when P /= "static" -> - UglyWorkaround = lists:member(Class, UglySkipList), - HaveVirtual = virtual_dest(C), - case hd(reverse(wx_gen_erl:parents(Class))) of - root when IsAbs == false, UglyWorkaround == true -> - w(" case ~p: /* delete (~s *) ptr;" - "These objects must be deleted by owner object */ " - "break;~n", [Id, Class]); - root when IsAbs == false, HaveVirtual == true -> - w(" case ~p: delete (E~s *) ptr; return false;~n", [Id, Class]); - root when IsAbs == false, UglyWorkaround == false -> - w(" case ~p: delete (~s *) ptr; break;~n", [Id, Class]); - _ -> ok - end; - (_) -> ok - end, - [Case(Class) || Class <- Defs], - w(" default: delete (wxObject *) ptr; return false;~n", []), - w(" }~n return true;~n}~n~n", []), - Res. - -gen_class(C=#class{name=Name,methods=Ms,options=Opts}) -> - put(current_class, Name), - NewMs = - case lists:member(taylormade, Opts) of - true -> - {ok, Bin} = file:read_file(filename:join([wx_extra,Name++".c_src"])), - ?WTC("gen_class"), - w("~s~n", [binary_to_list(Bin)]), - Ms; - false -> - case lists:keysearch(ifdef,1,Opts) of - {value, {ifdef, What}} -> - is_atom(What) andalso w("#if ~p~n",[What]), - is_list(What) andalso w("#if ~s~n",[What]), - Methods = lists:flatten(Ms), - MsR = [gen_method(Name,M) || - M <- lists:keysort(#method.id, Methods)], - w("#endif // ~p~n",[What]), - MsR; - false -> - Methods = lists:flatten(Ms), - [gen_method(Name,M) || - M <- lists:keysort(#method.id, Methods)] - end - end, - erase(current_class), - C#class{methods=NewMs}. - -gen_method(_CName, M=#method{where=erl_no_opt}) -> M; -gen_method(_CName, M=#method{where=erl_alias}) -> M; -gen_method(CName, M=#method{where=taylormade, name=Name, id=Id}) -> - {ok, Bin} = file:read_file(filename:join([wx_extra, CName ++".c_src"])), - Src = binary_to_list(Bin), - %% io:format("C++ Class ~p ~p~n", [CName, Name]), - Str = case gen_util:get_taylor_made(Src, Name) of - nomatch -> - {match, [Str0]} = gen_util:get_taylor_made(Src, wx_gen_erl:get_unique_name(Id)), - Str0; - {match, [Str0]} -> - Str0 - end, - ?WTC("gen_method"), - w(Str, [wx_gen_erl:get_unique_name(Id)]), - M; -gen_method(CName, M=#method{name=N,params=[Ps],method_type=destructor,id=MethodId}) -> - case hd(reverse(wx_gen_erl:parents(CName))) of - root -> - ?WTC("gen_method"), - w("case ~s: { // ~s::~s~n", [wx_gen_erl:get_unique_name(MethodId),CName,N]), - decode_arguments([Ps]), - w(" if(This) {", []), - w(" ((WxeApp *) wxTheApp)->clearPtr((void *) This);~n", []), - w(" delete This;}~n", []), - free_args(), - w(" break;~n}~n", []); - object -> %% Use default - ignore - end, - M; -gen_method(CName, M=#method{name=N,params=Ps0,type=T,method_type=MT,id=MethodId, opts=FOpts}) -> - put(current_func, N), - put(bin_count,-1), - ?WTC("gen_method"), - Endif1 = gen_if(deprecated, FOpts), - Endif2 = gen_if(test_if, FOpts), - w("case ~s: { // ~s::~s~n", [wx_gen_erl:get_unique_name(MethodId),CName,N]), - Ps1 = declare_variables(void, Ps0), - {Ps2,Align} = decode_arguments(Ps1), - Opts = [Opt || Opt = #param{def=Def,in=In,where=Where} <- Ps2, - Def =/= none, In =/= false, Where =/= c], - decode_options(Opts, Align), - case gen_util:get_hook(c, M#method.pre_hook) of - ignore -> skip; - Pre -> w(" ~s;~n", [Pre]) - end, - Ps3 = call_wx(N,{MT,CName},T,Ps2), - case gen_util:get_hook(c, M#method.post_hook) of - ignore -> skip; - Post -> w(" ~s;~n", [Post]) - end, - free_args(), - build_return_vals(T,Ps3), - w(" break;~n}~n", []), - Endif1 andalso w("#endif~n", []), - Endif2 andalso w("#endif~n", []), - erase(current_func), - M. - -gen_if(What, Opts) -> - case lists:keysearch(What, 1, Opts) of - {value, {What, IfDef}} -> - w("#if ~s~n", [IfDef]), - true; - _ -> false - end. - -declare_variables(void,Ps) -> - [declare_var(P) || P <- Ps]; -declare_variables(T, Ps) -> - declare_type("result", out, ignore, T), - [declare_var(P) || P <- Ps]. - -declare_var(P = #param{where=erl}) -> P; -declare_var(P = #param{where=this}) -> P; -declare_var(P = #param{name=Name,def=Def,type=Type,in=true}) when Def =/= none -> - declare_type(Name, true, Def, Type), - P; -declare_var(P = #param{in=In}) when In =/= false -> P; -declare_var(P = #param{name=Name,in=In,def=Def,type=Type}) -> - declare_type(Name, In, Def, Type), - P. - -declare_type(N,false,_,#type{name="wxArrayInt"}) -> - w(" wxArrayInt ~s;~n", [N]); -declare_type(N,false,_,#type{name="wxArrayDouble"}) -> - w(" wxArrayDouble ~s;~n", [N]); -declare_type(N,false,_,#type{name="wxArrayString"}) -> - w(" wxArrayString ~s;~n", [N]); -declare_type(N,false,_,#type{base=Base,single=true,name=Type,by_val=false,mod=Mod}) - when Base =:= int; Base =:= long; Base =:= float; Base =:= double -> - w(" ~s~s ~s;~n", [mods(Mod),Type,N]); -declare_type(N,false,_,#type{base={enum,_},single=true,name=Type,by_val=false,mod=Mod}) -> - w(" ~s~s ~s;~n", [mods(Mod),Type,N]); -declare_type(N,false,_,#type{name="wxArrayTreeItemIds",ref=reference}) -> - w(" wxArrayTreeItemIds ~s;~n", [N]); -declare_type(N,false,_,#type{name="wxDateTime"}) -> - w(" wxDateTime ~s;~n", [N]); -declare_type(N,false,_,#type{name="wxColour"}) -> - w(" wxColour ~s;~n", [N]); -declare_type(N,false,_,#type{name=Type, base=int, ref=reference}) -> - w(" ~s ~s;~n", [Type,N]); -declare_type(N,false,_,#type{name=Type, base=int64, ref=reference}) -> - w(" ~s ~s;~n", [Type,N]); -declare_type(N,false,_,#type{base={comp,_,_},single=true,name=Type,ref=reference}) -> - w(" ~s ~s;~n", [Type,N]); -declare_type(N,true,Def,#type{base=Base,single=true,name=Type,by_val=true}) - when Base =:= int; Base =:= long; Base =:= float; Base =:= double; Base =:= bool -> - w(" ~s ~s=~s;~n", [Type,N,Def]); -declare_type(N,true,Def,#type{base={comp,_,_},single=true,name=Type,mod=Mod,ref={pointer,1}}) -> - w(" ~s~s *~s=~s; ~s ~s;~n", [mods(Mod),Type,N,Def,Type,N++"Tmp"]); -declare_type(N,true,Def,#type{base={comp,_,_},single=true,name=Type,ref=reference}) -> - w(" ~s ~s= ~s;~n", [Type,N,Def]); -declare_type(N,true,Def,#type{base={enum,Type},single=true}) -> - Class = case Type of - {C,_} -> C++"::"; - _ -> "" - end, - w(" ~s ~s=~s~s;~n", [enum_type(Type),N,Class,Def]); -declare_type(N,true,Def,#type{base={class,_},single=true,name=Type,ref={pointer,1},mod=Mod}) -> - w(" ~s~s * ~s=~s;~n", [mods(Mod),Type,N,Def]); -declare_type(N,true,Def,#type{base={class,_},single=true,name=Type,ref=reference,mod=Mod}) -> - w(" ~s~s * ~s= &~s;~n", [mods(Mod),Type,N,Def]); -declare_type(N,true,Def,#type{base=Base,single=true,name=Type,by_val=false,ref={pointer,1}}) - when Base =:= int; Base =:= long; Base =:= float; Base =:= double; Base =:= bool -> - w(" ~s *~s=~s;~n", [Type,N,Def]); -declare_type(N,true,Def,#type{single=true,name="wxArtClient"}) -> - w(" wxArtClient ~s= ~s;~n", [N,Def]); -declare_type(N,true,_Def,#type{name="wxeLocaleC", single=true,base=string}) -> - w(" wxString ~s= wxEmptyString;~n", [N]); -declare_type(N,true,Def,#type{single=true,base=string}) -> - w(" wxString ~s= ~s;~n", [N,Def]); -%% declare_type(N,true,_Def,#type{name="wxString"}) -> -%% w(" wxString ~s= wxEmptyString;~n", [N]); -declare_type(N,true,Def,#type{name="wxColour"}) -> - w(" wxColour ~s = ~s;~n", [N, Def]); -declare_type(N,true,Def,#type{base=binary, name=char}) -> - w(" char ~sD[] = {~s}, * ~s = ~sD;~n", [N,Def,N,N]); -declare_type(_N,true,_Def,void) -> - skip; -declare_type(_N,true,_Def,voidp) -> - skip; -declare_type(N,true,Def,#type{name=Type, ref={pointer,2}}) -> - %% xxxx - w(" ~s ** ~s = ~s;~n", [Type,N,Def]); -declare_type(N,true,Def,#type{name=Type, single=array, ref={pointer,1}}) -> - w(" int * ~sLen = 0;~n", [N]), - w(" ~s * ~s = ~s;~n", [Type,N,Def]); -declare_type(N,true,"",#type{name="wxArrayString", single=array, ref=reference}) -> - w(" wxArrayString ~s;~n", [N]); -declare_type(N,true,Def,#type{name=Type, base={term,_}}) -> - w(" ~s * ~s= ~s;~n", [Type,N,Def]); -declare_type(N,In,Def,T) -> - ?error({unhandled_type, {N,In,Def,T}}). - -decode_options([], _Align) -> ok; -decode_options(Opts, Align) -> - align(Align, 64), - w(" while( * (int*) bp) { switch (* (int*) bp) {~n", []), - foldl(fun decode_opt/2, 1, Opts), - w(" }};~n", []). - -decode_opt(#param{name=Name,type=Type}, N) -> - w(" case ~p: {bp += 4;~n", [N]), - Align = decode_arg(Name,Type,opt,1), - align(Align, 64), - w(" } break;~n", []), - N+1. - -decode_arguments(Ps0) -> - lists:mapfoldl(fun decode_arg/2,0,Ps0). - -store_free(N) -> - case get(free_args) of - undefined -> put(free_args, [N]); - List -> put(free_args, [N|List]) - end. - -free_args() -> - case get(free_args) of - undefined -> ignore; - List -> - erase(free_args), - [w(" driver_free(~s);~n", [Arg]) || Arg <- List] - end. - -decode_arg(P = #param{where=erl},A) -> {P,A}; -decode_arg(P = #param{where=c},A) -> {P,A}; -decode_arg(P = #param{in=false},A) -> {P,A}; -decode_arg(P = #param{def=Def},A) when Def =/= none -> {P,A}; -decode_arg(P = #param{name=Name,type=Type},A0) -> - A = decode_arg(Name, Type, arg, A0), - {P, A}. - -wa(Decl,DA,Get,GetA,arg) -> - w(Decl,DA), - w(Get,GetA); -wa(_Decl,_DA,Get,GetA,opt) -> - w(Get,GetA). - -decode_arg(N,#type{name=Class,base={class,_},single=true},Arg,A0) -> - A = align(A0,32), - wa(" ~s *",[Class],"~s = (~s *) getPtr(bp,memenv); bp += 4;~n",[N,Class],Arg), - A; -decode_arg(N,{merged,[{_,#type{name=Class,base={class,_},single=true},_}|_]},arg,A0) -> - A = align(A0,32), - w(" ~s * ~s = (~s *) getPtr(bp,memenv); bp += 4;~n", [Class,N,Class]), - A; -decode_arg(N,#type{base=long,single=true,name=Type},arg,A0) -> - A = align(A0,64), - w(" long * ~s = (~s *) bp; bp += 8;~n", [N,Type]), - A; -decode_arg(N,#type{base=int,single=true,mod=Mod0,name=Type,ref=Ref},Arg,A0) -> - Mod = mods(Mod0), - case Arg of - arg -> w(" ~s~s * ~s = (~s~s *) bp; bp += 4;~n", [Mod,int,N,Mod,int]); - opt when Ref =:= {pointer,1} -> - w(" ~s = (~s *) bp; bp += 4;~n", [N,int]); - opt -> - w(" ~s = (~s)*(~s~s *) bp; bp += 4;~n", [N,Type,Mod,int]) - end, - align(A0,32); -decode_arg(N,#type{base=float,single=true,name=Type},arg,A0) -> - w(" ~s * ~s = (~s *) bp; bp += 4;~n", [Type,N,Type]), - align(A0,32); -decode_arg(N,#type{base=double,single=true,name=Type},Arg,A0) -> - A = align(A0,64), - case Arg of - arg -> w(" ~s * ~s = (~s *) bp; bp += 8;~n", [Type,N,Type]); - opt -> w(" ~s = * (~s *) bp; bp += 8;~n", [N,Type]) - end, - A; -decode_arg(N,#type{base=bool,single=true,name=Type},Arg,A0) -> - case Arg of - arg -> w(" bool * ~s = (~s *) bp; bp += 4;~n", [N,Type]); - opt -> w(" ~s = *(~s *) bp; bp += 4;~n", [N,Type]) - end, - align(A0,32); -decode_arg(N,#type{base={enum,Type},single=true},Arg,A0) -> - wa(" ~s ", [enum_type(Type)], "~s = *(~s *) bp; bp += 4;;~n",[N, enum_type(Type)], Arg), - align(A0,32); -decode_arg(N,#type{base={comp,"wxDateTime",List},single=true,name=Type,ref=Ref},Arg,A0) -> - Decl = fun({int,Spec}) -> - w(" int * ~s~s = (int *) bp; bp += 4;~n", [N,Spec]) - end, - align(A0,32), - lists:foreach(Decl,List), - Name = fun({_,"Mo"}) -> "(wxDateTime::Month) *"++N++"Mo"; - ({_,"Y"}) -> "*"++N++"Y"; - ({_,Spec}) -> "(wxDateTime::wxDateTime_t) *"++N++Spec - end, - case Arg of - arg -> w(" ~s ~s = ~s(~s);~n", [Type,N,Type,args(Name, ",", List)]); - opt when Ref =:= {pointer,1} -> - w(" ~sTmp = ~s(~s); ~s = & ~sTmp;~n", - [N,Type,args(Name, ",", List), N,N]); - opt -> - w(" ~s = ~s(~s);~n", [N,Type,args(Name, ",", List)]) - end, - (A0+length(List)) rem 2; -decode_arg(N,#type{base={comp,_,List},single=true,name=Type,ref=Ref},Arg,A0) -> - Decl = fun({int,Spec}) -> - w(" int * ~s~s = (int *) bp; bp += 4;~n", [N,Spec]); - ({double, Spec}) -> - w(" wxDouble * ~s~s = (wxDouble *) bp; bp += 8;~n", [N,Spec]) - end, - case hd(List) of - {int, _} -> align(A0,32); - {double, _} -> align(A0,64) - end, - lists:foreach(Decl,List), - Name = fun({_,Spec}) -> "*"++N++Spec end, - case Arg of - arg -> w(" ~s ~s = ~s(~s);~n", [Type,N,Type,args(Name, ",", List)]); - opt when Ref =:= {pointer,1} -> - w(" ~sTmp = ~s(~s); ~s = & ~sTmp;~n", - [N,Type,args(Name, ",", List), N,N]); - opt -> - w(" ~s = ~s(~s);~n", [N,Type,args(Name, ",", List)]) - end, - case hd(List) of - {int, _} -> (A0+length(List)) rem 2; - {double, _} -> 0 - end; - -decode_arg(N,#type{name=Class="wxTreeItemId",single=true},Arg,A0) -> - A = align(A0,64), - wa(" ~s ",[Class],"~s = wxTreeItemId((void *) *(wxUint64 *) bp); bp += 8;~n",[N],Arg), - A; -decode_arg(N,#type{name=Class="wxTreeItemIdValue",single=true},Arg,A0) -> - A = align(A0,64), - wa(" ~s ",[Class],"~s = (~s) * (wxUint64 *) bp; bp += 8;~n",[N,Class],Arg), - A; -decode_arg(N,#type{name="wxChar", single=S},Arg,A0) - when S =/= true -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - wa(" wxString", []," ~s = wxString(bp, wxConvUTF8);~n", [N],Arg), - w(" bp += *~sLen+((8-((~p+ *~sLen) & 7)) & 7);~n", [N,4*((A0+1) rem 2),N]), - 0; -decode_arg(N,#type{base=string, name="wxFileName"},Arg,A0) -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - wa(" wxString", []," ~sStr = wxString(bp, wxConvUTF8);~n", [N],Arg), - w(" bp += *~sLen+((8-((~p+ *~sLen) & 7)) & 7);~n", [N,4*((A0+1) rem 2),N]), - w(" wxFileName ~s = wxFileName(~sStr);~n",[N,N]), - 0; -decode_arg(N,#type{base=string},Arg,A0) -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - wa(" wxString", []," ~s = wxString(bp, wxConvUTF8);~n", [N],Arg), - w(" bp += *~sLen+((8-((~p+ *~sLen) & 7)) & 7);~n", [N,4*((A0+1) rem 2),N]), - 0; -decode_arg(N,#type{name="wxArrayString"},Place,A0) -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - case Place of - arg -> w(" wxArrayString ~s;~n", [N]); - opt -> ignore %% Already declared - end, - w(" int ~sASz = 0, * ~sTemp;~n", [N,N]), - w(" for(int i=0; i < *~sLen; i++) {~n", [N]), - w(" ~sTemp = (int *) bp; bp += 4;~n", [N]), - w(" ~s.Add(wxString(bp, wxConvUTF8));~n", [N]), - w(" bp += *~sTemp;~n", [N]), - w(" ~sASz += *~sTemp+4;~n }~n", [N,N]), - w(" bp += (8-((~p+ ~sASz) & 7 )) & 7;~n", [4*((A0+1) rem 2),N]), - 0; - -decode_arg(N,#type{name="wxArrayInt"},arg,A0) -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - w(" wxArrayInt ~s;~n", [N]), - w(" for(int i=0; i < *~sLen; i++) {", [N]), - w(" ~s.Add(*(int *) bp); bp += 4;}~n", [N]), - w(" bp += ((*~sLen + ~p) % 2 )*4;~n",[N, (A0+1)]), - 0; -decode_arg(N,#type{name="wxArrayDouble"},arg,A0) -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - align(A0+1,64), - w(" wxArrayDouble ~s;~n", [N]), - w(" for(int i=0; i < *~sLen; i++) {", [N]), - w(" ~s.Add(*(int *) bp); bp += 4;}~n", [N]), - 0; -decode_arg(_N,#type{base=eventType},_Arg,A0) -> -%% w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), -%% case Arg of -%% arg -> -%% w(" int ~s = wxeEventTypeFromAtom(bp);bp += *~sLen;~n",[N,N]), -%% w(" char *class_name = bp;~n", []), -%% w(" wxeCallbackData * Evt_cb = new wxeCallbackData(Ecmd.caller,This,class_name);~n", -%% []) -%% end, - A0; -decode_arg(N,#type{name=Type,base=binary,mod=Mod0},Arg,A0) -> - Mod = mods([M || M <- Mod0]), - case Arg of - arg -> - w(" ~s~s * ~s = (~s~s*) Ecmd.bin[~p].base;~n", - [Mod,Type,N,Mod,Type, next_id(bin_count)]); - opt -> - w(" ~s = (~s~s*) Ecmd.bin[~p].base;~n", - [N,Mod,Type,next_id(bin_count)]) - end, - A0; -decode_arg(N,#type{base={term,"wxTreeItemData"},mod=Mod0},Arg,A0) -> - Mod = mods([M || M <- Mod0]), - Type = "wxETreeItemData", - BinCnt = next_id(bin_count), - case Arg of - arg -> - w(" ~s~s * ~s = new ~s(Ecmd.bin[~p].size, Ecmd.bin[~p].base);~n", - [Mod,Type,N,Type,BinCnt,BinCnt]); - opt -> - w(" ~s = new ~s(Ecmd.bin[~p].size, Ecmd.bin[~p].base);~n", - [N,Type,BinCnt,BinCnt]) - end, - A0; -decode_arg(N,#type{name=Type,base={term,_},mod=Mod0},Arg,A0) -> - Mod = mods([M || M <- Mod0]), - BinCnt = next_id(bin_count), - case Arg of - arg -> - w(" ~s~s * ~s = new ~s(&Ecmd.bin[~p]);~n", - [Mod,Type,N,Type,BinCnt]); - opt -> - w(" ~s = new ~s(&Ecmd.bin[~p]);~n", - [N,Type,BinCnt]) - end, - A0; -decode_arg(N,#type{single=array,base=int},Arg,A0) -> - case Arg of - arg -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - w(" int * ~s = (int *) bp; bp += *~sLen*4+((~p+ *~sLen)%2 )*4;~n", - [N,N,(A0+1) rem 2,N]); - opt -> - w(" ~sLen = (int *) bp; bp += 4;~n", [N]), - w(" ~s = (int *) bp; bp += *~sLen*4+((~p+ *~sLen)%2 )*4;~n", - [N,N,(A0+1) rem 2,N]) - end, - 0; -decode_arg(N,#type{single=array,base=int64},Arg,A0) -> - case Arg of - arg -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - w(" int * ~s = (int *) bp; bp += *~sLen*4+((~p+ *~sLen)%2 )*4;~n", - [N,N,(A0+1) rem 2,N]); - opt -> - w(" ~sLen = (int *) bp; bp += 4;~n", [N]), - w(" ~s = (int *) bp; bp += *~sLen*4+((~p+ *~sLen)%2 )*4;~n", - [N,N,(A0+1) rem 2,N]) - end, - 0; -decode_arg(N,#type{by_val=true,single=array,base={comp,Class="wxPoint",_}},arg,A0) -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - w(" ~s *~s;~n",[Class,N]), - w(" ~s = (~s *) driver_alloc(sizeof(~s) * *~sLen);~n",[N,Class,Class,N]), - store_free(N), - w(" for(int i=0; i < *~sLen; i++) {~n", [N]), - w(" int x = * (int *) bp; bp += 4;~n int y = * (int *) bp; bp += 4;~n", []), - w(" ~s[i] = wxPoint(x,y);}~n", [N]), - align(A0,32); -decode_arg(N,#type{by_val=true,single=array,base={class,Class}},arg,A0) -> - A = align(A0,32), - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - w(" ~s *~s;~n",[Class,N]), - w(" ~s = (~s *) driver_alloc(sizeof(~s) * *~sLen);", [N, Class, Class, N]), - store_free(N), - w(" for(int i=0; i < *~sLen; i++) {", [N]), - w(" ~s[i] = * (~s *) getPtr(bp,memenv); bp += 4;}~n", [N,Class]), - w(" bp += ((~p+ *~sLen)%2 )*4;~n", [A, N]), - 0; -decode_arg(N,#type{name=Type,single=list,base={class,Class}},arg,A0) -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - A = align(A0,32), - w(" ~s ~s;~n",[Type,N]), - w(" for(int i=0; i < *~sLen; i++) {", [N]), - w(" ~s.Append(*(~s *) getPtr(bp,memenv)); bp += 4;}~n", [N,Class]), - w(" bp += ((~p+ *~sLen)%2 )*4;~n", [A,N]), - 0; -decode_arg(N,#type{single=array,base={comp,Class="wxPoint2DDouble",_}},arg,A0) -> - w(" int * ~sLen = (int *) bp; bp += 4;~n", [N]), - w(" ~s *~s;~n",[Class,N]), - w(" ~s = (~s *) driver_alloc(sizeof(~s) * *~sLen);~n",[N,Class,Class,N]), - store_free(N), - align(A0+1,64), - w(" for(int i=0; i < *~sLen; i++) {~n", [N]), - w(" double x = * (double *) bp; bp += 8;~n double y = * (double *) bp; bp += 8;~n", []), - w(" ~s[i] = wxPoint2DDouble(x,y);}~n", [N]), - 0; -decode_arg(Name,T, Arg,_A) -> - ?error({unhandled_type, {Name,T, Arg}}). - -align(0, 32) -> 1; -align(1, 32) -> 0; -align(0, 64) -> 0; -align(1, 64) -> - w(" bp += 4; /* Align */~n"), - 0; -align(N,Sz) -> - align(N rem 2, Sz). - -call_wx(_N,{constructor,_},#type{base={class,RClass}},Ps) -> - #class{id=Id} = ClassDef = get({class,RClass}), - Class = case is_derived(ClassDef) of - true -> "E" ++ RClass; - false -> RClass - end, - w(" ~s * Result = new ~s(~s);~n", - [RClass, Class,args(fun call_arg/1, ",",filter(Ps))]), - CType = case is_window(RClass) of - true -> %% Windows have parents that should be deleted first - case is_dialog(RClass) of - true -> 2; %% Dialogs must be closed first event before windows - false -> 0 - end; - false -> - case is_dc(RClass) of - true -> 8; - false -> - case hd(reverse(wx_gen_erl:parents(RClass))) of - root -> Id; - _ -> 1 - end - end - end, - case virtual_dest(ClassDef) orelse (CType =/= 0) of - true -> - w(" newPtr((void *) Result, ~p, memenv);~n", [CType]); - false -> %% Hmm window without virt dest - w(" /* Possible memory leak here, class is missing virt dest */ \n") - end, - Ps; -call_wx(N,{member,_},Type,Ps) -> - {Beg,End} = return_res(Type), - w(" if(!This) throw wxe_badarg(0);~n",[]), - w(" ~sThis->~s(~s)~s;~n",[Beg,N,args(fun call_arg/1, ",",filter(Ps)),End]), - Ps; -call_wx(N,{static,Class},Type,Ps) -> - {Beg,End} = return_res(Type), - #class{parent=Parent} = get({class,Class}), - case Parent of - "static" -> - w(" ~s::~s(~s)~s;~n",[Beg,N,args(fun call_arg/1, ",",filter(Ps)),End]); - _ -> - w(" ~s~s::~s(~s)~s;~n",[Beg,Class,N,args(fun call_arg/1, ",",filter(Ps)),End]) - end, - Ps. - - -return_res(void) -> {"", ""}; -return_res(Type = #type{mod=Mod}) -> - case lists:member(const, Mod) of - true -> - {Beg, End} = return_res1(Type), - {"const " ++ Beg, End}; - _ -> - return_res1(Type) - end. - -return_res1(#type{name=Type,ref={pointer,_}, base={term,_}}) -> - {Type ++ " * Result = (" ++ Type ++ "*)", ""}; -return_res1(#type{name=Type,ref={pointer,_}}) -> - {Type ++ " * Result = (" ++ Type ++ "*)", ""}; -return_res1(#type{name=Type,single=true,by_val=false,ref=reference}) -> - case Type of - "wxString" -> {Type ++ " Result = ", ""}; - _ -> {Type ++ " * Result = &", ""} - end; -return_res1(#type{name=Type,single=true,by_val=true}) - when is_atom(Type) -> - {atom_to_list(Type) ++ " Result = ", ""}; -return_res1(#type{name=Type="wxArrayInt"}) -> - {Type ++ " Result = ", ""}; -return_res1(#type{name=Type,base={class,_},single=list,ref=reference}) -> - {Type ++ " Result = ", ""}; -return_res1(#type{name=Type,base={comp,_,_},single=array,by_val=true}) -> - {Type ++ " Result = ", ""}; -return_res1(#type{name=Type,single=true,by_val=true, base={class, _}}) -> - case {need_copy_constr(Type), Type} of - {true, _} -> - {Type ++ " * Result = new E" ++ Type ++ "(", "); newPtr((void *) Result," - ++ "3, memenv);"}; - {false, "wxGraphics" ++ _} -> - %% {"wxGraphicsObject * Result = new wxGraphicsObject(", "); newPtr((void *) Result," - %% ++ "3, memenv);"}; - {Type ++ " * Result = new " ++ Type ++ "(", "); newPtr((void *) Result," - ++ "4, memenv);"}; - {false, _} -> - %% Temporary memory leak !!!!!! - io:format("~s::~s Building return value of temp ~s~n", - [get(current_class),get(current_func),Type]), - {Type ++ " * Result = new " ++ Type ++ "(", "); newPtr((void *) Result," - ++ "3, memenv);"} - end; -return_res1(#type{base={enum,_Type},single=true,by_val=true}) -> - {"int Result = " , ""}; -return_res1(#type{name="wxCharBuffer", base={binary,_},single=true,by_val=true}) -> - {"char * Result = ", ".data()"}; -return_res1(#type{name=Type,single=array,ref=reference}) -> - {Type ++ " Result = ", ""}; -return_res1(#type{name=Type,single=true,by_val=true}) -> - {Type ++ " Result = ", ""}. - -filter(Ps) -> - lists:filter(fun filter_arg/1, Ps). -filter_arg(#param{where=erl}) -> false; -filter_arg(#param{where=this}) -> false; -filter_arg(#param{}) -> true. -%%filter_arg(#param{def=Def, in=In}) -> Def =:= none orelse In =:= false. - - -call_arg(#param{where=c, alt={length,Alt}}) when is_list(Alt) -> - "*" ++ Alt ++ "Len"; -call_arg(#param{where=c, alt={size,Id}}) when is_integer(Id) -> - %% It's a binary - "Ecmd.bin["++ integer_to_list(Id) ++ "].size"; -call_arg(#param{name=N,def=Def,type=#type{by_val=true,single=true,base=Base}}) - when Base =:= int; Base =:= long; Base =:= float; Base =:= double; Base =:= bool -> - case Def of - none -> "*" ++ N; - _ -> N - end; -call_arg(#param{name=N,type=#type{base={enum,_Type}, by_val=true,single=true}}) -> - N; -call_arg(#param{name=N,type=#type{base={class,_},by_val=true,single=true}}) -> "*" ++ N; -call_arg(#param{name=N,type=#type{base={class,_},ref=reference,single=true}}) -> "*" ++ N; -call_arg(#param{name=N,type=#type{base=eventType}}) -> - N ++ ", (wxObjectEventFunction)(wxEventFunction) &WxeApp::handle_evt, Evt_cb, this"; -call_arg(#param{name=N,type=#type{by_val=true, single=_False}}) -> N; -call_arg(#param{name=N,def=Def,type=#type{by_val=false, ref={pointer,2}}}) - when Def =/= none -> N; -call_arg(#param{name=N,type=#type{base={term, Class}, by_val=false, ref={pointer,2}}}) -> - "(" ++ Class ++ " **) &" ++ N; -call_arg(#param{name=N,type=#type{base=Base, by_val=false, ref={pointer,2}}}) -> - io:format("~p: ~p~n",[?LINE, Base]), - "&" ++ N; -call_arg(#param{name=N,in=false,type=#type{ref=reference, single=true}}) -> N; -call_arg(#param{name=N,in=false,type=#type{by_val=false, single=true}}) -> "&" ++ N; -call_arg(#param{name=N,def=Def,type=#type{base={comp,_,_},ref={pointer,1},single=true}}) - when Def =:= none -> - "&" ++N; -call_arg(#param{name=N,type=#type{base=int, ref=reference, single=true}}) -> "*" ++ N; -call_arg(#param{name=N,type=#type{base=string, by_val=false, single=true, ref={pointer,1}}}) -> "&" ++ N; -call_arg(#param{name=N,type=#type{by_val=false}}) -> N; -call_arg(#param{name=N,type={merged,[{_,#type{base={class,_},single=true, - by_val=ByVal, - ref=Ref},_}|_]}}) - when ByVal =:= true; Ref =:= reference -> - "*" ++ N; -call_arg(#param{def=Def, type=void}) when Def =/= none -> Def; -call_arg(#param{def=Def, type=voidp}) when Def =/= none -> "(void **) " ++ Def; -call_arg(#param{name=N,type=#type{base={ref,_},by_val=true,single=true}}) -> N; -call_arg(#param{name=N,type={merged,_}}) -> N. - -%% call_arg(#param{name=N,type=#type{base=Tuple,ref=reference}}) -%% when is_tuple(Tuple) -> "&" ++ N; - -to_string(Type) when is_atom(Type) -> atom_to_list(Type); -to_string(Type) when is_list(Type) -> Type. - -virtual_dest(#class{abstract=true, parent=Parent}) -> - virtual_dest(get_parent_class(Parent)); -virtual_dest(#class{methods=Ms, parent=Parent}) -> - case lists:keysearch(destructor,#method.method_type, lists:append(Ms)) of - {value, #method{method_type=destructor, virtual=Virtual}} -> - case Virtual of - true -> true; - _ -> virtual_dest(get_parent_class(Parent)) - end; - false -> virtual_dest(get_parent_class(Parent)) - end; -virtual_dest("root") -> false; -virtual_dest("object") -> true. - -get_parent_class(Parent) -> - case get({class, Parent}) of - undefined -> Parent; - Class -> Class - end. - -debug(F,A) -> - case get(debug) of - true -> ?warning(F,A); - _ -> ok - end. - -is_derived(#class{abstract=true}) -> false; -is_derived(C = #class{}) -> virtual_dest(C). - -is_window(Class) -> - lists:member("wxWindow", wx_gen_erl:parents(Class)). - -is_dialog(Class) -> - lists:member("wxDialog", wx_gen_erl:parents(Class)). - -is_dc(Class) -> - Parents = wx_gen_erl:parents(Class), - lists:member("wxDC", Parents) orelse lists:member("wxGraphicsContext", Parents). - -build_return_vals(Type,Ps0) -> - Ps = [P || P = #param{in=In} <- Ps0, In =/= true], - HaveType = case Type of void -> 0; _ -> 1 end, - NoOut = length(Ps) + HaveType, - OutTupSz = if NoOut > 1 -> NoOut; true -> 0 end, - - CountFloats = fun(#param{type=#type{base=Float, single=true}}, Acc) - when Float =:= float; Float =:= double -> - Acc + 1; - (_, Acc) -> - Acc - end, - NofFloats = lists:foldl(CountFloats, 1, Ps), - case NofFloats > 1 of - true -> %%io:format("Floats ~p:~p ~p ~n",[get(current_class),get(current_func), NofFloats]); - w(" rt.ensureFloatCount(~p);~n",[NofFloats]); - false -> ignore - end, - build_ret_types(Type,Ps), - if - OutTupSz > 1 -> w(" rt.addTupleCount(~p);~n",[OutTupSz]); - true -> ignore - end, - Ps. - -build_ret_types(void,Ps) -> - Calc = fun(#param{name=N,in=In,type=T}, Free) -> - case build_ret(N, {arg, In}, T) of - ok -> Free; - Other -> [Other|Free] - end - end, - lists:foldl(Calc, [], Ps); -build_ret_types(Type,Ps) -> - Free = case build_ret("Result", {ret, out}, Type) of - ok -> []; - FreeStr -> [FreeStr] - end, - Calc = fun(#param{name=N,in=In,type=T}, FreeAcc) -> - case build_ret(N, {arg, In}, T) of - ok -> FreeAcc; - FreeMe -> [FreeMe|FreeAcc] - end - end, - lists:foldl(Calc, Free, Ps). - -build_ret(Name,_D,#type{base={class,Class},single=true}=_T) -> - case Class of - "wxGraphicsContext" -> - w(" rt.addRef(getRef((void *)~s,memenv,8), \"~s\");~n",[Name,Class]); - _ -> - w(" rt.addRef(getRef((void *)~s,memenv), \"~s\");~n",[Name,Class]) - end; -build_ret(Name,_,#type{name="wxTreeItemId",single=true}) -> - w(" rt.add((wxUIntPtr *) ~s.m_pItem);~n",[Name]); -build_ret(Name,_,#type{name="wxTreeItemIdValue",single=true}) -> - w(" rt.add((wxUIntPtr *) ~s);~n",[Name]); -build_ret(Name,_,#type{base={term,_},single=true}) -> - w(" rt.addExt2Term(~s);~n", [Name]); -build_ret(Name,_,#type{base={binary,Size},single=true}) -> - w(" if(~s) {~n", [Name]), - w(" rt.addBinary(~s, ~s);~n", [Name,Size]), - w(" } else {rt.addAtom(\"null\");};~n"); -build_ret(Name,_,#type{name="wxUIntPtr", ref={pointer,1}, single=true}) -> - w(" rt.add(~s);~n", [Name]); -build_ret(Name,_,#type{base={enum,_Type},single=true}) -> - w(" rt.addInt(~s);~n",[Name]); -build_ret(Name,_,#type{base={comp,_,{record, _}},single=true}) -> - w(" rt.add(~s);~n", [Name]); -build_ret(Name,{ret,_},#type{base={comp,_,_},single=true, by_val=true}) -> - w(" rt.add(~s);~n",[Name]); -build_ret(Name,{ret,_},#type{base={comp,_,_},single=true, ref=reference}) -> - w(" rt.add((*~s));~n",[Name]); -build_ret(Name,_,#type{base={comp,_,_},single=true}) -> - w(" rt.add(~s);~n",[Name]); -build_ret(Name = "ev->m_scanCode",_,#type{base=bool,single=true,by_val=true}) -> - %% Hardcoded workaround for 2.9 and later - w("#if !wxCHECK_VERSION(2,9,0)~n", []), - w(" rt.addBool(~s);~n",[Name]), - w("#else~n rt.addBool(false);~n",[]), - w("#endif~n",[]); -build_ret(Name = "ev->m_metaDown",_,#type{base=bool,single=true,by_val=true}) -> - %% Hardcoded workaround for MAC on 2.9 and later - w("#if wxCHECK_VERSION(2,9,0) && defined(_MACOSX)~n", []), - w(" rt.addBool(ev->m_rawControlDown);~n",[]), - w("#else~n rt.addBool(~s);~n",[Name]), - w("#endif~n",[]); - -build_ret(Name,_,#type{base=bool,single=true,by_val=true}) -> - w(" rt.addBool(~s);~n",[Name]); -build_ret(Name,{arg, both},#type{base=int,single=true,mod=M}) -> - case lists:member(unsigned, M) of - true -> w(" rt.addUint(*~s);~n",[Name]); - false -> w(" rt.addInt(*~s);~n",[Name]) - end; -build_ret(Name,_,#type{base=int,single=true,mod=M}) -> - case lists:member(unsigned, M) of - true -> w(" rt.addUint(~s);~n",[Name]); - false -> w(" rt.addInt(~s);~n",[Name]) - end; -build_ret(Name,_,#type{name="wxArrayInt"}) -> - w(" rt.add(~s);~n", [Name]); -build_ret(Name,_,#type{name="wxArrayDouble"}) -> - w(" rt.add(~s);~n", [Name]); -build_ret(Name,_,#type{base={comp,_,_},single=array}) -> - w(" for(unsigned int i=0; i < ~s.GetCount(); i++) {~n", [Name]), - w(" rt.add(~s[i]);~n }~n",[Name]), - w(" rt.endList(~s.GetCount());~n",[Name]); -build_ret(Name,_,#type{base={class,Class},single=array}) -> - w(" for(unsigned int i=0; i < ~s.GetCount(); i++) {~n", [Name]), - w(" rt.addRef(getRef((void *) &~s.Item(i), memenv), \"~s\");~n }~n",[Name, Class]), - w(" rt.endList(~s.GetCount());~n",[Name]); -build_ret(Name,_,#type{name=List,single=list,base={class,Class}}) -> - w(" int i=0;~n"), - w(" for(~s::const_iterator it = ~s.begin(); it != ~s.end(); ++it) {~n", - [List, Name, Name]), - w(" ~s * ~sTmp = *it;~n", [Class,Name]), - w(" rt.addRef(getRef((void *)~sTmp,memenv), \"~s\"); i++;}~n",[Name,Class]), - w(" rt.endList(~s.GetCount());~n",[Name]); - -build_ret(Name,_,#type{name="wxArrayTreeItemIds"}) -> - w(" for(unsigned int i=0; i < ~s.GetCount(); i++) {~n", [Name]), - w(" rt.add((wxUIntPtr *)~s[i].m_pItem);}~n",[Name]), - w(" rt.endList(~s.GetCount());~n",[Name]); - -build_ret(Name,_,#type{base=float,single=true}) -> - w(" rt.addFloat(~s);~n",[Name]); -build_ret(Name,_,#type{base=double,single=true}) -> - w(" rt.addFloat(~s);~n",[Name]); -build_ret(Name,_,#type{name="wxeLocaleC"}) -> - w(" rt.add(wxeLocaleC2String(~s));~n",[Name]); -build_ret(Name,_,#type{base=string,single=true}) -> - w(" rt.add(~s);~n",[Name]); -build_ret(Name,_,#type{name="wxArrayString", single=array}) -> - w(" rt.add(~s);~n", [Name]); -build_ret(Name,_,#type{name="wxString", single={list,Variable}}) -> - Obj = case Name of - "ev->" ++ _ -> "ev"; - _ -> "This" - end, - w(" wxArrayString tmpArrayStr(~s->~s, ~s);~n", [Obj,Variable,Name]), - w(" rt.add(tmpArrayStr);~n", []); -build_ret(Name,In,T) -> - ?error({nyi, Name,In, T}). - -mods([const|R]) -> "const " ++ mods(R); -mods([unsigned|R]) -> "unsigned " ++ mods(R); -mods([]) -> "". - -build_enums() -> - Tree = get(consts), - w(" /* This file is also generated */~n"), - w("#include <wx/wx.h>~n"), - w("#include \"../wxe_impl.h\"~n"), - w("#include \"wxe_macros.h\"~n"), - w("#include \"../wxe_return.h\"~n"), - w("void WxeApp::init_nonconsts(wxeMemEnv *memenv, ErlDrvTermData caller) {~n"), - NotConsts = [NC || NC = #const{is_const=false} <- gb_trees:values(Tree)], - Size = length(NotConsts), - GVars = get(gvars), - GSize = length(GVars), - w(" wxeReturn rt = wxeReturn(WXE_DRV_PORT, caller);~n"), - w(" rt.addAtom((char*)\"wx_consts\");~n"), - [build_enum(NConst) || NConst <- lists:keysort(#const.val, NotConsts)], - _Cnt = foldl(fun(Gvar, I) -> build_gvar(Gvar,I) end, 0, lists:sort(GVars)), - w(" rt.endList(~p);~n", [Size+GSize]), - w(" rt.addTupleCount(2);~n"), - w(" rt.send();~n"), - w("}~n"), - ok. - -build_enum(#const{name=Name}) -> - w(" rt.addAtom(\"~s\"); rt.addInt(~s);~n", [Name, Name]), - w(" rt.addTupleCount(2);~n"). - -build_gvar({Name, "wxColour", _Id}, Cnt) -> - w(" rt.addAtom(\"~s\"); rt.add(*(~s));~n",[Name,Name]), - w(" rt.addTupleCount(2);~n"), - Cnt; -build_gvar({Name, {address,Class}, _Id}, Cnt) -> - w(" rt.addAtom(\"~s\"); rt.addRef(getRef((void *)&~s,memenv), \"~s\");~n",[Name,Name,Class]), - w(" rt.addTupleCount(2);~n"), - Cnt+1; -build_gvar({Name, {test_if,Test}, _Id}, Cnt) -> - w("#if ~s~n", [Test]), - w(" rt.addAtom(\"~s\"); rt.addInt(~s);~n", [Name, Name]), - w(" rt.addTupleCount(2);~n"), - w("#else~n", []), - w(" rt.addAtom(\"~s\"); rt.addAtom(\"undefined\");~n", [Name]), - w(" rt.addTupleCount(2);~n"), - w("#endif~n", []), - Cnt+1; -build_gvar({Name, Class, _Id}, Cnt) -> - w(" rt.addAtom(\"~s\"); rt.addRef(getRef((void *)~s,memenv),\"~s\");~n",[Name,Name,Class]), - w(" rt.addTupleCount(2);~n"), - Cnt+1. - -gen_macros() -> - w("#include <wx/caret.h>~n"), %% Arrg wxw forgot?? some files - w("#include <wx/tooltip.h>~n"), - w("#include <wx/gbsizer.h>~n"), - w("#include <wx/splash.h>~n"), - w("#include <wx/grid.h>~n"), - w("#include <wx/image.h>~n"), - w("#include <wx/tglbtn.h>~n"), - w("#include <wx/calctrl.h>~n"), - w("#include <wx/dirctrl.h>~n"), - w("#include <wx/listctrl.h>~n"), - w("#include <wx/treectrl.h>~n"), - w("#include <wx/spinbutt.h>~n"), - w("#include <wx/spinctrl.h>~n"), - w("#include <wx/colordlg.h>~n"), - w("#include <wx/fdrepdlg.h>~n"), - w("#include <wx/fontdlg.h>~n"), - w("#include <wx/progdlg.h>~n"), - w("#include <wx/printdlg.h>~n"), - w("#include <wx/display.h>~n"), - w("#include <wx/dcbuffer.h>~n"), - w("#include <wx/dcmirror.h>~n"), - w("#include <wx/glcanvas.h>~n"), - w("#include <wx/dcps.h>~n"), - w("#include <wx/xrc/xmlres.h>~n"), - w("#include <wx/html/htmprint.h>~n"), - w("#include <wx/stc/stc.h>~n"), - w("#include <wx/minifram.h>~n"), - w("#include <wx/sashwin.h>~n"), - w("#include <wx/laywin.h>~n"), - w("#include <wx/graphics.h>~n"), - w("#include <wx/dcgraph.h>~n"), - w("#include <wx/aui/aui.h>~n"), - w("#include <wx/datectrl.h>~n"), - w("#include <wx/filepicker.h>~n"), - w("#include <wx/fontpicker.h>~n"), - w("#include <wx/clrpicker.h>~n"), - w("#include <wx/statline.h>~n"), - w("#include <wx/clipbrd.h>~n"), - w("#include <wx/splitter.h>~n"), - w("#include <wx/choicebk.h>~n"), - w("#include <wx/toolbook.h>~n"), - w("#include <wx/listbook.h>~n"), - w("#include <wx/treebook.h>~n"), - w("#include <wx/taskbar.h>~n"), - w("#include <wx/popupwin.h>~n"), - w("#include <wx/html/htmlwin.h>~n"), - w("#include <wx/html/htmlcell.h>~n"), - w("#include <wx/filename.h>~n"), - w("#include <wx/sysopt.h>~n"), - w("#include <wx/overlay.h>~n"), - w("#include <wx/notifmsg.h>~n"), - - w("~n~n", []), - w("#ifndef wxICON_DEFAULT_BITMAP_TYPE~n",[]), - w(" #define wxICON_DEFAULT_BITMAP_TYPE wxBITMAP_TYPE_ICO_RESOURCE~n",[]), - w("#endif~n", []), - w("~n~n", []), - - [w("#define ~s_~s ~p~n", [Class,Name,Id]) || - {Class,Name,_,Id} <- wx_gen_erl:get_unique_names()], - w("~n~n"). - -build_events() -> - open_write("../c_src/gen/wxe_events.cpp"), - c_copyright(), - w("~n/***** This file is generated do not edit ****/~n~n"), - w("#include <wx/wx.h>~n"), - w("#include \"../wxe_impl.h\"~n~n"), - w("#include \"wxe_macros.h\"~n"), - w("#include \"../wxe_events.h\"~n~n"), - w("#include \"../wxe_return.h\"~n~n"), - - w("wxeEtype::wxeEtype(const char *name, int Id) {eName = name;cID = Id;}~n~n"), - w("WX_DECLARE_HASH_MAP(int, wxeEtype*, wxIntegerHash, wxIntegerEqual, wxeETmap );~n~n"), - - w("wxeETmap etmap;~n~n"), - - w( -"int wxeEventTypeFromAtom(char *etype_atom) { - wxeETmap::iterator it; - for(it = etmap.begin(); it != etmap.end(); ++it) { - wxeEtype * value = it->second; - if(strcmp(value->eName, etype_atom) == 0) { - if(it->first > wxEVT_USER_FIRST) { - return it->first - wxEVT_USER_FIRST; - } else { - return it->first; - } - } - } - return -1; -} - -"), - - Evs0 = [C || {_,C=#class{event=Evs}} <- get(), Evs =/= false], - Evs = lists:keysort(#class.id, Evs0), - initEventTable(Evs), - encode_events(Evs), - close(). - -initEventTable(Evs) -> - w("void initEventTable()~n{~n"), - w(" struct { ",[]), - w("int ev_type; int class_id; const char * ev_name;} event_types[] =~n {~n",[]), - - lists:foreach(fun(Ev) -> init_event_classes(Ev) end, - [#class{id=0,event=[wxEVT_NULL]}|Evs]), - w(" {-1, 0, ""}~n };~n",[]), - w(" for(int i=0; event_types[i].ev_type != -1; i++) {~n",[]), - w(" if(NULL == etmap[event_types[i].ev_type]) {~n",[]), - w(" etmap[event_types[i].ev_type] =~n" - " new wxeEtype(event_types[i].ev_name, event_types[i].class_id);~n"), - w(" } else {~n",[]), - w(" wxeEtype *prev = etmap[event_types[i].ev_type];~n" - " wxString msg(wxT(\"Duplicate event defs: \"));~n" - " msg += wxString::FromAscii(event_types[i].ev_name);~n" - " msg += wxString::Format(wxT(\" %d \"), event_types[i].class_id);~n" - " msg += wxString::FromAscii(prev->eName);~n" - " msg += wxString::Format(wxT(\" %d\"), prev->cID);~n" - " send_msg(\"internal_error\", &msg);~n" - " }~n" - " }~n", []), - w("}~n~n"). - -init_event_classes(#class{event=ETs, id=Id}) -> - F = fun({Eev, Cev, OtherClass}) -> - w(" {~w + wxEVT_USER_FIRST, ~w, ~p},~n", - [Cev, find_id(OtherClass), wx_gen_erl:event_type_name(Eev)]); - ({Ev, {test_if, Test}}) -> - w("#if ~s~n", [Test]), - w(" {~w, ~w, ~p},~n", - [Ev, Id, wx_gen_erl:event_type_name(Ev)]), - w("#endif~n", []); - (Ev) -> - w(" {~w, ~w, ~p},~n", - [Ev, Id, wx_gen_erl:event_type_name(Ev)]) - end, - [F(ET) || ET <- ETs]. - -find_id(OtherClass) -> - Class = get({class,atom_to_list(OtherClass)}), - %%{value, Class} = lists:keysearch(atom_to_list(OtherClass), #class.name, All), - Class#class.id. - -encode_events(Evs) -> - ?WTC("encode_events"), - w("int getRef(void* ptr, wxeMemEnv* memenv)~n" - "{~n" - " WxeApp * app = (WxeApp *) wxTheApp;~n" - " return app->getRef(ptr,memenv);~n" - "}~n~n"), - w("bool sendevent(wxEvent *event, ErlDrvTermData port)~n{~n" - " int send_res ;~n" - " char * evClass = NULL;~n" - " wxMBConvUTF32 UTFconverter;~n" - " wxeEtype *Etype = etmap[event->GetEventType()];~n" - " wxeEvtListener *cb = (wxeEvtListener *)event->m_callbackUserData;~n" - " WxeApp * app = (WxeApp *) wxTheApp;~n" - " wxeMemEnv *memenv = app->getMemEnv(port);~n" - " if(!memenv) return 0;~n~n" - " wxeReturn rt = wxeReturn(port, cb->listener);~n"), - - w("~n rt.addAtom((char*)\"wx\");~n" - " rt.addInt((int) event->GetId());~n" - " rt.addRef(cb->obj, cb->class_name);~n" - " rt.addExt2Term(cb->user_data);~n"), - - w(" switch(Etype->cID) {~n"), - lists:foreach(fun(Ev) -> encode_event(Ev) end, Evs), - w(" }~n~n"), - - w(" rt.addTupleCount(5);~n"), - w(" if(cb->fun_id) {~n"), - w(" rt.addRef(getRef((void *)event,memenv), evClass);~n"), - w(" rt.addTupleCount(2);~n"), - w(" rt.addInt(cb->fun_id);~n"), - w(" rt.addAtom(\"_wx_invoke_cb_\");~n"), - w(" rt.addTupleCount(3);~n"), - w(" pre_callback();~n"), - w(" send_res = rt.send();~n"), - w(" if(send_res) handle_event_callback(WXE_DRV_PORT_HANDLE, cb->listener);~n"), - w(" app->clearPtr((void *) event);~n"), - w(" } else {~n"), - w(" send_res = rt.send();~n"), - w(" if(cb->skip) event->Skip();~n"), - #class{id=SizeId} = lists:keyfind("wxSizeEvent", #class.name, Evs), - #class{id=MoveId} = lists:keyfind("wxMoveEvent", #class.name, Evs), - w(" if(app->recurse_level < 1 && (Etype->cID == ~w || Etype->cID == ~w)) {~n", - [SizeId, MoveId]), - w(" app->recurse_level++;~n"), - w(" app->dispatch_cmds();~n"), - w(" app->recurse_level--;~n"), - w(" }~n"), - w(" };~n"), - w(" return send_res;~n"), - w(" }~n"). - -encode_event(C = #class{name=Class, id=Id, options=Opts}) -> - ?WTC("encode_event"), - case proplists:get_value("mixed_event", Opts) of - undefined -> - w("case ~p: {// ~s~n", [Id,Class]), - encode_event2(C), - ok; - Mixed -> - w("case ~p: {// ~s or ~s~n", [Id,Class,Mixed]), - w(" if(event->IsKindOf(CLASSINFO(~s))) {~n",[Class]), - encode_event2(C), - w(" } else {~n",[]), - w(" Etype = etmap[event->GetEventType() + wxEVT_USER_FIRST];~n",[]), - encode_event2(get({class,atom_to_list(Mixed)})), - w(" }~n",[]), - ok - end, - w(" break;~n}~n"). - -encode_event2(Class = #class{name=Name}) -> - Attrs = build_event_attrs(Class), - w(" evClass = (char*)\"~s\";~n",[Name]), - w(" rt.addAtom((char*)\"~s\");~n", [wx_gen_erl:event_rec_name(Name)]), - w(" rt.addAtom(Etype->eName);~n"), - build_ret_types(void, Attrs), - w(" rt.addTupleCount(~p);~n",[length(Attrs) + 2]). - -build_event_attrs(ClassRec = #class{name=Class}) -> - Attrs0 = wx_gen_erl:filter_attrs(ClassRec), - Rename = - fun(Att = #param{name=Name,prot=public,acc=undefined}, {All,Use}) -> - {[Att#param{name= "ev->" ++ Name}|All],Use}; - (Att = #param{acc=Acc}, {All,_}) -> - {[Att#param{name= "ev->" ++ Acc}|All], true} - end, - case foldr(Rename,{[],false},Attrs0) of - {[],_} -> []; -%% {Attrs,false} -> -%% w(" ~s ev = dynamic_cast<~s&>(event);~n",[Class,Class]), -%% Attrs; - {Attrs,_} -> - w(" ~s * ev = (~s *) event;~n",[Class,Class]), - FixClass = - fun(P=#param{name=N,acc=Acc,type=#type{single=Single,by_val=ByVal, - base={class,C}, mod=Mods, - ref = Ref}}) - when Acc =/= undefined -> - Var = var_name(N), - if Single, ByVal -> - w(" ~s * ~s = new ~s(~s);~n", [C,Var,C,N]), - w(" app->newPtr((void *) ~s,3, memenv);~n", [Var]); - Ref =:= reference -> - w(" ~s ~s * ~s = &~s;~n", [mods(Mods), C,Var,N]); - true -> - w(" ~s ~s * ~s = ~s;~n", [mods(Mods), C,Var,N]) - end, - P#param{name=Var}; - (P) -> P - end, - lists:map(FixClass, Attrs) - end. - -var_name("ev->" ++ Name0) -> - case reverse(Name0) of - ")(" ++ Name -> reverse(Name); - _ -> Name0 - end; -var_name(Name) -> Name. - -enum_name({Class,Type}) -> - uppercase_all(Class ++ "_" ++ Type); -enum_name(Type) -> - uppercase_all(Type). - - -enum_type({Class,Type}) -> - Class ++ "::" ++ Type; -enum_type(Type) -> Type. diff --git a/lib/wx/api_gen/wx_gen_erl.erl b/lib/wx/api_gen/wx_gen_erl.erl index b0cd67bad0..2ea5827843 100644 --- a/lib/wx/api_gen/wx_gen_erl.erl +++ b/lib/wx/api_gen/wx_gen_erl.erl @@ -76,6 +76,8 @@ gen_static(Files) -> w("-include(\"wxe.hrl\").~n",[]), %% w("-compile(export_all).~n~n", []), %% XXXX remove ??? [gen_static_exports(C) || C <- Files], + {ok, MiscExtra} = file:read_file(filename:join([wx_extra, "wx_misc.erl"])), + w("~s", [MiscExtra]), Classes = [gen_static_methods(C) || C <- Files], close(), Classes. @@ -97,10 +99,7 @@ gen_static_methods(C=#class{name=Name, parent="static",methods=Ms}) -> gen_class1(C=#class{parent="static"}) -> C; gen_class1(C=#class{name=Name,parent=Parent,methods=Ms,options=Opts}) -> - case Opts of - ["ignore"] -> throw(skipped); - _ -> ok - end, + lists:member("ignore", Opts) andalso throw(skipped), open_write("../src/gen/"++Name++".erl"), put(current_class, Name), erl_copyright(), diff --git a/lib/wx/api_gen/wx_gen_nif.erl b/lib/wx/api_gen/wx_gen_nif.erl index 4324d036e3..e71b155e6d 100644 --- a/lib/wx/api_gen/wx_gen_nif.erl +++ b/lib/wx/api_gen/wx_gen_nif.erl @@ -452,6 +452,8 @@ declare_type(N,false,_,#type{name="wxDateTime"}) -> w(" wxDateTime ~s;~n", [N]); declare_type(N,false,_,#type{name="wxColour"}) -> w(" wxColour ~s;~n", [N]); +declare_type(N,false,_,#type{name="wxString"}) -> + w(" wxString ~s;~n", [N]); declare_type(N,false,_,#type{name=Type, base=int, ref=reference}) -> w(" ~s ~s;~n", [Type,N]); declare_type(N,false,_,#type{name=Type, base=int64, ref=reference}) -> @@ -1233,19 +1235,29 @@ mods([]) -> "". gen_func_table(Defs) -> - Ms = [{Class,Method} || - #class{name=Class, methods=Ms} <- Defs, - Method <- lists:keysort(#method.id, lists:flatten(Ms))], w("~n"), w("#include <wx/wx.h>~n"), w("#include \"../wxe_impl.h\"~n"), w("~n"), - {_Id, Entries} = lists:foldl(fun gen_func_defs/2, {0,[]}, Ms), + {_Id, Entries} = gen_class_func_defs(Defs, {0,[]}), w("~n"), w("wxe_fns_t wxe_fns[] =~n{~n"), [w("~s", [Str]) || Str <- lists:reverse(Entries)], w("};~n"). +gen_class_func_defs([Class | Rest], Acc) -> + #class{name=Name, methods=Ms, options=Opts} = Class, + Methods = lists:keysort(#method.id, lists:flatten(Ms)), + AddOpts = case lists:keysearch(ifdef,1,Opts) of + {value, {ifdef, What}} when is_atom(What) -> [{ifdef, atom_to_list(What)}]; + {value, {ifdef, What}} when is_list(What) -> [{ifdef, What}]; + false -> [] + end, + Acc2 = lists:foldl(fun (Method = #method{opts=FOpts}, InAcc) -> + gen_func_defs({Name, Method#method{opts=FOpts ++ AddOpts}}, InAcc) + end, Acc, Methods), + gen_class_func_defs(Rest, Acc2); +gen_class_func_defs([], Acc) -> Acc. gen_func_defs({_, #method{where=erl_no_opt}}, Acc) -> Acc; gen_func_defs({_, #method{where=erl_alias}}, Acc) -> Acc; @@ -1258,11 +1270,17 @@ gen_func_defs({Class, #method{id=Id, method_type=MT, opts=FOpts, params=Ps}=Mtd} "wxEvtHandler_Disconnect_1", "wxEvtHandler_Disconnect_0"]), N = wx_gen_erl:erl_args_count(Ps, c), - Endif1 = gen_if(deprecated, FOpts, true), - Endif2 = gen_if(test_if, FOpts, true), - Depr = gen_if(deprecated, FOpts, false), - Vers = gen_if(test_if, FOpts, false), Name = wx_gen_erl:erl_func_name(Mtd), + Restrictions = [IfDef || {value, {_, IfDef}} <- [lists:keysearch(What, 1, FOpts) || What <- [ifdef, deprecated, test_if]]], + {Prefix, Stub, Postfix} = if + Restrictions == [] -> {"", "", ""}; + true -> { + io_lib:format("#if ~s~n", [string:join(Restrictions, " && ")]), + io_lib:format("#else~n {NULL, \"~s\", \"~s\", 0}, // ~w~n", [Class, Name, Id]), + io_lib:format("#endif // ~s~n", [string:join(Restrictions, " && ")]) + } + end, + w(Prefix), Str1 = if IsObjectDest -> io_lib:format(" {NULL, \"~s\", \"~s\", 1}, // ~w obj destructor ~s~n", [Class, Name, Id, Func]); IsTaylorMadeErl -> @@ -1271,12 +1289,8 @@ gen_func_defs({Class, #method{id=Id, method_type=MT, opts=FOpts, params=Ps}=Mtd} w("extern void ~s(WxeApp *app, wxeMemEnv *memenv, wxeCommand& Ecmd);~n", [Func]), io_lib:format(" {~s, \"~s\", \"~s\", ~w}, // ~w~n", [Func, Class, Name, N, Id]) end, - Str2 = if Endif1 orelse Endif2 -> - w("#endif~n"), - io_lib:format("#else~n {NULL, \"~s\", \"~s\", 0}, // ~w~n#endif~n", [Class, Name, Id]); - true -> "" - end, - {Id+1, [[Depr,Vers,Str1,Str2]|Strs]}; + w(Postfix), + {Id+1, [[Prefix,Str1,Stub,Postfix]|Strs]}; gen_func_defs({_, _}=CM, {50=Id, Strs}) -> w("extern void wxe_destroy(WxeApp *app, wxeMemEnv *memenv, wxeCommand& Ecmd);~n", []), Str = io_lib:format(" {wxe_destroy, \"wxe_util\", \"destroy\", 1}, // ~w~n", [Id]), @@ -1434,6 +1448,11 @@ gen_macros() -> w("#include <wx/sysopt.h>~n"), w("#include <wx/overlay.h>~n"), w("#include <wx/notifmsg.h>~n"), + w("#include <wx/webview.h>~n"), + w("#if wxUSE_WEBVIEW && wxUSE_WEBVIEW_IE~n"), + w("#include <wx/msw/webview_ie.h>~n"), + w("#endif~n"), + w("~n~n", []), w("#ifndef wxICON_DEFAULT_BITMAP_TYPE~n",[]), @@ -1583,6 +1602,11 @@ encode_events(Evs) -> encode_event(C = #class{name=Class, id=Id, options=Opts}) -> ?WTC("encode_event"), + case proplists:get_value(ifdef, Opts) of + undefined -> ok; + What when is_list(What)-> w("#if ~s~n",[What]); + What when is_atom(What) -> w("#if ~p~n",[What]) + end, case proplists:get_value("mixed_event", Opts) of undefined -> w(" case ~p: {// ~s~n", [Id,Class]), @@ -1598,7 +1622,11 @@ encode_event(C = #class{name=Class, id=Id, options=Opts}) -> w(" }~n",[]), ok end, - w(" break;~n }~n"). + w(" break;~n }~n"), + case proplists:get_value(ifdef, Opts) of + undefined -> ok; + Endif -> w("#endif // ~p~n~n",[Endif]) + end. encode_event2(#class{}=Class) -> Attrs = build_event_attrs(Class), diff --git a/lib/wx/api_gen/wxapi.conf b/lib/wx/api_gen/wxapi.conf index ed3da97c44..c17754925d 100644 --- a/lib/wx/api_gen/wxapi.conf +++ b/lib/wx/api_gen/wxapi.conf @@ -207,7 +207,15 @@ {wxSTC_V_PORT, {test_if, "wxCHECK_VERSION(3,1,1)"}}, {wxSTC_VHDL_BLOCK_COMMENT, {test_if, "wxCHECK_VERSION(3,1,1)"}}, {wxSTC_WRAP_WHITESPACE, {test_if, "wxCHECK_VERSION(3,1,1)"}}, - {wxSTC_WS_VISIBLEONLYIN, {test_if, "wxCHECK_VERSION(3,1,1)"}} + {wxSTC_WS_VISIBLEONLYIN, {test_if, "wxCHECK_VERSION(3,1,1)"}}, + + {wxWebViewZoom, {test_if, "WXE_WEBVIEW"}}, + {wxWebViewZoomType, {test_if, "WXE_WEBVIEW"}}, + {wxWebViewNavigationError, {test_if, "WXE_WEBVIEW"}}, + {wxWebViewReloadFlags, {test_if, "WXE_WEBVIEW"}}, + {wxWebViewFindFlags, {test_if, "WXE_WEBVIEW"}}, + {wxWebViewNavigationActionFlags, {test_if, "WXE_WEBVIEW && wxCHECK_VERSION(3,1,2)"}}, + {wxWebViewIE_EmulationLevel, {test_if, "WXE_WEBVIEW_IE && wxCHECK_VERSION(3,1,3)"}} ]}. {gvars, @@ -2319,3 +2327,60 @@ {'AddAction', [{test_if, "wxCHECK_VERSION(3,1,0)"}]},'Close', 'SetFlags',{'SetIcon', [{test_if, "wxCHECK_VERSION(3,1,0)"}]}, 'SetMessage','SetParent','SetTitle','Show']}. + +{class, wxWebView, wxControl, [{ifdef, "WXE_WEBVIEW"}, {skip, [{'New', 1}]}], + ['New','~wxWebView', + 'GetCurrentTitle','GetCurrentURL','GetPageSource','GetPageText', + 'IsBusy','IsEditable','LoadURL','Print', + + %% This probably needs a taylormade call + % 'RegisterHandler' + 'Reload', + {'RunScript', [{"output", out}, {test_if, "wxCHECK_VERSION(3,1,1)"}]}, + 'SetEditable','SetPage','Stop', + + %% Clipboard + 'CanCopy','CanCut','CanPaste','Copy','Cut','Paste', + + %% Context Menu + 'EnableContextMenu','IsContextMenuEnabled', + + %% History + 'CanGoBack','CanGoForward','ClearHistory','EnableHistory', + 'GoBack','GoForward', + %% Can not expose these ATM because of wxVector<wxSharedPtr<wxWebViewHistoryItem> + % 'GetBackwardHistory','GetForwardHistory','LoadHistoryItem', + + %% Selection + 'ClearSelection','DeleteSelection','GetSelectedSource','GetSelectedText', + 'HasSelection','SelectAll', + + %% Undo / Redo + 'CanRedo','CanUndo','Redo','Undo', + + %% Finding + 'Find', + + %% Zoom + 'CanSetZoomType','GetZoom','GetZoomType','SetZoom','SetZoomType', + {'GetZoomFactor', [{test_if, "wxCHECK_VERSION(3,1,4)"}]}, + {'SetZoomFactor', [{test_if, "wxCHECK_VERSION(3,1,4)"}]}, + + %% Static calls + {'IsBackendAvailable', [{test_if, "wxCHECK_VERSION(3,1,4)"}]}]}. + +{class, wxWebViewEvent, wxNotifyEvent, + [{ifdef, "WXE_WEBVIEW"}, + {acc, + [{m_string, "GetString()"}, + {m_int, "GetInt()"}, + {m_target, "GetTarget()"}, + {m_url, "GetURL()"}]}, + {event, + [{wxEVT_WEBVIEW_NAVIGATING, {test_if, "WXE_WEBVIEW"}}, + {wxEVT_WEBVIEW_NAVIGATED, {test_if, "WXE_WEBVIEW"}}, + {wxEVT_WEBVIEW_LOADED, {test_if, "WXE_WEBVIEW"}}, + {wxEVT_WEBVIEW_ERROR, {test_if, "WXE_WEBVIEW"}}, + {wxEVT_WEBVIEW_NEWWINDOW, {test_if, "WXE_WEBVIEW"}}, + {wxEVT_WEBVIEW_TITLE_CHANGED, {test_if, "WXE_WEBVIEW"}}]}], + ['GetString', 'GetInt', 'GetTarget','GetURL']}. |