Преглед изворни кода

Merge pull request #34043 from Paulb23/27421_line_edit_remove_text_alignment

Fixed LineEdit text removal and placeholder caret alignment
Rémi Verschelde пре 5 година
родитељ
комит
d441536379
2 измењених фајлова са 35 додато и 4 уклоњено
  1. 33 4
      scene/gui/line_edit.cpp
  2. 2 0
      scene/gui/line_edit.h

+ 33 - 4
scene/gui/line_edit.cpp

@@ -823,7 +823,7 @@ void LineEdit::_notification(int p_what) {
 				int yofs = y_ofs + (caret_height - font->get_height()) / 2;
 				drawer.draw_char(ci, Point2(x_ofs, yofs + font_ascent), cchar, next, selected ? font_color_selected : font_color);
 
-				if (char_ofs == cursor_pos && draw_caret) {
+				if (char_ofs == cursor_pos && draw_caret && !using_placeholder) {
 					if (ime_text.length() == 0) {
 #ifdef TOOLS_ENABLED
 						VisualServer::get_singleton()->canvas_item_add_rect(ci, Rect2(Point2(x_ofs, y_ofs), Size2(Math::round(EDSCALE), caret_height)), cursor_color);
@@ -866,12 +866,27 @@ void LineEdit::_notification(int p_what) {
 				}
 			}
 
-			if (char_ofs == cursor_pos && draw_caret) { // May be at the end.
+			if ((char_ofs == cursor_pos || using_placeholder) && draw_caret) { // May be at the end, or placeholder.
 				if (ime_text.length() == 0) {
+					int caret_x_ofs = x_ofs;
+					if (using_placeholder) {
+						switch (align) {
+							case ALIGN_LEFT:
+							case ALIGN_FILL: {
+								caret_x_ofs = style->get_offset().x;
+							} break;
+							case ALIGN_CENTER: {
+								caret_x_ofs = ofs_max / 2;
+							} break;
+							case ALIGN_RIGHT: {
+								caret_x_ofs = ofs_max;
+							} break;
+						}
+					}
 #ifdef TOOLS_ENABLED
-					VisualServer::get_singleton()->canvas_item_add_rect(ci, Rect2(Point2(x_ofs, y_ofs), Size2(Math::round(EDSCALE), caret_height)), cursor_color);
+					VisualServer::get_singleton()->canvas_item_add_rect(ci, Rect2(Point2(caret_x_ofs, y_ofs), Size2(Math::round(EDSCALE), caret_height)), cursor_color);
 #else
-					VisualServer::get_singleton()->canvas_item_add_rect(ci, Rect2(Point2(x_ofs, y_ofs), Size2(1, caret_height)), cursor_color);
+					VisualServer::get_singleton()->canvas_item_add_rect(ci, Rect2(Point2(caret_x_ofs, y_ofs), Size2(1, caret_height)), cursor_color);
 #endif
 				}
 			}
@@ -970,6 +985,8 @@ void LineEdit::undo() {
 	undo_stack_pos = undo_stack_pos->prev();
 	TextOperation op = undo_stack_pos->get();
 	text = op.text;
+	cached_width = op.cached_width;
+	window_pos = op.window_pos;
 	set_cursor_position(op.cursor_pos);
 
 	if (expand_to_text_length)
@@ -988,6 +1005,8 @@ void LineEdit::redo() {
 	undo_stack_pos = undo_stack_pos->next();
 	TextOperation op = undo_stack_pos->get();
 	text = op.text;
+	cached_width = op.cached_width;
+	window_pos = op.window_pos;
 	set_cursor_position(op.cursor_pos);
 
 	if (expand_to_text_length)
@@ -1169,6 +1188,10 @@ void LineEdit::delete_char() {
 
 	set_cursor_position(get_cursor_position() - 1);
 
+	if (align == ALIGN_CENTER || align == ALIGN_RIGHT) {
+		window_pos = CLAMP(window_pos - 1, 0, text.length() - 1);
+	}
+
 	_text_changed();
 }
 
@@ -1196,6 +1219,10 @@ void LineEdit::delete_text(int p_from_column, int p_to_column) {
 		window_pos = cursor_pos;
 	}
 
+	if (align == ALIGN_CENTER || align == ALIGN_RIGHT) {
+		window_pos = CLAMP(window_pos - (p_to_column - p_from_column), 0, text.length() - 1);
+	}
+
 	if (!text_changed_dirty) {
 		if (is_inside_tree()) {
 			MessageQueue::get_singleton()->push_call(this, "_text_changed");
@@ -1677,7 +1704,9 @@ void LineEdit::_clear_undo_stack() {
 void LineEdit::_create_undo_state() {
 	TextOperation op;
 	op.text = text;
+	op.cached_width = cached_width;
 	op.cursor_pos = cursor_pos;
+	op.window_pos = window_pos;
 	undo_stack.push_back(op);
 }
 

+ 2 - 0
scene/gui/line_edit.h

@@ -106,6 +106,8 @@ private:
 
 	struct TextOperation {
 		int cursor_pos;
+		int window_pos;
+		int cached_width;
 		String text;
 	};
 	List<TextOperation> undo_stack;