]>
code.delx.au - refind/blob - refind/line_edit.c
1 // Line-editing functions borrowed from gummiboot (cursor_left(),
2 // cursor_right(), & line_edit()).
5 * Simple UEFI boot loader which executes configured EFI images, where the
6 * default entry is selected by a configured pattern (glob) or an on-screen
9 * All gummiboot code is LGPL not GPL, to stay out of politics and to give
10 * the freedom of copying code from programs to possible future libraries.
12 * This program is free software; you can redistribute it and/or modify it
13 * under the terms of the GNU Lesser General Public License as published by
14 * the Free Software Foundation; either version 2.1 of the License, or
15 * (at your option) any later version.
17 * This program is distributed in the hope that it will be useful, but
18 * WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
20 * Lesser General Public License for more details.
22 * Copyright (C) 2012-2013 Kay Sievers <kay@vrfy.org>
23 * Copyright (C) 2012 Harald Hoyer <harald@redhat.com>
25 * "Any intelligent fool can make things bigger, more complex, and more violent.
33 #include "../include/refit_call_wrapper.h"
35 static void cursor_left(UINTN
*cursor
, UINTN
*first
)
39 else if ((*first
) > 0)
43 static void cursor_right(UINTN
*cursor
, UINTN
*first
, UINTN x_max
, UINTN len
)
45 if ((*cursor
)+2 < x_max
)
47 else if ((*first
) + (*cursor
) < len
)
51 BOOLEAN
line_edit(CHAR16
*line_in
, CHAR16
**line_out
, UINTN x_max
) {
62 DrawScreenHeader(L
"Line Editor");
63 refit_call3_wrapper(ST
->ConOut
->SetCursorPosition
, ST
->ConOut
, (ConWidth
- 71) / 2, ConHeight
- 1);
64 refit_call2_wrapper(ST
->ConOut
->OutputString
, ST
->ConOut
,
65 L
"Use cursor keys to edit, Esc to exit, Enter to boot with edited options");
69 size
= StrLen(line_in
) + 1024;
70 line
= AllocatePool(size
* sizeof(CHAR16
));
71 StrCpy(line
, line_in
);
73 print
= AllocatePool(x_max
* sizeof(CHAR16
));
75 refit_call2_wrapper(ST
->ConOut
->EnableCursor
, ST
->ConOut
, TRUE
);
90 CopyMem(print
, line
+ first
, i
* sizeof(CHAR16
));
94 refit_call3_wrapper(ST
->ConOut
->SetCursorPosition
, ST
->ConOut
, 0, y_pos
);
95 refit_call2_wrapper(ST
->ConOut
->OutputString
, ST
->ConOut
, print
);
96 refit_call3_wrapper(ST
->ConOut
->SetCursorPosition
, ST
->ConOut
, cursor
, y_pos
);
98 refit_call3_wrapper(BS
->WaitForEvent
, 1, &ST
->ConIn
->WaitForKey
, &index
);
99 err
= refit_call2_wrapper(ST
->ConIn
->ReadKeyStroke
, ST
->ConIn
, &key
);
103 switch (key
.ScanCode
) {
113 if (cursor
>= x_max
) {
115 first
= len
- (x_max
-2);
119 while((first
+ cursor
) && line
[first
+ cursor
] == ' ')
120 cursor_left(&cursor
, &first
);
121 while((first
+ cursor
) && line
[first
+ cursor
] != ' ')
122 cursor_left(&cursor
, &first
);
123 while((first
+ cursor
) && line
[first
+ cursor
] == ' ')
124 cursor_left(&cursor
, &first
);
125 if (first
+ cursor
!= len
&& first
+ cursor
)
126 cursor_right(&cursor
, &first
, x_max
, len
);
127 refit_call3_wrapper(ST
->ConOut
->SetCursorPosition
, ST
->ConOut
, cursor
, y_pos
);
130 while(line
[first
+ cursor
] && line
[first
+ cursor
] == ' ')
131 cursor_right(&cursor
, &first
, x_max
, len
);
132 while(line
[first
+ cursor
] && line
[first
+ cursor
] != ' ')
133 cursor_right(&cursor
, &first
, x_max
, len
);
134 while(line
[first
+ cursor
] && line
[first
+ cursor
] == ' ')
135 cursor_right(&cursor
, &first
, x_max
, len
);
136 refit_call3_wrapper(ST
->ConOut
->SetCursorPosition
, ST
->ConOut
, cursor
, y_pos
);
139 if (first
+ cursor
== len
)
141 cursor_right(&cursor
, &first
, x_max
, len
);
142 refit_call3_wrapper(ST
->ConOut
->SetCursorPosition
, ST
->ConOut
, cursor
, y_pos
);
145 cursor_left(&cursor
, &first
);
146 refit_call3_wrapper(ST
->ConOut
->SetCursorPosition
, ST
->ConOut
, cursor
, y_pos
);
151 if (first
+ cursor
== len
)
153 for (i
= first
+ cursor
; i
< len
; i
++)
160 switch (key
.UnicodeChar
) {
162 case CHAR_CARRIAGE_RETURN
:
171 if (first
== 0 && cursor
== 0)
173 for (i
= first
+ cursor
-1; i
< len
; i
++)
178 if (cursor
> 0 || first
== 0)
180 /* show full line if it fits */
186 /* jump left to see what we delete */
197 case 0x80 ... 0xffff:
200 for (i
= len
; i
> first
+ cursor
; i
--)
202 line
[first
+ cursor
] = key
.UnicodeChar
;
205 if (cursor
+2 < x_max
)
207 else if (first
+ cursor
< len
)
213 refit_call2_wrapper(ST
->ConOut
->EnableCursor
, ST
->ConOut
, FALSE
);
217 } /* BOOLEAN line_edit() */