Merge pull request #4920 from neikeq/pr-search-bar-fix

Fixed and improved search bar
This commit is contained in:
Rémi Verschelde 2016-05-30 22:33:01 +02:00
commit 78b4dcf84d
3 changed files with 130 additions and 90 deletions

View file

@ -3554,6 +3554,7 @@ void TextEdit::set_search_flags(uint32_t p_flags) {
void TextEdit::set_current_search_result(int line, int col) {
search_result_line = line;
search_result_col = col;
update();
}
void TextEdit::set_highlight_all_occurrences(const bool p_enabled) {

View file

@ -122,82 +122,30 @@ void FindReplaceBar::_unhandled_input(const InputEvent &p_event) {
}
}
bool FindReplaceBar::_search(bool p_include_current, bool p_backwards) {
bool FindReplaceBar::_search(uint32_t p_flags, int p_from_line, int p_from_col) {
int line, col;
String text=get_search_text();
uint32_t flags=0;
if (is_whole_words())
flags|=TextEdit::SEARCH_WHOLE_WORDS;
if (is_case_sensitive())
flags|=TextEdit::SEARCH_MATCH_CASE;
if (p_backwards)
flags|=TextEdit::SEARCH_BACKWARDS;
int line=text_edit->cursor_get_line();
int col=text_edit->cursor_get_column();
if (text_edit->is_selection_active() && !replace_all_mode) {
line = text_edit->get_selection_from_line();
col = text_edit->get_selection_from_column();
}
bool cursor_at_result=false;
if (line==current_result_line && col>=current_result_col && col<=current_result_col+text.length()) {
col=current_result_col;
cursor_at_result=true;
}
if (!p_include_current) {
if (p_backwards) {
col-=text.length();
if (col<0) {
line-=1;
if (line<0)
line=text_edit->get_line_count()-1;
col=text_edit->get_line(line).length();
}
} else if (cursor_at_result) {
col+=text.length();
if (col>text_edit->get_line(line).length()) {
line+=1;
if (line>=text_edit->get_line_count())
line=0;
col=0;
}
}
}
bool found = text_edit->search(text,flags,line,col,line,col);
if (!found) {
if (p_backwards) {
line = text_edit->get_line_count()-1;
col = text_edit->get_line(line).length()-1;
} else {
line = 0;
col = 0;
}
found = text_edit->search(text,flags,line,col,line,col);
}
bool found=text_edit->search(text,p_flags,p_from_line,p_from_col,line,col);
if (found) {
text_edit->cursor_set_line(line);
text_edit->cursor_set_column(p_backwards?col:col+text.length());
text_edit->select(line,col,line,col+text.length());
if (!preserve_cursor) {
text_edit->cursor_set_line(line);
text_edit->cursor_set_column(col+text.length());
}
text_edit->set_search_text(text);
text_edit->set_search_flags(flags);
text_edit->set_search_flags(p_flags);
text_edit->set_current_search_result(line,col);
current_result_line = line;
current_result_col = col;
result_line=line;
result_col=col;
set_error("");
} else {
current_result_line = -1;
current_result_col = -1;
result_line=-1;
result_col=-1;
text_edit->set_search_text("");
set_error(text.empty()?"":TTR("No Matches"));
}
@ -207,8 +155,13 @@ bool FindReplaceBar::_search(bool p_include_current, bool p_backwards) {
void FindReplaceBar::_replace() {
if (text_edit->get_selection_text()==get_search_text()) {
if (result_line!=-1 && result_col!=-1) {
text_edit->begin_complex_operation();
text_edit->select(result_line,result_col,result_line,result_col+get_search_text().length());
text_edit->insert_text_at_cursor(get_replace_text());
text_edit->end_complex_operation();
}
search_current();
@ -232,28 +185,26 @@ void FindReplaceBar::_replace_all() {
text_edit->cursor_set_line(0);
text_edit->cursor_set_column(0);
int search_text_len=get_search_text().length();
int rc=0;
replace_all_mode = true;
text_edit->begin_complex_operation();
while(_search(false)) {
if (!text_edit->is_selection_active()) {
// search selects
break;
}
while (search_next()) {
// replace area
Point2i match_from(text_edit->get_selection_from_line(),text_edit->get_selection_from_column());
Point2i match_to(text_edit->get_selection_to_line(),text_edit->get_selection_to_column());
Point2i match_from(result_line,result_col);
Point2i match_to(result_line,result_col+search_text_len);
if (match_from < prev_match)
break; // done
prev_match=match_to;
text_edit->select(result_line,result_col,result_line,match_to.y);
if (selection_enabled && is_selection_only()) {
if (match_from<selection_begin || match_to>selection_end)
@ -264,7 +215,7 @@ void FindReplaceBar::_replace_all() {
if (match_to.x==selection_end.x)
selection_end.y+=get_replace_text().length() - get_search_text().length();
} else {
//just replace
// just replace
text_edit->insert_text_at_cursor(get_replace_text());
}
@ -290,26 +241,96 @@ void FindReplaceBar::_replace_all() {
set_error(vformat(TTR("Replaced %d Ocurrence(s)."), rc));
}
void FindReplaceBar::search_current() {
void FindReplaceBar::_get_search_from(int& r_line, int& r_col) {
_search(true);
r_line=text_edit->cursor_get_line();
r_col=text_edit->cursor_get_column();
if (text_edit->is_selection_active() && !replace_all_mode) {
r_line=text_edit->get_selection_from_line();
r_col=text_edit->get_selection_to_column();
}
if (r_line==result_line && r_col>=result_col && r_col<=result_col+get_search_text().length()) {
r_col=result_col;
}
}
void FindReplaceBar::search_prev() {
bool FindReplaceBar::search_current() {
_search(false, true);
uint32_t flags=0;
if (is_whole_words())
flags|=TextEdit::SEARCH_WHOLE_WORDS;
if (is_case_sensitive())
flags|=TextEdit::SEARCH_MATCH_CASE;
int line, col;
_get_search_from(line, col);
return _search(flags,line,col);
}
void FindReplaceBar::search_next() {
bool FindReplaceBar::search_prev() {
_search();
uint32_t flags=0;
String text = get_search_text();
if (is_whole_words())
flags|=TextEdit::SEARCH_WHOLE_WORDS;
if (is_case_sensitive())
flags|=TextEdit::SEARCH_MATCH_CASE;
flags|=TextEdit::SEARCH_BACKWARDS;
int line, col;
_get_search_from(line, col);
col-=text.length();
if (col<0) {
line-=1;
if (line<0)
line=text_edit->get_line_count()-1;
col=text_edit->get_line(line).length();
}
return _search(flags,line,col);
}
bool FindReplaceBar::search_next() {
uint32_t flags=0;
String text = get_search_text();
if (is_whole_words())
flags|=TextEdit::SEARCH_WHOLE_WORDS;
if (is_case_sensitive())
flags|=TextEdit::SEARCH_MATCH_CASE;
int line, col;
_get_search_from(line, col);
if (line==result_line && col==result_col) {
col+=text.length();
if (col>text_edit->get_line(line).length()) {
line+=1;
if (line>=text_edit->get_line_count())
line=0;
col=0;
}
}
return _search(flags,line,col);
}
void FindReplaceBar::_hide_bar() {
if (replace_text->has_focus() || search_text->has_focus())
text_edit->grab_focus();
text_edit->set_search_text("");
current_result_line = -1;
current_result_col = -1;
result_line = -1;
result_col = -1;
replace_hbc->hide();
replace_options_hbc->hide();
hide();
@ -354,6 +375,15 @@ void FindReplaceBar::_search_options_changed(bool p_pressed) {
search_current();
}
void FindReplaceBar::_editor_text_changed() {
if (is_visible()) {
preserve_cursor=true;
search_current();
preserve_cursor=false;
}
}
void FindReplaceBar::_search_text_changed(const String& p_text) {
search_current();
@ -397,13 +427,14 @@ void FindReplaceBar::set_error(const String &p_label) {
void FindReplaceBar::set_text_edit(TextEdit *p_text_edit) {
text_edit = p_text_edit;
text_edit->connect("_text_changed",this,"_search_text_changed",varray(String()));
text_edit->connect("text_changed",this,"_editor_text_changed");
}
void FindReplaceBar::_bind_methods() {
ObjectTypeDB::bind_method("_unhandled_input",&FindReplaceBar::_unhandled_input);
ObjectTypeDB::bind_method("_editor_text_changed",&FindReplaceBar::_editor_text_changed);
ObjectTypeDB::bind_method("_search_text_changed",&FindReplaceBar::_search_text_changed);
ObjectTypeDB::bind_method("_search_text_entered",&FindReplaceBar::_search_text_entered);
ObjectTypeDB::bind_method("_search_current",&FindReplaceBar::search_current);
@ -419,6 +450,9 @@ void FindReplaceBar::_bind_methods() {
FindReplaceBar::FindReplaceBar() {
replace_all_mode=false;
preserve_cursor=false;
text_vbc = memnew(VBoxContainer);
add_child(text_vbc);

View file

@ -83,13 +83,18 @@ class FindReplaceBar : public HBoxContainer {
TextEdit *text_edit;
int current_result_line;
int current_result_col;
int result_line;
int result_col;
bool replace_all_mode;
bool preserve_cursor;
void _get_search_from(int& r_line, int& r_col);
void _show_search();
void _hide_bar();
void _editor_text_changed();
void _search_options_changed(bool p_pressed);
void _search_text_changed(const String& p_text);
void _search_text_entered(const String& p_text);
@ -98,7 +103,7 @@ protected:
void _notification(int p_what);
void _unhandled_input(const InputEvent &p_event);
bool _search(bool p_include_current=false, bool p_backwards=false);
bool _search(uint32_t p_flags, int p_from_line, int p_from_col);
void _replace();
void _replace_all();
@ -119,9 +124,9 @@ public:
void popup_search();
void popup_replace();
void search_current();
void search_prev();
void search_next();
bool search_current();
bool search_prev();
bool search_next();
FindReplaceBar();
};