From: Jakub Narebski Date: Fri, 29 Jul 2011 11:52:58 GMT Subject: [PATCH/RFC 5/6] gitweb: Highlight matched part of project name when searching projects Message-ID: <1311940379-9608-6-git-send-email-jnareb@gmail.com> In-Reply-To: <1311940379-9608-1-git-send-email-jnareb@gmail.com> Use newly introduced esc_html_match_hl() to escape HTML and mark match with span element with 'match' class. Currently only 'path' part (i.e. project name) is highlighted; match might be on the project description. The code makes use of the fact that defined $search_regexp means that there was search going on. Signed-off-by: Jakub Narebski --- The esc_html_match_hl() subroutine (I really need a better name for it) should probably be used in more places, everywhere where we do highlight match in non-shortened text. It is safe wrt. codes that need HTML escaping both in non-matched and in matched part, and with regular expression containing characters that would be escaped, for example "foo>?" (i.e. "foo|foo>"). gitweb/gitweb.perl | 28 +++++++++++++++++++++++++++- 1 files changed, 27 insertions(+), 1 deletions(-) diff --git a/gitweb/gitweb.perl b/gitweb/gitweb.perl index 9c82d79..692a6bb 100755 --- a/gitweb/gitweb.perl +++ b/gitweb/gitweb.perl @@ -1690,6 +1690,30 @@ sub chop_and_escape_str { } } +# highlight match (if any), and escape HTML +sub esc_html_match_hl { + my ($str, $regexp) = @_; + return esc_html($str) unless defined $regexp; + + my @matches; + while ($str =~ /$regexp/g) { + push @matches, [$-[0], $+[0]]; + } + return esc_html($str) unless @matches; + + my $out = ''; + my $pos = 0; + for my $m (@matches) { + $out .= esc_html(substr $str, $pos, $m->[0] - $pos); + $out .= $cgi->span({-class => 'match'}, + esc_html(substr $str, $m->[0], $m->[1] - $m->[0])); + $pos = $m->[1]; + } + $out .= esc_html(substr $str, $pos); + + return $out; +} + ## ---------------------------------------------------------------------- ## functions returning short strings @@ -5143,7 +5167,9 @@ sub git_project_list_rows { print "\n"; } print "" . $cgi->a({-href => href(project=>$pr->{'path'}, action=>"summary"), - -class => "list"}, esc_html($pr->{'path'})) . "\n" . + -class => "list"}, + esc_html_match_hl($pr->{'path'}, $search_regexp)) . + "\n" . "" . $cgi->a({-href => href(project=>$pr->{'path'}, action=>"summary"), -class => "list", -title => $pr->{'descr_long'}}, esc_html($pr->{'descr'})) . "\n" . -- 1.7.5