| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "chrome/renderer/spellchecker/spellcheck.h" | 5 #include "chrome/renderer/spellchecker/spellcheck.h" |
| 6 | 6 |
| 7 #include "base/bind.h" | 7 #include "base/bind.h" |
| 8 #include "base/message_loop/message_loop_proxy.h" | 8 #include "base/message_loop/message_loop_proxy.h" |
| 9 #include "base/strings/utf_string_conversions.h" | 9 #include "base/strings/utf_string_conversions.h" |
| 10 #include "chrome/common/render_messages.h" | 10 #include "chrome/common/render_messages.h" |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 64 for (size_t i = 0; i < markers.size(); ++i) | 64 for (size_t i = 0; i < markers.size(); ++i) |
| 65 markers_.push_back(markers[i]); | 65 markers_.push_back(markers[i]); |
| 66 // Visit all render views. | 66 // Visit all render views. |
| 67 return true; | 67 return true; |
| 68 } | 68 } |
| 69 | 69 |
| 70 } // namespace | 70 } // namespace |
| 71 | 71 |
| 72 class SpellCheck::SpellcheckRequest { | 72 class SpellCheck::SpellcheckRequest { |
| 73 public: | 73 public: |
| 74 SpellcheckRequest(const string16& text, | 74 SpellcheckRequest(const base::string16& text, |
| 75 blink::WebTextCheckingCompletion* completion) | 75 blink::WebTextCheckingCompletion* completion) |
| 76 : text_(text), completion_(completion) { | 76 : text_(text), completion_(completion) { |
| 77 DCHECK(completion); | 77 DCHECK(completion); |
| 78 } | 78 } |
| 79 ~SpellcheckRequest() {} | 79 ~SpellcheckRequest() {} |
| 80 | 80 |
| 81 string16 text() { return text_; } | 81 base::string16 text() { return text_; } |
| 82 blink::WebTextCheckingCompletion* completion() { return completion_; } | 82 blink::WebTextCheckingCompletion* completion() { return completion_; } |
| 83 | 83 |
| 84 private: | 84 private: |
| 85 string16 text_; // Text to be checked in this task. | 85 base::string16 text_; // Text to be checked in this task. |
| 86 | 86 |
| 87 // The interface to send the misspelled ranges to WebKit. | 87 // The interface to send the misspelled ranges to WebKit. |
| 88 blink::WebTextCheckingCompletion* completion_; | 88 blink::WebTextCheckingCompletion* completion_; |
| 89 | 89 |
| 90 DISALLOW_COPY_AND_ASSIGN(SpellcheckRequest); | 90 DISALLOW_COPY_AND_ASSIGN(SpellcheckRequest); |
| 91 }; | 91 }; |
| 92 | 92 |
| 93 | 93 |
| 94 // Initializes SpellCheck object. | 94 // Initializes SpellCheck object. |
| 95 // spellcheck_enabled_ currently MUST be set to true, due to peculiarities of | 95 // spellcheck_enabled_ currently MUST be set to true, due to peculiarities of |
| (...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 173 spellcheck_.Init(file, language); | 173 spellcheck_.Init(file, language); |
| 174 custom_dictionary_.Init(custom_words); | 174 custom_dictionary_.Init(custom_words); |
| 175 } | 175 } |
| 176 | 176 |
| 177 bool SpellCheck::SpellCheckWord( | 177 bool SpellCheck::SpellCheckWord( |
| 178 const char16* in_word, | 178 const char16* in_word, |
| 179 int in_word_len, | 179 int in_word_len, |
| 180 int tag, | 180 int tag, |
| 181 int* misspelling_start, | 181 int* misspelling_start, |
| 182 int* misspelling_len, | 182 int* misspelling_len, |
| 183 std::vector<string16>* optional_suggestions) { | 183 std::vector<base::string16>* optional_suggestions) { |
| 184 DCHECK(in_word_len >= 0); | 184 DCHECK(in_word_len >= 0); |
| 185 DCHECK(misspelling_start && misspelling_len) << "Out vars must be given."; | 185 DCHECK(misspelling_start && misspelling_len) << "Out vars must be given."; |
| 186 | 186 |
| 187 // Do nothing if we need to delay initialization. (Rather than blocking, | 187 // Do nothing if we need to delay initialization. (Rather than blocking, |
| 188 // report the word as correctly spelled.) | 188 // report the word as correctly spelled.) |
| 189 if (InitializeIfNeeded()) | 189 if (InitializeIfNeeded()) |
| 190 return true; | 190 return true; |
| 191 | 191 |
| 192 return spellcheck_.SpellCheckWord(in_word, in_word_len, | 192 return spellcheck_.SpellCheckWord(in_word, in_word_len, |
| 193 tag, | 193 tag, |
| 194 misspelling_start, misspelling_len, | 194 misspelling_start, misspelling_len, |
| 195 optional_suggestions); | 195 optional_suggestions); |
| 196 } | 196 } |
| 197 | 197 |
| 198 bool SpellCheck::SpellCheckParagraph( | 198 bool SpellCheck::SpellCheckParagraph( |
| 199 const string16& text, | 199 const base::string16& text, |
| 200 WebVector<WebTextCheckingResult>* results) { | 200 WebVector<WebTextCheckingResult>* results) { |
| 201 #if !defined(OS_MACOSX) | 201 #if !defined(OS_MACOSX) |
| 202 // Mac has its own spell checker, so this method will not be used. | 202 // Mac has its own spell checker, so this method will not be used. |
| 203 DCHECK(results); | 203 DCHECK(results); |
| 204 std::vector<WebTextCheckingResult> textcheck_results; | 204 std::vector<WebTextCheckingResult> textcheck_results; |
| 205 size_t length = text.length(); | 205 size_t length = text.length(); |
| 206 size_t offset = 0; | 206 size_t offset = 0; |
| 207 | 207 |
| 208 // Spellcheck::SpellCheckWord() automatically breaks text into words and | 208 // Spellcheck::SpellCheckWord() automatically breaks text into words and |
| 209 // checks the spellings of the extracted words. This function sets the | 209 // checks the spellings of the extracted words. This function sets the |
| 210 // position and length of the first misspelled word and returns false when | 210 // position and length of the first misspelled word and returns false when |
| 211 // the text includes misspelled words. Therefore, we just repeat calling the | 211 // the text includes misspelled words. Therefore, we just repeat calling the |
| 212 // function until it returns true to check the whole text. | 212 // function until it returns true to check the whole text. |
| 213 int misspelling_start = 0; | 213 int misspelling_start = 0; |
| 214 int misspelling_length = 0; | 214 int misspelling_length = 0; |
| 215 while (offset <= length) { | 215 while (offset <= length) { |
| 216 if (SpellCheckWord(&text[offset], | 216 if (SpellCheckWord(&text[offset], |
| 217 length - offset, | 217 length - offset, |
| 218 0, | 218 0, |
| 219 &misspelling_start, | 219 &misspelling_start, |
| 220 &misspelling_length, | 220 &misspelling_length, |
| 221 NULL)) { | 221 NULL)) { |
| 222 results->assign(textcheck_results); | 222 results->assign(textcheck_results); |
| 223 return true; | 223 return true; |
| 224 } | 224 } |
| 225 | 225 |
| 226 if (!custom_dictionary_.SpellCheckWord( | 226 if (!custom_dictionary_.SpellCheckWord( |
| 227 text, misspelling_start + offset, misspelling_length)) { | 227 text, misspelling_start + offset, misspelling_length)) { |
| 228 string16 replacement; | 228 base::string16 replacement; |
| 229 textcheck_results.push_back(WebTextCheckingResult( | 229 textcheck_results.push_back(WebTextCheckingResult( |
| 230 blink::WebTextDecorationTypeSpelling, | 230 blink::WebTextDecorationTypeSpelling, |
| 231 misspelling_start + offset, | 231 misspelling_start + offset, |
| 232 misspelling_length, | 232 misspelling_length, |
| 233 replacement)); | 233 replacement)); |
| 234 } | 234 } |
| 235 offset += misspelling_start + misspelling_length; | 235 offset += misspelling_start + misspelling_length; |
| 236 } | 236 } |
| 237 results->assign(textcheck_results); | 237 results->assign(textcheck_results); |
| 238 return false; | 238 return false; |
| 239 #else | 239 #else |
| 240 // This function is only invoked for spell checker functionality that runs | 240 // This function is only invoked for spell checker functionality that runs |
| 241 // on the render thread. OSX builds don't have that. | 241 // on the render thread. OSX builds don't have that. |
| 242 NOTREACHED(); | 242 NOTREACHED(); |
| 243 return true; | 243 return true; |
| 244 #endif | 244 #endif |
| 245 } | 245 } |
| 246 | 246 |
| 247 string16 SpellCheck::GetAutoCorrectionWord(const string16& word, int tag) { | 247 base::string16 SpellCheck::GetAutoCorrectionWord(const base::string16& word, |
| 248 string16 autocorrect_word; | 248 int tag) { |
| 249 base::string16 autocorrect_word; |
| 249 if (!auto_spell_correct_turned_on_) | 250 if (!auto_spell_correct_turned_on_) |
| 250 return autocorrect_word; // Return the empty string. | 251 return autocorrect_word; // Return the empty string. |
| 251 | 252 |
| 252 int word_length = static_cast<int>(word.size()); | 253 int word_length = static_cast<int>(word.size()); |
| 253 if (word_length < 2 || | 254 if (word_length < 2 || |
| 254 word_length > chrome::spellcheck_common::kMaxAutoCorrectWordSize) | 255 word_length > chrome::spellcheck_common::kMaxAutoCorrectWordSize) |
| 255 return autocorrect_word; | 256 return autocorrect_word; |
| 256 | 257 |
| 257 if (InitializeIfNeeded()) | 258 if (InitializeIfNeeded()) |
| 258 return autocorrect_word; | 259 return autocorrect_word; |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 291 } | 292 } |
| 292 | 293 |
| 293 // Restore the swapped characters. | 294 // Restore the swapped characters. |
| 294 std::swap(misspelled_word[i], misspelled_word[i + 1]); | 295 std::swap(misspelled_word[i], misspelled_word[i + 1]); |
| 295 } | 296 } |
| 296 return autocorrect_word; | 297 return autocorrect_word; |
| 297 } | 298 } |
| 298 | 299 |
| 299 #if !defined(OS_MACOSX) // OSX uses its own spell checker | 300 #if !defined(OS_MACOSX) // OSX uses its own spell checker |
| 300 void SpellCheck::RequestTextChecking( | 301 void SpellCheck::RequestTextChecking( |
| 301 const string16& text, | 302 const base::string16& text, |
| 302 blink::WebTextCheckingCompletion* completion) { | 303 blink::WebTextCheckingCompletion* completion) { |
| 303 // Clean up the previous request before starting a new request. | 304 // Clean up the previous request before starting a new request. |
| 304 if (pending_request_param_.get()) | 305 if (pending_request_param_.get()) |
| 305 pending_request_param_->completion()->didCancelCheckingText(); | 306 pending_request_param_->completion()->didCancelCheckingText(); |
| 306 | 307 |
| 307 pending_request_param_.reset(new SpellcheckRequest( | 308 pending_request_param_.reset(new SpellcheckRequest( |
| 308 text, completion)); | 309 text, completion)); |
| 309 // We will check this text after we finish loading the hunspell dictionary. | 310 // We will check this text after we finish loading the hunspell dictionary. |
| 310 if (InitializeIfNeeded()) | 311 if (InitializeIfNeeded()) |
| 311 return; | 312 return; |
| (...skipping 28 matching lines...) Expand all Loading... |
| 340 WebVector<blink::WebTextCheckingResult> results; | 341 WebVector<blink::WebTextCheckingResult> results; |
| 341 SpellCheckParagraph(param->text(), &results); | 342 SpellCheckParagraph(param->text(), &results); |
| 342 param->completion()->didFinishCheckingText(results); | 343 param->completion()->didFinishCheckingText(results); |
| 343 } | 344 } |
| 344 } | 345 } |
| 345 #endif | 346 #endif |
| 346 | 347 |
| 347 void SpellCheck::CreateTextCheckingResults( | 348 void SpellCheck::CreateTextCheckingResults( |
| 348 ResultFilter filter, | 349 ResultFilter filter, |
| 349 int line_offset, | 350 int line_offset, |
| 350 const string16& line_text, | 351 const base::string16& line_text, |
| 351 const std::vector<SpellCheckResult>& spellcheck_results, | 352 const std::vector<SpellCheckResult>& spellcheck_results, |
| 352 WebVector<WebTextCheckingResult>* textcheck_results) { | 353 WebVector<WebTextCheckingResult>* textcheck_results) { |
| 353 // Double-check misspelled words with our spellchecker and attach grammar | 354 // Double-check misspelled words with our spellchecker and attach grammar |
| 354 // markers to them if our spellchecker tells they are correct words, i.e. they | 355 // markers to them if our spellchecker tells they are correct words, i.e. they |
| 355 // are probably contextually-misspelled words. | 356 // are probably contextually-misspelled words. |
| 356 const char16* text = line_text.c_str(); | 357 const char16* text = line_text.c_str(); |
| 357 std::vector<WebTextCheckingResult> list; | 358 std::vector<WebTextCheckingResult> list; |
| 358 for (size_t i = 0; i < spellcheck_results.size(); ++i) { | 359 for (size_t i = 0; i < spellcheck_results.size(); ++i) { |
| 359 SpellCheckResult::Decoration decoration = spellcheck_results[i].decoration; | 360 SpellCheckResult::Decoration decoration = spellcheck_results[i].decoration; |
| 360 int word_location = spellcheck_results[i].location; | 361 int word_location = spellcheck_results[i].location; |
| (...skipping 12 matching lines...) Expand all Loading... |
| 373 list.push_back(WebTextCheckingResult( | 374 list.push_back(WebTextCheckingResult( |
| 374 static_cast<WebTextDecorationType>(decoration), | 375 static_cast<WebTextDecorationType>(decoration), |
| 375 word_location + line_offset, | 376 word_location + line_offset, |
| 376 word_length, | 377 word_length, |
| 377 spellcheck_results[i].replacement, | 378 spellcheck_results[i].replacement, |
| 378 spellcheck_results[i].hash)); | 379 spellcheck_results[i].hash)); |
| 379 } | 380 } |
| 380 } | 381 } |
| 381 textcheck_results->assign(list); | 382 textcheck_results->assign(list); |
| 382 } | 383 } |
| OLD | NEW |