// $Revision: 1.4 $ // Copyright (c) 1994-1995 Taligent, Inc. All rights reserved. #ifndef TaligentSamples_TEXTITERATIONSNIPPETS #include "TextIterationSnippets.h" #endif #ifndef Taligent_UNICODEGENERAL #include #endif #ifndef Taligent_TEXTITERATOR #include #endif #ifndef Taligent_STYLERUNITERATOR #include #endif #ifndef Taligent_FONTSTYLES #include #endif #ifndef Taligent_LINELAYOUTSTYLES #include #endif #ifndef Taligent_TEXTCOMPARISON #include #endif TaligentTypeExtensionMacro(TTextIterationSnippets) TTextIterationSnippets::TTextIterationSnippets() : TSnippets() { SNIPPETINFO(IteratingCharacters_1); SNIPPETINFO(IteratingCharacters_2); SNIPPETINFO(IteratingStyles_1); SNIPPETINFO(IteratingStyles_2); SNIPPETINFO(IteratingStyles_3); SNIPPETINFO(IteratingExactTextMatches); SNIPPETINFO(IteratingExactTextSpans); SNIPPETINFO(IteratingCaseInsensitiveTextMatches); } TTextIterationSnippets::~TTextIterationSnippets() { } TStandardText TTextIterationSnippets::GetSampleStyledText() { TStandardText text("Blue 24pt. Helvetica."); const TTextRange rangeBlue(0, TTextCount(4)); const TTextRange range24(5, TTextCount(2)); const TTextRange rangeHelvetica(11, TTextCount(9)); text.AddStyles(TTextColorStyle::GetBlue(), rangeBlue); text.AddStyles(TFontPointSizeStyle(24.0), range24); text.AddStyles(TFontFamilyStyle(TToken("Helvetica")), rangeHelvetica); return text; } // Iterate over characters in a text string. void TTextIterationSnippets::IteratingCharacters_1() { TStandardText text("Hello, world."); TCharacterIterator iter(&text); GetDisplay() << text << endl; for (UniChar c = iter.First(); (c != TCharacterIterator::kOutOfBounds) || iter.IsValid(); c = iter.Next()) { // GetDisplay() << "[" << iter.GetCurrentIndex() << "] " << TRepUniChars(&c, 1) << endl; } } // Iterate over a text string, replacing the Null character with comma. // We must cast TGeneralPunctuation::kNull to UniChar because it can // also be interpreted as a char*. Note that Null does not represent // the end of a string and may be returned by the iterator. IsValid // only needs to be called when Null is returned. void TTextIterationSnippets::IteratingCharacters_2() { TStandardText text = TStandardText("Hello") + TStandardText((UniChar)TGeneralPunctuation::kNull) + TStandardText(" world."); GetDisplay() << text << endl; TCharacterIterator iter(&text); for (UniChar c = iter.First(); (c != TCharacterIterator::kOutOfBounds) || iter.IsValid(); c = iter.Next()) { // if (c == TGeneralPunctuation::kNull) { iter.SetCurrent(TLatin1::kComma); } } GetDisplay() << text << endl; } // Iterate over styles in a text object using TTextIterator. Generally, // you would use TStyleRunIterator for this. void TTextIterationSnippets::IteratingStyles_1() { TStandardText text = GetSampleStyledText(); GetDisplay() << text << endl; TTextIterator iter(&text); TStyleSet styles; iter.First(styles); while (iter.IsValid()) { TTextIndex firstIndex = iter.GetChunkFirstIndex(); TTextIndex lastIndex = iter.GetChunkLastIndex(); GetDisplay() << firstIndex << "-" << lastIndex << endl; iter.SetIteratorAt(iter.GetChunkLastIndex() + 1); } } // Use a style run iterator to return all the style runs of the text object. // // The major differences betwen this and using a text iterator are: // 1) TStyleRunIterator takes a const TText*, while TTextIterator takes a TText*. // 2) TStyleRunIterator returns ranges (offset to offset) while in the previous // example the accessors used return indexes. // 3) TStyleRunIterator can use a TFilter to control what style runs are returned, // and a TTextRange to limit what part of the TText to iterate over. // // The default style run iterator uses a TNullFilter (and so reports all style runs) // over the entire range of the text. void TTextIterationSnippets::IteratingStyles_2() { TStandardText text = GetSampleStyledText(); GetDisplay() << text << endl; TStyleRunIterator iter(&text); TTextRange range; for (bool ok = iter.First(range); ok; ok = iter.Next(range)) { GetDisplay() << range.GetBegin() << "-" << range.GetEnd() << endl; } } // Use a style run iterator with filters to return all the style runs that do not // have any TFontPointSizeStyle identified with them. void TTextIterationSnippets::IteratingStyles_3() { TStandardText text = GetSampleStyledText(); GetDisplay() << text << endl; TSingleTypeStyleFilter typeFilter(TFontPointSizeStyle(0)); TNotStyleFilter notTypeFilter(typeFilter); TStyleRunIterator iter(&text, notTypeFilter); TTextRange range; for (bool ok = iter.First(range); ok; ok = iter.Next(range)) { GetDisplay() << range.GetBegin() << "-" << range.GetEnd() << endl; } } // Use a TExactTextPatternIterator to find exact matches of a pattern in a TText object. void TTextIterationSnippets::IteratingExactTextMatches() { TStandardText text("This and this and this and this."); TStandardText pattern("this"); GetDisplay() << "Text: " << text << endl << "Pattern: " << pattern << endl; TExactTextPatternIterator iter(&text, pattern); TTextRange range; for (TTextOffset offset = iter.First(range); offset != TTextPatternIterator::kNotFoundOffset; offset = iter.Next(range)) { // GetDisplay() << range.GetBegin() << "-" << range.GetEnd() << endl; } } // This replicates the function of strspn (return a range of the text that consists // of only characters from pattern); void TTextIterationSnippets::IteratingExactTextSpans() { TStandardText text("This and this and this and this."); TStandardText pattern("abcdefghijklmnopqrstuvwxyz"); GetDisplay() << "Text: " << text << endl << "Pattern: " << pattern << endl; TSpanTextPatternIterator iter(&text, pattern, TSpanTextPatternIterator::kInclusive); TTextRange range; for (TTextOffset offset = iter.First(range); offset != TTextPatternIterator::kNotFoundOffset; offset = iter.Next(range)) { // GetDisplay() << range.GetBegin() << "-" << range.GetEnd() << endl; } } // Use a TStandardTextPatternIterator to provide case-insensitive matching of English // text. For more examples of language-sensitive operations, see (!!! no sample yet.) // You must supply a TLanguageTextOrder to the iterator so it will know how to perform // language-sensitive comparisons. // By default TTableBasedTextOrder considers all differences significant. To // get case-insensitive matching, you must call SetOnlyUsePrimaryAndSecondaryDifference. // (Using primary and secondary differences will do case-insensitive matching since in // English 'a' and 'A' is a tertiary difference. Differences such as that between // 'ae' and TLatin::kSmallLigatureAe are secondary, so this code will consider them // significant.) void TTextIterationSnippets::IteratingCaseInsensitiveTextMatches() { TStandardText text("This and this and THIS and tHiS."); TStandardText pattern("this"); GetDisplay() << "Text: " << text << endl << "Pattern: " << pattern << endl; TTableBasedTextOrder textorder(TToken("English")); textorder.SetOnlyUsePrimaryAndSecondaryDifference(true); TStandardTextPatternIterator iter(&text, pattern, TTextRange::GetMaximumRange(), &textorder); TTextRange range; for (TTextOffset offset = iter.First(range); offset != TTextPatternIterator::kNotFoundOffset; offset = iter.Next(range)) { // GetDisplay() << range.GetBegin() << "-" << range.GetEnd() << endl; } }