1 /**
2 Contains functions to mixin to simplify code reuse. For these to work, the parameters of a native function
3 must be called context, thisObj, args, and nfe. They should not be placed in inner scopes or under if statements.
4 
5 ────────────────────────────────────────────────────────────────────────────────
6 
7 Copyright (C) 2021 pillager86.rf.gd
8 
9 This program is free software: you can redistribute it and/or modify it under 
10 the terms of the GNU General Public License as published by the Free Software 
11 Foundation, either version 3 of the License, or (at your option) any later 
12 version.
13 
14 This program is distributed in the hope that it will be useful, but WITHOUT ANY
15 WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
16 PARTICULAR PURPOSE.  See the GNU General Public License for more details.
17 
18 You should have received a copy of the GNU General Public License along with 
19 this program.  If not, see <https://www.gnu.org/licenses/>.
20  */
21 module mildew.binder;
22 
23 import std.format: format;
24 import std.conv: to;
25 
26 /**
27  * Check for a minimum number of arguments. This must be used if using TO_ARG
28  */
29 string CHECK_MINIMUM_ARGS(int num)()
30 {
31     return format(q{
32         if(args.length < %1$s)
33         {
34             nfe = NativeFunctionError.WRONG_NUMBER_OF_ARGS;
35             return ScriptAny.UNDEFINED;
36         }
37     }, num.to!string);
38 }
39 
40 /**
41  * Shorthand for validating a "this" object as a native type
42  */
43 string CHECK_THIS_NATIVE_OBJECT(string varName, alias dclass)()
44 {
45     return format(q{
46         auto %1$s = thisObj.toNativeObject!%2$s;
47         if(%1$s is null)
48         {
49             nfe = NativeFunctionError.WRONG_TYPE_OF_ARG;
50             return ScriptAny.UNDEFINED;
51         }
52     }, varName, dclass.stringof);
53 }
54 
55 /**
56  * Must check minimum arguments before using this. Gets an argument without regard to type.
57  */
58 string TO_ARG(string varName, int index, alias type)()
59 {
60     return format(q{
61         auto %1$s = args[%2$s].toValue!%3$s;
62     }, varName, index.to!string, type.stringof);
63 }
64 
65 /**
66  * Get an optional argument and assign it a default value if it doesn't exist
67  */
68 string TO_ARG_OPT(string varName, int index, alias defaultValue, alias type)()
69 {
70     return format(q{
71         auto %1$s = %3$s;
72         if(%2$s < args.length)
73         {
74             %1$s = args[%2$s].toValue!%4$s;
75         }
76     }, varName, index.to!string, defaultValue.stringof, type.stringof);
77 }
78 
79 /**
80  * Shorthand for extracting an argument without validating its type
81  */
82 string TO_ARG_CHECK_INDEX(string varName, int index, alias type)()
83 {   
84     return format(q{
85         if(args.length < %2$s + 1)
86         {
87             nfe = NativeFunctionError.WRONG_NUMBER_OF_ARGS;
88             return ScriptAny.UNDEFINED;
89         }
90         auto %1$s = args[%2$s].toValue!%3$s;
91     }, varName, index.to!string, type.stringof);
92 }
93