1 /* anchor_engine.c -- identify strokes along full-screen, non-uniform 3X3 grid
2
3 Copyright (C) 2000 Carl Worth
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2, or (at your option)
8 any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14 */
15
16 #include <stdio.h>
17 #include <stdlib.h>
18 #include <errno.h>
19 #include <string.h>
20
21 #include "rec.h"
22 #include "grid.h"
23 #include "regex_feature.h"
24 #include "anchor_engine.h"
25 #include "sprintf_alloc.h"
26 #include "fixed.h"
27
28 #ifdef DMALLOC
29 #include "dmalloc.h"
30 #endif
31
32 /* anchor_engine_funcs are defined statically in rec_engine.c
33 rec_engine_funcs_t engine_funcs =
34 {
35 anchor_priv_alloc,
36 anchor_priv_free,
37 anchor_feature_data_alloc,
38 anchor_feature_data_free,
39 anchor_classify_stroke,
40 anchor_classification_str_alloc,
41 anchor_free_classification,
42 anchor_recognize_feature
43 };
44 */
45
anchor_priv_alloc(rec_engine_t * engine)46 int anchor_priv_alloc(rec_engine_t *engine)
47 {
48 anchor_priv_t *priv;
49
50 priv = malloc(sizeof(anchor_priv_t));
51 if (priv == NULL) {
52 fprintf(stderr, "%s: Out of memory\n", __FUNCTION__);
53 return ENOMEM;
54 }
55
56 priv->border_width_ratio = ANCHOR_DEFAULT_BORDER_WIDTH_PERCENT / 100.0;
57 engine->priv = priv;
58 return 0;
59 }
60
anchor_priv_free(rec_engine_t * engine)61 void anchor_priv_free(rec_engine_t *engine)
62 {
63 free(engine->priv);
64 engine->priv = NULL;
65 }
66
anchor_feature_data_alloc(rec_engine_t * engine,char * feature_data_str)67 void *anchor_feature_data_alloc(rec_engine_t *engine, char *feature_data_str)
68 {
69 return regex_feature_alloc(feature_data_str);
70 }
71
anchor_feature_data_free(rec_engine_t * engine,void * feature_data)72 void anchor_feature_data_free(rec_engine_t *engine, void *feature_data)
73 {
74 regex_feature_free((regex_t *) feature_data);
75 }
76
anchor_classify_stroke(rec_engine_t * engine,stroke_t * stroke)77 void anchor_classify_stroke(rec_engine_t *engine, stroke_t *stroke)
78 {
79 anchor_priv_t *priv = engine->priv;
80 double bwr = priv->border_width_ratio;
81 int x_thresh_low, x_thresh_high;
82 int y_thresh_low, y_thresh_high;
83
84 x_thresh_low = f_to_fixed(engine->rec->width * bwr, stroke->precision_bits);
85 x_thresh_high = f_to_fixed(engine->rec->width * (1.0 - bwr), stroke->precision_bits);
86 y_thresh_low = f_to_fixed(engine->rec->height * bwr, stroke->precision_bits);
87 y_thresh_high = f_to_fixed(engine->rec->height * (1.0 - bwr), stroke->precision_bits);
88
89 stroke->classifications[engine->num] =
90 grid_stroke_sequence_alloc(stroke,
91 x_thresh_low, x_thresh_high,
92 y_thresh_low, y_thresh_high);
93 }
94
anchor_classification_str_alloc(rec_engine_t * engine,stroke_t * stroke)95 char *anchor_classification_str_alloc(rec_engine_t *engine, stroke_t *stroke)
96 {
97 return strdup((char *) stroke->classifications[engine->num]);
98 }
99
anchor_free_classification(rec_engine_t * engine,stroke_t * stroke)100 void anchor_free_classification(rec_engine_t *engine, stroke_t *stroke)
101 {
102 free(stroke->classifications[engine->num]);
103 }
104
anchor_recognize_stroke(rec_engine_t * engine,stroke_t * stroke,void * feature_data)105 double anchor_recognize_stroke(rec_engine_t *engine, stroke_t *stroke,
106 void *feature_data)
107 {
108 char *sequence = (char *) stroke->classifications[engine->num];
109 regex_t *regex = (regex_t *) feature_data;
110
111 return regex_feature_recognize(regex, sequence);
112 }
113
anchor_set_option(rec_engine_t * engine,char * option,char * value)114 int anchor_set_option(rec_engine_t *engine, char *option, char *value)
115 {
116 anchor_priv_t *priv;
117
118 priv = (anchor_priv_t *) engine->priv;
119 if (strcmp(option, "BorderWidthPercent") == 0) {
120 priv->border_width_ratio = atof(value) / 100.0;
121 return 0;
122 }
123
124 return EINVAL;
125 }
126