Nuklear
This is a minimal-state, immediate-mode graphical user interface toolkit written in ANSI C and licensed under public domain. It was designed as a simple embeddable user interface for application and does not have any dependencies, a default render backend or OS window/input handling but instead provides a highly modular, library-based approach, with simple input state for input and draw commands describing primitive shapes as output. So instead of providing a layered library that tries to abstract over a number of platform and render backends, it focuses only on the actual UI.
 
Loading...
Searching...
No Matches
nuklear_selectable.c
1#include "nuklear.h"
2#include "nuklear_internal.h"
3
4/* ===============================================================
5 *
6 * SELECTABLE
7 *
8 * ===============================================================*/
9NK_LIB void
10nk_draw_selectable(struct nk_command_buffer *out,
11 nk_flags state, const struct nk_style_selectable *style, nk_bool active,
12 const struct nk_rect *bounds,
13 const struct nk_rect *icon, const struct nk_image *img, enum nk_symbol_type sym,
14 const char *string, int len, nk_flags align, const struct nk_user_font *font)
15{
16 const struct nk_style_item *background;
17 struct nk_text text;
18 text.padding = style->padding;
19
20 /* select correct colors/images */
21 if (!active) {
22 if (state & NK_WIDGET_STATE_ACTIVED) {
23 background = &style->pressed;
24 text.text = style->text_pressed;
25 } else if (state & NK_WIDGET_STATE_HOVER) {
26 background = &style->hover;
27 text.text = style->text_hover;
28 } else {
29 background = &style->normal;
30 text.text = style->text_normal;
31 }
32 } else {
33 if (state & NK_WIDGET_STATE_ACTIVED) {
34 background = &style->pressed_active;
35 text.text = style->text_pressed_active;
36 } else if (state & NK_WIDGET_STATE_HOVER) {
37 background = &style->hover_active;
38 text.text = style->text_hover_active;
39 } else {
40 background = &style->normal_active;
41 text.text = style->text_normal_active;
42 }
43 }
44
45 text.text = nk_rgb_factor(text.text, style->color_factor);
46
47 /* draw selectable background and text */
48 switch (background->type) {
49 case NK_STYLE_ITEM_IMAGE:
50 text.background = nk_rgba(0, 0, 0, 0);
51 nk_draw_image(out, *bounds, &background->data.image, nk_rgb_factor(nk_white, style->color_factor));
52 break;
53 case NK_STYLE_ITEM_NINE_SLICE:
54 text.background = nk_rgba(0, 0, 0, 0);
55 nk_draw_nine_slice(out, *bounds, &background->data.slice, nk_rgb_factor(nk_white, style->color_factor));
56 break;
57 case NK_STYLE_ITEM_COLOR:
58 text.background = background->data.color;
59 nk_fill_rect(out, *bounds, style->rounding, background->data.color);
60 break;
61 }
62 if (icon) {
63 if (img) nk_draw_image(out, *icon, img, nk_rgb_factor(nk_white, style->color_factor));
64 else nk_draw_symbol(out, sym, *icon, text.background, text.text, 1, font);
65 }
66 nk_widget_text(out, *bounds, string, len, &text, align, font);
67}
68NK_LIB nk_bool
69nk_do_selectable(nk_flags *state, struct nk_command_buffer *out,
70 struct nk_rect bounds, const char *str, int len, nk_flags align, nk_bool *value,
71 const struct nk_style_selectable *style, const struct nk_input *in,
72 const struct nk_user_font *font)
73{
74 int old_value;
75 struct nk_rect touch;
76
77 NK_ASSERT(state);
78 NK_ASSERT(out);
79 NK_ASSERT(str);
80 NK_ASSERT(len);
81 NK_ASSERT(value);
82 NK_ASSERT(style);
83 NK_ASSERT(font);
84
85 if (!state || !out || !str || !len || !value || !style || !font) return 0;
86 old_value = *value;
87
88 /* remove padding */
89 touch.x = bounds.x - style->touch_padding.x;
90 touch.y = bounds.y - style->touch_padding.y;
91 touch.w = bounds.w + style->touch_padding.x * 2;
92 touch.h = bounds.h + style->touch_padding.y * 2;
93
94 /* update button */
95 if (nk_button_behavior(state, touch, in, NK_BUTTON_DEFAULT))
96 *value = !(*value);
97
98 /* draw selectable */
99 if (style->draw_begin) style->draw_begin(out, style->userdata);
100 nk_draw_selectable(out, *state, style, *value, &bounds, 0,0,NK_SYMBOL_NONE, str, len, align, font);
101 if (style->draw_end) style->draw_end(out, style->userdata);
102 return old_value != *value;
103}
104NK_LIB nk_bool
105nk_do_selectable_image(nk_flags *state, struct nk_command_buffer *out,
106 struct nk_rect bounds, const char *str, int len, nk_flags align, nk_bool *value,
107 const struct nk_image *img, const struct nk_style_selectable *style,
108 const struct nk_input *in, const struct nk_user_font *font)
109{
110 nk_bool old_value;
111 struct nk_rect touch;
112 struct nk_rect icon;
113
114 NK_ASSERT(state);
115 NK_ASSERT(out);
116 NK_ASSERT(str);
117 NK_ASSERT(len);
118 NK_ASSERT(value);
119 NK_ASSERT(style);
120 NK_ASSERT(font);
121
122 if (!state || !out || !str || !len || !value || !style || !font) return 0;
123 old_value = *value;
124
125 /* toggle behavior */
126 touch.x = bounds.x - style->touch_padding.x;
127 touch.y = bounds.y - style->touch_padding.y;
128 touch.w = bounds.w + style->touch_padding.x * 2;
129 touch.h = bounds.h + style->touch_padding.y * 2;
130 if (nk_button_behavior(state, touch, in, NK_BUTTON_DEFAULT))
131 *value = !(*value);
132
133 icon.y = bounds.y + style->padding.y;
134 icon.w = icon.h = bounds.h - 2 * style->padding.y;
135 if (align & NK_TEXT_ALIGN_LEFT) {
136 icon.x = (bounds.x + bounds.w) - (2 * style->padding.x + icon.w);
137 icon.x = NK_MAX(icon.x, 0);
138 } else icon.x = bounds.x + 2 * style->padding.x;
139
140 icon.x += style->image_padding.x;
141 icon.y += style->image_padding.y;
142 icon.w -= 2 * style->image_padding.x;
143 icon.h -= 2 * style->image_padding.y;
144
145 /* draw selectable */
146 if (style->draw_begin) style->draw_begin(out, style->userdata);
147 nk_draw_selectable(out, *state, style, *value, &bounds, &icon, img, NK_SYMBOL_NONE, str, len, align, font);
148 if (style->draw_end) style->draw_end(out, style->userdata);
149 return old_value != *value;
150}
151NK_LIB nk_bool
152nk_do_selectable_symbol(nk_flags *state, struct nk_command_buffer *out,
153 struct nk_rect bounds, const char *str, int len, nk_flags align, nk_bool *value,
154 enum nk_symbol_type sym, const struct nk_style_selectable *style,
155 const struct nk_input *in, const struct nk_user_font *font)
156{
157 int old_value;
158 struct nk_rect touch;
159 struct nk_rect icon;
160
161 NK_ASSERT(state);
162 NK_ASSERT(out);
163 NK_ASSERT(str);
164 NK_ASSERT(len);
165 NK_ASSERT(value);
166 NK_ASSERT(style);
167 NK_ASSERT(font);
168
169 if (!state || !out || !str || !len || !value || !style || !font) return 0;
170 old_value = *value;
171
172 /* toggle behavior */
173 touch.x = bounds.x - style->touch_padding.x;
174 touch.y = bounds.y - style->touch_padding.y;
175 touch.w = bounds.w + style->touch_padding.x * 2;
176 touch.h = bounds.h + style->touch_padding.y * 2;
177 if (nk_button_behavior(state, touch, in, NK_BUTTON_DEFAULT))
178 *value = !(*value);
179
180 icon.y = bounds.y + style->padding.y;
181 icon.w = icon.h = bounds.h - 2 * style->padding.y;
182 if (align & NK_TEXT_ALIGN_LEFT) {
183 icon.x = (bounds.x + bounds.w) - (2 * style->padding.x + icon.w);
184 icon.x = NK_MAX(icon.x, 0);
185 } else icon.x = bounds.x + 2 * style->padding.x;
186
187 icon.x += style->image_padding.x;
188 icon.y += style->image_padding.y;
189 icon.w -= 2 * style->image_padding.x;
190 icon.h -= 2 * style->image_padding.y;
191
192 /* draw selectable */
193 if (style->draw_begin) style->draw_begin(out, style->userdata);
194 nk_draw_selectable(out, *state, style, *value, &bounds, &icon, 0, sym, str, len, align, font);
195 if (style->draw_end) style->draw_end(out, style->userdata);
196 return old_value != *value;
197}
198
199NK_API nk_bool
200nk_selectable_text(struct nk_context *ctx, const char *str, int len,
201 nk_flags align, nk_bool *value)
202{
203 struct nk_window *win;
204 struct nk_panel *layout;
205 const struct nk_input *in;
206 const struct nk_style *style;
207
208 enum nk_widget_layout_states state;
209 struct nk_rect bounds;
210
211 NK_ASSERT(ctx);
212 NK_ASSERT(value);
213 NK_ASSERT(ctx->current);
214 NK_ASSERT(ctx->current->layout);
215 if (!ctx || !ctx->current || !ctx->current->layout || !value)
216 return 0;
217
218 win = ctx->current;
219 layout = win->layout;
220 style = &ctx->style;
221
222 state = nk_widget(&bounds, ctx);
223 if (!state) return 0;
224 in = (state == NK_WIDGET_ROM || state == NK_WIDGET_DISABLED || layout->flags & NK_WINDOW_ROM) ? 0 : &ctx->input;
225 return nk_do_selectable(&ctx->last_widget_state, &win->buffer, bounds,
226 str, len, align, value, &style->selectable, in, style->font);
227}
228NK_API nk_bool
229nk_selectable_image_text(struct nk_context *ctx, struct nk_image img,
230 const char *str, int len, nk_flags align, nk_bool *value)
231{
232 struct nk_window *win;
233 struct nk_panel *layout;
234 const struct nk_input *in;
235 const struct nk_style *style;
236
237 enum nk_widget_layout_states state;
238 struct nk_rect bounds;
239
240 NK_ASSERT(ctx);
241 NK_ASSERT(value);
242 NK_ASSERT(ctx->current);
243 NK_ASSERT(ctx->current->layout);
244 if (!ctx || !ctx->current || !ctx->current->layout || !value)
245 return 0;
246
247 win = ctx->current;
248 layout = win->layout;
249 style = &ctx->style;
250
251 state = nk_widget(&bounds, ctx);
252 if (!state) return 0;
253 in = (state == NK_WIDGET_ROM || state == NK_WIDGET_DISABLED || layout->flags & NK_WINDOW_ROM) ? 0 : &ctx->input;
254 return nk_do_selectable_image(&ctx->last_widget_state, &win->buffer, bounds,
255 str, len, align, value, &img, &style->selectable, in, style->font);
256}
257NK_API nk_bool
258nk_selectable_symbol_text(struct nk_context *ctx, enum nk_symbol_type sym,
259 const char *str, int len, nk_flags align, nk_bool *value)
260{
261 struct nk_window *win;
262 struct nk_panel *layout;
263 const struct nk_input *in;
264 const struct nk_style *style;
265
266 enum nk_widget_layout_states state;
267 struct nk_rect bounds;
268
269 NK_ASSERT(ctx);
270 NK_ASSERT(value);
271 NK_ASSERT(ctx->current);
272 NK_ASSERT(ctx->current->layout);
273 if (!ctx || !ctx->current || !ctx->current->layout || !value)
274 return 0;
275
276 win = ctx->current;
277 layout = win->layout;
278 style = &ctx->style;
279
280 state = nk_widget(&bounds, ctx);
281 if (!state) return 0;
282 in = (state == NK_WIDGET_ROM || state == NK_WIDGET_DISABLED || layout->flags & NK_WINDOW_ROM) ? 0 : &ctx->input;
283 return nk_do_selectable_symbol(&ctx->last_widget_state, &win->buffer, bounds,
284 str, len, align, value, sym, &style->selectable, in, style->font);
285}
286NK_API nk_bool
287nk_selectable_symbol_label(struct nk_context *ctx, enum nk_symbol_type sym,
288 const char *title, nk_flags align, nk_bool *value)
289{
290 return nk_selectable_symbol_text(ctx, sym, title, nk_strlen(title), align, value);
291}
292NK_API nk_bool nk_select_text(struct nk_context *ctx, const char *str, int len,
293 nk_flags align, nk_bool value)
294{
295 nk_selectable_text(ctx, str, len, align, &value);return value;
296}
297NK_API nk_bool nk_selectable_label(struct nk_context *ctx, const char *str, nk_flags align, nk_bool *value)
298{
299 return nk_selectable_text(ctx, str, nk_strlen(str), align, value);
300}
301NK_API nk_bool nk_selectable_image_label(struct nk_context *ctx,struct nk_image img,
302 const char *str, nk_flags align, nk_bool *value)
303{
304 return nk_selectable_image_text(ctx, img, str, nk_strlen(str), align, value);
305}
306NK_API nk_bool nk_select_label(struct nk_context *ctx, const char *str, nk_flags align, nk_bool value)
307{
308 nk_selectable_text(ctx, str, nk_strlen(str), align, &value);return value;
309}
310NK_API nk_bool nk_select_image_label(struct nk_context *ctx, struct nk_image img,
311 const char *str, nk_flags align, nk_bool value)
312{
313 nk_selectable_image_text(ctx, img, str, nk_strlen(str), align, &value);return value;
314}
315NK_API nk_bool nk_select_image_text(struct nk_context *ctx, struct nk_image img,
316 const char *str, int len, nk_flags align, nk_bool value)
317{
318 nk_selectable_image_text(ctx, img, str, len, align, &value);return value;
319}
320NK_API nk_bool
321nk_select_symbol_text(struct nk_context *ctx, enum nk_symbol_type sym,
322 const char *title, int title_len, nk_flags align, nk_bool value)
323{
324 nk_selectable_symbol_text(ctx, sym, title, title_len, align, &value);return value;
325}
326NK_API nk_bool
327nk_select_symbol_label(struct nk_context *ctx, enum nk_symbol_type sym,
328 const char *title, nk_flags align, nk_bool value)
329{
330 return nk_select_symbol_text(ctx, sym, title, nk_strlen(title), align, value);
331}
332
main API and documentation file
@ NK_WINDOW_ROM
sets window widgets into a read only mode and does not allow input changes
Definition nuklear.h:5492
NK_API void nk_draw_image(struct nk_command_buffer *, struct nk_rect, const struct nk_image *, struct nk_color)
misc
NK_API void nk_fill_rect(struct nk_command_buffer *, struct nk_rect, float rounding, struct nk_color)
filled shades
@ NK_WIDGET_STATE_ACTIVED
!< widget is being hovered
Definition nuklear.h:3092
@ NK_WIDGET_STATE_HOVER
!< widget has been hovered on the current frame
Definition nuklear.h:3091
nk_widget_layout_states
Definition nuklear.h:3081
@ NK_WIDGET_DISABLED
The widget is manually disabled and acts like NK_WIDGET_ROM.
Definition nuklear.h:3085
@ NK_WIDGET_ROM
The widget is partially visible and cannot be updated.
Definition nuklear.h:3084