1 /**************************************************************************/
2 /* */
3 /* Copyright (c) Microsoft Corporation. All rights reserved. */
4 /* */
5 /* This software is licensed under the Microsoft Software License */
6 /* Terms for Microsoft Azure RTOS. Full text of the license can be */
7 /* found in the LICENSE file at https://aka.ms/AzureRTOS_EULA */
8 /* and in the root directory of this software. */
9 /* */
10 /**************************************************************************/
11
12
13 /**************************************************************************/
14 /**************************************************************************/
15 /** */
16 /** GUIX Component */
17 /** */
18 /** Text Input Management (Single Line Text Input) */
19 /** */
20 /**************************************************************************/
21
22 #define GX_SOURCE_CODE
23
24
25 /* Include necessary system files. */
26
27 #include "gx_api.h"
28 #include "gx_system.h"
29 #include "gx_display.h"
30 #include "gx_context.h"
31 #include "gx_widget.h"
32 #include "gx_single_line_text_input.h"
33 #include "gx_text_input_cursor.h"
34
35 /**************************************************************************/
36 /* */
37 /* FUNCTION RELEASE */
38 /* */
39 /* _gx_single_line_text_input_home PORTABLE C */
40 /* 6.1 */
41 /* AUTHOR */
42 /* */
43 /* Kenneth Maxwell, Microsoft Corporation */
44 /* */
45 /* DESCRIPTION */
46 /* */
47 /* This service moves the text input cursor position to the start of */
48 /* the input string. */
49 /* */
50 /* INPUT */
51 /* */
52 /* text_input Single-line text input widget */
53 /* control block */
54 /* */
55 /* OUTPUT */
56 /* */
57 /* None */
58 /* */
59 /* CALLS */
60 /* */
61 /* _gx_widget_font_get Get font by specified ID */
62 /* _gx_widget_border_width_get Get the widget border width */
63 /* _gx_widget_client_get Retrieves client area of the */
64 /* widget */
65 /* _gx_system_string_width_get Get the width of a string */
66 /* _gx_system_dirty_mark Mart the area of the widget */
67 /* dirty */
68 /* _gx_system_dirty_partial_add Mark the partial area of a */
69 /* widget as dirty */
70 /* */
71 /* CALLED BY */
72 /* */
73 /* Application Code */
74 /* GUIX Internal Code */
75 /* */
76 /* RELEASE HISTORY */
77 /* */
78 /* DATE NAME DESCRIPTION */
79 /* */
80 /* 05-19-2020 Kenneth Maxwell Initial Version 6.0 */
81 /* 09-30-2020 Kenneth Maxwell Modified comment(s), */
82 /* resulting in version 6.1 */
83 /* */
84 /**************************************************************************/
_gx_single_line_text_input_home(GX_SINGLE_LINE_TEXT_INPUT * text_input)85 UINT _gx_single_line_text_input_home(GX_SINGLE_LINE_TEXT_INPUT *text_input)
86 {
87 GX_TEXT_INPUT_CURSOR *cursor_ptr;
88 GX_VALUE border_width;
89 GX_VALUE text_width;
90 GX_RECTANGLE client;
91 GX_FONT *gx_font;
92 GX_VALUE new_xoffset;
93 GX_VALUE new_cursor_pos;
94 UINT start_mark = text_input -> gx_single_line_text_input_start_mark;
95 UINT end_mark = text_input -> gx_single_line_text_input_end_mark;
96 GX_BOOL mark_new_cursor_dirty = GX_FALSE;
97 GX_STRING string;
98
99 if (start_mark != end_mark)
100 {
101 text_input -> gx_single_line_text_input_start_mark = 0;
102 text_input -> gx_single_line_text_input_end_mark = 0;
103 }
104
105 cursor_ptr = &text_input -> gx_single_line_text_input_cursor_instance;
106
107 /* Check if cursor already in the home position. */
108 if (text_input -> gx_single_line_text_input_insert_pos == 0)
109 {
110 return GX_SUCCESS;
111 }
112
113 _gx_widget_border_width_get((GX_WIDGET *)text_input, &border_width);
114 _gx_widget_client_get((GX_WIDGET *)text_input, border_width, &client);
115
116 switch (text_input -> gx_widget_style & GX_STYLE_TEXT_ALIGNMENT_MASK)
117 {
118 case GX_STYLE_TEXT_RIGHT:
119 /* Calculate new x offset. */
120 _gx_widget_font_get((GX_WIDGET *)text_input, text_input -> gx_prompt_font_id, &gx_font);
121
122 string.gx_string_ptr = text_input -> gx_single_line_text_input_buffer;
123 string.gx_string_length = text_input -> gx_single_line_text_input_string_size;
124 _gx_system_string_width_get_ext(gx_font, &string, &text_width);
125 new_xoffset = (GX_VALUE)(client.gx_rectangle_right - client.gx_rectangle_left + 1);
126
127 new_xoffset = (GX_VALUE)(new_xoffset - 3);
128
129 if (text_width < new_xoffset)
130 {
131 new_xoffset = text_width;
132 }
133
134 /* Calculate new cursor position. */
135 new_cursor_pos = (GX_VALUE)(client.gx_rectangle_right - 1 - new_xoffset);
136 break;
137
138 case GX_STYLE_TEXT_CENTER:
139 /* Calculate new cursor position. */
140 new_xoffset = 0;
141 new_cursor_pos = (GX_VALUE)(client.gx_rectangle_left + 1 + ((client.gx_rectangle_right - client.gx_rectangle_left + 1) >> 1));
142 new_cursor_pos = (GX_VALUE)(new_cursor_pos - text_input -> gx_single_line_text_input_xoffset);
143 break;
144
145
146 case GX_STYLE_TEXT_LEFT:
147 default:
148 new_xoffset = 0;
149 new_cursor_pos = (GX_VALUE)(client.gx_rectangle_left + 1);
150 break;
151 }
152
153 if (text_input -> gx_single_line_text_input_xoffset != new_xoffset)
154 {
155 /* We need to update x offset, mark whole text input area dirty. */
156 _gx_system_dirty_mark((GX_WIDGET *)text_input);
157 }
158 else
159 {
160 if (start_mark != end_mark)
161 {
162 /* Get bounding rectangle of highlight text. */
163 _gx_single_line_text_input_text_rectangle_get(text_input, (INT)(start_mark - end_mark), &client);
164
165 /* Mark highlight area as dirty. */
166 _gx_system_dirty_partial_add((GX_WIDGET *)text_input, &client);
167
168 mark_new_cursor_dirty = GX_TRUE;
169 }
170 else
171 {
172 /* No need to update x offset, mark old and new cursor position area dirty. */
173
174 /* Mark old curosr rectangle as dirty. */
175 _gx_text_input_cursor_dirty_rectangle_get(cursor_ptr, &client);
176 _gx_system_dirty_partial_add((GX_WIDGET *)text_input, &client);
177
178 mark_new_cursor_dirty = GX_TRUE;
179 }
180 }
181
182 /* Update cursor position. */
183 cursor_ptr -> gx_text_input_cursor_pos.gx_point_x = new_cursor_pos;
184
185 /* Update character insert position. */
186 text_input -> gx_single_line_text_input_insert_pos = 0;
187
188 /* Update text input x offset. */
189 text_input -> gx_single_line_text_input_xoffset = new_xoffset;
190
191 if (mark_new_cursor_dirty)
192 {
193 /* Mark new cursor rectangle as dirty. */
194 _gx_text_input_cursor_dirty_rectangle_get(cursor_ptr, &client);
195 _gx_system_dirty_partial_add((GX_WIDGET *)text_input, &client);
196 }
197
198 return GX_SUCCESS;
199 }
200
201