doodles
This commit is contained in:
parent
fcf44f55a1
commit
ae17d21f4f
226
src/gd_v_call.erl
Normal file
226
src/gd_v_call.erl
Normal file
@ -0,0 +1,226 @@
|
||||
-module(gd_v_devman).
|
||||
-vsn("0.8.1").
|
||||
-author("Craig Everett <craigeverett@qpq.swiss>").
|
||||
-copyright("QPQ AG <info@qpq.swiss>").
|
||||
-license("GPL-3.0-or-later").
|
||||
|
||||
-behavior(wx_object).
|
||||
%-behavior(gd_v).
|
||||
-include_lib("wx/include/wx.hrl").
|
||||
-export([to_front/1]).
|
||||
% -export([]).
|
||||
-export([start_link/1]).
|
||||
-export([init/1, terminate/2, code_change/3,
|
||||
handle_call/3, handle_cast/2, handle_info/2, handle_event/2]).
|
||||
-include("$zx_include/zx_logger.hrl").
|
||||
-include("gd.hrl").
|
||||
|
||||
|
||||
% Widgets
|
||||
-record(w,
|
||||
{name = none :: atom() | {FunName :: binary(), call | dryr},
|
||||
id = 0 :: integer(),
|
||||
wx = none :: none | wx:wx_object()}).
|
||||
|
||||
% State
|
||||
-record(s,
|
||||
{wx = none :: none | wx:wx_object(),
|
||||
frame = none :: none | wx:wx_object(),
|
||||
lang = en :: en | jp,
|
||||
j = none :: none | fun(),
|
||||
args = [] :: [#wx{}],
|
||||
ttl = #wx{} :: #wx{},
|
||||
gasprice = #wx{} :: #wx{},
|
||||
gas = #wx{} :: #wx{},
|
||||
amount = #wx{} :: #wx{},
|
||||
retry = #wx{} :: #wx{},
|
||||
copy = #wx{} :: #wx{},
|
||||
done = #wx{} :: #wx{}}).
|
||||
|
||||
|
||||
|
||||
%%% Startup Functions
|
||||
|
||||
start_link(Args) ->
|
||||
wx_object:start_link({local, ?MODULE}, ?MODULE, Args, []).
|
||||
|
||||
|
||||
init({Prefs, {FunName, FunType}, ConID, AACI}) ->
|
||||
{aaci, ConName, FunSpecs, _} = AACI,
|
||||
FunSpec = maps:get(FunName, FunSpecs),
|
||||
CallType =
|
||||
case FunType of
|
||||
call -> J("Contract Call");
|
||||
dryr -> J("Dry Run")
|
||||
end,
|
||||
Title = [CallType, ": ", ConName, ".", FunName, "/", integer_to_list(length(element(1, FunSpec)))],
|
||||
Lang = maps:get(lang, Prefs, en_us),
|
||||
Trans = gd_jt:read_translations(?MODULE),
|
||||
J = gd_jt:j(Lang, Trans),
|
||||
Wx = wx:new(),
|
||||
Frame = wxFrame:new(Wx, ?wxID_ANY, Title),
|
||||
|
||||
{ArgSz, Args} = call_arg_sizer(Frame, J, FunSpec),
|
||||
{ParamSz, TTL_T, GasPriceT, GasT, AmountT} = call_param_sizer(Frame, J),
|
||||
|
||||
_ = wxFrame:setSizer(Frame, MainSz),
|
||||
_ = wxSizer:layout(MainSz),
|
||||
ok = gd_v:safe_size(Frame, Prefs),
|
||||
ok = wxFrame:connect(Frame, close_window),
|
||||
ok = wxFrame:connect(Frame, command_button_clicked),
|
||||
% TODO: Decide where to put the frame -- should probably be slightly randomized.
|
||||
% ok = wxFrame:center(Frame),
|
||||
true = wxFrame:show(Frame),
|
||||
State =
|
||||
#s{wx = Wx, frame = Frame, j = J, prefs = Prefs,
|
||||
args = Args,
|
||||
ttl = TTL_T, gasprice = GasPriceT, gas = GasT, amount = AmountT,
|
||||
retry = RetryBn, copy = CopyBn, done = DoneBn},
|
||||
{Frame, State}.
|
||||
|
||||
|
||||
call_arg_sizer(Frame, J, {CallArgs, ReturnType}) ->
|
||||
SpecSz = wxStaticBoxSizer:new(?wxVERTICAL, Frame, [{label, J("Function Spec")}]),
|
||||
{CallSz, CallControls, Dimensions} = call_sizer(Frame, J, CallArgs),
|
||||
ReturnSz = return_sizer(Frame, J, ReturnType),
|
||||
_ = wxStaticBoxSizer:add(SpecSz, CallSz, zxw:flags({wide, 5})),
|
||||
_ = wxStaticBoxSizer:add(SpecSz, ReturnSz, zxw:flags({base, 5})),
|
||||
{SpecSz, CallControls, Dimensions}.
|
||||
|
||||
call_sizer(Frame, J, []) ->
|
||||
CallSz = wxStaticBoxSizer:new(?wxVERTICAL, Frame, [{label, J("Call Args")}]),
|
||||
Args = wxStaticText:new(Frame, ?wxID_ANY, ["[", J("No Args"), "]"]),
|
||||
_ = wxStaticBoxSizer:add(CallSz, Args, zxw:flags({wide, 5})),
|
||||
{CallSz, [], {500, 500}};
|
||||
call_sizer(Frame, J, CallArgs) ->
|
||||
ScrollWin = wxScrolledWindow:new(Frame),
|
||||
ScrollSz = wxBoxSizer:new(?wxVERTICAL),
|
||||
ok = wxScrolledWindow:setSizerAndFit(ScrollWin, ScrollSz),
|
||||
ok = wxScrolledWindow:setScrollRate(ScrollWin, 5, 5),
|
||||
CallSz = wxStaticBoxSizer:new(?wxVERTICAL, Frame, [{label, J("Call Args")}]),
|
||||
GridSz = wxFlexGridSizer:new(2, [{gap, {4, 4}}]),
|
||||
ok = wxFlexGridSizer:setFlexibleDirection(GridSz, ?wxHORIZONTAL),
|
||||
ok = wxFlexGridSizer:addGrowableCol(GridSz, 1),
|
||||
AddArg =
|
||||
fun({Name, Type}) ->
|
||||
L = wxStaticText:new(ScrollWin, ?wxID_ANY, [Name, " : ", textify(Type)]),
|
||||
C = wxTextCtrl:new(ScrollWin, ?wxID_ANY),
|
||||
_ = wxFlexGridSizer:add(GridSz, L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, C, zxw:flags({wide, 5})),
|
||||
{Name, C}
|
||||
end,
|
||||
_ = wxStaticBoxSizer:add(ScrollSz, GridSz, zxw:flags(wide)),
|
||||
_ = wxStaticBoxSizer:add(CallSz, ScrollWin, zxw:flags(wide)),
|
||||
Controls = lists:map(AddArg, CallArgs),
|
||||
{CallSz, Controls, {600, 700}}.
|
||||
|
||||
return_sizer(Frame, J, ReturnType) ->
|
||||
ReturnSz = wxStaticBoxSizer:new(?wxVERTICAL, Frame, [{label, J("Return Type")}]),
|
||||
Return = wxStaticText:new(Frame, ?wxID_ANY, textify(ReturnType)),
|
||||
_ = wxStaticBoxSizer:add(ReturnSz, Return, zxw:flags({wide, 5})),
|
||||
ReturnSz.
|
||||
|
||||
|
||||
call_param_sizer(Frame, J) ->
|
||||
{ok, Height} = hz:top_height(),
|
||||
DefTTL = Height + 10000,
|
||||
DefGasP = hz:min_gas_price(),
|
||||
DefGas = 5000000,
|
||||
DefAmount = 0,
|
||||
ParamSz = wxStaticBoxSizer:new(?wxVERTICAL, Frame, [{label, J("TX Parameters")}]),
|
||||
GridSz = wxFlexGridSizer:new(2, 4, 4),
|
||||
ok = wxFlexGridSizer:setFlexibleDirection(GridSz, ?wxHORIZONTAL),
|
||||
ok = wxFlexGridSizer:addGrowableCol(GridSz, 1),
|
||||
TTL_L = wxStaticText:new(Frame, ?wxID_ANY, "TTL"),
|
||||
TTL_Tx = wxTextCtrl:new(Frame, ?wxID_ANY),
|
||||
ok = wxTextCtrl:setValue(TTL_Tx, integer_to_list(DefTTL)),
|
||||
GasP_L = wxStaticText:new(Frame, ?wxID_ANY, J("Gas Price")),
|
||||
GasP_Tx = wxTextCtrl:new(Frame, ?wxID_ANY),
|
||||
ok = wxTextCtrl:setValue(GasP_Tx, integer_to_list(DefGasP)),
|
||||
Gas_L = wxStaticText:new(Frame, ?wxID_ANY, J("Gas")),
|
||||
Gas_Tx = wxTextCtrl:new(Frame, ?wxID_ANY),
|
||||
ok = wxTextCtrl:setValue(Gas_Tx, integer_to_list(DefGas)),
|
||||
Amount_L = wxStaticText:new(Frame, ?wxID_ANY, J("TX Amount")),
|
||||
Amount_Tx = wxTextCtrl:new(Frame, ?wxID_ANY),
|
||||
ok = wxTextCtrl:setValue(Amount_Tx, integer_to_list(DefAmount)),
|
||||
_ = wxFlexGridSizer:add(GridSz, TTL_L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, TTL_Tx, zxw:flags({wide, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, GasP_L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, GasP_Tx, zxw:flags({wide, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, Gas_L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, Gas_Tx, zxw:flags({wide, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, Amount_L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, Amount_Tx, zxw:flags({wide, 5})),
|
||||
_ = wxSizer:add(ParamSz, GridSz, zxw:flags(wide)),
|
||||
{ParamSz, TTL_Tx, GasP_Tx, Gas_Tx, Amount_Tx}.
|
||||
|
||||
|
||||
|
||||
textify({integer, _, _}) -> "int";
|
||||
textify({boolean, _, _}) -> "bool";
|
||||
textify({{bytes, [I]}, _, _}) -> io_lib:format("bytes(~w)", [I]);
|
||||
textify({{bytes, any}, _, _}) -> "bytes()";
|
||||
textify({T, _, _}) when is_atom(T) -> atom_to_list(T);
|
||||
textify({T, _, _}) when is_list(T) -> T;
|
||||
textify({T, _, _}) -> io_lib:format("~tp", [T]).
|
||||
|
||||
|
||||
extract_args(Controls) ->
|
||||
extract_args(Controls, []).
|
||||
|
||||
extract_args([], Acc) ->
|
||||
pack_args(Acc);
|
||||
extract_args([{Name, Control} | T], Acc) ->
|
||||
String = wxTextCtrl:getValue(Control),
|
||||
extract_args(T, [{Name, String} | Acc]).
|
||||
|
||||
pack_args(Args) ->
|
||||
pack_args(Args, [], []).
|
||||
|
||||
pack_args([], M, A) ->
|
||||
Message = unicode:characters_to_list(["Call Args:\n", M]),
|
||||
{Message, A};
|
||||
pack_args([{N, S} | T], M, A) ->
|
||||
pack_args(T, [[N, ": ", S, "\n"] | M], [S | A]).
|
||||
|
||||
call_params(Controls) ->
|
||||
call_params(Controls, {[], []}).
|
||||
|
||||
call_params([], {Acc, []}) ->
|
||||
{ok, lists:reverse(Acc)};
|
||||
call_params([], {_, Errors}) ->
|
||||
{error, lists:reverse(Errors)};
|
||||
call_params([{{Label, Validate}, Control} | T], {Acc, Errors}) ->
|
||||
String = wxTextCtrl:getValue(Control),
|
||||
case Validate(String) of
|
||||
{ok, Value} -> call_params(T, {[Value | Acc], Errors});
|
||||
{error, Reason} -> call_params(T, {Acc, [{Label, Reason} | Errors]})
|
||||
end.
|
||||
|
||||
gt_0(S) ->
|
||||
C = "Must be an integer greater than 0",
|
||||
R =
|
||||
try
|
||||
{ok, list_to_integer(S)}
|
||||
catch
|
||||
error:badarg -> {error, {S, C}}
|
||||
end,
|
||||
case R of
|
||||
{ok, N} when N > 0 -> {ok, N};
|
||||
{ok, N} when N =< 0 -> {error, {S, C}};
|
||||
Error -> Error
|
||||
end.
|
||||
|
||||
gte_0(S) ->
|
||||
C = "Must be a non-negative integer.",
|
||||
R =
|
||||
try
|
||||
{ok, list_to_integer(S)}
|
||||
catch
|
||||
error:badarg -> {error, {S, C}}
|
||||
end,
|
||||
case R of
|
||||
{ok, N} when N >= 0 -> {ok, N};
|
||||
{ok, N} when N < 0 -> {error, {S, C}};
|
||||
Error -> Error
|
||||
end.
|
||||
@ -322,7 +322,9 @@ clicked(State = #s{cons = {Consbook, Contracts}}, Name) ->
|
||||
ok = tell(warning, "Inconcievable! No notebook page is selected!"),
|
||||
State;
|
||||
Index ->
|
||||
Contract = lists:nth(Index + 1, Contracts),
|
||||
#c{id = ConID, build = #{aaci := AACI}} = lists:nth(Index + 1, Contracts),
|
||||
|
||||
|
||||
clicked2(State, Contract, Name)
|
||||
end.
|
||||
|
||||
@ -337,8 +339,10 @@ clicked2(State, Contract, Name) ->
|
||||
end.
|
||||
|
||||
clicked3(State = #s{frame = Frame, j = J}, Contract, Name = {FunName, FunType}, Selected, Keys) ->
|
||||
{FunName, FunType} = Name,
|
||||
#c{id = ConID, build = #{aaci := AACI}} = Contract,
|
||||
{FunDef, ConID, AACI}
|
||||
|
||||
|
||||
{aaci, ConName, FunSpecs, _} = AACI,
|
||||
FunSpec = maps:get(FunName, FunSpecs),
|
||||
tell("FunName: ~tp", [FunName]),
|
||||
@ -400,149 +404,6 @@ clicked3(State = #s{frame = Frame, j = J}, Contract, Name = {FunName, FunType},
|
||||
Error -> handle_troubling(State, Error)
|
||||
end.
|
||||
|
||||
extract_args(Controls) ->
|
||||
extract_args(Controls, []).
|
||||
|
||||
extract_args([], Acc) ->
|
||||
pack_args(Acc);
|
||||
extract_args([{Name, Control} | T], Acc) ->
|
||||
String = wxTextCtrl:getValue(Control),
|
||||
extract_args(T, [{Name, String} | Acc]).
|
||||
|
||||
pack_args(Args) ->
|
||||
pack_args(Args, [], []).
|
||||
|
||||
pack_args([], M, A) ->
|
||||
Message = unicode:characters_to_list(["Call Args:\n", M]),
|
||||
{Message, A};
|
||||
pack_args([{N, S} | T], M, A) ->
|
||||
pack_args(T, [[N, ": ", S, "\n"] | M], [S | A]).
|
||||
|
||||
|
||||
call_arg_sizer(Dialog, J, {CallArgs, ReturnType}) ->
|
||||
SpecSz = wxStaticBoxSizer:new(?wxVERTICAL, Dialog, [{label, J("Function Spec")}]),
|
||||
{CallSz, CallControls, Dimensions} = call_sizer(Dialog, J, CallArgs),
|
||||
ReturnSz = return_sizer(Dialog, J, ReturnType),
|
||||
_ = wxStaticBoxSizer:add(SpecSz, CallSz, zxw:flags({wide, 5})),
|
||||
_ = wxStaticBoxSizer:add(SpecSz, ReturnSz, zxw:flags({base, 5})),
|
||||
{SpecSz, CallControls, Dimensions}.
|
||||
|
||||
call_sizer(Dialog, J, []) ->
|
||||
CallSz = wxStaticBoxSizer:new(?wxVERTICAL, Dialog, [{label, J("Call Args")}]),
|
||||
Args = wxStaticText:new(Dialog, ?wxID_ANY, ["[", J("No Args"), "]"]),
|
||||
_ = wxStaticBoxSizer:add(CallSz, Args, zxw:flags({wide, 5})),
|
||||
{CallSz, [], {500, 500}};
|
||||
call_sizer(Dialog, J, CallArgs) ->
|
||||
ScrollWin = wxScrolledWindow:new(Dialog),
|
||||
ScrollSz = wxBoxSizer:new(?wxVERTICAL),
|
||||
ok = wxScrolledWindow:setSizerAndFit(ScrollWin, ScrollSz),
|
||||
ok = wxScrolledWindow:setScrollRate(ScrollWin, 5, 5),
|
||||
CallSz = wxStaticBoxSizer:new(?wxVERTICAL, Dialog, [{label, J("Call Args")}]),
|
||||
GridSz = wxFlexGridSizer:new(2, [{gap, {4, 4}}]),
|
||||
ok = wxFlexGridSizer:setFlexibleDirection(GridSz, ?wxHORIZONTAL),
|
||||
ok = wxFlexGridSizer:addGrowableCol(GridSz, 1),
|
||||
AddArg =
|
||||
fun({Name, Type}) ->
|
||||
L = wxStaticText:new(ScrollWin, ?wxID_ANY, [Name, " : ", textify(Type)]),
|
||||
C = wxTextCtrl:new(ScrollWin, ?wxID_ANY),
|
||||
_ = wxFlexGridSizer:add(GridSz, L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, C, zxw:flags({wide, 5})),
|
||||
{Name, C}
|
||||
end,
|
||||
_ = wxStaticBoxSizer:add(ScrollSz, GridSz, zxw:flags(wide)),
|
||||
_ = wxStaticBoxSizer:add(CallSz, ScrollWin, zxw:flags(wide)),
|
||||
Controls = lists:map(AddArg, CallArgs),
|
||||
{CallSz, Controls, {600, 700}}.
|
||||
|
||||
return_sizer(Dialog, J, ReturnType) ->
|
||||
ReturnSz = wxStaticBoxSizer:new(?wxVERTICAL, Dialog, [{label, J("Return Type")}]),
|
||||
Return = wxStaticText:new(Dialog, ?wxID_ANY, textify(ReturnType)),
|
||||
_ = wxStaticBoxSizer:add(ReturnSz, Return, zxw:flags({wide, 5})),
|
||||
ReturnSz.
|
||||
|
||||
textify({integer, _, _}) -> "int";
|
||||
textify({boolean, _, _}) -> "bool";
|
||||
textify({{bytes, [I]}, _, _}) -> io_lib:format("bytes(~w)", [I]);
|
||||
textify({{bytes, any}, _, _}) -> "bytes()";
|
||||
textify({T, _, _}) when is_atom(T) -> atom_to_list(T);
|
||||
textify({T, _, _}) when is_list(T) -> T;
|
||||
textify({T, _, _}) -> io_lib:format("~tp", [T]).
|
||||
|
||||
|
||||
call_param_sizer(Dialog, J) ->
|
||||
{ok, Height} = hz:top_height(),
|
||||
DefTTL = Height + 10000,
|
||||
DefGasP = hz:min_gas_price(),
|
||||
DefGas = 5000000,
|
||||
DefAmount = 0,
|
||||
ParamSz = wxStaticBoxSizer:new(?wxVERTICAL, Dialog, [{label, J("TX Parameters")}]),
|
||||
GridSz = wxFlexGridSizer:new(2, 4, 4),
|
||||
ok = wxFlexGridSizer:setFlexibleDirection(GridSz, ?wxHORIZONTAL),
|
||||
ok = wxFlexGridSizer:addGrowableCol(GridSz, 1),
|
||||
TTL_L = wxStaticText:new(Dialog, ?wxID_ANY, "TTL"),
|
||||
TTL_Tx = wxTextCtrl:new(Dialog, ?wxID_ANY),
|
||||
ok = wxTextCtrl:setValue(TTL_Tx, integer_to_list(DefTTL)),
|
||||
GasP_L = wxStaticText:new(Dialog, ?wxID_ANY, J("Gas Price")),
|
||||
GasP_Tx = wxTextCtrl:new(Dialog, ?wxID_ANY),
|
||||
ok = wxTextCtrl:setValue(GasP_Tx, integer_to_list(DefGasP)),
|
||||
Gas_L = wxStaticText:new(Dialog, ?wxID_ANY, J("Gas")),
|
||||
Gas_Tx = wxTextCtrl:new(Dialog, ?wxID_ANY),
|
||||
ok = wxTextCtrl:setValue(Gas_Tx, integer_to_list(DefGas)),
|
||||
Amount_L = wxStaticText:new(Dialog, ?wxID_ANY, J("TX Amount")),
|
||||
Amount_Tx = wxTextCtrl:new(Dialog, ?wxID_ANY),
|
||||
ok = wxTextCtrl:setValue(Amount_Tx, integer_to_list(DefAmount)),
|
||||
_ = wxFlexGridSizer:add(GridSz, TTL_L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, TTL_Tx, zxw:flags({wide, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, GasP_L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, GasP_Tx, zxw:flags({wide, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, Gas_L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, Gas_Tx, zxw:flags({wide, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, Amount_L, zxw:flags({base, 5})),
|
||||
_ = wxFlexGridSizer:add(GridSz, Amount_Tx, zxw:flags({wide, 5})),
|
||||
_ = wxSizer:add(ParamSz, GridSz, zxw:flags(wide)),
|
||||
{ParamSz, TTL_Tx, GasP_Tx, Gas_Tx, Amount_Tx}.
|
||||
|
||||
call_params(Controls) ->
|
||||
call_params(Controls, {[], []}).
|
||||
|
||||
call_params([], {Acc, []}) ->
|
||||
{ok, lists:reverse(Acc)};
|
||||
call_params([], {_, Errors}) ->
|
||||
{error, lists:reverse(Errors)};
|
||||
call_params([{{Label, Validate}, Control} | T], {Acc, Errors}) ->
|
||||
String = wxTextCtrl:getValue(Control),
|
||||
case Validate(String) of
|
||||
{ok, Value} -> call_params(T, {[Value | Acc], Errors});
|
||||
{error, Reason} -> call_params(T, {Acc, [{Label, Reason} | Errors]})
|
||||
end.
|
||||
|
||||
gt_0(S) ->
|
||||
C = "Must be an integer greater than 0",
|
||||
R =
|
||||
try
|
||||
{ok, list_to_integer(S)}
|
||||
catch
|
||||
error:badarg -> {error, {S, C}}
|
||||
end,
|
||||
case R of
|
||||
{ok, N} when N > 0 -> {ok, N};
|
||||
{ok, N} when N =< 0 -> {error, {S, C}};
|
||||
Error -> Error
|
||||
end.
|
||||
|
||||
gte_0(S) ->
|
||||
C = "Must be a non-negative integer.",
|
||||
R =
|
||||
try
|
||||
{ok, list_to_integer(S)}
|
||||
catch
|
||||
error:badarg -> {error, {S, C}}
|
||||
end,
|
||||
case R of
|
||||
{ok, N} when N >= 0 -> {ok, N};
|
||||
{ok, N} when N < 0 -> {error, {S, C}};
|
||||
Error -> Error
|
||||
end.
|
||||
|
||||
clicked4(State,
|
||||
#c{id = ConID, build = #{aaci := AACI}},
|
||||
@ -785,7 +646,6 @@ deploy4(State = #s{frame = Frame, j = J}, InitSpec, Build, Selected, Keys) ->
|
||||
end.
|
||||
|
||||
deploy5(State, Build, Params, Args) ->
|
||||
tell(info, "Build: ~p", [Build]),
|
||||
ok = gd_con:deploy(Build, Params, Args),
|
||||
State.
|
||||
|
||||
@ -952,7 +812,7 @@ save(State = #s{prefs = Prefs, code = {Codebook, Pages}}) ->
|
||||
Index ->
|
||||
case lists:nth(Index + 1, Pages) of
|
||||
#p{path = {file, Path}, code = Widget} ->
|
||||
Source = wxStyledTextCtrl:getText(Widget),
|
||||
Source = gd_sophia_editor:get_text(Widget),
|
||||
case filelib:ensure_dir(Path) of
|
||||
ok ->
|
||||
case file:write_file(Path, Source) of
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user