func.h 9.85 KB
Newer Older
1 2
#ifndef _GNM_FUNC_H_
# define _GNM_FUNC_H_
3

4 5
#include <gnumeric.h>
#include <dependent.h>
6

7 8
G_BEGIN_DECLS

Jody Goldberg's avatar
Jody Goldberg committed
9 10
/* Setup of the symbol table */
void functions_init     (void);
11 12
void functions_shutdown (void);

13
GPtrArray *gnm_func_enumerate (void);
14

Jody Goldberg's avatar
Jody Goldberg committed
15
/******************************************************************************/
16
/* Function group support */
17

18
struct _GnmFuncGroup {
19
	GOString *internal_name, *display_name;
20
	gboolean has_translation;
21
	GSList *functions;
22
	unsigned ref_count; /* boxed type */
23
};
24

25
GType gnm_func_group_get_type (void); /* boxed type */
26
GnmFuncGroup *gnm_func_group_get_nth (gint n);
27 28
GnmFuncGroup *gnm_func_group_fetch (char const *name,
				    char const *translation);
Jody Goldberg's avatar
Jody Goldberg committed
29 30

/******************************************************************************/
31

32
/*
33
 * Function registration routines
Jody Goldberg's avatar
Jody Goldberg committed
34
 *
35 36 37 38 39
 * Functions come in two fashions:  Those that only deal with
 * very specific data types and a constant number of arguments,
 * and those who don't.
 *
 * The former kind of functions receives a precomputed array of
Jody Goldberg's avatar
Jody Goldberg committed
40
 * GnmValue pointers.
41 42 43 44 45 46
 *
 * The latter sort of functions receives the plain ExprNodes and
 * it is up to that routine to do the value computations and range
 * processing.
 */

47
/*
48
 *  Argument tokens passed in 'args'
Jody Goldberg's avatar
Jody Goldberg committed
49 50
 *
 * With intersection and iteration support
51
 *	f : floating point	(no errors, string conversion attempted)
52 53 54 55
 *	b : boolean		(identical to f, Do we need this ?)
 *	s : string		(no errors)
 *	S : 'scalar': any non-error value
 *	E : scalar including errors
Jody Goldberg's avatar
Jody Goldberg committed
56 57 58 59 60 61
 * Without intersection or iteration support
 *	r : cell range	content is _NOT_ guaranteed to have been evaluated yet
 *	A : area	either range or array (as above)
 *	a : array
 *	? : anything
 *
62 63
 *  For optional arguments do:
 * "ff|ss" where the strings are optional
64
 */
Jody Goldberg's avatar
Jody Goldberg committed
65

66
typedef enum {
67 68
	GNM_FUNC_TYPE_ARGS,	/* Arguments get marshalled by type */
	GNM_FUNC_TYPE_NODES,	/* Takes unevaulated expers directly */
69 70 71 72 73 74

	/* implementation has not been loaded yet, but we know where it is */
	GNM_FUNC_TYPE_STUB
} GnmFuncType;

typedef enum {
75
	GNM_FUNC_SIMPLE			= 0,
76 77
	GNM_FUNC_VOLATILE		= 1 << 0, /* eg now(), today() */
	GNM_FUNC_RETURNS_NON_SCALAR	= 1 << 1, /* eg transpose(), mmult() */
78

79
	/* an unknown function that will hopefully be defined later */
80 81
	GNM_FUNC_IS_PLACEHOLDER		= 1 << 3,
	GNM_FUNC_IS_WORKBOOK_LOCAL	= 1 << 5,
82
	GNM_FUNC_INTERNAL		= 1 << 6,
83 84 85 86 87 88 89 90 91 92

	GNM_FUNC_AUTO_UNKNOWN           = 0 << 8,
	GNM_FUNC_AUTO_MONETARY          = 1 << 8,  /* Like PV */
	GNM_FUNC_AUTO_DATE              = 2 << 8,  /* Like DATE */
	GNM_FUNC_AUTO_TIME              = 3 << 8,  /* Like TIME */
	GNM_FUNC_AUTO_PERCENT           = 4 << 8,  /* Like IRR */
	GNM_FUNC_AUTO_FIRST             = 5 << 8,  /* Like SUM */
	GNM_FUNC_AUTO_SECOND            = 6 << 8,  /* Like IF */
	GNM_FUNC_AUTO_UNITLESS          = 7 << 8,  /* Like COUNT */
	GNM_FUNC_AUTO_MASK              = 7 << 8   /* The bits we use for AUTO.  */
93
} GnmFuncFlags;
94

95 96 97
/* I do not like this.  It is going to be different for different apps probably
 * want to split it into bit file with our notion of its state, and 2 bits of
 * state per import format.
Jody Goldberg's avatar
Jody Goldberg committed
98
 */
99 100 101 102 103 104 105 106
typedef enum {
	GNM_FUNC_IMPL_STATUS_EXISTS = 0,
	GNM_FUNC_IMPL_STATUS_UNIMPLEMENTED,
	GNM_FUNC_IMPL_STATUS_SUBSET,
	GNM_FUNC_IMPL_STATUS_COMPLETE,
	GNM_FUNC_IMPL_STATUS_SUPERSET,
	GNM_FUNC_IMPL_STATUS_SUBSET_WITH_EXTENSIONS,
	GNM_FUNC_IMPL_STATUS_UNDER_DEVELOPMENT,
107
	GNM_FUNC_IMPL_STATUS_UNIQUE_TO_GNUMERIC
108
} GnmFuncImplStatus;
109

110 111
typedef enum {
	GNM_FUNC_TEST_STATUS_UNKNOWN = 0,
Jody Goldberg's avatar
Jody Goldberg committed
112
	GNM_FUNC_TEST_STATUS_NO_TESTSUITE,
113 114 115 116 117
	GNM_FUNC_TEST_STATUS_BASIC,
	GNM_FUNC_TEST_STATUS_EXHAUSTIVE,
	GNM_FUNC_TEST_STATUS_UNDER_DEVELOPMENT
} GnmFuncTestStatus;

118 119
typedef GnmValue	*(*GnmFuncArgs)	  (GnmFuncEvalInfo *ei, GnmValue const * const *args);
typedef GnmValue	*(*GnmFuncNodes)  (GnmFuncEvalInfo *ei,
120
					   int argc, GnmExprConstPtr const *argv);
121

122 123 124
typedef enum {
	GNM_FUNC_HELP_END,		/* Format */
					/* ------ */
125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157
	GNM_FUNC_HELP_NAME,
	/* <NAME>:<1 SENTENCE DESCRIPTION> (translated) */

	GNM_FUNC_HELP_ARG,
	/* <NAME>:<1 SENTENCE DESCRIPTION> (translated) */

	GNM_FUNC_HELP_DESCRIPTION,
	/* <LONG DESCRIPTION (reference args using @{arg})> (translated) */

	GNM_FUNC_HELP_NOTE,
	/* <SPECIAL CASES (reference args using @{arg})> (translated) */

	GNM_FUNC_HELP_EXAMPLES,
	/*
	 * Either translated text, or a formula that is only marked for
	 * translation if it contains strings that need to be translated.
	 */

	GNM_FUNC_HELP_SEEALSO,
	/* name,name,name ...	(not translated) */

	GNM_FUNC_HELP_EXTREF,
	/*
	 * Link to external descriptions.  The following styles defined:
	 * wolfram:Sine.html
	 * wiki:en:Trigonometric_functions
	 */

	GNM_FUNC_HELP_EXCEL,
	/* <SPECIAL NOTE RE EXCEL (reference args using @{arg})> (translated) */

	GNM_FUNC_HELP_ODF
	/* <SPECIAL NOTE RE ODF (reference args using @{arg})> (translated) */
158
} GnmFuncHelpType;
159

160 161 162 163 164
typedef struct {
    GnmFuncHelpType	 type;
    char const		*text;
} GnmFuncHelp;

165 166 167
struct _GnmFuncDescriptor {
	char const *name;
	char const *arg_spec;
168
	GnmFuncHelp const *help;
169 170 171 172 173
	GnmFuncArgs	  fn_args;
	GnmFuncNodes	  fn_nodes;
	GnmFuncFlags	  flags;
	GnmFuncImplStatus impl_status;
	GnmFuncTestStatus test_status;
174 175
};

176 177 178
struct GnmFunc_ {
	GObject	base;

179
	char const *name;
180
	GnmFuncHelp *help;
181

182
	/* <private> */
Morten Welinder's avatar
Morten Welinder committed
183 184 185 186 187 188 189 190 191 192
	GnmFuncType fn_type;
	GnmFuncGroup *fn_group;
	GnmFuncFlags flags;
	GnmFuncImplStatus impl_status;
	GnmFuncTestStatus test_status;

	GOString *tdomain;
	char *localized_name;

	gint usage_count;
193 194

	// Meaningful for ARGS only
Morten Welinder's avatar
Morten Welinder committed
195 196 197 198 199 200 201 202 203 204
	char *arg_spec;
	GnmFuncArgs args_func;

	// Meaningful for NODES only
	GnmFuncNodes nodes_func;

	// Derived for quick access
	GPtrArray *arg_names;
	int min_args, max_args;
	char *arg_types;
205
	int help_count;
206 207
};

208 209 210
#define GNM_FUNC_TYPE	(gnm_func_get_type ())
#define GNM_FUNC(obj)   (G_TYPE_CHECK_INSTANCE_CAST ((obj), GNM_FUNC_TYPE, GnmFunc))
#define GNM_IS_FUNC(o)  (G_TYPE_CHECK_INSTANCE_TYPE ((o), GNM_FUNC_TYPE))
Morten Welinder's avatar
Morten Welinder committed
211

212
GType       gnm_func_get_type        (void);
Morten Welinder's avatar
Morten Welinder committed
213
void        gnm_func_load_if_stub    (GnmFunc *func);
214
void        gnm_func_dispose         (GnmFunc *func);
215 216 217 218 219 220 221 222

GnmFunc	   *gnm_func_inc_usage	     (GnmFunc *func);
void	    gnm_func_dec_usage	     (GnmFunc *func);
gboolean    gnm_func_get_in_use      (GnmFunc *func);

char const *gnm_func_get_translation_domain (GnmFunc *func);
void        gnm_func_set_translation_domain (GnmFunc *func,
					     const char *tdomain);
223
char const *gnm_func_gettext         (GnmFunc *func, const char *str);
224

Morten Welinder's avatar
Morten Welinder committed
225 226 227 228 229 230 231 232 233 234
GnmFuncFlags gnm_func_get_flags      (GnmFunc *func);
void        gnm_func_set_flags       (GnmFunc *func, GnmFuncFlags f);


GnmFuncImplStatus gnm_func_get_impl_status (GnmFunc *func);
void        gnm_func_set_impl_status (GnmFunc *func, GnmFuncImplStatus st);

GnmFuncTestStatus gnm_func_get_test_status (GnmFunc *func);
void        gnm_func_set_test_status (GnmFunc *func, GnmFuncTestStatus st);

235
GnmFuncGroup*gnm_func_get_function_group (GnmFunc *func);
236 237
void        gnm_func_set_function_group (GnmFunc *func, GnmFuncGroup *group);

Morten Welinder's avatar
Morten Welinder committed
238 239 240 241
gboolean    gnm_func_is_varargs      (GnmFunc *func);
gboolean    gnm_func_is_fixargs      (GnmFunc *func);

void        gnm_func_set_stub        (GnmFunc *func);
242 243
void        gnm_func_set_varargs     (GnmFunc *func, GnmFuncNodes fn,
				      const char *spec);
Morten Welinder's avatar
Morten Welinder committed
244 245
void        gnm_func_set_fixargs     (GnmFunc *func, GnmFuncArgs fn,
				      const char *spec);
246

247 248 249
GnmFuncHelp const *gnm_func_get_help (GnmFunc *func, int *n);
void        gnm_func_set_help (GnmFunc *func, GnmFuncHelp const *help, int n);

250 251
GnmDependentFlags gnm_func_link_dep (GnmFunc *func, GnmFuncEvalInfo *ei, gboolean qlink);

252
char const *gnm_func_get_name	     (GnmFunc const *func,
253
				      gboolean localized);
254
GnmFunc	   *gnm_func_lookup	     (char const *name, Workbook *scope);
255 256 257
GnmFunc    *gnm_func_lookup_localized (char const *name, Workbook *scope);
GSList	   *gnm_func_lookup_prefix   (char const *prefix, Workbook *scope,
				      gboolean trans);
258
GnmFunc    *gnm_func_add	     (GnmFuncGroup *group,
259
				      GnmFuncDescriptor const *descriptor,
260
				      const char *tdomain);
261 262
void        gnm_func_set_from_desc   (GnmFunc *func, GnmFuncDescriptor const *desc);

263
GnmFunc    *gnm_func_add_placeholder (Workbook *scope,
264
				      char const *name,
265
				      char const *type);
266
GnmFunc    *gnm_func_add_placeholder_localized (char const *gname, char const *lname);
267
GnmFunc	   *gnm_func_lookup_or_add_placeholder (char const *name);
268 269

/* TODO */
270
char const *gnm_func_get_description (GnmFunc *func);
271 272 273
void        gnm_func_count_args    (GnmFunc *func, gint *min, int *max);
char        gnm_func_get_arg_type  (GnmFunc *func, gint arg_idx);
char const *gnm_func_get_arg_type_string  (GnmFunc *func, gint arg_idx);
Morten Welinder's avatar
Morten Welinder committed
274
char       *gnm_func_get_arg_name  (GnmFunc const *func, guint arg_idx);
275
char const *gnm_func_get_arg_description (GnmFunc *func, guint arg_idx);
276 277
char       *gnm_func_convert_markup_to_pango (char const *desc,
					      GtkWidget *target);
Michael Meeks's avatar
Michael Meeks committed
278

279
/*************************************************************************/
280

281
GnmValue *function_call_with_exprs	(GnmFuncEvalInfo *ei);
Morten Welinder's avatar
Morten Welinder committed
282
GnmValue *function_call_with_values     (GnmEvalPos const *ep, char const *name,
Jody Goldberg's avatar
Jody Goldberg committed
283
					 int argc, GnmValue const * const *values);
Morten Welinder's avatar
Morten Welinder committed
284
GnmValue *function_def_call_with_values (GnmEvalPos const *ep, GnmFunc const *fn,
Jody Goldberg's avatar
Jody Goldberg committed
285
					 int argc, GnmValue const * const *values);
Jody Goldberg's avatar
Jody Goldberg committed
286 287

/* Utilies to interate through ranges and argument lists */
Jody Goldberg's avatar
Jody Goldberg committed
288 289
typedef GnmValue * (*FunctionIterateCB) (GnmEvalPos const *ep, GnmValue const *value,
					 gpointer user_data);
290
GnmValue *function_iterate_argument_values (GnmEvalPos const *ep,
291 292
					    FunctionIterateCB callback,
					    gpointer callback_closure,
293
					    int argc,
294
					    GnmExprConstPtr const *argv,
295 296
					    gboolean strict,
					    CellIterFlags iter_flags);
297

298 299 300 301 302 303 304 305 306 307 308
/*************************************************************************/

struct _GnmFuncEvalInfo {
	GnmEvalPos const *pos;
	GnmExprFunction const *func_call;
	GnmExprEvalFlags flags;
};

GnmFunc const *gnm_eval_info_get_func (GnmFuncEvalInfo const *ei);
int gnm_eval_info_get_arg_count (GnmFuncEvalInfo const *ei);

309 310 311
G_END_DECLS

#endif /* _GNM_FUNC_H_ */