Read ComponentOne RichTextBox for Silverlight text version

ComponentOne

RichTextBox for Silverlight

Copyright 2012 ComponentOne LLC. All rights reserved.

Corporate Headquarters ComponentOne LLC 201 South Highland Avenue 3rd Floor Pittsburgh, PA 15206 USA Internet: Web site: Sales E-mail: [email protected] Telephone: 1.800.858.2739 or 1.412.681.4343 (Pittsburgh, PA USA Office) [email protected] http://www.componentone.com

Trademarks The ComponentOne product name is a trademark and ComponentOne is a registered trademark of ComponentOne LLC. All other trademarks used herein are the properties of their respective owners. Warranty ComponentOne warrants that the original CD (or diskettes) are free from defects in material and workmanship, assuming normal use, for a period of 90 days from the date of purchase. If a defect occurs during this time, you may return the defective CD (or disk) to ComponentOne, along with a dated proof of purchase, and ComponentOne will replace it at no charge. After 90 days, you can obtain a replacement for a defective CD (or disk) by sending it and a check for $25 (to cover postage and handling) to ComponentOne. Except for the express warranty of the original CD (or disks) set forth here, ComponentOne makes no other warranties, express or implied. Every attempt has been made to ensure that the information contained in this manual is correct as of the time it was written. We are not responsible for any errors or omissions. ComponentOne's liability is limited to the amount you paid for the product. ComponentOne is not liable for any special, consequential, or other damages for any reason. Copying and Distribution While you are welcome to make backup copies of the software for your own use and protection, you are not permitted to make copies for the use of anyone else. We put a lot of time and effort into creating this product, and we appreciate your support in seeing that it is used by licensed users only.

This manual was produced using ComponentOne Doc-To-HelpTM.

Table of Contents

ComponentOne RichTextBox for Silverlight ...................................................................................................... 1 Installing Studio for Silverlight ............................................................................................................................ 1 Studio for Silverlight Setup Files ........................................................................................................... 1 Using Maps Powered by Esri ................................................................................................................ 2 System Requirements ............................................................................................................................. 3 Installing Demonstration Versions ........................................................................................................ 3 Uninstalling Studio for Silverlight ......................................................................................................... 3 End-User License Agreement .............................................................................................................................. 3 Licensing FAQs .................................................................................................................................................... 3 What is Licensing? ................................................................................................................................. 3 Studio for Silverlight Licensing ............................................................................................................. 3 Technical Support ................................................................................................................................................. 6 Redistributable Files ............................................................................................................................................. 6 About This Documentation ................................................................................................................................. 7 The C1.Silverlight.RichTextBox.dll Assembly ................................................................................................... 7 The C1.Silverlight.RichTextBox.Toolbar.dll Assembly .................................................................................... 7 The C1.Silverlight.RichTextBox.RtfFilter.dll Assembly ................................................................................... 8 RichTextBox for Silverlight Samples .................................................................................................................. 8 C1.Silverlight.RichTextBox Samples .................................................................................................... 8 ControlExplorer Sample ...................................................................................................................... 10 Factories Sample .................................................................................................................................. 10 Olympics Sample .................................................................................................................................. 10 QuickStart Sample ................................................................................................................................ 10 SamplesCommon Sample .................................................................................................................... 10 SilverTunes Sample .............................................................................................................................. 11 StockPortfolio Sample .......................................................................................................................... 11 Templates Sample ................................................................................................................................ 11 Introduction to Silverlight ................................................................................................................................ 13 Silverlight Resources .......................................................................................................................................... 13 Creating a New Silverlight Project .................................................................................................................... 14

iii

Theming .......................................................................................................................................................... 17 Available Themes ............................................................................................................................................... 17 BureauBlack .......................................................................................................................................... 17 Cosmopolitan........................................................................................................................................ 18 ExpressionDark .................................................................................................................................... 19 ExpressionLight .................................................................................................................................... 19 RainierOrange ...................................................................................................................................... 20 ShinyBlue .............................................................................................................................................. 21 WhistlerBlue ......................................................................................................................................... 21 Custom Themes .................................................................................................................................................. 22 Included XAML Files ........................................................................................................................................ 22 C1.Silverlight ........................................................................................................................................ 23 C1.Silverlight.Chart .............................................................................................................................. 23 C1.Silverlight.Chart.Editor .................................................................................................................. 24 C1.Silverlight.Chart3D ........................................................................................................................ 24 C1.Silverlight.DataGrid ....................................................................................................................... 25 C1.Silverlight.DataGrid.Filters ........................................................................................................... 25 C1.Silverlight.DataGrid.Ria ................................................................................................................ 25 C1.Silverlight.DataGrid.Summaries ................................................................................................... 25 C1.Silverlight.DateTimeEditors .......................................................................................................... 26 C1.Silverlight.Docking ......................................................................................................................... 26 C1.Silverlight.Extended ....................................................................................................................... 26 C1.Silverlight.FlexGrid ........................................................................................................................ 27 C1.Silverlight.FlexGrid.Filter .............................................................................................................. 27 C1.Silverlight.Gauge ............................................................................................................................ 27 C1.Silverlight.Imaging ......................................................................................................................... 27 C1.Silverlight.Legacy ........................................................................................................................... 27 C1.Silverlight.Maps .............................................................................................................................. 28 C1.Silverlight.MediaPlayer .................................................................................................................. 28 C1.Silverlight.OrgChart ....................................................................................................................... 28 C1.Silverlight.OutlookBar ................................................................................................................... 28 C1.Silverlight.PdfViewer ..................................................................................................................... 28 C1.Silverlight.ReportViewer ................................................................................................................ 29 C1.Silverlight.RichTextBox ................................................................................................................. 29 C1.Silverlight.RichTextBox.Toolbar .................................................................................................. 29 C1.Silverlight.Schedule ........................................................................................................................ 29 C1.Silverlight.SpellChecker ................................................................................................................. 30

iv

C1.Silverlight.Theming.BureauBlack ................................................................................................. 30 C1.Silverlight.Theming.Cosmopolitan ............................................................................................... 30 C1.Silverlight.Theming.ExpressionDark ............................................................................................ 31 C1.Silverlight.Theming.ExpressionLight ........................................................................................... 31 C1.Silverlight.Theming.Office2007..................................................................................................... 31 C1.Silverlight.Theming.Office2010..................................................................................................... 31 C1.Silverlight.Theming.RainierOrange .............................................................................................. 32 C1.Silverlight.Theming.ShinyBlue ..................................................................................................... 32 C1.Silverlight.Theming.WhistlerBlue ................................................................................................. 32 C1.Silverlight.TileView ........................................................................................................................ 32 C1.Silverlight.Toolbar .......................................................................................................................... 32 Implicit and Explicit Styles ................................................................................................................................ 33 Implicit Styles ....................................................................................................................................... 33 WPF and Silverlight Styling ................................................................................................................ 33 Using the ImplicitStyleManager.......................................................................................................... 34 Applying Themes to Controls ............................................................................................................................ 34 Applying Themes to an Application ................................................................................................................. 36 ComponentOne ClearStyle Technology ........................................................................................................... 38 How ClearStyle Works ........................................................................................................................ 39 ClearStyle Properties ............................................................................................................................ 39 RichTextBox .................................................................................................................................................... 41 RichTextBox for Silverlight Key Features ........................................................................................................ 41 RichTextBox for Silverlight Quick Start ........................................................................................................... 42 Step 1 of 3: Creating a Silverlight Application ................................................................................... 42 Step 2 of 3: Adding Spelling Checking ............................................................................................... 43 Step 3 of 3: Running the Application .................................................................................................. 45 XAML Quick Reference .................................................................................................................................... 47 Working with RichTextBox for Silverlight ....................................................................................................... 49 C1RichTextBox Concepts and Main Properties ................................................................................ 49 C1RichTextBox Content ..................................................................................................................... 51 Saving and Loading HTML ................................................................................................................ 51 Hyperlinks ............................................................................................................................................. 52 Accessing Layout Information ............................................................................................................ 54 Painters .................................................................................................................................................. 56 Spell-Checking ...................................................................................................................................... 58 Syntax Coloring .................................................................................................................................... 61 Overriding Styles .................................................................................................................................. 65

v

Hit-Testing ............................................................................................................................................ 68 HtmlFilter Customization .................................................................................................................... 71 Working with the C1Document Object ............................................................................................................ 73 Creating Documents and Reports ....................................................................................................... 73 Implementing Split Views .................................................................................................................... 81 Using the C1Document Class ............................................................................................................. 83 Understanding C1TextPointer ............................................................................................................ 84 Working with C1RichTextBoxToolbar............................................................................................................. 88 Edit Group ............................................................................................................................................ 89 Font Group ........................................................................................................................................... 89 Paragraph Group .................................................................................................................................. 91 Insert Group .......................................................................................................................................... 92 Tools Group .......................................................................................................................................... 94 Elements Supported in RichTextBox ................................................................................................................ 95 HTML Elements................................................................................................................................... 95 HTML Attributes ................................................................................................................................. 98 CSS2 Properties .................................................................................................................................. 105 CSS2 Selectors .................................................................................................................................... 108 RichTextBox for Silverlight Task-Based Help ................................................................................................ 110 Setting the Text Content .................................................................................................................... 110 Setting the HTML Content ................................................................................................................ 111 Connecting a C1RichTextBoxToolbar to a C1RichTextBox .......................................................... 112 Implementing a Simple Formatting Toolbar .................................................................................... 112 Adding Spell Checking ....................................................................................................................... 115

vi

ComponentOne RichTextBox for Silverlight

The most complete rich text editor available for Silverlight. Load, edit, and save formatted text as HTML or RTF documents with ComponentOne RichTextBoxTM for Silverlight. The C1RichTextBox control provides rich formatting, automatic line wrapping, HTML and RTF import/export, table support, images, annotations, and more. For a list of the latest features added to ComponentOne Studio for Silverlight, visit What's New in Studio for Silverlight.

Installing Studio for Silverlight

The following sections provide helpful information on installing ComponentOne Studio for Silverlight.

Studio for Silverlight Setup Files

The ComponentOne Studio for Silverlight installation program will create the following directory: C:\Program Files\ComponentOne\Studio for Silverlight 4.0. This directory contains the following subdirectories:

Bin Help Samples

Contains copies of ComponentOne binaries (DLLs, EXEs, design-time assemblies). Contains documentation for all Studio components and other useful resources including XAML files.

Samples for the product are installed in the ComponentOne Samples folder by default. The path of the ComponentOne Samples directory is slightly different on Windows XP and Windows Vista/Windows 7 machines: Windows XP path: C:\Documents and Settings\<username>\My Documents\ComponentOne Samples\Studio for Silverlight 4.0 Windows Vista and Windows 7 path: C:\Users\<username>\Documents\ComponentOne Samples\Studio for Silverlight 4.0 See the RichTextBox for Silverlight Samples (page 8) topic for more information about each sample. Esri Maps Esri® files are installed with ComponentOne Studio for Silverlight, ComponentOne Studio for WPF, and ComponentOne Studio for Windows Phone by default to the following folders: 32-bit machine : C:\Program Files\ESRI SDKs\<Platform>\<version number> 64-bit machine: C:\Program Files (x86)\ESRI SDKs\<Platform>\<version number> Files are provided for multiple languages, including: English, German (de), Spanish (es), French (fr), Italian (it), Japanese (ja), Portuguese (pt-BR), Russian (ru) and Chinese (zh-CN). See Using Maps Powered by Esri (page 2) or visit the Esri website at http://www.esri.com for additional information.

1

Using Maps Powered by Esri

Easily transform GIS data into business intelligence with controls for Silverlight, WPF, and Windows Phone powered by Esri® software. By using the ComponentOne award-winning UI controls, you'll have the tools you need to seamlessly create rich, map-enabled user interfaces. Benefits of Maps powered by Esri: Esri knows maps: Esri is the leading online map and GIS provider. Maps are technical: Using maps within your application is a very technical thing, so you don't want to take your chance using anyone but the best. Company of choice: Esri is the company of choice of many top companies and government agencies. Fulfill any developers' mapping needs: Esri mapping tools are flexible and will fill the needs of any mapping solution.

E sri Map Example There are no additional charges for using the Esri maps included with ComponentOne products. Simply create a free online account at http://www.arcgisonline.com to start taking advantage of the Esri map controls. Esri licensing terms can be found in our Licensing Information and End User Licensing Agreement at http://www.componentone.com/SuperPages/Licensing/. To learn more about Esri and Esri maps, please visit Esri at http://www.esri.com. There you will find detailed support, including documentation, forums, samples, and much more. See the Studio for Silverlight Setup Files (page 1) topic for more information on the Esri files installed with this product.

2

System Requirements

System requirements for ComponentOne Studio for Silverlight include the following: Microsoft Silverlight 4.0 or later Microsoft Visual Studio 2008 or later

Installing Demonstration Versions

If you wish to try ComponentOne Studio for Silverlight and do not have a serial number, follow the steps through the installation wizard and use the default serial number. The only difference between unregistered (demonstration) and registered (purchased) versions of our products is that the registered version will stamp every application you compile so a ComponentOne banner will not appear when your users run the applications.

Uninstalling Studio for Silverlight

To uninstall ComponentOne Studio for Silverlight: 1. 2. 3. Open the Control Panel and select Add or Remove Programs (XP) or Programs and Features (Windows 7/Vista). Select ComponentOne Studio for Silverlight 4.0 and click the Remove button. Click Yes to remove the program.

End-User License Agreement

All of the ComponentOne licensing information, including the ComponentOne end-user license agreements, frequently asked licensing questions, and the ComponentOne licensing model, is available online at http://www.componentone.com/SuperPages/Licensing/.

Licensing FAQs

The ComponentOne Studio for Silverlight product is a commercial product. It is not shareware, freeware, or open source. If you use it in production applications, please purchase a copy from our Web site or from the software reseller of your choice. This section describes the main technical aspects of licensing. It may help the user to understand and resolve licensing problems he may experience when using ComponentOne products.

What is Licensing?

Licensing is a mechanism used to protect intellectual property by ensuring that users are authorized to use software products. Licensing is not only used to prevent illegal distribution of software products. Many software vendors, including ComponentOne, use licensing to allow potential users to test products before they decide to purchase them. Without licensing, this type of distribution would not be practical for the vendor or convenient for the user. Vendors would either have to distribute evaluation software with limited functionality, or shift the burden of managing software licenses to customers, who could easily forget that the software being used is an evaluation version and has not been purchased.

Studio for Silverlight Licensing

Licensing for ComponentOne Studio for Silverlight is similar to licensing in other ComponentOne products but there are a few differences to note.

3

Initially licensing in handled similarly to other ComponentOne products. When a user decides to purchase a product, he receives an installation program and a Serial Number. During the installation process, the user is prompted for the serial number that is saved on the system. In ComponentOne Studio for Silverlight, when a control is dropped on a form, a license nag dialog box appears one time. The nag screen appears similar to the following image:

The About dialog box displays version information, online resources, and (if the control is unlicensed) buttons to purchase, activate, and register the product. All ComponentOne products are designed to display licensing information at run time if the product is not licensed. None will throw licensing exceptions and prevent applications from running. Each time an unlicensed Silverlight application is run; end-users will see the following pop-up dialog box:

4

To stop this message from appearing, enter the product's serial number by clicking the Activate button on the About dialog box of any ComponentOne product, if available, or by rerunning the installation and entering the serial number in the licensing dialog box. To open the About dialog box, right-click the control and select the About option:

Note that when the user modifies any property of a ComponentOne Silverlight control in Visual Studio or Blend, the product will check if a valid license is present. If the product is not currently licensed, an attached property will be added to the control (the C1NagScreen.Nag property). Then, when the application executed, the product will check if that property is set, and show a nag screen if the C1NagScreen.Nag property is set to True. If the user has a valid license the property is not added or is just removed. One important aspect of this of this process is that the user should manually remove all instances of c1:C1NagScreen.Nag="true" in the XAML markup in all files after registering the license (or re-open all the files

5

that include ComponentOne controls in any of the editors). This will ensure that the nag screen does not appear when the application is run.

Technical Support

ComponentOne offers various support options. For a complete list and a description of each, visit the ComponentOne Web site at http://www.componentone.com/SuperProducts/SupportServices/. Some methods for obtaining technical support include: Online Resources ComponentOne provides customers with a comprehensive set of technical resources in the form of FAQs, samples and videos, Version Release History, searchable Knowledge base, searchable Online Help and more. We recommend this as the first place to look for answers to your technical questions. Online Support via our Incident Submission Form This online support service provides you with direct access to our Technical Support staff via an online incident submission form. When you submit an incident, you'll immediately receive a response via e-mail confirming that you've successfully created an incident. This email will provide you with an Issue Reference ID and will provide you with a set of possible answers to your question from our Knowledgebase. You will receive a response from one of the ComponentOne staff members via e-mail in 2 business days or less. Product Forums ComponentOne's product forums are available for users to share information, tips, and techniques regarding ComponentOne products. ComponentOne developers will be available on the forums to share insider tips and technique and answer users' questions. Please note that a ComponentOne User Account is required to participate in the ComponentOne Product Forums. Installation Issues Registered users can obtain help with problems installing ComponentOne products. Contact technical support by using the online incident submission form or by phone (412.681.4738). Please note that this does not include issues related to distributing a product to end-users in an application. Documentation Microsoft integrated ComponentOne documentation can be installed with each of our products, and documentation is also available online. If you have suggestions on how we can improve our documentation, please email the Documentation team. Please note that e-mail sent to the Documentation team is for documentation feedback only. Technical Support and Sales issues should be sent directly to their respective departments.

Note: You must create a ComponentOne Account and register your product with a valid serial number to obtain support using some of the above methods.

Redistributable Files

ComponentOne RichTextBox for Silverlight is developed and published by ComponentOne LLC. You may use it to develop applications in conjunction with Microsoft Visual Studio or any other programming environment that enables the user to use and integrate the control(s). You may also distribute, free of royalties, the following Redistributable Files with any such application you develop to the extent that they are used separately on a single CPU on the client/workstation side of the network: C1.Silverlight.dll C1.Silverlight.RichTextBox.dll C1.Silverlight.RichTextBox.LegacyHtmlFilter.dll C1.Silverlight.RichTextBox.PdfFilter.dll

6

C1.Silverlight.RichTextBox.RtfFilter.dll C1.Silverlight.RichTextBox.Toolbar.dll

Site licenses are available for groups of multiple developers. Please contact [email protected] for details.

About This Documentation

Acknowledgements Microsoft, Windows, Windows Vista, and Visual Studio, and Silverlight, are either registered trademarks or trademarks of Microsoft Corporation in the United States and/or other countries. Firefox is a registered trademark of the Mozilla Foundation. Safari is a trademark of Apple Inc., registered in the U.S. and other countries. Esri is a registered trademark of Environmental Systems Research Institute, Inc. (Esri) in the United States, the European Community, or certain other jurisdictions. ComponentOne If you have any suggestions or ideas for new features or controls, please call us or write: Corporate Headquarters ComponentOne LLC 201 South Highland Avenue 3rd Floor Pittsburgh, PA 15206 · USA 412.681.4343 412.681.4384 (Fax) http://www.componentone.com ComponentOne Doc-To-Help This documentation was produced using ComponentOne Doc-To-Help® Enterprise.

The C1.Silverlight.RichTextBox.dll Assembly

C1.Silverlight.RichTextBox.dll contains the C1RichTextBox control, a full-fledged editor with a documentbased architecture similar to the one used in WPF. Main Classes The following main classes are included in the C1.Silverlight.RichTextBox.dll assembly: C1RichTextBox: Control used to view and edit C1Document documents. The control can import and export HTML, and supports rich formatting including fonts, foreground and background colors, borders, paragraph alignment, images, hyperlinks, lists, arbitrary UIElement objects, and more. C1Document: Class that represents documents as a hierarchical list of elements that represent document components such as paragraphs, lists, images, and so on. The object model exposed by the C1Document object is similar to the one used in the WPF FlowDocument class and in the HTML DOM.

The C1.Silverlight.RichTextBox.Toolbar.dll Assembly

C1.Silverlight.RichTextBox.Toolbar.dll contains the C1RichTextBoxToolbar control, a toolbar that attaches to a C1RichTextBox control and provides common formatting commands. The toolbar is packaged in a separate DLL because many applications may choose to implement their own custom toolbars (or no toolbars at all) for the C1RichTextBox. These applications don't have to deploy the standard toolbar. Main Classes The following main classes are included in the C1.Silverlight.RichTextBox.Toolbar.dll assembly:

7

C1RichTextBoxToolbar: Toolbar control that attaches to a C1RichTextBox control and provides common formatting commands such as bold, italics, underline, font size, alignment, and so on.

The C1.Silverlight.RichTextBox.RtfFilter.dll Assembly

C1.Silverlight.RichTextBox.RtfFilter.dll contains the filter required to import/export Rich Text Format documents from/to the C1RichTextBox (C1Document). Main Classes The following main classes are included in the C1.Silverlight.RichTextBox.RtfFilter.dll assembly: RrfFilter: This class provides the methods: ConvertToDocument and ConvertFromDocument that can be used with any C1Document.

RichTextBox for Silverlight Samples

If you just installed ComponentOne Studio for Silverlight, open Visual Studio 2008 and load the Samples.sln solution located in the C:\Documents and Settings\<username>\My Documents\ComponentOne Samples\Studio for Silverlight or C:\Users\<username>\Documents\ComponentOne Samples\Studio for Silverlight folder. This solution contains all the samples that ship with this release. Each sample has a readme.txt file that describes it and two projects named as follows: <SampleName> <SampleName>Web Silverlight project (client-side project) ASP.NET project that hosts the Silverlight project (serverside project)

To run a sample, right-click the <SampleName>Web project in the Solution Explorer, select Set as Startup Project, and press F5. The following topics, organized by folder, describe each of the included samples.

C1.Silverlight.RichTextBox Samples

The following samples are installed in the C1.Silverlight.RichTextBox folder in the samples directory.

Annotations Sample

The Annotations sample is installed in the C1.Silverlight.RichTextBox\Annotations folder in the samples directory. This sample shows how to use the C1RichTextBox control in the C1.Silverlight.RichTextBox.dll assembly. The sample demonstrates adding notes and annotations to text in the C1RichTextBox control.

C1.Silverlight.RichTextBox.RtfFilter Sample

The C1.Silverlight.RichTextBox.RtfFilter sample is installed in the C1.Silverlight.RichTextBox\C1.Silverlight.RichTextBox.RtfFilter folder in the samples directory. This sample shows how to use the C1RichTextBox control in the C1.Silverlight.RichTextBox.dll assembly. The sample demonstrates the filter required to import/export Rich Text Format documents from/to the C1RichTextBox control. This sample project includes elements that are incorporated in other sample projects.

C1.Silverlight.RichTextBox.Toolbar Sample

The C1.Silverlight.RichTextBox.Toolbar sample is installed in the C1.Silverlight.RichTextBox\C1.Silverlight.RichTextBox.Toolbar folder in the samples directory.

8

This sample shows how to use the C1RichTextBox control in the C1.Silverlight.RichTextBox.dll assembly. The sample demonstrates a toolbar that attaches to a C1RichTextBox control and provides common formatting commands. This sample project includes elements that are incorporated in other sample projects.

C1RichTextBox_Localization Sample

The C1RichTextBox_Localization sample is installed in the C1.Silverlight.RichTextBox\C1RichTextBox_Localization folder in the samples directory. This sample shows how to use the C1RichTextBox control in the C1.Silverlight.RichTextBox.dll assembly and demonstrates how C1RichTextBox's toolbar is localized. This sample sets the current culture of the application to Spanish to show C1RichTextBox's toolbar localized. The toolbar ships localized inseveral languages, and new languages can be added by developers.

Formatting Sample

The Formatting sample is installed in the C1.Silverlight.RichTextBox\Formatting folder in the samples directory. This sample shows how to use the C1RichTextBox control in the C1.Silverlight.RichTextBox.dll assembly and demonstrates the different formatting options of the C1RichTextBox control. Shows most formatting options available in C1RichTextBox and how they can be used in XAML markup.

Hyperlinks Sample

The Hyperlinks sample is installed in the C1.Silverlight.RichTextBox\Hyperlinks folder in the samples directory. This sample shows how to use the C1RichTextBox control in the C1.Silverlight.RichTextBox.dll assembly and shows how to support hyperlinks in C1RichTextBox. The C1RichTextBox control parses hyperlinks defined in HTML ("a" tags). When the user clicks a link, C1RichTextBox fires a RequestNavigate event. The application can handle the click (by opening a new browser instance and navigating to the link for example), or it can ignore it. When the mouse hovers over a link, the C1RichTextBox also fires ElementMouseEnter and ElementMouseLeave events so the application can update the UI (for example telling users to click or control-click the link in order to follow it).

PdfExport Sample

The PdfExport sample is installed in the C1.Silverlight.RichTextBox\PdfExport folder in the samples directory. This sample shows how to use the C1RichTextBox control in the C1.Silverlight.RichTextBox.dll assembly and shows how to support a way to export the content of a C1RichTextBox control to a PDF. The export is done in the server and it requires the C1Pdf component.

Printing Sample

The Printing sample is installed in the C1.Silverlight.RichTextBox\PrintHtml folder in the samples directory. This sample shows how to print the content of a rich text box or a data grid. This sample shows how to print the content of a RichTextBox. It takes the HTML and shows a browser window with the preview and the printing dialog box. In the data grid case it builds the HTML using properties of the grid.

RichTextBoxSamples Sample

The RichTextBoxSamples sample is installed in the C1.Silverlight.RichTextBox\RichTextBoxSamples folder in the samples directory. This sample shows how to use the C1RichTextBox control in the C1.Silverlight.RichTextBox.dll assembly and samples of the rich text box control. This sample includes the following examples:

9

Spell checking HTML import /export RTF import /export

SyntaxHighlight Sample

The SyntaxHighlight sample is installed in the C1.Silverlight.RichTextBox\SyntaxHighlight folder in the samples directory. This sample shows how to use the C1RichTextBox control in the C1.Silverlight.RichTextBox.dll assembly and shows how to use C1RichTextBox to implement an editor with syntax highlighting. This sample demonstrates the StyleOverride feature of C1RichTextBox to implement a syntax highlighted editor with great performance. The StyleOverride feature allows easy and fast styling of sections of a document, without modifying it. Multiple layers of style overrides can be used to display different information, like syntax highlighting or spell checking.

ControlExplorer Sample

The ControlExplorer sample is installed in the ControlExplorer folder in the samples directory. This sample displays a tree with all C1.Silverlight controls and demonstrates them in action. The application has two panes. The left pane contains a tree that lists all controls in the C1.Silverlight library. Select a control on the tree and an instance appears on the right pane, along with a few properties that you can modify to see how they affect the control. The projects show all controls in the C1.Silverlight library, and shows how to use reflection to create controls and interact with them dynamically. The project is driven by an XML resource file that lists the controls that should be exposed by the sample. The DataGrid sample uses a data source that is a DataSet stored as a zip-compressed embedded resource.

Factories Sample

The Factories sample is installed in the Factories folder in the samples directory. This sample demonstrates how to use C1Maps to show production and distribution information from a manufacturer. There are three types of location marked in the map: factories, offices and stores. Each has a small icon providing related information, click on it to view an expanded version. Stores are only visible by zooming in near an office. The user can position new locations by dragging them from the top-right toolbar to the map.

Olympics Sample

The Olympics sample is installed in the Olympics folder in the samples directory. This sample allows you to check out the performance of any country in the Olympic Games. The sample was built during the 2008 Olympic Games in Beijing, and got a lot of traffic during the games. The sample used a Web service to retrieve the number of medals won by each country in real time, and then displayed that information in three different ways: map, chart, and grid.

QuickStart Sample

The Factories sample is installed in the QuickStart folder in the samples directory. This sample demonstrates how to instantiate and use the several of the controls in ComponentOne Studio for Silverlight.

SamplesCommon Sample

The SamplesCommon project is installed in the SamplesCommon\SamplesCommon folder in the samples directory. This sample project includes elements that are incorporated in other sample projects.

10

SilverTunes Sample

The SilverTunes sample is installed in the SilverTunes folder in the samples directory. This sample showcases a Silverlight implementation of an 'iTunes' like application. The sample loads artist, album, and song information from a database. It then shows the album covers in a carousel, with a rotating effect and reflection. The user can search by artist, album, and song. The sample includes a few MP3files so the user can play some of the songs. The MP3 files included in the sample are provided for demonstration purposes only and are truncated to protect the copyright owners.

StockPortfolio Sample

The StockPortfolio sample is installed in the StockPortfolio folder in the samples directory. This sample demonstrates a stock portfolio application. This sample was created for the ReMIX 07 in Boston, to demonstrate a business application in Silverlight. When it starts, the sample loads the stock portfolio from isolated storage (or creates a new one when run for the first time). Once the portfolio is loaded, the application retrieves real-time stock quotes using a web service and shows the portfolio information in a grid. The grid shows the personal portfolio information (stocks, quantities, price paid), real time stock information (last traded price, day high and low), and some calculated data (current market value, gain/loss). The user can add new stocks to the portfolio or remove existing ones. When the application exits, the current portfolio information is saved to isolated storage so it is available next time the application runs. The user can also see the historical data for companies in the portfolio. Double-clicking a symbol on the grid shows a composite chart with detailed information on the top and a zoom chart below. The user can slide and expand the zoom window in the bottom chart to see details on the top chart.

Templates Sample

The Templates sample is installed in the Templates folder in the samples directory. This sample shows how to use Data Templates to determine how data is displayed in controls. The sample creates a list of items and applies the same data template to two controls of different types (a ListBox and a C1ComboBox). See the Data Templates topic in the documentation for more information.

11

Introduction to Silverlight

The following topics detail information about getting started with Silverlight, including Silverlight resources, and general information about templates and deploying Silverlight files.

Silverlight Resources

This help file focuses on ComponentOne Studio for Silverlight. For general help on getting started with Silverlight, we recommend the following resources: http://www.silverlight.net The official Silverlight site, with many links to downloads, samples, tutorials, and more. http://silverlight.net/learn/tutorials.aspx Silverlight tutorials by Jesse Liberty. Topics covered include: Tutorial 1: Silverlight User Interface Controls Tutorial 2: Data Binding Tutorial 3: Displaying SQL Database Data in a DataGrid using LINQ and WCF Tutorial 4: User Controls Tutorial 5: Styles, Templates and Visual State Manager Tutorial 6: Expression Blend for Developers Tutorial 7: DataBinding & DataTemplates Using Expression Blend Tutorial 8: Multi-page Applications Tutorial 9: ADO.NET DataEntities and WCF Feeding a Silverlight DataGrid Tutorial 10: Hyper-Video

http://timheuer.com/blog/articles/getting-started-with-silverlight-development.aspx Silverlight tutorials by Tim Heuer. Topics covered include: Part 1: Really getting started ­ the tools you need and getting your first Hello World Part 2: Defining UI Layout ­ understanding layout and using Blend to help Part 3: Accessing data ­ how to get data from where Part 4: Binding the data ­ once you get the data, how can you use it? Part 5: Integrating additional controls ­ using controls that aren't a part of the core Part 6: Polishing the UI with styles and templates Part 7: Taking the application out-of-browser

http://weblogs.asp.net/scottgu/pages/silverlight-posts.aspx Scott Guthrie's Silverlight Tips, Tricks, Tutorials and Links Page. A useful resource, this page links to several tutorials and samples.

http://weblogs.asp.net/scottgu/archive/2008/02/22/first-look-at-silverlight-2.aspx An excellent eight-part tutorial by Scott Guthrie, covering the following topics:

13

Part 1: Creating "Hello World" with Silverlight 2 and VS 2008 Part 2: Using Layout Management Part 3: Using Networking to Retrieve Data and Populate a DataGrid Part 4: Using Style Elements to Better Encapsulate Look and Feel Part 5: Using the ListBox and DataBinding to Display List Data Part 6: Using User Controls to Implement Master/Details Scenarios Part 7: Using Templates to Customize Control Look and Feel Part 8: Creating a Digg Desktop Version of our Application using WPF

http://blogs.msdn.com/corrinab/archive/2008/03/11/silverlight-2-control-skins.aspx A practical discussion of skinning Silverlight controls and applications by Corrina Barber.

Creating a New Silverlight Project

The following topic details how to create a new Silverlight project in Microsoft Visual Studio 2008 and in Microsoft Expression Blend 3. In Visual Studio 2008 Complete the following steps to create a new Silverlight project in Microsoft Visual Studio 2008: 1. 2. 3. Select File | New | Project to open the New Project dialog box in Visual Studio 2008. In the Project types pane, expand either the Visual Basic or Visual C# node and select Silverlight. Choose Silverlight Application in the Templates pane.

4.

Name the project, specify a location for the project, and click OK.

14

Next, Visual Studio will prompt you for the type of hosting you want to use for the new project. 5. In the NewSilverlight Application dialog box, select OK to accept the default name and options and to create the project.

In Expression Blend 4 Complete the following steps to create a new Silverlight project in Microsoft Expression Blend 4: 1. 2. 3. 4. Select File | New Project to open the New Project dialog box in Blend 4. In the Project types pane, click the Silverlight node. In the right pane, choose Silverlight Application + Website in the Templates pane to create a project with an associated Web site. Name the project, specify a location for the project, choose a language (Visual C# or Visual Basic), and click OK.

15

Your new project will be created. The Project The solution you just created will contain two projects, YourProject and YourProject.Web: YourProject: This is the Silverlight application proper. It will produce a XAP file that gets downloaded to the client and runs inside the Silverlight plug-in. YourProject.Web: This is the host application. It runs on the server and provides support for the Silverlight application.

16

Theming

One of the main advantages to using Silverlight is the ability to change the style or template of any control. Controls are "lookless" with fully customizable user interfaces and the ability to use built-in and custom themes. Themes allow you to customize the appearance of controls and take advantage of Silverlight's XAML-based styling. The following topics introduce you to styling Silverlight controls with themes. You can customize WPF and Microsoft Silverlight controls by creating and modifying control templates and styles. This results in a unique and consistent look for your application. Templates and styles define the pieces that make up a control and the default behavior of the control, respectively. You can create templates and styles by making copies of the original styles and templates for a control. Modifying templates and styles is an easy way to essentially make new controls in Design view of Microsoft Expression Blend, without having to use code. The following topics provide a detailed comparison of styles and templates to help you decide whether you want to modify the style or template of a control, or both. The topics also discuss the built-in themes available in ComponentOne Studio for Silverlight.

Available Themes

ComponentOne Studio for Silverlight includes several theming options, and several built-in Silverlight Toolkit themes including: BureauBlack Cosmopolitan ExpressionDark ExpressionLight RainierOrange ShinyBlue WhistlerBlue

Each of these themes is based on themes in the Silverlight Toolkit and installed in its own assembly in the Studio for Silverlight installation directory. The following topics detail each built-in theme.

BureauBlack

The BureauBlack theme is a dark colored theme similar to the Microsoft Bureau Black theme included in the Silverlight Toolkit. The BureauBlack theme appears similar to the following when applied to the ComponentOne Studio for Silverlight charting controls:

17

Cosmopolitan

The Cosmopolitan theme is a modern, clean UI theme based on the Microsoft Cosmopolitan theme, which is included in the Silverlight Toolkit. For example, the theme appears similar to the following when applied to the ComponentOne Studio for Silverlight charting controls:

18

ExpressionDark

The ExpressionDark theme is a grayscale theme based on the Microsoft Expression Dark theme, which is included in the Silverlight Toolkit. For example, the theme appears similar to the following when applied to the ComponentOne Studio for Silverlight charting controls:

ExpressionLight

The ExpressionLight theme is a grayscale theme based on the Microsoft Expression Light theme, which is included in the Silverlight Toolkit. For example, the theme appears similar to the following when applied to the ComponentOne Studio for Silverlight charting controls:

19

RainierOrange

The RainerOrange theme is an orange-based theme similar to the Microsoft Rainer Orange theme, which is included in the Silverlight Toolkit. The RainerOrange theme appears similar to the following when applied to the ComponentOne Studio for Silverlight charting controls:

20

ShinyBlue

The ShinyBlue theme is a blue-based theme similar to the Microsoft Shiny Blue theme included in the Silverlight Toolkit. The ShinyBlue theme appears similar to the following when applied to the ComponentOne Studio for Silverlight charting controls:

WhistlerBlue

The WhistlerBlue theme is a blue-based theme similar to the Microsoft Whistler Blue theme, which is included in the Silverlight Toolkit. The WhistlerBlue theme appears similar to the following when applied to the ComponentOne Studio for Silverlight charting controls:

21

Custom Themes

In addition to using one of the built-in themes, you can create your own custom theme from scratch or create a custom theme based on an existing built-in theme. See Included XAML Files (page 22) for the included files that you can base a theme on.

Included XAML Files

Several auxiliary XAML elements are installed with ComponentOne Studio for Silverlight. These elements include templates and themes and are located in the Studio for Silverlight installation directory. You can incorporate these elements into your project to, for example, create your own theme based on the included themes. By default, these files are located in the generics.zip file in the C:\Program Files\ComponentOne\Studio for Silverlight\Help folder. Unzip the generics.zip file to a folder to see all the XAML files associated with Studio for Silverlight controls. In the following topics the included files are listed by assembly with their location folder within the generics.zip file noted. Silverlight 4.0, Silverlight 5.0, and Windows Phone XAML files are named differently. For example, the same version of the generic.xaml file would follow the following naming conventions:

Platform Silverlight 4.0 Silverlight 5.0 Windows Phone Name generic.xaml generic_SL5rd.xaml generic.Phone.xaml

The following topics list the Silverlight 4.0 file names, simply add "_SL5rd" or ".Phone" to the file name for the Silverlight 5.0 and Windows Phone files respectively.

22

C1.Silverlight

The following XAML files can be used to customize items in the C1.Silverlight assembly:

Element generic.xaml Common.xaml C1Button.xaml C1ComboBox.xaml C1DateTimePicker.xaml C1DropDown.xaml C1FilePicker.xaml C1HeaderedContentContro l.xaml C1LayoutTransformer.xam l C1LoopingList.xaml C1Menu.xaml C1NumericBox.xaml C1ProgressBar.xaml C1RangeSlider.xaml C1ScrollBar.xaml C1ScrollViewer.xaml C1Separator.xaml C1TabControl.xaml C1TextBoxBase.xaml C1TextEditableContentCon trol.xaml C1ToggleSwitch.xaml C1TreeView.xaml C1ValidationDecorator.xa ml C1Window.xaml Folder C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes C1.Silverlight\themes Description Specifies the templates for different styles and the initial style of the controls. Specifies attributes for common elements in the controls. Specifies attributes for C1Button. Specifies attributes for C1ComboBox. Specifies attributes for C1DateTimePicker. Specifies attributes for C1DropDown. Specifies attributes for C1FilePicker. Specifies attributes for C1HeaderedContentControl. Specifies attributes for C1LayoutTransformer. Specifies attributes for C1LoopingList. Specifies attributes for C1Menu. Specifies attributes for C1NumericBox. Specifies attributes for C1ProgressBar. Specifies attributes for C1RangeSlider. Specifies attributes for C1ScrollBar. Specifies attributes for C1ScrollViewer. Specifies attributes for C1Separator. Specifies attributes for C1TabControl. Specifies attributes for C1TextBoxBase. Specifies attributes for C1TextEditableContentControl. Specifies attributes for C1ToggleSwitch. Specifies attributes for C1TreeView. Specifies attributes for C1ValidationDecorator. Specifies attributes for C1Window.

C1.Silverlight.Chart

The following XAML files can be used to customize items in the C1.Silverlight.Chart assembly:

Element generic.xaml DuskBlue.xaml Folder C1.Silverlight.Chart\t hemes C1.Silverlight.Chart\T hemesSL Description Specifies the templates for different styles and the initial style of the chart. Specifies the attributes for the DuskBlue theme.

23

DuskGreen.xaml MediaPlayer.xaml Office2003Blue.xaml Office2003Classic.xaml Office2003Olive.xaml Office2003Royale.xaml Office2003Silver.xaml Office2007Black.xaml Office2007Blue.xaml Office2007Silver.xaml Vista.xaml generic.xaml

C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\T hemesSL C1.Silverlight.Chart\P hone\themes

Specifies the attributes for the DuskGreen theme. Specifies the attributes for the MediaPlayer theme. Specifies the attributes for the Office2003Blue theme. Specifies the attributes for the Office2003Classic theme. Specifies the attributes for the Office2003Olive theme. Specifies the attributes for the Office2003Royale theme. Specifies the attributes for the Office2003Silver theme. Specifies the attributes for the Office2007Black theme. Specifies the attributes for the Office2007Blue theme. Specifies the attributes for the Office2007Silver theme. Specifies the attributes for the Vista theme. Specifies the templates for the Metro theme for the controls.

C1.Silverlight.Chart.Editor

The following XAML files can be used to customize items in the C1.Silverlight.Chart.Editor assembly:

Element AxisEditor.xaml ChartEditor.xaml DataLabelEditor.xaml LegendEditor.xaml DashesEditor.xaml PropertyEditor.xaml Folder C1.Silverlight.Chart.E ditor C1.Silverlight.Chart.E ditor C1.Silverlight.Chart.E ditor C1.Silverlight.Chart.E ditor C1.Silverlight.Chart.E ditor\AuxControls C1.Silverlight.Chart.E ditor\PropertyEditors Description Specifies the attributes for the Axis Editor. Specifies the attributes for the Chart Editor. Specifies the attributes for the Data Label Editor. Specifies the attributes for the Legend Editor. Specifies the attributes for the Dashes Editor. Specifies the attributes for the Property Editor.

C1.Silverlight.Chart3D

The following XAML files can be used to customize items in the C1.Silverlight.Chart3D assembly:

Element generic.xaml Folder C1.Silverlight.Chart3 Description Specifies the templates for different styles and

24

D\themes

the initial style of the chart.

C1.Silverlight.DataGrid

The following XAML file can be used to customize items in the C1.Silverlight.DataGrid assembly:

Element generic.xaml Common.xaml DataGridCellPresenter.xa ml DataGridColumnHeaderPre senter.xaml DataGridDetailsPresenter. xaml DataGridDragNDrop.xaml DataGridFilter.xaml DataGridGroupingPresente r.xaml DataGridRowHeaderPresen ter.xaml DataGridRowPresenter.xa ml DataGridVerticalFreezingS eparatorPresenter.xaml Folder C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes C1.Silverlight.DataGri d\themes Description Specifies the templates for different styles and the initial style of the controls. Specifies attributes for common elements in the controls. Specifies attributes for common elements in the controls. Specifies attributes for the column header presenter. Specifies attributes for the data details presenter. Specifies attributes for grid drag-and-drop operation. Specifies attributes for the grid's filtering. Specifies attributes for the grouping presenter. Specifies attributes for the row header presenter. Specifies attributes for the row presenter. Specifies attributes for the freezing separator presenter.

C1.Silverlight.DataGrid.Filters

The following XAML file can be used to customize items in the C1.Silverlight.DataGrid.Filters assembly:

Element generic.xaml Folder C1.Silverlight.DataGri d.Filters\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.DataGrid.Ria

The following XAML file can be used to customize items in the C1.Silverlight.DataGrid.Ria assembly:

Element generic.xaml Folder C1.Silverlight.DataGri d.Ria\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.DataGrid.Summaries

The following XAML file can be used to customize items in the C1.Silverlight.DataGrid.Summaries assembly:

25

Element generic.xaml

Folder C1.Silverlight.DataGri d.Summaries\themes

Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.DateTimeEditors

The following XAML file can be used to customize items in the C1.Silverlight.DateTimeEditors assembly:

Element generic.xaml Folder C1.Silverlight.DateTi meEditors\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.Docking

The following XAML file can be used to customize items in the C1.Silverlight.Docking assembly:

Element generic.xaml Folder C1.Silverlight.Dockin g\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.Extended

The following XAML file can be used to customize items in the C1.Silverlight.Extended assembly:

Element generic.xaml C1Accordion.xaml C1Book.xaml C1ColorPicker.xaml C1CoverFlow.xaml C1Expander.xaml C1PropertyGrid.xaml C1Reflector.xaml generic.xaml C1Accordion.xaml C1Book.xaml C1ColorPicker.xaml Folder C1.Silverlight.Extend ed\themes C1.Silverlight.Extend ed\themes C1.Silverlight.Extend ed\themes C1.Silverlight.Extend ed\themes C1.Silverlight.Extend ed\themes C1.Silverlight.Extend ed\themes C1.Silverlight.Extend ed\themes C1.Silverlight.Extend ed\themes C1.Silverlight.Extend ed\Phone\Themes C1.Silverlight.Extend ed\Phone\Themes C1.Silverlight.Extend ed\Phone\Themes C1.Silverlight.Extend ed\Phone\Themes Description Specifies the templates for different styles and the initial style of the controls. Specifies attributes for C1Accordion. Specifies attributes for C1Book. Specifies attributes for C1ColorPicker. Specifies attributes for C1CoverFlow. Specifies attributes for C1Expander. Specifies attributes for C1PropertyGrid. Specifies attributes for C1Reflector. Specifies the templates for the Metro theme of the controls. Specifies attributes for the Metro theme for C1Accordion. Specifies attributes for the Metro theme for C1Book. Specifies attributes for the Metro theme for C1ColorPicker.

26

C1CoverFlow.xaml C1Expander.xaml C1PropertyGrid.xaml C1Reflector.xaml

C1.Silverlight.Extend ed\Phone\Themes C1.Silverlight.Extend ed\Phone\Themes C1.Silverlight.Extend ed\Phone\Themes C1.Silverlight.Extend ed\Phone\Themes

Specifies attributes for the Metro theme for C1CoverFlow. Specifies attributes for the Metro theme for C1Expander. Specifies attributes for the Metro theme for C1PropertyGrid. Specifies attributes for the Metro theme for C1Reflector.

C1.Silverlight.FlexGrid

The following XAML file can be used to customize items in the C1.Silverlight.FlexGrid assembly:

Element generic.xaml Folder C1.Silverlight.FlexGri d\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.FlexGrid.Filter

The following XAML file can be used to customize items in the C1.Silverlight.FlexGrid.Filter assembly:

Element generic.xaml Folder C1.Silverlight.FlexGri d.Filter\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.Gauge

The following XAML file can be used to customize items in the C1.Silverlight.Gauge assembly:

Element generic.xaml Folder C1.Silverlight.Gauge\ themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.Imaging

The following XAML file can be used to customize items in the C1.Silverlight.Imaging assembly:

Element generic.xaml Folder C1.Silverlight.Imagin g\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.Legacy

The following XAML file can be used to customize items in the C1.Silverlight.Legacy assembly:

Element generic.xaml Folder C1.Silverlight.Legacy \themes Description Specifies the templates for different styles and the initial style of the controls.

27

C1.Silverlight.Maps

The following XAML file can be used to customize items in the C1.Silverlight.Maps assembly:

Element generic.xaml ZoomScrollBar.xaml Folder C1.Silverlight.Maps\t hemes C1.Silverlight.Maps\t hemes Description Specifies the templates for different styles and the initial style of the controls. Specifies attributes for the zoom scroll bar.

C1.Silverlight.MediaPlayer

The following XAML file can be used to customize items in the C1.Silverlight.MediaPlayer assembly:

Element generic.xaml Folder C1.Silverlight.MediaPl ayer\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.OrgChart

The following XAML files can be used to customize items in the C1.Silverlight.OrgChart assembly:

Element generic.xaml Folder C1.Silverlight.OrgCha rt\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.OutlookBar

The following XAML files can be used to customize items in the C1.Silverlight.OutlookBar assembly:

Element generic.xaml OutlookBar2007.xaml OutlookBar2007Black.xam l OutlookBar2007Silver.xam l OutlookBar2010.xaml OutlookBar2010Black.xam l OutlookBar2010Silver.xam l Folder C1.Silverlight.Outlook Bar\themes C1.Silverlight.Outlook Bar\themes C1.Silverlight.Outlook Bar\themes C1.Silverlight.Outlook Bar\themes C1.Silverlight.Outlook Bar\themes C1.Silverlight.Outlook Bar\themes C1.Silverlight.Outlook Bar\themes Description Specifies the templates for different styles and the initial style of the controls. Specifies the templates for different styles and the initial style of the controls. Specifies the templates for different styles and the initial style of the controls. Specifies the templates for different styles and the initial style of the controls. Specifies the templates for different styles and the initial style of the controls. Specifies the templates for different styles and the initial style of the controls. Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.PdfViewer

The following XAML file can be used to customize items in the C1.Silverlight.PdfViewer assembly:

28

Element generic.xaml

Folder C1.Silverlight.PdfVie wer\themes

Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.ReportViewer

The following XAML file can be used to customize items in the C1.Silverlight.ReportViewer assembly:

Element generic.xaml Folder C1.Silverlight.Report Viewer\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.RichTextBox

The following XAML file can be used to customize items in the C1.Silverlight.RichTextBox assembly:

Element generic.xaml Folder C1.Silverlight.RichTe xtBox\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.RichTextBox.Toolbar

The following XAML file can be used to customize items in the C1.Silverlight.RichTextBox.Toolbar assembly:

Element generic.xaml Folder C1.Silverlight.RichTe xtBox.Toolbar\theme s Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.Schedule

The following XAML files can be used to customize items in the C1.Silverlight.Schedule assembly:

Element EditAppointmentControl.Sil verlight.xaml EditCollectionControl.xaml EditRecurrenceControl.Silv erlight.xaml RecChoiceControl.Silverlig ht.xaml SelectFromListScene.Silve rlight.xaml SelectFromListScene.WPF. xaml ShowRemindersControl.Sil verlight.xaml Folder C1.Silverlight.Schedu le\Dialogs C1.Silverlight.Schedu le\Dialogs C1.Silverlight.Schedu le\Dialogs C1.Silverlight.Schedu le\Dialogs C1.Silverlight.Schedu le\Dialogs C1.Silverlight.Schedu le\Dialogs C1.Silverlight.Schedu le\Dialogs Description Specifies the attributes for editing appointments. Specifies the attributes for editing collections. Specifies the attributes for editing appointment recurrence. Specifies the attributes for choosing recurrence. Specifies the attributes for resources from lists.

Specifies the attributes for resources from lists.

Specifies the attributes for schedule reminders.

29

generic.xaml Auxiliary.xaml C1Calendar.xaml C1SchedulerParts.xaml Common.xaml generic.xaml IntervalAppointmentPrese nter.xaml

C1.Silverlight.Schedu le\Dialogs C1.Silverlight.Schedu le\themes C1.Silverlight.Schedu le\themes C1.Silverlight.Schedu le\themes C1.Silverlight.Schedu le\themes C1.Silverlight.Schedu le\themes C1.Silverlight.Schedu le\themes

Specifies the templates for different styles and the initial style of the controls. Specifies attributes for auxiliary elements of the control. Specifies attributes for the C1Calendar. Specifies attributes for parts of the scheduler. Specifies attributes for common elements of the scheduler. Specifies the templates for different styles and the initial style of the controls. Specifies attributes for the interval appointmnet presenter.

C1.Silverlight.SpellChecker

The following XAML file can be used to customize items in the C1.Silverlight.SpellChecker assembly:

Element C1SpellDialog.xaml Folder C1.Silverlight.SpellCh ecker Description Specifies the attributes for the Spell Checker Dialog Box.

C1.Silverlight.Theming.BureauBlack

The following XAML files can be used to customize items in the C1.Silverlight.BureauBlack assembly:

Element BureauBlack.xaml System.Windows.Controls. Theming.BureauBlack.xam l Theme.xaml Folder C1.Silverlight.Themin g.BureauBlack C1.Silverlight.Themin g.BureauBlack C1.Silverlight.Themin g.BureauBlack Description Specifies resources and styling elements for each ComponentOne Silverlight control. Specifies the standard Microsoft BureauBlack resources and styling elements. Specifies the standard resources and styling elements.

C1.Silverlight.Theming.Cosmopolitan

The following XAML files can be used to customize items in the C1.Silverlight.Cosmopolitan assembly:

Element Cosmopolitan.xaml/Cosmo politan_SL5rd.xaml Merged.xaml Theme.xaml/Theme_SL5r d.xaml Folder C1.Silverlight.Themin g.Cosmopolitan C1.Silverlight.Themin g.Cosmopolitan C1.Silverlight.Themin g.Cosmopolitan Description Specifies resources and styling elements for each ComponentOne Silverlight control. Specifies the resources for each ComponentOne WPF control. Specifies the standard resources and styling elements.

30

C1.Silverlight.Theming.ExpressionDark

The following XAML files can be used to customize items in the C1.Silverlight.ExpressionDark assembly:

Element ExpressionDark.xaml System.Windows.Controls. Theming.ExpressionDark.x aml Theme.xaml Folder C1.Silverlight.Themin g.ExpressionDark C1.Silverlight.Themin g.ExpressionDark C1.Silverlight.Themin g.ExpressionDark Description Specifies resources and styling elements for each ComponentOne Silverlight control. Specifies the standard Microsoft ExpressionDark resources and styling elements. Specifies the standard resources and styling elements.

C1.Silverlight.Theming.ExpressionLight

The following XAML files can be used to customize items in the C1.Silverlight.ExpressionLight assembly:

Element ExpressionLight.xaml System.Windows.Controls. Theming.ExpressionLight.x aml Theme.xaml Folder C1.Silverlight.Themin g.ExpressionLight C1.Silverlight.Themin g.ExpressionLight C1.Silverlight.Themin g.ExpressionLight Description Specifies resources and styling elements for each ComponentOne Silverlight control. Specifies the standard Microsoft ExpressionLight resources and styling elements. Specifies the standard resources and styling elements.

C1.Silverlight.Theming.Office2007

The following XAML files can be used to customize items in the C1.Silverlight.Office2007 assembly:

Element Office2007.xaml Office2007Black.xaml Office2007Silver.xaml Theme.xaml Folder C1.Silverlight.Themin g.Office2007 C1.Silverlight.Themin g.Office2007 C1.Silverlight.Themin g.Office2007 C1.Silverlight.Themin g.Office2007 Description Specifies the standard resources and styling elements. Specifies the standard resources and styling elements. Specifies the standard resources and styling elements. Specifies the standard resources and styling elements.

C1.Silverlight.Theming.Office2010

The following XAML files can be used to customize items in the C1.Silverlight.Office2010 assembly:

Element Office2010.xaml Office2010Black.xaml Office2010Silver.xaml Folder C1.Silverlight.Themin g.Office2010 C1.Silverlight.Themin g.Office2010 C1.Silverlight.Themin Description Specifies the standard resources and styling elements. Specifies the standard resources and styling elements. Specifies the standard resources and styling

31

g.Office2010 Theme.xaml C1.Silverlight.Themin g.Office2010

elements. Specifies the standard resources and styling elements.

C1.Silverlight.Theming.RainierOrange

The following XAML files can be used to customize items in the C1.Silverlight.RainierOrange assembly:

Element RainierOrange.xaml Theme.xaml Folder C1.Silverlight.Themin g.RainierOrange C1.Silverlight.Themin g.RainierOrange Description Specifies resources and styling elements for each ComponentOne Silverlight control. Specifies the standard resources and styling elements.

C1.Silverlight.Theming.ShinyBlue

The following XAML files can be used to customize items in the C1.Silverlight.ShinyBlue assembly:

Element ShinyBlue.xaml Theme.xaml Folder C1.Silverlight.Themin g.ShinyBlue C1.Silverlight.Themin g.ShinyBlue Description Specifies resources and styling elements for each ComponentOne Silverlight control. Specifies the standard resources and styling elements.

C1.Silverlight.Theming.WhistlerBlue

The following XAML files can be used to customize items in the C1.Silverlight.WhistlerBlue assembly:

Element WhistlerBlue.xaml Theme.xaml Folder C1.Silverlight.Themin g.WhistlerBlue C1.Silverlight.Themin g.WhistlerBlue Description Specifies resources and styling elements for each ComponentOne Silverlight control. Specifies the standard resources and styling elements.

C1.Silverlight.TileView

The following XAML files can be used to customize items in the C1.Silverlight.TileView assembly:

Element generic.xaml Folder C1.Silverlight.TileVie w\themes Description Specifies the templates for different styles and the initial style of the controls.

C1.Silverlight.Toolbar

The following XAML files can be used to customize items in the C1.Silverlight.Toolbar assembly:

Element generic.xaml Folder C1.Silverlight.Toolbar \themes Description Specifies the templates for different styles and the initial style of the controls.

32

C1ToolbarTab.xaml

C1.Silverlight.Toolbar \themes

Specifies the attributes for the C1ToolbarTab.

Implicit and Explicit Styles

The following topic detail using implicit and explicit styles and using the ImplicitStyleManager which is included in the Silverlight Toolkit. For more information about the Silverlight Toolkit, see CodePlex.

Implicit Styles

If you're familiar with WPF (Windows Presentation Foundation) you may be used to setting styles implicitly so the application has a uniform appearance ­ for example, you're used to setting the style for all instances of a particular control in the application's resources. Unfortunately Silverlight does not support implicit styles in the same way that WPF does and you would normally have to indicate the style to use in each instance of the control. This can be tedious to do if you have several controls on a page and that's where the ImplicitStyleManager comes in handy. The ImplicitStyleManager class is located in the Microsoft.Windows.Controls.Theming namespace (in the Microsoft.Windows.Controls assembly).

WPF and Silverlight Styling

In WPF, you can set styles implicitly. When you set styles implicitly all instances of a particular type can be styled at once. For example, the WPF C1DropDown control might be styled with the following markup: <Grid> <Grid.Resources> <Style TargetType="{x:Type c1:C1DropDown}"> <Setter Property="Background" Value="Red" /> </Style> </Grid.Resources> <c1:C1DropDown Height="30" HorizontalAlignment="Center" Name="C1DropDown1" VerticalAlignment="Center" Width="100" /> </Grid> This would set the background of the control to be the color red as in the following image:

All C1DropDown controls in the grid would also appear red; C1DropDown controls outside of the Grid would not appear red. This is what is meant by implicit styles ­ the style is assigned to all controls of a particular type. Inherited controls would also inherit the style. Silverlight, however, does not support implicit styles. In Silverlight you could add the style to the Grid's resources similarly: <Grid.Resources> <Style x:Key="DropDownStyle" TargetType="c1:C1DropDown"> <Setter Property="Background" Value="Red" /> </Style> </Grid.Resources>

33

But the Silverlight C1DropDown control would not be styled unless the style was explicitly set, as in the following example: <c1:C1DropDown Height="30" HorizontalAlignment="Center" Name="C1DropDown1" VerticalAlignment="Center" Width="100" Style="{StaticResource DropDownStyle}"/> While this is easy enough to set on one control, if you have several controls it can be tedious to set the style on each one. That's where the ImplicitStyleManager comes in. See Using the ImplicitStyleManager (page 34) for more information.

Using the ImplicitStyleManager

The ImplicitStyleManager lets you set styles implicitly in Silverlight as you might in WPF. You can find the ImplicitStyleManger in the System.Windows.Controls.Theming.Toolkit.dll assembly installed with the Silverlight Toolkit. To use the ImplicitStyleManager add a reference in your project to the System.Windows.Controls.Theming.Toolkit.dll assembly and add its namespace to the initial UserControl tag as in the following markup: <UserControl xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:c1="clrnamespace:C1.Silverlight;assembly=C1.Silverlight" xmlns:theming="clrnamespace:System.Windows.Controls.Theming;assembly=System.Windows.Controls.Th eming.Toolkit" x:Class="C1Theming.MainPage" Width="640" Height="480"> Once you've added the reference and namespace you can use the ImplicitStyleManager in your application. For example, in the following markup a style is added and implicitly implemented: <Grid x:Name="LayoutRoot" Background="White" theming:ImplicitStyleManager.ApplyMode="OneTime"> <Grid.Resources> <Style TargetType="c1:C1DropDown"> <Setter Property="Background" Value="Red" /> </Style> </Grid.Resources> <StackPanel HorizontalAlignment="Center" VerticalAlignment="Center"> <c1:C1DropDown Margin="5" Content="C1DropDown" Height="30" Width="100"/> </StackPanel> </Grid>

Applying Themes to Controls

You can easily customize your application, by applying one of the built-in themes to your ComponentOne Silverlight control. Each of the built-in themes is based on a Silverlight Toolkit theme. For information about each of the built-in themes, see Available Themes (page 17). In this example, you'll add the RainierOrange theme to the C1DropDown control on a page. To apply the theme, complete the following steps: 1. In Visual Studio, select File | New Project.

34

2. 3.

In the New Project dialog box, select the language in the left pane and in the right-pane select Silverlight Application. Enter a Name and Location for your project and click OK. In the New Silverlight Application dialog box, leave the default settings and click OK. A new application will be created and should open with the MainPage.xaml file displayed in XAML view.

4. 5.

Place the mouse cursor between the <Grid> and </Grid> tags in XAML view. You will add the theme and control to the Grid in the next steps. Navigate to the Visual Studio Toolbox and double-click on the C1ThemeRanierOrange icon to declare the theme. The theme's namespace will be added to the page and the theme's tags will be added to the Grid in XAML view. The markup will appear similar to the following: <UserControl xmlns:my="clrnamespace:C1.Silverlight.Theming.RainierOrange;assembly=C1.Silverlight. Theming.RainierOrange" x:Class="C1Silverlight.MainPage" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d" d:DesignWidth="640" d:DesignHeight="480"> <Grid x:Name="LayoutRoot"> <my:C1ThemeRainierOrange></my:C1ThemeRainierOrange> </Grid> </UserControl> Any controls that you add within the theme's tags will now be themed. Place your cursor between the <my:C1ThemeRanierOrange> and </my:C1ThemeRanierOrange> tags. In the Toolbox, double-click the C1DropDown icon to add the control to the project. The C1.Silverlight namespace will be added to the page and the control's tags will be added within the theme's tags in XAML view. The markup will appear similar to the following: <UserControl xmlns:c1="clrnamespace:C1.Silverlight;assembly=C1.Silverlight" xmlns:my="clrnamespace:C1.Silverlight.Theming.RainierOrange;assembly=C1.Silverlight. Theming.RainierOrange" x:Class="C1Silverlight.MainPage" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d" d:DesignWidth="640" d:DesignHeight="480"> <Grid x:Name="LayoutRoot"> <my:C1ThemeRainierOrange> <c1:C1DropDown Width="100" Height="30"></c1:C1DropDown> </my:C1ThemeRainierOrange> </Grid> </UserControl>

6. 7.

What You've Accomplished Run your project and observe that the C1DropDown control now appears in the RainierOrange theme. Note that you can only set the Content property on the theme once, so to theme multiple controls using this method you will need to add a panel, for example a Grid or StackPanel, within the theme and then add multiple controls within the panel.

35

You can also use the ImplicitStyleManager to theme all controls of a particular type. For more information, see Using the ImplicitStyleManager (page 34).

Applying Themes to an Application

The following topic details one method of applying a theme application-wide in Visual Studio. In this topic you'll add a class to your application that initializes a built-in theme. You'll then apply the theme to the MainPage of your application. To apply the theme, complete the following steps: 1. 2. 3. In Visual Studio, select File | New Project. In the New Project dialog box, select the language in the left pane and in the right-pane select Silverlight Application. Enter a Name and Location for your project and click OK. In the New Silverlight Application dialog box, leave the default settings and click OK. A new application will be created and should open with the MainPage.xaml file displayed in XAML view. 4. 5. 6. 7. 8. In the Solution Explorer, right-click the project and choose Add Reference. In the Add Reference dialog box choose the C1.Silverlight.Theming and C1.Silverlight.Theming.RainierOrange assemblies and click OK. In the Solution Explorer, right-click the project and select Add | New Item. In the Add New Item dialog box, choose Class from the templates list, name the class "MyThemes", and click the Add button to create and a new class. The newly created MyThemes class will open. Add the following import statements to the top of the class: Visual Basic Imports C1.Silverlight.Theming Imports C1.Silverlight.Theming.RainierOrange C# using C1.Silverlight.Theming; using C1.Silverlight.RainierOrange; Visual Basic Public Class MyThemes Private _myTheme As C1Theme = Nothing Public ReadOnly Property MyTheme() As C1Theme Get If _myTheme Is Nothing Then _myTheme = New C1ThemeRainierOrange() End If Return _myTheme End Get End Property End Class C# public class MyThemes { private static C1Theme _myTheme = null; public static C1Theme MyTheme { get

9.

Add code to the class so it appears like the following:

36

{ if (_myTheme == null) _myTheme = new C1ThemeRainierOrange(); return _myTheme; } } } 10. In the Solution Explorer, double-click the App.xaml.vb or App.xaml.cs file. 11. Add the following import statement to the top of the file, where ProjectName is the name of your application: Visual Basic Imports ProjectName C# using ProjectName;

12. Add code to the Application_Startup event of the App.xaml.vb or App.xaml.cs file so it appears like the following: Visual Basic Private Sub Application_Startup(ByVal o As Object, ByVal e As StartupEventArgs) Handles Me.Startup Dim MyMainPage As New MainPage() Dim themes As New MyThemes themes.MyTheme.Apply(MyMainPage) Me.RootVisual = MyMainPage End Sub C# private void Application_Startup(object sender, StartupEventArgs e) { MainPage MyMainPage = new MainPage(); MyThemes.MyTheme.Apply(MyMainPage); this.RootVisual = MyMainPage; }

Now any control you add to the MainPage.xaml file will automatically be themed. 13. Return to the MainPage.xaml file and place the mouse cursor between the <Grid> and </Grid> tags in XAML view. 14. In the Toolbox, double-click the C1DropDown icon to add the control to the project. 15. Update the control's markup so it appears like the following: <c1:C1DropDown Width="100" Height="30"></c1:C1DropDown> What You've Accomplished Run your project and observe that the C1DropDown control now appears in the RainierOrange theme. To change the theme chosen, now all you would need to do is change the theme in the MyThemes class. For example, to change to the ExpressionDark theme: 1. 2. Add a reference to the C1.Theming.Silverlight.ExpressionDark.dll assembly. Open the MyThemes class in your project and add the following import statements to the top of the class: Visual Basic Imports C1.Silverlight.Theming.ExpressionDark C#

37

using C1.Silverlight.Theming.ExpressionDark; 3. Update code in the class so it appears like the following: Visual Basic Public Class MyThemes Private _myTheme As C1Theme = Nothing Public ReadOnly Property MyTheme() As C1Theme Get If _myTheme Is Nothing Then _myTheme = New C1ThemeExpressionDark() End If Return _myTheme End Get End Property End Class C# public class MyThemes { private static C1Theme _myTheme = null; public static C1Theme MyTheme { get { if (_myTheme == null) _myTheme = new C1ThemeExpressionDark(); return _myTheme; } } }

Note that the above steps apply the theme to the MainPage.xaml file. To apply the theme to additional pages, you would need to add the following code to each page: Visual Basic Dim themes As New MyThemes themes.MyTheme.Apply(MyMainPage) C# MyThemes.MyTheme.Apply(LayoutRoot);

The theme will then be applied to the page. So, you only have to change one line of code to the class to change the theme, and you only have to add one line of code to each page to apply the theme.

ComponentOne ClearStyle Technology

ComponentOne ClearStyleTM technology is a new, quick and easy approach to providing Silverlight and WPF control styling. ClearStyle allows you to create a custom style for a control without having to deal with the hassle of XAML templates and style resources. Currently, to add a theme to all standard Silverlight controls, you must create a style resource template. In Microsoft Visual Studio this process can be difficult; this is why Microsoft introduced Expression Blend to make the task a bit easier. Having to jump between two environments can be a bit challenging to developers who are not familiar with Blend or do not have the time to learn it. You could hire a designer, but that can complicate things when your designer and your developers are sharing XAML files. That's where ClearStyle comes in. With ClearStyle the styling capabilities are brought to you in Visual Studio in the most intuitive manner possible. In most situations you just want to make simple styling changes to the controls in your application so this process should be simple. For example, if you just want to change the row color of your

38

data grid this should be as simple as setting one property. You shouldn't have to create a full and complicatedlooking template just to simply change a few colors.

How ClearStyle Works

Each key piece of the control's style is surfaced as a simple color property. This leads to a unique set of style properties for each control. For example, a Gauge has PointerFill and PointerStroke properties, whereas a DataGrid has SelectedBrush and MouseOverBrush for rows. Let's say you have a control on your form that does not support ClearStyle. You can take the XAML resource created by ClearStyle and use it to help mold other controls on your form to match (such as grabbing exact colors). Or let's say you'd like to override part of a style set with ClearStyle (such as your own custom scrollbar). This is also possible because ClearStyle can be extended and you can override the style where desired. ClearStyle is intended to be a solution to quick and easy style modification but you're still free to do it the old fashioned way with ComponentOne's controls to get the exact style needed. ClearStyle does not interfere with those less common situations where a full custom design is required.

ClearStyle Properties

With each release, ComponentOne will be adding ClearStyle functionality to more controls. Currently several Silverlight and WPF controls support ClearStyle. The following table lists all of the ClearStyle-supported Silverlight controls as well as the ClearStyle properties that each supports.

Property AlternatingBackground AppointmentForeground AlternatingRowBackground AlternatingRowForeground Background Supported Controls C1Scheduler C1Scheduler C1DataGrid C1DataGrid C1Accordion, C1AccordionItem, C1ColorPicker, C1ComboBox, C1ComboBoxItem, C1ContextMenu, C1CoverFlow, C1DataGrid, C1DateTimePicker, C1Docking, C1DropDown, C1Expander, C1ExpanderButton, C1FilePicker, C1HeaderedContentControl, C1Map, C1MediaPlayer. C1Menu, C1MenuList, C1MenuItem, C1NumericBox, C1Window, C1RangeSlider, C1PropertyGrid, C1Scheduler, C1TabControl, C1TabItem, C1TextBoxBase, C1TimeEditor, C1Toolbar, C1ToolbarGroup, C1ToolbarStrip, C1ToolbarStripItem, C1TreeView, C1TreeViewItem, C1Window C1ComboBox, C1CoverFlow, C1DropDown, C1FilePicker, C1NumericBox, C1TimeEditor, C1ToolbarStrip, C1Window C1ComboBox, C1CoverFlow, C1DropDown, C1FilePicker, C1NumericBox, C1TimeEditor, C1ToolbarStrip, C1Window C1ColorPicker, C1ComboBox, C1DateTimePicker, C1NumericBox, C1TextBoxBase, C1TimeEditor C1PropertyGrid C1PropertyGrid C1Scheduler C1Scheduler C1AccordionItem, C1Expander, C1ExpanderButton, C1ColorPicker, C1ComboBox, C1DataGrid, C1DateTimePicker, C1DropDown, C1Expander, C1ExpanderButton, C1FilePicker, C1MediaPlayer. C1NumericBox, C1Window, C1RangeSlider,

ButtonBackground ButtonForeground CaretBrush CategoryBackground CategoryForeground ControlBackground ControlForeground ExpandedBackground FocusBrush

39

C1TextBoxBase, C1TimeEditor, C1Toolbar, C1ToolbarGroup, C1ToolbarStrip, C1ToolbarStripItem Header HighlightedBackground HorizontalGridLinesBrush MouseOverBrush C1Accordion, C1AccordionItem, C1Expander, C1HeaderedContentControl, C1Window C1ContextMenu, C1Menu, C1MenuList, C1MenuItem C1DataGrid C1Accordion, C1AccordionItem, C1ColorPicker, C1ComboBox, C1ComboBoxItem, C1CoverFlow, C1DataGrid, C1DateTimePicker, C1Docking, C1DropDown, C1Expander, C1ExpanderButton, C1FilePicker, C1Map, C1MediaPlayer. C1NumericBox, C1RangeSlider, C1PropertyGrid, C1TabControl, C1TabItem, C1TextBoxBase, C1TimeEditor, C1Toolbar, C1ToolbarGroup, C1ToolbarStrip, C1ToolbarStripItem, C1TreeView, C1TreeViewItem, C1Window C1ContextMenu, C1Menu, C1MenuList, C1MenuItem C1ColorPicker, C1ComboBox, C1CoverFlow, C1DataGrid, C1DateTimePicker, C1DropDown, C1ExpanderButton, C1FilePicker, C1Map, C1MediaPlayer. C1NumericBox, C1PropertyGrid, C1RangeSlider, C1TextBoxBase, C1TimeEditor, C1Toolbar, C1ToolbarGroup, C1ToolbarStrip, C1ToolbarStripItem, C1Window C1DataGrid C1DataGrid C1ComboBox, C1ComboBoxItem, C1DataGrid, C1Scheduler, C1TabControl, C1TabItem, C1TreeView, C1TreeViewItem, C1ColorPicker, C1ComboBox, C1DateTimePicker, C1FilePicker, C1NumericBox, C1TextBoxBase, C1TimeEditor C1ColorPicker, C1ComboBox, C1DateTimePicker, C1FilePicker, C1NumericBox, C1TextBoxBase, C1TimeEditor

OpenedBackground PressedBrush

RowBackground RowForeground SelectedBackground SelectionBackground SelectionForeground TabItemBackground, TabStripBackground TabStripForeground TodayBackground

C1Docking

C1Docking, C1TabControl C1Docking, C1TabControl C1Scheduler

40

RichTextBox

ComponentOne RichTextBoxTM for Silverlight is the most complete rich text editor available for Silverlight. Load, edit, and save formatted text as HTML or RTF documents. The C1RichTextBox control provides rich formatting, automatic line wrapping, HTML and RTF import/export, table support, images, annotations, and more.

Getting Started

Get started with the following topics: - Key Features (page 41) - Working with RichTextBox (page 49) - Concepts and Main Properties (page 49)

RichTextBox for Silverlight Key Features

ComponentOne RichTextBox for Silverlight allows you to create customized, rich applications. Make the most of RichTextBox for Silverlight by taking advantage of the following key features: Import and Export Formats ComponentOne RichTextBox for Silverlight supports importing and exporting RTF, HTML, and plain text. Load existing rich text or HTML into the C1RichTextBox control, edit the document, and then export it back to RTF or HTML. Apply Rich Formatting Edit and format text containing multiple fonts, decorations, colors, tables, images, lists, and more. C1RichTextBoxToolbar Get started immediately with the full-featured C1RichTextBoxToolbar control, or build your own custom toolbar. The included actions include: Font Family, Font Size, Grow Font, Shrink Font, Bold, Italic, Underline, Change Case, Subscript, Superscript, Text Color, Text Highlight Color, Align Left, Align Center, Align Right, Justify, Bullets, Numbering, Text Wrapping, Border Thickness, Border Color, Paragraph Color, Margin, Padding, Insert Image, Insert Symbol, Insert Hyperlink, Remove Hyperlink, Cut, Copy, Paste, Undo, Redo, Find and Replace, and Spell Check. The RichTextBoxToolbar uses the C1Toolbar control enabling complete customization. See the Working with C1RichTextBoxToolbar (page 88) topics for more information. Page Zooming RichTextBox supports page zooming in both print layout and draft views. Spell-check Your Text RichTextBox supports two types of spell-checking using the C1SpellChecker component: o Modal spell checking: Shows a Spell dialog box and selects each spelling mistake in the document. The end-user may choose to ignore the mistake, fix it by typing or picking from a list of suggestions, or add the word to a user dictionary. See the Modal Spell-Checking (page 58) topic for more information. As-you-type checking: Highlights spelling mistakes as the end-user types, typically with a wavy, red underline. The end-user may right-click the mistake in the document to see a menu with options that include options to ignore, add to dictionary, or pick a suggestion to correct the mistake automatically. See the Spell-Checking (page 58) topic for more information.

o

41

Undo/Redo Support Edit data in the RichTextBox with confidence. You have the ability to easily undo and redo your changes with the click of a button.

Clipboard Support C1RichTextBox fully supports the clipboard. Implement cut/copy/paste activities within the RichTextBox.

Annotations Add highlights and annotations to your documents with C1RichTextBox. Annotations are comments, notes, remarks or explanations that can be attached to specific part of a Web document.

Save as PDF In addition to direct printing, The C1RichTextBox content can be exported to PDF format. Rich Document Object Model Patterned after the Document class in WPF, RichTextBox's rich document object model (DOM) supports images, lists, hyperlinks, borders, background and foreground colors for text ranges, and more. Use the rich DOM to create and modify documents programmatically. See the Working with the C1Document Object (page 73) topic for more information.

Lightning-speed Performance RichTextBox allows instantaneous editing and really fast document loading. Silverlight Toolkit Themes Support Add style to your UI with built-in support for the most popular Microsoft Silverlight Toolkit themes, including ExpressionDark, ExpressionLight, WhistlerBlue, RainerOrange, ShinyBlue, and BureauBlack.

RichTextBox for Silverlight Quick Start

In this quick start you'll create a Silverlight application in Visual Studio 2010, add the C1RichTextBox and C1RichTextBoxToolbar to the application, add code to customize the application, and run the application to view possible run-time interactions.

Step 1 of 3: Creating a Silverlight Application

In this step you'll create a new Silverlight application, set the application up, and add the C1RichTextBox and C1RichTextBoxToolbar controls to the application. After completing this step, you should have a mostly functional Rich Text editor. Complete the following steps: 1. 2. In Visual Studio 2010, select File | New | Project. In the New Project dialog box, select a language in the left pane, and in the templates list select Silverlight Application. Enter a Name for your project and click OK. The New Silverlight Application dialog box will appear. Click OK to accept default settings, close the New Silverlight Application dialog box, and create your project. The MainPage.xaml file should open. In the Solution Explorer, right-click the project and, from the context menu, choose Add Reference. In the Add Reference dialog box, select the following assemblies and click OK: C1.Silverlight C1.Silverlight.RichTextBox

3. 4. 5.

42

6. 7.

C1.Silverlight.RichTextBox.Toolbar C1.Silverlight.SpellChecker

In the XAML window of the project, place the cursor between the <Grid> and </Grid> tags and click once. Add the control namespaces to the page, by editing the UserControl tag in XAML view so it appears similar to the following: <UserControl x:Class="C1RichTextBox.MainPage" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markupcompatibility/2006" mc:Ignorable="d" d:DesignHeight="300" d:DesignWidth="400" xmlns:c1="http://schemas.componentone.com/winfx/2006/xaml" >

8.

Add the following markup within the <Grid> tags to add a StackPanel panel: <!--StackPanel that will contain the C1RichTextBox and C1RichTextBoxToolbar controls. --> <StackPanel HorizontalAlignment="Left" Margin="0,10,0,0" Name="SP" VerticalAlignment="Top" Height="425" Width="675" Grid.ColumnSpan="2" Grid.Column="1"> </StackPanel>

9.

Click between the StackPanel's tags in XAML view, and add the following markup to add C1RichTextBoxToolbar and C1RichTextBox controls: <c1:C1RichTextBoxToolbar Name="C1RTBTB" /> <c1:C1RichTextBox Height="300" Width="675" />

10. In the XAML view, bind the C1RichTextBoxToolbar to the C1RichTextBox by adding RichTextBox="{Binding ElementName=C1RTB}" to the C1RichTextBoxToolbar's tag. The markup will appear similar to the following: <c1:C1RichTextBoxToolbar RichTextBox="{Binding ElementName=C1RTB}" Name="C1RTBTB" /> What You've Accomplished If you run the application, you'll see an almost fully functional C1RichTextBox application. You can enter text in the C1RichTextBox control and edit the text with the options in the C1RichTextBoxToolbar. However, spellchecking is not currently fully functional. In the next step you'll set up spell-checking and customize the application further.

Step 2 of 3: Adding Spelling Checking

In the previous step you created a new Silverlight application, set the application up, and added the C1RichTextBox and C1RichTextBoxToolbar controls to the application. If you currently click the Spell Check button in the toolbar at run time, you'll receive a message that spell checking is currently not set up. In this step you'll customize the application further and add spell-checking functionality to the application. Complete the following steps: 1. In the Solution Explorer, right-click the .Web project and select Add | Existing Item. The Add Existing Item dialog box will appear.

43

2.

In the Add Existing Item dialog box locate the C1Spell_en-US.dct file included in the RichTextBoxSamples sample folder. By default, it should be installed in the Documents or My Documents folder in ComponentOne Samples\Studio for Silverlight 4.0\C1.Silverlight.RichTextBox\RichTextBoxSamples\RichTextBoxSamples.Web. This is a US English dictionary file ­ if you add another file, instead, you can adapt the steps below with the appropriate code.

3. 4.

In the Solution Explorer, right-click the MainPage.xaml file and select View Code to open the code file. In the Code Editor, add the following code to import the following namespaces: Visual Basic Imports C1.Silverlight.RichTextBox Imports C1.Silverlight.SpellChecker C# using C1.Silverlight.RichTextBox; using C1.Silverlight.SpellChecker;

5.

Add code to the MainPage constructor so that it appears similar to the following: Visual Basic Public Sub New() InitializeComponent() Dim spell As New C1SpellChecker() spell.MainDictionary.LoadAsync("C1Spell_en-US.dct") Me.C1RTB.SpellChecker = spell End Sub C# public MainPage() { InitializeComponent(); var spell = new C1SpellChecker(); spell.MainDictionary.LoadAsync("C1Spell_en-US.dct"); this.C1RTB.SpellChecker = spell; }

This code adds spell-checking ­ including as-you-type spell-checking ­ to the application. 6. Add the following code to the MainPage constructor, under the code you just added: Visual Basic Me.C1RTB.Text = "Hello World! Weelcome to the most complete rich text editor availible for Silverlight. Load, edit, and save formattted text as HTML or RTF documents with ComponentOne RichTextBox for Silverlight. The C1RichTextBox control provids rich formatting, automatic line wrapping, HTML and RTF import/export, table support, images, anotations, and more." C# this.C1RTB.Text = "Hello World! Weelcome to the most complete rich text editor availible for Silverlight. Load, edit, and save formattted text as HTML or RTF documents with ComponentOne RichTextBox for Silverlight. The C1RichTextBox control provids rich formatting, automatic line wrapping, HTML and RTF import/export, table support, images, anotations, and more.";

This code adds content to the C1RichTextBox control. Note that the misspellings in the text are deliberate.

44

What You've Accomplished In this step you added content and spell-checking to your C1RichTextBox application. Now that you've customized the application is to run it. In the next step you'll run the application and view some of the run-time interactions possible with the C1RichTextBoxToolbar and C1RichTextBox controls.

Step 3 of 3: Running the Application

In the previous steps you created a new Silverlight application, added the C1RichTextBox and C1RichTextBoxToolbar controls, and added spell-checking functionality to the application. All that's left now, is to run the application and view some possible run-time interactions. Complete the following steps: 1. In the menu select Debug | Start Debugging to run the application. The running application will appear similar to the following image:

Note that as-you-type spell-checking is visibly implemented as indicated by wavy red lines under words not included in the dictionary. 2. Right-click the first misspelled word, "Weelcome", and from the options that appear, choose the correct spelling:

45

3.

Click the Spell Check button in the Tools group. The Spelling dialog box will appear:

4. 5. 6. 7. 8. 9.

Click Change to accept the suggested spelling. The dialog box will move onto the next word. Click Add in the Spelling dialog box to add "Silverlight" to the dictionary. Click Change for each of the following words to accept the suggested spellings. The dialog box will then close. Use the mouse to highlight "ComponentOne RichTextBox for Silverlight" and click the Bold button in the Font group to bold the text. Highlight "C1RichTextBox" and click the Hyperlink button in the Insert group to open the Insert Hyperlink dialog box. In the URL box of the Insert Hyperlink dialog box, enter "http://www.componentone.com/" and click OK to close the dialog box. The link will be added.

46

The text will now be linked to the ComponentOne Web site. 10. Highlight the "Hello World!" text and click the Font Color drop-down box in the Font group and choose Red to turn the text red. 11. Highlight the entire paragraph and click the Align Text Center button in the Paragraph group to align the text. The application will now appear similar to the following:

What You've Accomplished Congratulations, you've completed this tutorial! You learned a bit abut using the C1RichTextBox and C1RichTextBoxToolbar controls. In this tutorial you created a new Silverlight application, added the C1RichTextBox and C1RichTextBoxToolbar controls, added spell-checking functionality to the application, and viewed some possible run-time interactions.

XAML Quick Reference

This topic is dedicated to providing a quick overview of the XAML used to create a C1RichTextBox and C1RichTextBoxToolbar control.

47

To get started developing, add a c1 namespace declaration in the root element tag: xmlns:c1="http://schemas.componentone.com/winfx/2006/xaml" Here is a sample C1RichTextBox and C1RichTextBoxToolbar:

Below is the XAML for the sample:

<UserControl xmlns:c1="http://schemas.componentone.com/winfx/2006/xaml" x:Class="SilverlightApplication2.MainPage" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d" d:DesignHeight="489" d:DesignWidth="668">

<Grid x:Name="LayoutRoot" Background="White">

<c1:C1RichTextBox Name="C1RTB" Margin="0,133,12,28" />

<c1:C1RichTextBoxToolbar Name="richToolbar" RichTextBox="{Binding ElementName=C1RTB}" Margin="2,12,12,0" Height="123" VerticalAlignment="Top" /> </Grid>

48

</UserControl>

Working with RichTextBox for Silverlight

The most complete rich text editor available for Silverlight, load, edit, and save formatted text as HTML or RTF documents with ComponentOne RichTextBoxTM for Silverlight. The C1RichTextBox control provides rich formatting, automatic line wrapping, HTML and RTF import/export, table support, images, annotations, and more. The C1.Silverlight.RichTextBox assembly contains two main objects: the C1RichTextBox control and the C1Document object. C1RichTextBox is a powerful text editor that allows you to display and edit formatted text. C1RichTextBox supports all the usual formatting options, including fonts, background and foreground colors, lists, hyperlinks, images, borders, and so on. C1RichTextBox also supports loading and saving documents in HTML format. C1Document is the class that represents the contents of a C1RichTextBox. It is analogous to the FlowDocument class in WPF. As in WPF, a C1Document is composed of stacked elements (C1Block objects) which in turn are composed of inline elements (C1Run objects). Many applications may deal only with the C1RichTextBox control, which provides a simple linear view of the document. Other applications may choose to use the rich object model provided by the C1Document class to create and manage documents directly, with full access to the document structure. You can also use related elements such as the C1RichTextBoxToolbar control and C1SpellChecker component to expand the functionality of the C1RichTextBox control. C1RichTextBoxToolBar is a Ribbon-like toolbar included in the C1.Silverlight.RichTextBox.Toolbar assembly. You can easily add a C1RichTextBoxToolBar control and link it to a C1RichTextBox control to create a full featured Rich Text editor. C1SpellChecker is located in the C1.Silverlight.SpellChecker assembly and can be used to add spell-checking functionality to the editor.

C1RichTextBox Concepts and Main Properties

On the surface, the C1RichTextBox control appears just like a standard TextBox. It provides the same properties to control the font, colors, text, and selection. That can be an advantage ­ if you have an application that uses TextBox controls, you may be able to simply replace them with C1RichTextBox controls without any additional changes. For example, the following code implements a simple search-and-replace routine that works on TextBox and on C1RichTextBox controls: Visual Basic Private Sub SearchAndReplace(tb As TextBox, find As String, replace As String) Dim start As Integer = 0 While True Dim pos As Integer = tb.Text.IndexOf(find, start) If pos < 0 Then Exit While End If tb.[Select](pos, find.Length) ' Optionally show a dialog box to confirm the change. tb.SelectedText = replace start = pos + 1 End While End Sub C#

49

void SearchAndReplace(TextBox tb, string find, string replace) { for (int start = 0; ; ) { int pos = tb.Text.IndexOf(find, start); if (pos < 0) break; tb.Select(pos, find.Length); // Optionally show a dialog box to confirm the change. tb.SelectedText = replace; start = pos + 1; } } The code looks for matches in the Text property. It selects each match using the Select method, and then replaces the text using the SelectedText property. To convert this method for use with the C1RichTextBox control, you would simply change the type of the first argument to use a C1RichTextBox instead of a regular TextBox. This is what the C1RichTextBox has in common with the regular TextBox. But of course it goes way beyond that. Suppose you wanted to highlight the replacements with a yellow background. This would be impossible with a regular TextBox. With the C1RichTextBox, you could accomplish that with one additional line of code: Visual Basic Private Sub SearchAndReplace(tb As TextBox, find As String, replace As String) Dim start As Integer = 0 While True Dim pos As Integer = tb.Text.IndexOf(find, start) If pos < 0 Then Exit While End If tb.[Select](pos, find.Length) ' Optionally show a dialog box to confirm the change. tb.Selection.InlineBackground = New SolidColorBrush(Colors.Yellow) tb.SelectedText = replace start = pos + 1 End While End Sub C# void SearchAndReplace(TextBox tb, string find, string replace) { for (int start = 0; ; ) { int pos = tb.Text.IndexOf(find, start); if (pos < 0) break; tb.Select(pos, find.Length); // Optionally show a dialog box to confirm the change. tb.Selection.InlineBackground = new SolidColorBrush(Colors.Yellow); tb.SelectedText = replace; start = pos + 1; } }

The Selection property provides properties that allow you to inspect and modify the formatting of the current selection. With this property and the ones in common with the TextBox control, you can easily create documents and add rich formatting. You could use the technique described above to implement a toolbar or to add syntax coloring to documents. These topics are described in more detail in later sections.

50

C1RichTextBox Content

The content of the C1RichTextBox can be specified in two ways, using the Text property or the Html property. The Text property is used to assign and retrieve the control content as plain text. Visual Basic Me.C1RichTextBox1.Text = "Hello World!" C# this.c1RichTextBox1.Text = "Hello World!";

The Html property is used to assign and retrieve formatted text as HTML. The HTML text needs to be encoded in the XAML file, so, for example, instead of <b> for bold, tags are encoded as <b>. Visual Basic Me.C1RichTextBox1.Html = "<b>Hello World!</b>" C# this.c1RichTextBox1.Html = "<b>Hello World!</b>"

The C1RichTextBox exposes a TextWrapping property that specifies whether the control should wrap long lines or whether it should keep the lines together and provide a horizontal scrollbar instead. Visual Basic Me.C1RichTextBox1.TextWrapping = TextWrapping.NoWrap C# this.c1RichTextBox1.TextWrapping = TextWrapping.NoWrap;

The code above sets the C1RichTextBox control so that text content will not wrap in the control and will appear in a continuous line.

Saving and Loading HTML

You can persist the contents of a simple TextBox control using the Text property. You can also use the Text property to persist content in the C1RichTextBox control, but you will lose any rich formatting. Instead, you can use the Html property to persist the content of a C1RichTextBox while preserving the formatting. The Html property gets or sets the formatted content of a C1RichTextBox as an HTML string. The HTML filter built into the C1RichTextBox is fairly rich. It supports CSS styles, images, hyperlinks, lists, and so on. But the filter does not support all HTML; it is limited to features supported by the C1RichTextBox control itself. For example, the current version of C1RichTextBox does not support tables. Still, you can use the Html property to display simple HTML documents. If you type "Hello world." into a C1RichTextBox, the Html property will return the following markup: <html> <head> <style type="text/css"> .c0 { font-family:Portable User Interface;font-size:9pt; } .c1 { margin-bottom:7.5pt; } </style> </head> <body class="c0"> <p class="c1">Hello world.</p> </body> </html> Note that the Html property is just a filter between HTML and the internal C1Document class. Any information in the HTML stream that is not supported by the C1RichTextBox (for example, comments and meta information) is discarded, and will not be preserved when you save the HTML document later.

51

Hyperlinks

The C1RichTextBox supports hyperlinks. As in regular HTML documents, this feature allows you to make certain parts of the document active. When the user clicks them, the application receives a notification and takes some action. The code below shows how you can create a hyperlink: Visual Basic Public Sub New() InitializeComponent() ' Set text _rtb.Text = "This is some text with a hyperlink in it." ' Create hyperlink Dim pos As Integer = _rtb.Text.IndexOf("hyperlink") _rtb.[Select](pos, 9) Dim uri = New Uri("http://www.componentone.com", UriKind.Absolute) _rtb.Selection.MakeHyperlink(uri) ' Handle navigation requests _rtb.NavigationMode = NavigationMode.OnControlKey AddHandler _rtb.RequestNavigate, AddressOf _rtb_RequestNavigate; End Sub C# public MainPage() { InitializeComponent(); // Set text _rtb.Text = "This is some text with a hyperlink in it."; // Create hyperlink int pos = _rtb.Text.IndexOf("hyperlink"); _rtb.Select(pos, 9); var uri = new Uri("http://www.componentone.com", UriKind.Absolute); _rtb.Selection.MakeHyperlink(uri); // Handle navigation requests _rtb.NavigationMode = NavigationMode.OnControlKey; _rtb.RequestNavigate += _rtb_RequestNavigate; } The code starts by assigning some text to the C1RichTextBox. Next, it selects the word "hyperlink" and calls the MakeHyperlink method to make it a hyperlink. The parameter is a URI that is assigned to the new hyperlink's NavigateUri property. Then, the code sets the NavigationMode property to determine how the C1RichTextBox should handle the mouse over hyperlinks. The default behavior is like that of Microsoft Word and Visual Studio: moving the mouse over a hyperlink while holding down the CTRL key causes the cursor to turn into a hand, and clicking while the CTRL key is pressed fires the RequestNavigate event. This allows users to edit the hyperlink text as they would edit regular text. The RequestNavigate event handler is responsible for handling the hyperlink navigation. In many cases this requires opening a new browser window and navigating to a different URL. This is illustrated below: Visual Basic

52

Private Sub _rtb_RequestNavigate(sender As Object, e As RequestNavigateEventArgs) ' Open link in a new window ("_self" would use the current one) Dim target As String = "_blank" System.Windows.Browser.HtmlPage.Window.Navigate(e.Hyperlink.NavigateUri, target) End Sub C# void _rtb_RequestNavigate(object sender, RequestNavigateEventArgs e) { // Open link in a new window ("_self" would use the current one) string target = "_blank"; System.Windows.Browser.HtmlPage.Window.Navigate(e.Hyperlink.NavigateUri, target); } Note that hyperlink actions are not restricted to URI navigation. You could define a set of custom URI actions to be used as commands within your application. The custom URIs would be parsed and handled by the RequestNavigate handler. For example, the code below uses hyperlinks to show message boxes: Visual Basic Public Sub New() InitializeComponent() ' Set text _rtb.Text = "This is some text with a hyperlink in it." ' Create hyperlink Dim pos As Integer = _rtb.Text.IndexOf("hyperlink") _rtb.[Select](pos, 9) Dim uri = New Uri("msgbox:Thanks for clicking!") _rtb.Selection.MakeHyperlink(uri) ' Handle navigation requests _rtb.NavigationMode = NavigationMode.OnControlKey AddHandler _rtb.RequestNavigate, AddressOf _rtb_RequestNavigate End Sub Private Sub _rtb_RequestNavigate(sender As Object, e As RequestNavigateEventArgs) Dim uri As Uri = e.Hyperlink.NavigateUri If uri.Scheme = "msgbox" Then MessageBox.Show(uri.LocalPath) End If End Sub C# public MainPage() { InitializeComponent(); // Set text _rtb.Text = "This is some text with a hyperlink in it."; // Create hyperlink int pos = _rtb.Text.IndexOf("hyperlink");

53

_rtb.Select(pos, 9); var uri = new Uri("msgbox:Thanks for clicking!"); _rtb.Selection.MakeHyperlink(uri); // Handle navigation requests _rtb.NavigationMode = NavigationMode.OnControlKey; _rtb.RequestNavigate += _rtb_RequestNavigate; } void _rtb_RequestNavigate(object sender, RequestNavigateEventArgs e) { Uri uri = e.Hyperlink.NavigateUri; if (uri.Scheme == "msgbox") { MessageBox.Show(uri.LocalPath); } } The only change in the MakeHyperlink code is the line that creates the URI. The RequestNavigate handler uses the URI members to parse the command and argument. You could use this technique to create documents with embedded menus for example. Note that the CreateHyperlink method is just a quick and easy way to turn an existing part of a document into a hyperlink. You can also create hyperlinks by adding C1Hyperlink elements to C1Document objects. This is described in later sections.

Accessing Layout Information

When C1RichTextBox creates the C1Document layout, it creates a parallel tree composed of C1TextElementView objects. For each C1TextElement in the C1Document tree, there is at least one C1TextElementView that is tasked with its layout and drawing. Take this C1Document tree as an example:

Its corresponding view tree will look like the following:

54

Each C1TextElementView provides some basic layout information for its corresponding C1TextElement: Origin: this is the origin of the view in document coordinates. DesiredSize: this is the desired size of the view from the last time it was measured.

Multiple C1TextElementViews can be composed to handle layout and drawing for out C1TextElement. When this is done, the Content property contains the inner most C1TextElementView in the composition. The content view's children correspond to the Children collection of the associated C1TextElement. View composition is used in C1BoxView to handle margin, padding and border for its Content view. This means that the origin of each C1BoxView is outside the margin, padding and border box, while the origin of its Content is inside. C1FlowView takes care of flowing boxes and text into lines. Each line is represented by a C1Line object. Note that C1Lines not only contains single lines of text, but may also contain an entire paragraph. Each C1FlowView contains a list of C1Line, which are always vertically stacked. In turn, each C1Line is composed of C1LineFragments, which are horizontally stacked. C1LineFragments have a reference to the child element whose origin matches the position of the fragment. For example, the following code counts the lines in a C1RichTextBox: Visual Basic Private Function CountLines(rtb As C1RichTextBox) As Integer Dim root = rtb.ViewManager.GetView(rtb.Document) Return CountLines(root) End Function Private Function CountLines(view As C1TextElementView) As Integer Dim count As Integer = 0 Dim flow = TryCast(view, C1FlowView) If flow IsNot Nothing Then For Each line As var In flow.Lines If TypeOf line.Fragments.First().Element Is C1Inline Then count += 1 End If Next

55

End If For Each child As var In view.Children count += CountLines(child) Next Return count End Function C# int CountLines(C1RichTextBox rtb) { var root = rtb.ViewManager.GetView(rtb.Document); return CountLines(root); } int CountLines(C1TextElementView view) { int count = 0; var flow = view as C1FlowView; if (flow != null) { foreach (var line in flow.Lines) { if (line.Fragments.First().Element is C1Inline) { ++count; } } } foreach (var child in view.Children) { count += CountLines(child); } return count; } At first, the root view is obtained. That's the same as the view associated to root element, so GetView is used to get the view of rtb.Document. After that, the view tree is traversed counting the lines in each C1FlowView found. Note that you only count the lines with C1Inline elements; otherwise you would also count paragraphs and other container blocks.

Painters

Painters are a way of extending C1RichTextBox by displaying UIElements in the same canvas where C1RichTextBox displays text. This allows more general extensions than style overrides, but might be harder to use. Painters are used internally by C1RichTextBox to display the selection. A painter is an implementation of the IRichTextPainter interface. This interface has two methods, Paint and PaintInline, which are called at different stages of C1RichTextBox's painting pass. Each method receives a C1PaintingContext object that is used to check the viewport being painted, and has the methods that are used for painting custom UIElements. Paint is called each time the entire screen is repainted. Note that each time this method is called, all UIElements must be painted by calling Paint, otherwise they will be removed. Passing the same UIElement each time is more efficient, as it is not removed from the visual tree. PaintInline is called for each C1Line that is painted. This method allows finer control over the layer where custom UIElements are painted. For instance, it is possible to paint above the text background, but below the text itself. It has the same rule as Paint. All UIElements must be painted by calling PaintInline, otherwise they will be removed.

56

The Annotations sample uses painters to display sticky notes. Here is the implementation: Visual Basic Class StickyPainter Implements IRichTextPainter Private _stickies As List(Of StickyNote) Public Sub New(stickies As List(Of StickyNote)) _stickies = stickies End Sub Public Sub Paint(context As C1PaintingContext) For Each sticky As var In _stickies Dim rect = context.ViewManager.GetRectFromPosition(sticky.Range.Start) context.Paint(Math.Round(rect.X), Math.Round(rect.Bottom), False, sticky) Next End Sub Public Sub PaintInline(context As C1PaintingContext, line As C1Line) End Sub Public Event PainterChanged As EventHandler(Of RichTextPainterChangeEventArgs) End Class C# class StickyPainter : IRichTextPainter { List<StickyNote> _stickies; public StickyPainter(List<StickyNote> stickies) { _stickies = stickies; } public void Paint(C1PaintingContext context) { foreach (var sticky in _stickies) { var rect = context.ViewManager.GetRectFromPosition(sticky.Range.Start); context.Paint(Math.Round(rect.X), Math.Round(rect.Bottom), false, sticky); } } public void PaintInline(C1PaintingContext context, C1Line line) { } public event EventHandler<RichTextPainterChangeEventArgs> PainterChanged; } StickyPainter only uses the Paint method. For each sticky note it just gets the coordinates inside document and then calls Paint. Note that these are document coordinates; they are independent of paging, scrolling and zooming.

57

Spell-Checking

Most rich editors implement two types of spell-checking: Modal spell checking: Shows the Spelling dialog box and selects each spelling mistake in the document. The user may choose to ignore the mistake, fix it by typing or picking from a list of suggestions, or add the word to a user dictionary. As-you-type checking: Highlights spelling mistakes as the user types, typically with a wavy red underline. The user may right-click the mistake in the document to see a menu with options that include ignore, add to dictionary, or pick a suggestion to correct the mistake automatically.

The C1RichTextBox supports both types of spell-checking using the C1SpellChecker component, which is also included in ComponentOne Studio for Silverlight. The C1SpellChecker ships as a separate assembly because it can spell-check other controls as well.

Modal Spell-Checking

To implement modal spell checking, you start by adding to your project a reference to the C1.Silverlight.SpellChecker assembly. Then, add the following code to your project: Visual Basic Imports C1.Silverlight.SpellChecker Public Partial Class MainPage Inherits UserControl ' Spell-checker used by all controls on this page Private _spell As New C1SpellChecker() ' Page constructor Public Sub New() ' Regular Standard initialization InitializeComponent() ' Load main spelling dictionary AddHandler _spell.MainDictionary.LoadCompleted, AddressOf MainDictionary_LoadCompleted _spell.MainDictionary.LoadAsync("C1Spell_en-US.dct") ' Load user dictionary Dim ud As UserDictionary = _spell.UserDictionary ud.LoadFromIsolatedStorage("Custom.dct") ' Other initializations ' ... AddHandler App.Current.[Exit], AddressOf App_Exit End Sub End Class C# using C1.Silverlight.SpellChecker; public partial class MainPage : UserControl { // Spell-checker used by all controls on this page C1SpellChecker _spell = new C1SpellChecker(); // Page constructor public MainPage()

58

{ // Standard initialization InitializeComponent(); // Load main spelling dictionary _spell.MainDictionary.LoadCompleted += MainDictionary_LoadCompleted; _spell.MainDictionary.LoadAsync("C1Spell_en-US.dct"); // Load user dictionary UserDictionary ud = _spell.UserDictionary; ud.LoadFromIsolatedStorage("Custom.dct"); App.Current.Exit += App_Exit; // Other initializations // ... } } The code creates a new C1SpellChecker object to be shared by all controls on the page that require spell-checking. Later, the page constructor invokes the LoadAsync method to load the main spell dictionary. In this case, we are loading C1Spell_en-US.dct, the American English dictionary. This file must be present on the application folder on the server. C1SpellChecker includes over 20 other dictionaries which can be downloaded from our site. The code adds a handler to the SpellDictionaryBase.LoadCompleted event so it can detect when the main dictionary finishes loading and whether there were any errors. Here is a typical event handler: Visual Basic Private Sub MainDictionary_LoadCompleted(sender As Object, e As OpenReadCompletedEventArgs) If e.[Error] IsNot Nothing Then MessageBox.Show("Error loading spell dictionary, " & "spellchecking is disabled.") End If End Sub C# void MainDictionary_LoadCompleted(object sender, OpenReadCompletedEventArgs e) { if (e.Error != null) MessageBox.Show("Error loading spell dictionary, " + "spell-checking is disabled."); }

The code also loads a user dictionary from isolated storage. This step is optional. The user dictionary stores words such as names and technical terms. The code attaches an event handler to the application's Exit event to save the user dictionary when the application finishes executing: Visual Basic Private Sub App_Exit(sender As Object, e As EventArgs) Dim ud As UserDictionary = _spell.UserDictionary ud.SaveToIsolatedStorage("Custom.dct") End Sub C# void App_Exit(object sender, EventArgs e) { UserDictionary ud = _spell.UserDictionary; ud.SaveToIsolatedStorage("Custom.dct");

59

} Once the dictionary has been loaded, you can invoke the modal spell-checker by calling the C1SpellChecker.CheckControlAsync method. For example: Visual Basic Private Sub SpellCheck_Click(sender As Object, e As RoutedEventArgs) AddHandler _spell.CheckControlCompleted, AddressOf _spell_CheckControlCompleted _spell.CheckControlAsync(_rtb) End Sub Private Sub _spell_CheckControlCompleted(sender As Object, e As CheckControlCompletedEventArgs) If Not e.Cancelled Then Dim msg = String.Format("Spell-check complete. {0} error(s) found.", e.ErrorCount) MessageBox.Show(msg, "Spell-check complete", MessageBoxButton.OK) End If End Sub C# private void SpellCheck_Click(object sender, RoutedEventArgs e) { _spell.CheckControlCompleted += _spell_CheckControlCompleted; _spell.CheckControlAsync(_rtb); } void _spell_CheckControlCompleted(object sender, CheckControlCompletedEventArgs e) { if (!e.Cancelled) { var msg = string.Format( "Spell-check complete. {0} error(s) found.", e.ErrorCount); MessageBox.Show(msg, "Spell-check complete..", MessageBoxButton.OK); } }

The code calls C1SpellChecker.CheckControlAsync. When the modal checking is complete, the C1SpellChecker.CheckControlCompleted event fires and shows a dialog box to indicate that the spell-checking operation is complete. The image below shows the spell-checking dialog box in action:

60

Syntax Coloring

The Understanding C1TextPointer (page 84) section describes how you can use the Selection property to obtain a C1TextRange object that corresponds to the current selection, and how to use that object to inspect and apply custom formatting to parts of the document. In some cases, however, you may want to inspect and apply formatting to ranges without selecting them. To do that using the Selection property, you would have to save the current selection, apply all the formatting, and then restore the original selection. Also, changing the selection may cause the document to scroll in order to keep the selection in view. To handle these situations, the C1RichTextBox exposes a GetTextRange method. The GetTextRange method returns a C1TextRange object that may be used without affecting the current selection. For example, you could use the GetTextRange method to add HTML syntax coloring to a C1RichTextBox. The first step is to detect any changes to the document. The changes will trigger the method that performs the actual syntax coloring: Visual Basic ' Update syntax coloring on a timer Private _updating As Boolean Private _syntax As Storyboard ' Start the timer whenever the document changes Private Sub tb_TextChanged(sender As Object, e As C1TextChangedEventArgs) If Not _updating Then ' Create storyboard if it's still null If _syntax Is Nothing Then _syntax = New Storyboard() AddHandler _syntax.Completed, AddressOf _syntax_Completed _syntax.Duration = New Duration(TimeSpan.FromMilliseconds(1000)) End If ' Re-start storyboard

61

_syntax.[Stop]() _syntax.Seek(TimeSpan.Zero) _syntax.Begin() End If End Sub ' Timer elapsed, update syntax coloring Private Sub _syntax_Completed(sender As Object, e As EventArgs) _updating = True UpdateSyntaxColoring(_rtb) _updating = False End Sub C# // Update syntax coloring on a timer bool _updating; Storyboard _syntax; // Start the timer whenever the document changes void tb_TextChanged(object sender, C1TextChangedEventArgs e) { if (!_updating) { // Create storyboard if it's still null if (_syntax == null) { _syntax = new Storyboard(); _syntax.Completed += _syntax_Completed; _syntax.Duration = new Duration(TimeSpan.FromMilliseconds(1000)); } // Re-start storyboard _syntax.Stop(); _syntax.Seek(TimeSpan.Zero); _syntax.Begin(); } } // Timer elapsed, update syntax coloring void _syntax_Completed(object sender, EventArgs e) { _updating = true; UpdateSyntaxColoring(_rtb); _updating = false; } The code creates a timer that starts ticking whenever the user changes the document in any way. If the user changes the document while the timer is active, then the timer is reset. This prevents the code from updating the syntax coloring too often, while the user is typing quickly. When the timer elapses, the code sets a flag to prevent the changes made while updating the syntax coloring from triggering the timer, then calls the UpdateSyntaxColoring method: Visual Basic ' Perform syntax coloring Private Sub UpdateSyntaxColoring(rtb As C1RichTextBox) ' Initialize regular expression used to parse HTML Dim pattern As String = "</?(?<tagName>[a-zA-Z0-9_:\-]+)" & "(\s+(?<attName>[a-zA-Z0-9_:\-]+)(?<attValue>(=""[^""]+"")?))*\s*/?>"

62

' Initialize brushes used to color the document Dim brDarkBlue As Brush = New SolidColorBrush(Color.FromArgb(255, 0, 0, 180)) Dim brDarkRed As Brush = New SolidColorBrush(Color.FromArgb(255, 180, 0, 0)) Dim brLightRed As Brush = New SolidColorBrush(Colors.Red) ' Remove old coloring Dim input = rtb.Text Dim range = rtb.GetTextRange(0, input.Length) range.Foreground = rtb.Foreground ' Highlight the matches For Each m As Match In Regex.Matches(input, pattern) ' Select whole tag, make it dark blue range = rtb.GetTextRange(m.Index, m.Length) range.Foreground = brDarkBlue ' Select tag name, make it dark red Dim tagName = m.Groups("tagName") range = rtb.GetTextRange(tagName.Index, tagName.Length) range.Foreground = brDarkRed ' Select attribute names, make them light red Dim attGroup = m.Groups("attName") If attGroup IsNot Nothing Then Dim atts = attGroup.Captures For i As Integer = 0 To atts.Count - 1 Dim att = atts(i) range = rtb.GetTextRange(att.Index, att.Length) range.Foreground = brLightRed Next End If Next End Sub C# // Perform syntax coloring void UpdateSyntaxColoring(C1RichTextBox rtb) { // Initialize regular expression used to parse HTML string pattern = @"</?(?<tagName>[a-zA-Z0-9_:\-]+)" + @"(\s+(?<attName>[a-zA-Z0-9_:\]+)(?<attValue>(=""[^""]+"")?))*\s*/?>"; // Initialize brushes used to color the document Brush brDarkBlue = new SolidColorBrush(Color.FromArgb(255, 0, 0, 180)); Brush brDarkRed = new SolidColorBrush(Color.FromArgb(255, 180, 0, 0)); Brush brLightRed = new SolidColorBrush(Colors.Red); // Remove old coloring var input = rtb.Text; var range = rtb.GetTextRange(0, input.Length); range.Foreground = rtb.Foreground;

63

// Highlight the matches foreach (Match m in Regex.Matches(input, pattern)) { // Select whole tag, make it dark blue range = rtb.GetTextRange(m.Index, m.Length); range.Foreground = brDarkBlue; // Select tag name, make it dark red var tagName = m.Groups["tagName"]; range = rtb.GetTextRange(tagName.Index, tagName.Length); range.Foreground = brDarkRed; // Select attribute names, make them light red var attGroup = m.Groups["attName"]; if (attGroup != null) { var atts = attGroup.Captures; for (int i = 0; i < atts.Count; i++) { var att = atts[i]; range = rtb.GetTextRange(att.Index, att.Length); range.Foreground = brLightRed; } } } } The code starts by defining a regular expression pattern to parse the HTML. This is not the most efficient way to parse HTML, and the expression is not terribly easy to read or maintain. We don't recommend using regular expressions for parsing HTML except in sample code, where it may help keep the code compact and easy to understand. The next step is to remove any old coloring left over. This is done by creating a range that spans the whole document and setting its Foreground property to match the Foreground of the C1RichTextBox control. Next, the regular expression is used to parse the document. The code scans each match, creates a C1TextRange object, and sets the Foreground property to the desired value. We use dark blue for the HTML tag, dark red for the tag name, and light red for the attribute names. That's all the code that is required. The image below shows an HTML document viewed in the syntax-coloring C1RichTextBox we just created:

64

Test the application by typing or pasting some HTML text into the control. Notice that shortly after you stop typing, the new text is colored automatically. A real application could optimize the syntax coloring process by detecting the type of text change and updating the coloring of small parts of the document. Also, it would detect additional elements such as style sheets and comments, and it probably would use a specialized parser instead of regular expressions. The essential mechanism would be the same, however: detect ranges within the document, get C1TextRange objects, and apply the formatting.

Overriding Styles

The Syntax Coloring (page 61) section described how you can use C1TextRange objects to modify the style of parts of a document without moving the selection. In some cases, however, you may want to modify only the view, and not the document itself. For example, the current selection is highlighted with different foreground and background colors. This style change does not belong to the document itself; it belongs to the view. Other examples are syntax coloring and asyou-type spell-checking. The C1RichTextBox control supports these scenarios with the StyleOverrides property. This property contains a collection of objects that specify ranges and style modifications to be applied to the view only. This approach has two advantages over applying style modifications to C1TextRange objects as you did in the previous section: The style overrides are not applied to the document, and therefore are not applied when you save a document as HTML (you would not normally want the current selection and spelling error indicators to be persisted to a file). Because the changes are not added to the document, and only affect the part that is currently visible, this approach is much more efficient than changing C1TextRange objects directly.

The limitation of this approach is that the style changes cannot involve style elements that affect the document flow. You can use style overrides to change the background, foreground, and to underline parts of the document. But you cannot change the font size or style, for example, since that would affect the document flow.

65

Let us demonstrate the use of style overrides by modifying the previous syntax coloring example. First, we need to declare a C1RangeStyleCollection object and add that to the control's StyleOverrides collection. Once that is done, any overrides added to our collection will be applied to the control. We will later populate the collection with the syntax-colored parts of the document. Visual Basic Private _rangeStyles As New C1RangeStyleCollection() Public Sub New() InitializeComponent() _rtb = New C1RichTextBox() LayoutRoot.Children.Add(_rtb) AddHandler _rtb.TextChanged, AddressOf tb_TextChanged _rtb.FontFamily = New FontFamily("Courier New") _rtb.FontSize = 16 _rtb.Text = GetStringResource("w3c.htm") ' Add our C1RangeStyleCollection to the control's ' StyleOverrides collection _rtb.StyleOverrides.Add(_rangeStyles) End Sub C# C1RangeStyleCollection _rangeStyles = new C1RangeStyleCollection(); public MainPage() { InitializeComponent(); _rtb = new C1RichTextBox(); LayoutRoot.Children.Add(_rtb); _rtb.TextChanged += tb_TextChanged; _rtb.FontFamily = new FontFamily("Courier New"); _rtb.FontSize = 16; _rtb.Text = GetStringResource("w3c.htm"); // Add our C1RangeStyleCollection to the control's // StyleOverrides collection _rtb.StyleOverrides.Add(_rangeStyles); } Now, all we need to do is modify the UpdateSyntaxColoring method shown earlier and have it populate our collection of range styles (instead of applying the coloring to the document as we did before): Visual Basic ' Perform syntax coloring using StyleOverrides collection ' (takes a fraction of a second to highlight the default document) Private Sub UpdateSyntaxColoring(ByVal rtb As C1RichTextBox) ' Initialize regular expression used to parse HTML String pattern = "</?(?<tagName>[a-zA-Z0-9_:\-]+)" + "(\s+(?<attName>[a-zA-Z0-9_:\-]+)" + (?<attValue>(\s*=\s*""(^"")+"")?))*\s*/?>" ' Initialize styles used to color the document

66

Dim key As var = C1TextElement.ForegroundProperty Dim brDarkBlue As var = New C1TextElementStyle() brDarkBlue(key) = New SolidColorBrush(Color.FromArgb(255, 0, 0, 180)) Dim brDarkRed As var = New C1TextElementStyle() brDarkRed(key) = New SolidColorBrush(Color.FromArgb(255, 180, 0, 0)) Dim brLightRed As var = New C1TextElementStyle() brLightRed(key) = New SolidColorBrush(Colors.Red) ' Remove old coloring _rangeStyles.Clear() ' Highlight the matches Dim input As var = rtb.Text Dim m As Match For Each m In Regex.Matches(input,pattern) ' Select whole tag, make it dark blue Dim range As var = rtb.GetTextRange(m.Index,m.Length) _rangeStyles.Add(New C1RangeStyle(range,brDarkBlue)) ' Select tag name, make it dark red Dim tagName As var = m.Groups("tagName") range = rtb.GetTextRange(tagName.Index, tagName.Length) _rangeStyles.Add(New C1RangeStyle(range,brDarkRed)) ' Select attribute names, make them light red Dim attGroup As var = m.Groups("attName") If Not attGroup Is Nothing Then Dim att As Capture For Each att In attGroup.Captures range = rtb.GetTextRange(att.Index, att.Length) _rangeStyles.Add(New C1RangeStyle(range,brLightRed)) Next End If Next End Sub C# // Perform syntax coloring using StyleOverrides collection // (takes a fraction of a second to highlight the default document) void UpdateSyntaxColoring(C1RichTextBox rtb) { // Initialize regular expression used to parse HTML string pattern = @"</?(?<tagName>[a-zA-Z0-9_:\-]+)" + @"(\s+(?<attName>[a-zA-Z0-9_:\-]+)" + (?<attValue>(\s*=\s*""[^""]+"")?))*\s*/?>"; // Initialize styles used to color the document var key = C1TextElement.ForegroundProperty; var brDarkBlue = new C1TextElementStyle(); brDarkBlue[key] = new SolidColorBrush(Color.FromArgb(255, 0, 0, 180)); var brDarkRed = new C1TextElementStyle(); brDarkRed[key] = new SolidColorBrush(Color.FromArgb(255, 180, 0, 0)); var brLightRed = new C1TextElementStyle(); brLightRed[key] = new SolidColorBrush(Colors.Red); // Remove old coloring

67

_rangeStyles.Clear(); // Highlight the matches var input = rtb.Text; foreach (Match m in Regex.Matches(input, pattern)) { // Select whole tag, make it dark blue var range = rtb.GetTextRange(m.Index, m.Length); _rangeStyles.Add(new C1RangeStyle(range, brDarkBlue)); // Select tag name, make it dark red var tagName = m.Groups["tagName"]; range = rtb.GetTextRange(tagName.Index, tagName.Length); _rangeStyles.Add(new C1RangeStyle(range, brDarkRed)); // Select attribute names, make them light red var attGroup = m.Groups["attName"]; if (attGroup != null) { foreach (Capture att in attGroup.Captures) { range = rtb.GetTextRange(att.Index, att.Length); _rangeStyles.Add(new C1RangeStyle(range, brLightRed)); } } } } The revised code is very similar to the original. Instead of creating brushes to color the document, it creates C1TextElementStyle objects that contain an override for the foreground property. The code starts by clearing the override collection, then uses a regular expression to locate each HTML tag in the document, and finally populates the overrides collection with C1RangeStyle objects that associate ranges with C1TextElementStyle objects. If you run this new version of the code, you should notice the dramatic performance increase. The new version is thousands of times faster than the original.

Hit-Testing

The C1RichTextBox supports hyperlinks (page 52), which provide a standard mechanism for implementing user interactivity. In some cases, you may want to go beyond that and provide additional, custom mouse interactions. For example, you may want to apply some custom formatting or show a context menu when the user clicks an element. To enable these scenarios, the C1RichTextBox exposes ElementMouse* events and a GetPositionFromPoint method. If all you need to know is the element that triggered the mouse event, you can get it from the source parameter in the event handler. If you need more detailed information (the specific word that was clicked within the element for example), then you need the GetPositionFromPoint method. GetPositionFromPoint takes a point in client coordinates and returns a C1TextPosition object that expresses the position in document coordinates. The C1TextPosition object has two main properties: Element and Offset. The Element property represents an element within the document; Offset is a character index (if the element is a C1Run) or the index of the child element at the given point. For example, the code below creates a C1RichTextBox and attaches a handler to the ElementMouseLeftButtonDown event: Visual Basic Public Sub New()

68

' Default initialization InitializeComponent() ' Create a C1RichTextBox and add it to the page _rtb = New C1RichTextBox() LayoutRoot.Children.Add(_rtb) ' Attach event handler Add Handler _rtb.ElementMouseLeftButtonDown AddressOf rtb_ElementMouseLeftButtonDown End Sub C# public MainPage() { // Default initialization InitializeComponent(); // Create a C1RichTextBox and add it to the page _rtb = new C1RichTextBox(); LayoutRoot.Children.Add(_rtb); // Attach event handler _rtb.ElementMouseLeftButtonDown += rtb_ElementMouseLeftButtonDown; } The event handler below toggles the FontWeight property for the entire element that was clicked. This could be a word, a sentence, or a whole paragraph: Visual Basic Private Sub _rtb_ElementMouseLeftButtonDown(sender As Object, e As MouseButtonEventArgs) If Keyboard.Modifiers <> 0 Then Dim run = TryCast(sender, C1Run) If run IsNot Nothing Then run.FontWeight = If(run.FontWeight = FontWeights.Bold, FontWeights.Normal, FontWeights.Bold) End If End If End Sub C# void _rtb_ElementMouseLeftButtonDown(object sender, MouseButtonEventArgs e) { if (Keyboard.Modifiers != 0) { var run = sender as C1Run; if (run != null) { run.FontWeight = run.FontWeight == FontWeights.Bold ? FontWeights.Normal : FontWeights.Bold; } } }

The code gets the element that was clicked by casting the sender parameter to a C1Run object.

69

If you wanted to toggle the FontWeight value of a single word instead, then you would need to determine which character was clicked and expand the selection to the whole word. This is where the GetPositionFromPoint method becomes necessary. Here is a revised version of the event handler that accomplishes that: Visual Basic Private Sub _rtb_ElementMouseLeftButtonDown(sender As Object, e As MouseButtonEventArgs) If Keyboard.Modifiers <> 0 Then ' Get position in control coordinates Dim pt = e.GetPosition(_rtb) ' Get text pointer at position Dim pointer = _rtb.GetPositionFromPoint(pt) ' Check that the pointer is pointing to a C1Run Dim run = TryCast(pointer.Element, C1Run) If run IsNot Nothing Then ' Get the word within the C1Run Dim text = run.Text Dim start = pointer.Offset Dim [end] = pointer.Offset While start > 0 AndAlso Char.IsLetterOrDigit(text, start - 1) start -= 1 End While While [end] < text.Length - 1 AndAlso Char.IsLetterOrDigit(text, [end] + 1) [end] += 1 End While ' Toggle the bold property for the run that was clicked Dim word = New C1TextRange(pointer.Element, start, [end] start + 1) word.FontWeight = If(word.FontWeight.HasValue AndAlso word.FontWeight.Value = FontWeights.Bold, FontWeights.Normal, FontWeights.Bold) End If End If End Sub C# void _rtb_ElementMouseLeftButtonDown(object sender, MouseButtonEventArgs e) { if (Keyboard.Modifiers != 0) { // Get position in control coordinates var pt = e.GetPosition(_rtb); // Get text pointer at position var pointer = _rtb.GetPositionFromPoint(pt); // Check that the pointer is pointing to a C1Run var run = pointer.Element as C1Run; if (run != null) { // Get the word within the C1Run var text = run.Text;

70

var start = pointer.Offset; var end = pointer.Offset; while (start > 0 && char.IsLetterOrDigit(text, start - 1)) start--; while (end < text.Length - 1 && char.IsLetterOrDigit(text, end + 1)) end++; // Toggle the bold property for the run that was clicked var word = new C1TextRange(pointer.Element, start, end - start + 1); word.FontWeight = word.FontWeight.HasValue && word.FontWeight.Value == FontWeights.Bold ? FontWeights.Normal : FontWeights.Bold; } } } Notice that the FontWeight property returns a nullable value. If the range contains a mix of values for this attribute, the property returns null. The code used to toggle the FontWeight property is the same we used earlier when implementing the formatting toolbar.

HtmlFilter Customization

HtmlFilter is the component in C1RichTextBox that transforms HTML strings to C1Documents and back. It's also capable of transforming to and from an intermediate representation of an HTML document called C1HtmlDocument. When transforming between C1HtmlDocument and C1Document, several events are fired allowing customization of each node that is transformed. These events are: ConvertingHtmlNode: this event is fired just before an HTML node is transformed. If marked as handled by the event handler then HtmlFilter assumes the node was transformed and skips it. ConvertedHtmlNode: this event is fired after a node was transformed. It can be used to make minor changes to the transformation result. ConvertingTextElement: this event is fired just before a C1TextElement is transformed. If marked as handled by the event handler then HtmlFilter assumes the element was transformed and skips it. ConvertedTextElement: this event is fired after a C1TextElement is transformed. It can be used to make minor changes to the transformation result.

As an example you can see how the HtmlFilterCustomization sample adds support for GIF images using C1.Silverlight.Imaging. It uses both ConvertingHtmlNode and ConvertingTextElement events. Here is the ConvertingHtmlNode event handler: Visual Basic Private Sub HtmlFilter_ConvertingHtmlNode(sender As Object, e As ConvertingHtmlNodeEventArgs) Dim htmlElement = TryCast(e.HtmlNode, C1HtmlElement) If htmlElement IsNot Nothing AndAlso htmlElement.Name = "img" Then Dim src As String If htmlElement.Attributes.TryGetValue("src", src) Then Dim uri = New Uri("/HtmlFilterCustomization;component/" & src, UriKind.Relative) Dim resource = Application.GetResourceStream(uri) If resource IsNot Nothing Then Dim imageSource = New C1Bitmap(resource.Stream).ImageSource

71

Dim image = New Image() With { _ Key .Source = imageSource _ } SetImageSource(image, src) e.Parent.Children.Add(New C1InlineUIContainer() With { _ Key .Child = image _ }) e.Handled = True End If End If End If End Sub C# void HtmlFilter_ConvertingHtmlNode(object sender, ConvertingHtmlNodeEventArgs e) { var htmlElement = e.HtmlNode as C1HtmlElement; if (htmlElement != null && htmlElement.Name == "img") { string src; if (htmlElement.Attributes.TryGetValue("src", out src)) { var uri = new Uri("/HtmlFilterCustomization;component/" + src, UriKind.Relative); var resource = Application.GetResourceStream(uri); if(resource != null) { var imageSource = new C1Bitmap(resource.Stream).ImageSource; var image = new Image { Source = imageSource }; SetImageSource(image, src); e.Parent.Children.Add(new C1InlineUIContainer { Child = image }); e.Handled = true; } } } }

The first thing the event handler does is cast e.HtmlNode to C1HtmlElement. There are two types that inherit from C1HtmlNode: C1HtmlElement, which represents an HTML element like <img/>, and C1HtmlText, which represents a text node. Once the C1HtmlNode object has been cast to C1HtmlElement, it's possible to check the tag name, and access its attributes. This is done to see if the element is in fact an IMG tag, and to obtain the SRC attribute. The rest of the code takes core of creating the appropriate element, which is then added to e.Parent. Note that the SRC value is saved as an attached property, to be accessed when exporting. Once the transformation is done, the handler can set e.Handled to True in order to prevent HtmlFilter from transforming this C1HtmlNode. The ConvertingTextElement event handler looks like the following: Visual Basic Private Sub HtmlFilter_ConvertingTextElement(sender As Object, e As ConvertingTextElementEventArgs) Dim inlineContainer = TryCast(e.TextElement, C1InlineUIContainer) If inlineContainer IsNot Nothing Then

72

Dim src = GetImageSource(inlineContainer.Child) If src IsNot Nothing Then Dim element = New C1HtmlElement("img") element.Attributes("src") = src e.Parent.Add(element) e.Handled = True End If End If End Sub C# void HtmlFilter_ConvertingTextElement(object sender, ConvertingTextElementEventArgs e) { var inlineContainer = e.TextElement as C1InlineUIContainer; if (inlineContainer != null) { var src = GetImageSource(inlineContainer.Child); if (src != null) { var element = new C1HtmlElement("img"); element.Attributes["src"] = src; e.Parent.Add(element); e.Handled = true; } } }

This is pretty similar to the other handler, only it transforms a C1TextElement to a C1HtmlElement. Note that the SRC value is recovered from the attached property, and a C1HtmlElement is created with that attribute. As before, the new element is added to e.Parent, and the event is marked as Handled.

Working with the C1Document Object

So far we have focused on the object model of the C1RichTextBox control. But the control is just an editable view of a C1Document object, which exposes a rich object model for creating and editing the underlying document. This architecture is similar to the one used by the Microsoft WPF RichTextBox control, which provides a view of a FlowDocument object. Programming directly against the C1Document object is the best way to perform many tasks, including report generation and the implementation of import and export filters. For example, the Html property exposes an HTML filter with methods that convert C1Document objects to and from HTML strings. You could implement a similar filter class to import and export other popular formats such as RTF or PDF. The C1RichTextBox deals mainly with text. It provides a flat, linear view of the control content. The C1Document, on the other hand, exposes the structure of the document. The document model makes it easy to enumerate the runs within each paragraph, items within each list, and so on. This will be shown in a later section.

Creating Documents and Reports

To illustrate the process of creating a C1Document, we will walk through the steps required to implement a simple assembly documentation utility. To start, create a new project and add a reference to the C1.Silverlight and C1.Silverlight.RichTextBox assemblies. Then edit the page constructor as follows: Visual Basic Imports C1.Silverlight Imports C1.Silverlight.RichTextBox

73

Imports C1.Silverlight.RichTextBox.Documents Public Partial Class MainPage Inherits UserControl ' C1RichTextBox that will display the C1Document Private _rtb As C1RichTextBox Public Sub New() ' Default initialization InitializeComponent() ' Create the C1RichTextBox and add it to the page _rtb = New C1RichTextBox() LayoutRoot.Children.Add(_rtb) ' Create document and show it in the C1RichTextBox _rtb.Document = DocumentAssembly(GetType(C1RichTextBox).Assembly) _rtb.IsReadOnly = True End Sub End Class C# using C1.Silverlight; using C1.Silverlight.RichTextBox; using C1.Silverlight.RichTextBox.Documents; public partial class MainPage : UserControl { // C1RichTextBox that will display the C1Document C1RichTextBox _rtb; public MainPage() { // Default initialization InitializeComponent(); // Create the C1RichTextBox and add it to the page _rtb = new C1RichTextBox(); LayoutRoot.Children.Add(_rtb); // Create document and show it in the C1RichTextBox _rtb.Document = DocumentAssembly(typeof(C1RichTextBox).Assembly); _rtb.IsReadOnly = true; } } The code creates the C1RichTextBox and assigns its Document property to the result of a call to the DocumentAssembly method. It then makes the control read-only so users can't change the report. The DocumentAssembly method takes an Assembly as argument and builds a C1Document containing the assembly documentation. Here is the implementation: Visual Basic Private Function DocumentAssembly(asm As Assembly) As C1Document ' Create document Dim doc As New C1Document() doc.FontFamily = New FontFamily("Tahoma")

74

' Assembly doc.Blocks.Add(New Heading1("Assembly" & vbCr & vbLf + asm.FullName.Split(","C)(0))) ' Types For Each t As Type In asm.GetTypes() DocumentType(doc, t) Next ' Done Return doc End Function C# C1Document DocumentAssembly(Assembly asm) { // Create document C1Document doc = new C1Document(); doc.FontFamily = new FontFamily("Tahoma"); // Assembly doc.Blocks.Add(new Heading1("Assembly\r\n" + asm.FullName.Split(',')[0])); // Types foreach (Type t in asm.GetTypes()) DocumentType(doc, t); // Done return doc; } The method starts by creating a new C1Document object and setting its FontFamily property. This will be the default value for all text elements added to the document. Next, the method adds a Heading1 paragraph containing the assembly name to the new document's Blocks collection. Blocks are elements such as paragraphs and list items that flow down the document. They are similar to "div" elements in HTML. Some document elements contain an Inlines collection instead. These collections contain elements that flow horizontally, similar to "span" elements in HTML. The Heading1 class inherits from C1Paragraph and adds some formatting. We will add several such classes to the project, for normal paragraphs and headings 1 through 4. The Normal paragraph is a C1Paragraph that takes a content string in its constructor: Visual Basic Class Normal Inherits C1Paragraph Public Sub New(text As String) Me.Inlines.Add(New C1Run() With { _ Key .Text = text _ }) Me.Padding = New Thickness(30, 0, 0, 0) Me.Margin = New Thickness(0) End Sub End Class C# class Normal : C1Paragraph {

75

public Normal(string text) { this.Inlines.Add(new C1Run() { Text = text }); this.Padding = new Thickness(30, 0, 0, 0); this.Margin = new Thickness(0); } } The Heading paragraph extends Normal and makes the text bold: Visual Basic Class Heading Inherits Normal Public Sub New(text As String) MyBase.New(text) Me.FontWeight = FontWeights.Bold End Sub End Class C# class Heading : Normal { public Heading(string text) : base(text) { this.FontWeight = FontWeights.Bold; } }

Heading1 through Heading4 extend Heading to specify font sizes, padding, borders, and colors: Visual Basic Class Heading1 Inherits Heading Public Sub New(text As String) MyBase.New(text) Me.Background = New SolidColorBrush(Colors.Yellow) Me.FontSize = 24 Me.Padding = New Thickness(0, 10, 0, 10) Me.BorderBrush = New SolidColorBrush(Colors.Black) Me.BorderThickness = New Thickness(3, 1, 1, 0) End Sub End Class Class Heading2 Inherits Heading Public Sub New(text As String) MyBase.New(text) Me.FontSize = 18 Me.FontStyle = FontStyles.Italic Me.Background = New SolidColorBrush(Colors.Yellow) Me.Padding = New Thickness(10, 5, 0, 5) Me.BorderBrush = New SolidColorBrush(Colors.Black) Me.BorderThickness = New Thickness(3, 1, 1, 1) End Sub End Class Class Heading3 Inherits Heading Public Sub New(text As String) MyBase.New(text) Me.FontSize = 14

76

Me.Background = New SolidColorBrush(Colors.LightGray) Me.Padding = New Thickness(20, 3, 0, 0) End Sub End Class Class Heading4 Inherits Heading Public Sub New(text As String) MyBase.New(text) Me.FontSize = 14 Me.Padding = New Thickness(30, 0, 0, 0) End Sub End Class C# class Heading1 : Heading { public Heading1(string text) : base(text) { this.Background = new SolidColorBrush(Colors.Yellow); this.FontSize = 24; this.Padding = new Thickness(0, 10, 0, 10); this.BorderBrush = new SolidColorBrush(Colors.Black); this.BorderThickness = new Thickness(3, 1, 1, 0); } } class Heading2 : Heading { public Heading2(string text): base(text) { this.FontSize = 18; this.FontStyle = FontStyles.Italic; this.Background = new SolidColorBrush(Colors.Yellow); this.Padding = new Thickness(10, 5, 0, 5); this.BorderBrush = new SolidColorBrush(Colors.Black); this.BorderThickness = new Thickness(3, 1, 1, 1); } } class Heading3 : Heading { public Heading3(string text) : base(text) { this.FontSize = 14; this.Background = new SolidColorBrush(Colors.LightGray); this.Padding = new Thickness(20, 3, 0, 0); } } class Heading4 : Heading { public Heading4(string text): base(text) { this.FontSize = 14; this.Padding = new Thickness(30, 0, 0, 0); } }

Now that we have classes for all paragraph types in the document, it's time to add the content. Recall that we used a DocumentType method in the first code block. Here is the implementation for that method:

77

Visual Basic Private Sub DocumentType(doc As C1Document, t As Type) ' Skip non-public/generic If Not t.IsPublic OrElse t.ContainsGenericParameters Then Return End If ' Type doc.Blocks.Add(New Heading2("Class " & Convert.ToString(t.Name))) ' Properties doc.Blocks.Add(New Heading3("Properties")) For Each pi As PropertyInfo In t.GetProperties() If pi.DeclaringType = t Then DocumentProperty(doc, pi) End If Next ' Methods doc.Blocks.Add(New Heading3("Methods")) For Each mi As MethodInfo In t.GetMethods() If mi.DeclaringType = t Then DocumentMethod(doc, mi) End If Next ' Events doc.Blocks.Add(New Heading3("Events")) For Each ei As EventInfo In t.GetEvents() If ei.DeclaringType = t Then DocumentEvent(doc, ei) End If Next End Sub

C# void DocumentType(C1Document doc, Type t) { // Skip non-public/generic if (!t.IsPublic || t.ContainsGenericParameters) return; // Type doc.Blocks.Add(new Heading2("Class " + t.Name)); // Properties doc.Blocks.Add(new Heading3("Properties")); foreach (PropertyInfo pi in t.GetProperties()) { if (pi.DeclaringType == t) DocumentProperty(doc, pi); } // Methods doc.Blocks.Add(new Heading3("Methods")); foreach (MethodInfo mi in t.GetMethods()) {

78

if (mi.DeclaringType == t) DocumentMethod(doc, mi); } // Events doc.Blocks.Add(new Heading3("Events")); foreach (EventInfo ei in t.GetEvents()) { if (ei.DeclaringType == t) DocumentEvent(doc, ei); } } The method adds a Heading2 paragraph with the class name and then uses reflection to enumerate all the public properties, events, and methods in the type. The code for these methods is simple: Visual Basic Private Sub DocumentProperty(doc As C1Document, pi As PropertyInfo) If pi.PropertyType.ContainsGenericParameters Then Return End If doc.Blocks.Add(New Heading4(pi.Name)) Dim text = String.Format("public {0} {1} {{ {2}{3} }}", pi.PropertyType.Name, pi.Name, If(pi.CanRead, "get; ", String.Empty), If(pi.CanWrite, "set; ", String.Empty)) doc.Blocks.Add(New Normal(text)) End Sub C# void DocumentProperty(C1Document doc, PropertyInfo pi) { if (pi.PropertyType.ContainsGenericParameters) return; doc.Blocks.Add(new Heading4(pi.Name)); var text = string.Format("public {0} {1} {{ {2}{3} }}", pi.PropertyType.Name, pi.Name, pi.CanRead ? "get; " : string.Empty, pi.CanWrite ? "set; " : string.Empty); doc.Blocks.Add(new Normal(text)); } The method adds a Heading4 paragraph containing the property name, then some Normal text containing the property type, name, and accessors. The methods used for documenting events and properties are analogous: Visual Basic Private Sub DocumentMethod(doc As C1Document, mi As MethodInfo) If mi.IsSpecialName Then Return End If doc.Blocks.Add(New Heading4(mi.Name))

79

Dim parms = New StringBuilder() For Each parm As var In mi.GetParameters() If parms.Length > 0 Then parms.Append(", ") End If parms.AppendFormat("{0} {1}", parm.ParameterType.Name, parm.Name) Next Dim text = String.Format("public {0} {1}({2})", mi.ReturnType.Name, mi.Name, parms.ToString()) doc.Blocks.Add(New Normal(text)) End Sub Private Sub DocumentEvent(doc As C1Document, ei As EventInfo) doc.Blocks.Add(New Heading4(ei.Name)) Dim text = String.Format("public {0} {1}", ei.EventHandlerType.Name, ei.Name) doc.Blocks.Add(New Normal(text)) End Sub C# void DocumentMethod(C1Document doc, MethodInfo mi) { if (mi.IsSpecialName) return; doc.Blocks.Add(new Heading4(mi.Name)); var parms = new StringBuilder(); foreach (var parm in mi.GetParameters()) { if (parms.Length > 0) parms.Append(", "); parms.AppendFormat("{0} {1}", parm.ParameterType.Name, parm.Name); } var text = string.Format("public {0} {1}({2})", mi.ReturnType.Name, mi.Name, parms.ToString()); doc.Blocks.Add(new Normal(text)); } void DocumentEvent(C1Document doc, EventInfo ei) { doc.Blocks.Add(new Heading4(ei.Name)); var text = string.Format("public {0} {1}", ei.EventHandlerType.Name, ei.Name); doc.Blocks.Add(new Normal(text)); } If you run the project now, you will see a window like the one shown below:

80

The resulting document can be viewed and edited in the C1RichTextBox like any other. It can also be exported to HTML using the Html property in the C1RichTextBox, or copied through the clipboard to applications such as Microsoft Word or Excel. You could use the same technique to create reports based on data from a database. In addition to formatted text, the C1Document object model supports the following features: Lists Lists are created by adding C1List objects to the document. The C1List object has a ListItems property that contains C1ListItem objects, which are also blocks. Hyperlinks Hyperlinks are created by adding C1Hyperlink objects to the document. The C1Hyperlink object has an Inlines property that contains a collection of runs (typically C1Run elements that contain text), and a NavigateUrl property that determines the action to be taken when the hyperlink is clicked. Images Images and other FrameworkElement objects are created by adding C1BlockUIContainer objects to the document. The C1BlockUIContainer object has a Child property that can be set to any FrameworkElement object. Note that not all objects can be exported to HTML. Images are a special case that the HTML filter knows how to handle.

Implementing Split Views

Many editors offer split-views of a document, allowing you to keep a part of the document visible while you work on another part.

81

You can achieve this easily by connecting two or more C1RichTextBox controls to the same underlying C1Document. Each control acts as an independent view, allowing you to scroll, select, and edit the document as usual. Changes made to one view are reflected on all other views. To show how this works, let's extend the previous example by adding a few lines of code to the page constructor: Visual Basic Public Sub New() ' Default initialization InitializeComponent() ' Create the C1RichTextBox and add it to the page _rtb = New C1RichTextBox() LayoutRoot.Children.Add(_rtb) ' Create document and show it in the C1RichTextBox _rtb.Document = DocumentAssembly(GetType(C1RichTextBox).Assembly) _rtb.IsReadOnly = True ' Attach event handler AddHandler _rtb.ElementMouseLeftButtonDown, AddressOf _rtb_ElementMouseLeftButtonDown ' Add a second C1RichTextBox to the page LayoutRoot.RowDefinitions.Add(New RowDefinition()) LayoutRoot.RowDefinitions.Add(New RowDefinition()) Dim rtb2 = New C1RichTextBox() rtb2.SetValue(Grid.RowProperty, 1) LayoutRoot.Children.Add(rtb2) ' Bind the second C1RichTextBox to the same document rtb2.Document = _rtb.Document End Sub C# public MainPage() { // Default initialization InitializeComponent(); // Create the C1RichTextBox and add it to the page _rtb = new C1RichTextBox(); LayoutRoot.Children.Add(_rtb); // Create document and show it in the C1RichTextBox _rtb.Document = DocumentAssembly(typeof(C1RichTextBox).Assembly); _rtb.IsReadOnly = true; // Attach event handler _rtb.ElementMouseLeftButtonDown += _rtb_ElementMouseLeftButtonDown; // Add a second C1RichTextBox to the page LayoutRoot.RowDefinitions.Add(new RowDefinition()); LayoutRoot.RowDefinitions.Add(new RowDefinition()); var rtb2 = new C1RichTextBox(); rtb2.SetValue(Grid.RowProperty, 1); LayoutRoot.Children.Add(rtb2);

82

// Bind the second C1RichTextBox to the same document rtb2.Document = _rtb.Document; } The new code adds a new C1RichTextBox to the page and then sets its Document property to the document being shown by the original C1RichTextBox. If you run the project again, you will see a window like the one shown below:

The bottom control is editable (we did not set its IsReadOnly property to False). If you type into it, you will see the changes on both controls simultaneously. The mechanism is general; we could easily attach more views of the same document. Moreover, any changes you make to the underlying document are immediately reflected on all views.

Using the C1Document Class

As we mentioned earlier, the C1RichTextBox provides a linear, flat view of the control content, while C1Document class exposes the document structure. To illustrate the advantages of working directly with the document object, suppose you wanted to add some functionality to the previous sample: when the user presses the CTRL key, you want to capitalize the text in all paragraphs of type Heading2. The object model exposed by the C1RichTextBox is not powerful enough to do this reliably. You would have to locate spans based on their formatting, which would be inefficient and unreliable (what if the user formatted some plain text with the same format used by Heading2?). Using the C1Document object model, this task becomes trivial:

83

Visual Basic Public Sub New() ' Default initialization InitializeComponent() ' No changes here... ' Bind the second C1RichTextBox to the same document rtb2.Document = _rtb.Document AddHandler rtb2.KeyDown, AddressOf rtb2_KeyDown End Sub Private Sub rtb2_KeyDown(sender As Object, e As KeyEventArgs) If e.Key = Key.Ctrl Then For Each heading2 As var In _rtb.Document.Blocks.OfType(Of Heading2)() Dim text = heading2.ContentRange.Text heading2.ContentRange.Text = text.ToUpper() Next End If End Sub

C# public MainPage() { // Default initialization InitializeComponent(); // No changes here... // Bind the second C1RichTextBox to the same document rtb2.Document = _rtb.Document; rtb2.KeyDown += rtb2_KeyDown; } void rtb2_KeyDown(object sender, KeyEventArgs e) { if (e.Key == Key.Ctrl) { foreach (var heading2 in _rtb.Document.Blocks.OfType<Heading2>()) { var text = heading2.ContentRange.Text; heading2.ContentRange.Text = text.ToUpper(); } } }

The code monitors the keyboard. When the user presses the CTRL key, it enumerates all Heading2 elements in the document and replaces their content with capitals. Doing the same thing using the C1RichTextBox object model would require a lot more code and the result would not be as reliable.

Understanding C1TextPointer

The C1TextPointer class represents a position inside a C1Document. It is intended to facilitate traversal and manipulation of C1Documents. The functionality is analogous to WPF's TextPointer class, although the object model has many differences. A C1TextPointer is defined by a C1TextElement and an offset inside of it. Let's take this document as an example:

84

C1Document

C1Paragraph

C1Paragraph

C1Run

C1InlineUIContainer

C1Run

C

A

T

UI

D

O

G

The blue bracketed nodes above are C1TextElements; the offset of a C1TextPointer indicates between which children the position is located. For instance, a position that points to the C1Document above with offset 0 is just before the first C1Paragraph, offset 1 is between the two paragraphs, and offset 2 is after the second paragraph. When a C1TextPointer points to a C1Run, each character in its text is considered a child of C1Run, so the offset indicates a position inside the text. A C1InlineUIContainer is considered to have a single child (the UIElement it displays) so it has two positions, one before and one after the child. An alternative way to visualize a document is as a sequence of symbols, where a symbol can be either an element tag or some type of content. An element tag indicates the start or end of an element. In XML, the above document would be written as: <C1Document> <C1Paragraph> <C1Run>CAT</C1Run> <C1InlineUIContainer><UI/></C1InlineUIContainer> </C1Paragraph> <C1Paragraph> <C1Run>DOG</C1Run> </C1Paragraph> </C1Document> Viewing the document like this, a C1TextPointer points to a position between tags or content. This view also gives a clear order to C1TextPointer. In fact, C1TextPointer implements IComparable, and also overloads the comparison operators for convenience. The symbol that is after a C1TextPointer can be obtained using the Symbol property. This property returns an object that can be of type StartTag, EndTag, char or UIElement. If you want to iterate through the positions in a document, there are two methods available: GetPositionAtOffset and Enumerate. GetPositionAtOffset is the low-level method; it just returns the position at a specified integer offset. Enumerate is the recommended way to iterate through positions. It returns an IEnumerable<C1TextPointer> that iterates through all the positions in a specified direction. For instance, this returns all the positions in a document: document.ContentStart.Enumerate() Note that ContentStart returns the first C1TextPointer in a C1TextElement; there is also a ContentEnd property that returns the last position. The interesting thing about Enumerate is that it returns a lazy enumeration. That is, C1TextPointer objects are only created when the IEnumerable is iterated. This allows for efficient use of LINQ extensions methods for filtering, finding, selecting, and so on. As an example, let's say you want to get the C1TextRange for the word contained under a C1TextPointer. You can do the following:

85

Visual Basic Private Function ExpandToWord(pos As C1TextPointer) As C1TextRange ' Find word start Dim wordStart = If(pos.IsWordStart, pos, pos.Enumerate(LogicalDirection.Backward).First(Function(p) p.IsWordStart)) ' Find word end Dim wordEnd = If(pos.IsWordEnd, pos, pos.Enumerate(LogicalDirection.Forward).First(Function(p) p.IsWordEnd)) ' Return new range from word start to word end Return New C1TextRange(wordStart, wordEnd) End Function

C# C1TextRange ExpandToWord(C1TextPointer pos) { // Find word start var wordStart = pos.IsWordStart ? pos : pos.Enumerate(LogicalDirection.Backward).First(p => p.IsWordStart); // Find word end var wordEnd = pos.IsWordEnd ? pos : pos.Enumerate(LogicalDirection.Forward).First(p => p.IsWordEnd); // Return new range from word start to word end return new C1TextRange(wordStart, wordEnd); }

The Enumerate method returns the positions in a specified direction, but it doesn't include the current position. So the code first checks if the parameter position is a word start, and if not, searches backward for a position that is a word start. Likewise for the word end, it checks the parameter position and then searches forward. We want to find the word that contains the parameter position, so we need the first word end moving forward and the first word start moving backward. C1TextPointer already contains the properties IsWordStart and IsWordEnd that tells you whether a position is a word start or end depending on the surrounding symbols. We use the First LINQ extension method to find the first position that satisfies our required predicate. And finally we create a C1TextRange from the two positions. LINQ extension methods can be very useful when working with positions. As another example we can count the words in a document like this: Visual Basic document.ContentStart.Enumerate().Count(Function(p) p.IsWordStart AndAlso TypeOf p.Symbol Is Char) C# document.ContentStart.Enumerate().Count(p => p.IsWordStart && p.Symbol is char)

Note that we need to check that the symbol following a word start is a char because IsWordStart returns True for positions that are not exactly at the start of a word. For instance the position just before a C1Run start tag is considered a word start if the first position of the C1Run is a word start. Let's implement a Find method as another example: Visual Basic

86

Private Function FindWordFromPosition(position As C1TextPointer, word As String) As C1TextRange ' Get all ranges whose text length is equal to word.Length Dim ranges = position.Enumerate().[Select](Function(pos) ' Get a position that is at word.Length offset ' but ignoring tags that do not change the text flow Dim [end] = pos.GetPositionAtOffset(word.Length, C1TextRange.TextTagFilter) Return New C1TextRange(pos, [end]) End Function) ' returned value will be null if word is not found. Return ranges.FirstOrDefault(Function(range) range.Text = word) End Function C# C1TextRange FindWordFromPosition(C1TextPointer position, string word) { // Get all ranges whose text length is equal to word.Length var ranges = position.Enumerate().Select(pos => { // Get a position that is at word.Length offset // but ignoring tags that do not change the text flow var end = pos.GetPositionAtOffset(word.Length, C1TextRange.TextTagFilter); return new C1TextRange(pos, end); }); // returned value will be null if word is not found. return ranges.FirstOrDefault(range => range.Text == word); }

We want to find the word from a specified position, so we enumerate all positions forward, and select all ranges whose text length is word.Length. For each position we need to find the position that is at word.Length distance. For this we use the GetPositionAtOffset method. This method returns a position at a specified offset, but it also counts all inline tags as valid positions, we need to ignore this to account for the case when a word is split between two C1Run elements. That is why we use C1TextRange.TextTagFilter; this is the same filter method used by the internal logic that translates document trees into text. As a final step we search for the range whose text matches the searched word. As a last example let's replace the first occurrence of a word: Visual Basic Dim wordRange = FindWordFromPosition(document.ContentStart, "cat") If wordRange IsNot Nothing Then wordRange.Text = "dog" End If C# var wordRange = FindWordFromPosition(document.ContentStart, "cat"); if (wordRange != null) { wordRange.Text = "dog"; }

We can use the previous example to first find the word, and then replace the text by just assigning to Text property.

87

Working with C1RichTextBoxToolbar

The C1RichTextBoxToolbar control is a full-featured, ribbon-like toolbar that easily turns the C1RichTextBox control into a complete text editor. The C1RichTextBoxToolbar control is based on the C1Toolbar control allowing complete customization. To connect a C1RichTextBoxToolbar control to a C1RichTextBox control you would need to set the RichTextBox property to the name of the control you want to link with the toolbar. For an example, see Connecting a C1RichTextBoxToolbar to a C1RichTextBox (page 112) topic. When you add the C1RichTextBoxToolbar to your application, it appears similar to the following:

The buttons within the toolbar appear very similar to options in Microsoft Word and other editors, so they should appear familiar to end-users. There are two tabs: Home and Tables. Home Tab The Home tab includes five defined groups of elements: Edit, Font, Paragraph, Insert, and Tools.

Tables Tab The Tables tab includes four defined groups of elements: Table, Rows & Columns, Merge, and Cell.

The following topics explain the elements within each group.

88

Edit Group

The Edit group provides standard editing tools, such as copy, paste, and undo. It looks similar to the following image:

The Edit group includes the following options: Paste: Clicking the Paste button pastes the selected text into the C1RichTextBox. You can also paste text by pressing the CTRL + V key combination while text is selected. Cut: Clicking the Cut button cuts the selected text and places it on the clipboard. You can also cut text by pressing the CTRL + X key combination while text is selected. Copy: Clicking the Copy button copies the selected text so that it can be pasted into the C1RichTextBox or another application. You can also copy text by pressing the CTRL + C key combination while text is selected. Undo: Clicking the Undo button reverses the previous changes made to the content of the C1RichTextBox. The Undo button is not active unless changes have been made. You can also undo changes by pressing the CTRL + Z key combination. Redo: Clicking the Redo button after the Undo button has been clicked repeats the changes that had been previously reversed. The Redo button is not active unless the Undo button has been clicked. You can also redo changes by pressing the CTRL + Y key combination. FP: Clicking the FP button copies the formatting of the selected text and allows you to apply it to other text.

Font Group

The Font group includes several options for customizing the font used in the C1RichTextBox control. The Font group appears similar to the following image:

The Font group includes the following options: Font: The Font option is a drop-down list that allows you to choose the font that will be applied to text in the C1RichTextBox control. The default font is Portable User Interface.

89

Font Size: The Font Size option is a drop-down list that allows you to choose the size of the font that will be applied to text in the C1RichTextBox control. The default font size is 9. Grow Font: Clicking the Grow Font button increases the size of the selected text. Shrink Font: Clicking the Shrink Font button decreases the size of the selected text. Bold: Clicking the Bold button bolds or removes bolding from the selected text. Italic: Clicking the Italic button italicizes or removes italics from the selected text. Underline: Clicking the Underline button underlines or removes underlining from the selected text. Change Case: The Change Case option is a drop-down list that lists options that will change the case of the selected text. Options include: lowercase, UPPERCASE, Capitalize Each Word, and tOGGLE cASE (which turns lowercase text into uppercase text and uppercase text into lowercase text).

Superscript: Clicking the Superscript button turns the selected text into superscript text (the text will appear placed higher vertically than text that is not superscript text). Subscript: Clicking the Subscript button turns the selected text into subscript text (the text will appear placed lower vertically than text that is not superscript text). Font Color: The Font Color option is a drop-down color picker that lists common colors that will change the color of the selected text.

90

Text Highlight Color: The Text Highlight Color option is a drop-down color picker that lists common colors that will change the color of the background surrounding the selected text.

Paragraph Group

The Paragraph group includes several options for customizing the paragraph settings used in the C1RichTextBox control. The Paragraph group appears similar to the following image:

The Paragraph group includes the following options: Align Text Left: The Align Text Left option aligns the selected text so that it is left justified. This is the default alignment option. Align Text Center: The Align Text Center option aligns the selected text so that it is centered in the RichTextBox control. Align Text Right: The Align Text Right option aligns the selected text so that it is right justified. Justify: The Justify option spaces the selected text so that it is fully justified. Bullets: The Bullets option is a button that adds or removes bulleting from the selected text. Numbering: The Numbering option is a button that adds or removes numbering from the selected text. Text Wrapping: The Text Wrapping option determines if lines of text should be wrapped to fit in the RichTextBox. By default text is wrapped. Borders: The Borders drop-down box allows you to set the border color, thickness, and where the borders appear.

91

Paragraph Color: The Paragraph Color option is a drop-down color picker that lists common colors that will change the color of the background of the entire paragraph. By default this option is set to White.

Margin: The Margin drop-down box, allows you to set the margin thickness of the Left, Right, Top, and Bottom margins surrounding the text. By default the Left, Right, and Top values are set to 0 and the Bottom margin is set to 10. Padding: The Padding drop-down box, allows you to set the padding space of the Left, Right, Top, and Bottom areas surrounding the selected text. By default these values are set to 0 and there is no padding.

Insert Group

The Insert group allows inserting content in the C1RichTextBox control. The Insert group appears similar to the following image:

92

The Insert group includes the following options: Insert Image: Clicking the Insert Image button brings up the Insert Image dialog box which allows you to browse for and select an image to insert or enter a URL for the image to be inserted:

Insert Symbol: Clicking the Insert Symbol option brings up a drop-down box that allows you to choose a symbol to insert into the RichTextBox:

Insert Hyperlink: Clicking the Insert Hyperlink button brings up the Insert Hyperlink dialog box which allows you to enter the hyperlink text and URL to insert:

93

Remove Hyperlink: Clicking the Remove Hyperlink button removes any hyperlinks within the selected text. Highlight the hyperlink in the RichTextBox and click the Remove Hyperlink button to remove the link.

Tools Group

The Tools group allows manipulating and editing content in the C1RichTextBox control. The Tools group appears similar to the following image:

The Tools group includes the following options: Spell Check: Clicking the Spell Check button opens the Spelling dialog box. Note that spell-checking must be set up for this button to be active. See Spell-Checking (page 58) for details. In the Spelling dialog box you can view suggested spellings and Ignore the error, Ignore All errors in instances of the same word, Change the current spelling to a suggested one, Change All instances of the current spelling, Add the current spelling to the spell-checking dictionary, Suggest to view additional spellings based on a suggested spelling, and Cancel to close the dialog box and cancel the spell-check operation.

94

Find and Replace: Clicking the Find and Replace option displays a drop-down box that allows you to enter text to find or find and replace in the content of the RichTextBox. You can Replace each instance one by one, Replace All instances, or Find Next instance.

Elements Supported in RichTextBox

The following sections detail what HTML 4 elements, HTML attributes, CSS2 properties, and CSS selectors are supported in RichTextBox for Silverlight.

HTML Elements

RichTextBox for Silverlight supports several HTML 4 elements. The following table lists HTML elements by names and notes whether they are supported by RichTextBox for Silverlight.

Name Supported

A ABBR ACRONYM ADDRESS APPLET

Yes Yes Yes Yes No

95

AREA B BASE BASEFONT BDO BIG BLOCKQUOTE BODY BR BUTTON CAPTION CENTER CITE CODE COL COLGROUP DD DEL DFN DIR DIV DL DT EM FIELDSET FONT FORM FRAME FRAMESET H1 H2 H3

No Yes No Yes No Yes Yes Yes Yes No No Yes Yes Yes Yes Yes Yes Yes Yes Yes Yes Yes Yes Yes No Yes No No No Yes Yes Yes

96

H4 H5 H6 HEAD HR HTML I IFRAME IMG INPUT INS ISINDEX KBD LABEL LEGEND LI LINK MAP MENU META NOFRAMES NOSCRIPT OBJECT OL OPTGROUP OPTION P PARAM PRE Q S SAMP

Yes Yes Yes Yes Yes Yes Yes No Yes No Yes No Yes Yes No Yes No No Yes No No No No Yes No No Yes No Yes No Yes Yes

97

SCRIPT SELECT SMALL SPAN STRIKE STRONG STYLE SUB SUP TABLE TBODY TD TEXTAREA TFOOT TH THEAD TITLE TR TT U UL VAR

No No Yes Yes Yes Yes Yes Yes Yes Yes Yes Yes No Yes Yes Yes No Yes Yes Yes Yes Yes

HTML Attributes

RichTextBox for Silverlight supports several HTML 4 attribute. The following table lists HTML attributes by name and element and notes whether they are supported by RichTextBox for Silverlight.

Name Elements Supported

abbr accept-charset accept accesskey action align

TD, TH FORM FORM, INPUT A, AREA, BUTTON, INPUT, LABEL, LEGEND, TEXTAREA FORM CAPTION

No No No No No No

98

align align align align align align alink alt alt alt archive archive axis background bgcolor bgcolor bgcolor bgcolor border border cellpadding cellspacing char charoff charset checked cite cite class classid clear code

APPLET, IFRAME, IMG, INPUT, OBJECT LEGEND TABLE HR DIV, H1, H2, H3, H4, H5, H6, P COL, COLGROUP, TBODY, TD, TFOOT, TH, THEAD, TR BODY APPLET AREA, IMG INPUT APPLET OBJECT TD, TH BODY TABLE TR TD, TH BODY TABLE IMG, OBJECT TABLE TABLE COL, COLGROUP, TBODY, TD, TFOOT, TH, THEAD, TR COL, COLGROUP, TBODY, TD, TFOOT, TH, THEAD, TR A, LINK, SCRIPT INPUT BLOCKQUOTE, Q DEL, INS All elements but BASE, BASEFONT, HEAD, HTML, META, PARAM, SCRIPT, STYLE, TITLE OBJECT BR APPLET

No No No No Yes No No No No No No No No No Yes Yes Yes Yes Yes Yes No Yes No No No No No No Yes No No No

99

codebase codebase codetype color cols cols colspan compact content coords coords data datetime declare defer dir dir disabled enctype face for frame frameborder headers height height height height href href hreflang hspace

OBJECT APPLET OBJECT BASEFONT, FONT FRAMESET TEXTAREA TD, TH DIR, DL, MENU, OL, UL META AREA A OBJECT DEL, INS OBJECT SCRIPT All elements but APPLET, BASE, BASEFONT, BDO, BR, FRAME, FRAMESET, IFRAME, PARAM, SCRIPT BDO

No No No No No No Yes No No No No No No No No No No

BUTTON, INPUT, OPTGROUP, OPTION, SELECT, TEXTAREA No FORM BASEFONT, FONT LABEL TABLE FRAME, IFRAME TD, TH IFRAME TD, TH IMG, OBJECT APPLET A, AREA, LINK BASE A, LINK APPLET, IMG, OBJECT No Yes No Yes No No No No Yes No Yes No No Yes

100

http-equiv id ismap label label lang language link longdesc longdesc marginheight marginwidth maxlength media media method multiple name name name name name name name name name name name nohref noresize noshade

META All elements but BASE, HEAD, HTML, META, SCRIPT, STYLE, TITLE IMG, INPUT OPTION OPTGROUP All elements but APPLET, BASE, BASEFONT, BR, FRAME, FRAMESET, IFRAME, PARAM, SCRIPT SCRIPT BODY IMG FRAME, IFRAME FRAME, IFRAME FRAME, IFRAME INPUT STYLE LINK FORM SELECT BUTTON, TEXTAREA APPLET SELECT FORM FRAME, IFRAME IMG A INPUT, OBJECT MAP PARAM META AREA FRAME HR

No Yes No No No No No No No No No No No No No No No No No No No No No No No No No No No No No

101

nowrap object onblur onchange onclick

TD, TH APPLET A, AREA, BUTTON, INPUT, LABEL, SELECT, TEXTAREA INPUT, SELECT, TEXTAREA All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE A, AREA, BUTTON, INPUT, LABEL, SELECT, TEXTAREA All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE FRAMESET BODY

No No No No No

ondblclick

No

onfocus onkeydown

No No

onkeypress

No

onkeyup

No

onload onload

No No No

onmousedown All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE onmousemove All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE onmouseout All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE All elements but APPLET, BASE, BASEFONT, BDO, BR, FONT, FRAME, FRAMESET, HEAD, HTML, IFRAME, ISINDEX, META, PARAM, SCRIPT, STYLE, TITLE FORM INPUT, TEXTAREA

No

No

onmouseover

No

onmouseup

No

onreset onselect

No No

102

onsubmit onunload onunload profile prompt readonly readonly rel rev rows rows rowspan rules scheme scope scrolling selected shape shape size size size size size span span src src src src standby start

FORM FRAMESET BODY HEAD ISINDEX TEXTAREA INPUT A, LINK A, LINK FRAMESET TEXTAREA TD, TH TABLE META TD, TH FRAME, IFRAME OPTION AREA A HR FONT INPUT BASEFONT SELECT COL COLGROUP SCRIPT INPUT FRAME, IFRAME IMG OBJECT OL

No No No No No No No No No No No Yes Yes No No No No No No No No No No No No No No No No No No Yes

103

style summary tabindex target text title type type type type type type type type type type usemap valign value value value value value valuetype version vlink vspace width width width width

All elements but BASE, BASEFONT, HEAD, HTML, META, PARAM, SCRIPT, STYLE, TITLE TABLE A, AREA, BUTTON, INPUT, OBJECT, SELECT, TEXTAREA A, AREA, BASE, FORM, LINK BODY All elements but BASE, BASEFONT, HEAD, HTML, META, PARAM, SCRIPT, TITLE A, LINK OBJECT PARAM SCRIPT STYLE INPUT LI OL UL BUTTON IMG, INPUT, OBJECT COL, COLGROUP, TBODY, TD, TFOOT, TH, THEAD, TR INPUT OPTION PARAM BUTTON LI PARAM HTML BODY APPLET, IMG, OBJECT HR IFRAME IMG, OBJECT TABLE

Yes No No No No Yes No No No No No No No No No No No Yes No No No No No No No No Yes No No Yes No

104

width width width width width

TD, TH APPLET COL COLGROUP PRE

No No Yes No No

CSS2 Properties

RichTextBox for Silverlight supports several CSS2 properties. The following table lists CSS2 properties by name and media group and notes whether they are supported by RichTextBox for Silverlight.

Name Media groups Supported Comments

azimuth background-attachment background-color background-image background-position background-repeat background border-collapse border-color border-spacing border-style

aural visual visual visual visual visual visual visual visual visual visual

No No Yes Yes No No Yes Yes Yes Yes Yes Supports 'none', 'hidden', and solid. Other values are treated as solid. Only supports color and image. The image is not repeated.

border-top border-right border-bottom border-left border-top-color borderright-color border-bottomcolor border-left-color border-top-style borderright-style border-bottomstyle border-left-style border-top-width borderright-width border-bottomwidth border-left-width

visual visual

Yes Yes

visual

Yes

visual

Yes

105

border-width border bottom caption-side clear clip color content counter-increment counter-reset cue-after cue-before cue cursor

visual visual visual visual visual visual visual all all all aural aural aural visual, interactive

Yes Yes No No No No Yes No No No No No No Yes All values except crosshair, move, progress, help, and <uri>.

direction display

visual all

No Yes All values except run-in, inline-block, inline-table, and table-caption.

elevation empty-cells float font-family font-size font-style font-variant font-weight font height left letter-spacing line-height

aural visual visual visual visual visual visual visual visual visual visual visual visual

No No No Yes Yes Yes No Yes Yes Yes No No Yes Only in img elements.

106

list-style-image list-style-position list-style-type

visual visual visual

Yes No Yes All values except georgian, armenian and, lower-greek.

list-style margin-right margin-left margin-top margin-bottom margin max-height max-width min-height min-width orphans outline-color outline-style outline-width outline overflow padding-top padding-right padding-bottom paddingleft padding page-break-after page-break-before page-break-inside pause-after pause-before pause pitch-range pitch

visual visual visual visual visual visual visual visual visual, paged visual, interactive visual, interactive visual, interactive visual, interactive visual visual

Yes Yes Yes Yes No No No No No No No No No No Yes

visual visual, paged visual, paged visual, paged aural aural aural aural aural

Yes No No No No No No No No

107

play-during position quotes richness right speak-header speak-numeral speak-punctuation speak speech-rate stress table-layout text-align text-decoration text-indent text-transform top unicode-bidi vertical-align

aural visual visual aural visual aural aural aural aural aural aural visual visual visual visual visual visual visual visual

No No No No No No No No No No No No Yes Yes Yes No No No Yes All values except <percentage> and <length>.

visibility voice-family volume white-space

visual aural aural visual

Yes No No Yes Nowrap and pre are treated like normal and pre-wrap.

widows width word-spacing z-index

visual, paged visual visual visual

No Yes No No Only in img elements.

CSS2 Selectors

RichTextBox for Silverlight supports several CSS2 selectors. The following table lists CSS2 selectors by pattern and CSS level and notes whether they are supported by RichTextBox for Silverlight.

108

Pattern

CSS level

Supported

* E E[foo] E[foo="bar"] E[foo~="bar"] E[foo^="bar"] E[foo$="bar"] E[foo*="bar"] E[foo|="en"] E:root E:nth-child(n) E:nth-last-child(n) E:nth-of-type(n) E:nth-last-of-type(n) E:first-child E:last-child E:first-of-type E:last-of-type E:only-child E:only-of-type E:empty E:link E:visited E:active E:hover E:focus E:target E:lang(fr) E:enabled E:disabled E:checked

2 1 2 2 2 3 3 3 2 3 3 3 3 3 2 3 3 3 3 3 3 1 1 2 2 2 3 2 3 3 3

Yes Yes Yes Yes Yes Yes Yes Yes Yes No No No No No No No No No No No No No No No No No No No No No No

109

E::first-line E::first-letter E::before E::after E.warning E#myid E:not(s) EF E>F E+F E~F

1 1 2 2 1 1 3 1 2 2 3

No No No No No Yes No Yes Yes Yes Yes

RichTextBox for Silverlight Task-Based Help

The task-based help assumes that you are familiar with programming in Visual Studio .NET and know how to use the C1RichTextBox control in general. If you are unfamiliar with the ComponentOne RichTextBox for Silverlight product, please see the RichTextBox for Silverlight Quick Start (page 42) first. Each topic in this section provides a solution for specific tasks using the ComponentOne RichTextBox for Silverlight product. Each task-based help topic also assumes that you have created a new Silverlight project.

Setting the Text Content

The Text property determines the text content of the C1RichTextBox control. By default the C1RichTextBox control starts blank and without content but you can customize this at design time, in XAML, and in code. Note that you can also set HTML markup as the control's content. See Setting the HTML Content (page 111) for details. At Design Time To set the Text property, complete the following steps: 1. 2. Click the C1RichTextBox control once to select it. Navigate to the Properties window, and enter text, for example "Hello World!", in the text box next to the Text property. This will set the Text property to the value you chose. In XAML For example, to set the Text property add Text="Hello World!" to the <c1rtb:C1RichTextBox> tag so that it appears similar to the following: <c1rtb:C1RichTextBox HorizontalAlignment="Left" Margin="10,10,0,0" Name="C1RichTextBox1" VerticalAlignment="Top" Height="83" Width="208" Text="Hello World!" /> In Code For example, to set the Text property add the following code to your project: Visual Basic C1RichTextBox1.Text = "Hello World!"

110

C# c1RichTextBox1.Text = "Hello World!";

What You've Accomplished You've set the text content of the C1RichTextBox control. Run your application and observe that initially "Hello World!" (or the text you chose) will appear in the control:

Note that you can also set HTML markup as the control's content. See Setting the HTML Content (page 111) for details.

Setting the HTML Content

The Html property determines the HTML markup content of the C1RichTextBox control. By default the C1RichTextBox control starts blank and without content but you can customize this at design time, in XAML, and in code. Note that you can also set text as the control's content. See Setting the Text Content (page 110) for details. At Design Time To set the Html property, complete the following steps: 1. 2. Click the C1RichTextBox control once to select it. Navigate to the Properties window, and enter text, for example "<h1>Hello World!</h1>", in the text box next to the Html property. This will set the Html property to the value you chose. In XAML For example, to set the Html property add Html="Hello World!" to the <c1rtb:C1RichTextBox> tag so that it appears similar to the following: <c1rtb:C1RichTextBox HorizontalAlignment="Left" Margin="10,10,0,0" Name="C1RichTextBox1" VerticalAlignment="Top" c1:C1NagScreen.Nag="True" Height="83" Width="208" Html="<h1>Hello World!</h1>" /> In Code For example, to set the Html property add the following code to your project: Visual Basic Me.C1RichTextBox1.Html = "<h1>Hello World!</h1>" C# this.c1RichTextBox1.Html = "<h1>Hello World!</h1>";

What You've Accomplished You've set the text content of the C1RichTextBox control. Note that you had to represent angle brackets (< >) as "<" and ">". Run your application and observe that initially "Hello World!" (or the text you chose) will appear in the control in large text:

111

Note that you can also set text as the control's content. See Setting the Text Content (page 110) for details. For an example of adding a hyperlink to the content of the C1RichTextBox control, see the Hyperlinks (page 52) topic.

Connecting a C1RichTextBoxToolbar to a C1RichTextBox

To connect a C1RichTextBoxToolbar control to a C1RichTextBox control you would need to set the RichTextBox property to the name of the control you want to link with the toolbar. You can connect a C1RichTextBoxToolbar control to a C1RichTextBox control at design time, in XAML, and in code. At Design Time To set the RichTextBox property in Microsoft Expression Blend, complete the following steps: 1. 2. 3. 4. Click the C1RichTextBox control once to select it. Navigate to the Properties window, and click the Advanced Options button next to the RichTextBox property. In the Create Data Binding dialog box, click the Element Property tab. In the Element Property tab, select the C1RichTextBox1 item and click OK. This will set the RichTextBox property to C1RichTextBox1. In XAML For example, to set the RichTextBox property add RichTextBox="{Binding ElementName=C1RichTextBox1}" to the <c1rtb:C1RichTextBox> tag so that it appears similar to the following: <c1rtb:C1RichTextBox HorizontalAlignment="Left" Margin="10,10,0,0" Name="C1RichTextBox1" VerticalAlignment="Top" c1:C1NagScreen.Nag="True" Height="83" Width="208" RichTextBox="{Binding ElementName=C1RichTextBox1}" /> In Code For example, to set the RichTextBox property add the following code to your project: Visual Basic Me.C1RichTextBoxToolbar1.RichTextBox = C1RichTextBox1 C# this.c1RichTextBoxToolbar1.RichTextBox = c1RichTextBox1;

What You've Accomplished You've linked a C1RichTextBoxToolbar to a C1RichTextBox control. Now when you type text in the C1RichTextBox, for example, change the content appearance, for example, the font. For more information about the C1RichTextBox control, see the Working with C1RichTextBoxToolbar (page 88) topics.

Implementing a Simple Formatting Toolbar

While you can use the C1RichTextBox control to add a full toolbar to use with the C1RichTextBox control, you can also easily create your own simple toolbar. Most rich editors include a toolbar with buttons that format the current selection, making it bold, italic, or underlined. The buttons also change state when you move the selection, to show that the selected text is bold, italic, underlined, and so on.

112

Implementing a simple toolbar with the C1RichTextBox is easy. For example, complete the following steps: 1. 2. 3. In the Solution Explorer, right-click the project and, from the context menu, choose Add Reference. In the Add Reference dialog box, select the C1.Silverlight.RichTextBox assembly and click OK. Update the XAML on the page, so it appears similar to the following: <UserControl x:Class="C1RichTextBoxIntro.MainPage" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:c1rtb= "clrnamespace:C1.Silverlight.RichTextBox;assembly=C1.Silverlight.RichTextBox"> <Grid x:Name="LayoutRoot" Background="White"> <Grid.RowDefinitions> <RowDefinition Height="Auto" /> <RowDefinition /> </Grid.RowDefinitions> <StackPanel Orientation="Horizontal" > <ToggleButton x:Name="_btnBold" Content="B" Click="_btnBold_Click" /> <ToggleButton x:Name="_btnItalic" Content="I" Click="_btnItalic_Click" /> <ToggleButton x:Name="_btnUnderline" Content="U" Click="_btnUnderline_Click" /> </StackPanel> <c1rtb:C1RichTextBox x:Name="_rtb" Grid.Row="1" AcceptsReturn="True" SelectionChanged="_rtb_SelectionChanged"/> </Grid> </UserControl> This markup adds a C1RichTextBox control and three buttons (bold, italic, and underline) that control its formatting. When a button is clicked, the attached event handlers are responsible for updating the format of the selection. The code in the next step accomplishes that. 4. 5. Right-click the page and choose View Code to switch to the Code Editor. Add the following code to your application: Visual Basic Private Sub _btnBold_Click(sender As Object, e As RoutedEventArgs) Dim fw As System.Nullable(Of FontWeight) = _rtb.Selection.FontWeight _rtb.Selection.FontWeight = If(fw.HasValue AndAlso fw.Value = FontWeights.Bold, FontWeights.Normal, FontWeights.Bold) End Sub C# private void _btnBold_Click(object sender, RoutedEventArgs e) { FontWeight? fw = _rtb.Selection.FontWeight; _rtb.Selection.FontWeight = fw.HasValue && fw.Value == FontWeights.Bold ? FontWeights.Normal : FontWeights.Bold; }

The code starts by getting the value of the FontWeight property for the current selection. Note that the value returned is nullable (hence the '?' in the type declaration). If the selection contains a mix of different

113

font weights, the value returned is null. The code above sets the font weight to "normal" if the whole selection has a single font weight and is bold; otherwise, the code sets the font weight to "bold". 6. Add the following code to initialize the italics button: Visual Basic Private Sub _btnItalic_Click(sender As Object, e As RoutedEventArgs) Dim fs As System.Nullable(Of FontStyle) = _rtb.Selection.FontStyle _rtb.Selection.FontStyle = If(fs.HasValue AndAlso fs.Value = FontStyles.Italic, FontStyles.Normal, FontStyles.Italic) End Sub C# private void _btnItalic_Click(object sender, RoutedEventArgs e) { FontStyle? fs = _rtb.Selection.FontStyle; _rtb.Selection.FontStyle = fs.HasValue && fs.Value == FontStyles.Italic ? FontStyles.Normal : FontStyles.Italic; }

The code that handles the italics button is very similar to the code that handles the bold button, except it uses the FontStyle property instead of FontWeight. 7. Add the following code to initialize the underline button: Visual Basic Private Sub _btnUnderline_Click(sender As Object, e As RoutedEventArgs) If _btnUnderline.IsChecked.HasValue Then rtb.Selection.TextDecorations = If(_btnUnderline.IsChecked.Value, C1TextDecorations.Underline, Nothing) End If End Sub C# private void _btnUnderline_Click(object sender, RoutedEventArgs e) { if (_btnUnderline.IsChecked.HasValue) { _rtb.Selection.TextDecorations = _btnUnderline.IsChecked.Value ? C1TextDecorations.Underline : null; } }

The code that handles the underline button is similar, this time using the TextDecorations property. Note that TextDecorations property returns an actual object, and thus is not a nullable property. The above code is all it takes to make the three buttons work. 8. Add the following code to implement the event handler for the SelectionChanged event: Visual Basic Private Sub _rtb_SelectionChanged(sender As Object, e As EventArgs) Dim fw As System.Nullable(Of FontWeight) = _rtb.Selection.FontWeight _btnBold.IsChecked = fw.HasValue AndAlso fw.Value = FontWeights.Bold Dim fs As System.Nullable(Of FontStyle) = _rtb.Selection.FontStyle

114

_btnItalic.IsChecked = fs.HasValue AndAlso fs.Value = FontStyles.Italic _btnUnderline.IsChecked = (sel.TextDecorations IsNot Nothing) End Sub C# void _rtb_SelectionChanged(object sender, EventArgs e) { var sel = _rtb.Selection; FontWeight? fw = _rtb.Selection.FontWeight; _btnBold.IsChecked = fw.HasValue && fw.Value == FontWeights.Bold; FontStyle? fs = _rtb.Selection.FontStyle; _btnItalic.IsChecked = fs.HasValue && fs.Value == FontStyles.Italic; _btnUnderline.IsChecked = (sel.TextDecorations != null); } This event handler is responsible for changing the state of the buttons as the user moves the selection. For example, selecting a word that is bold and underlined would make the buttons appear pressed. The code uses the FontWeight, FontStyle, and TextDecorations properties as before, and sets the IsChecked property on the corresponding buttons. What You've Accomplished You've created a simple toolbar. When run, the application would appear similar to the following image:

You can enter text and press the bold, italic, and underline buttons to format the text as in the above image. A full toolbar would include more buttons and controls, and would handle them in a similar fashion. ComponentOne Studio for Silverlight includes C1RichTextBoxToolbar, a complete toolbar as a separate assembly. The source code for the C1RichTextBoxToolbar control is included so you can create your own customized version. For details, see Working with C1RichTextBoxToolbar (page 88).

Adding Spell Checking

In this topic you'll add spell-checking to your application. This topic assumes you have added a C1RichTextBox control and a C1RichTextBoxToolbar control to your page and linked the two together (page 112). If you currently click the Spell Check button in the toolbar at run time, you'll receive a message that spell checking is currently not set up. In this step you'll add a dictionary and set up spell-checking. Complete the following steps:

115

1. 2.

In the Solution Explorer, right-click the .Web project and select Add | Existing Item. The Add Existing Item dialog box will appear. In the Add Existing Item dialog box locate the C1Spell_en-US.dct file included in the RichTextBoxSamples sample folder. By default, it should be installed in the Documents or My Documents folder in ComponentOne Samples\Studio for Silverlight 4.0\C1.Silverlight.RichTextBox\RichTextBoxSamples\RichTextBoxSamples.Web. This is a US English dictionary file ­ if you add another file, instead, you can adapt the steps below with the appropriate code.

3. 4.

In the Solution Explorer, right-click the MainPage.xaml file and select View Code to open the code file. In the Code Editor, add the following code to import the following namespaces: Visual Basic Imports C1.Silverlight.RichTextBox Imports C1.Silverlight.SpellChecker C# using C1.Silverlight.RichTextBox; using C1.Silverlight.SpellChecker;

5.

Add code to the MainPage constructor so that it appears similar to the following: Visual Basic Public Sub New() InitializeComponent() Dim spell As New C1SpellChecker() spell.MainDictionary.LoadAsync("C1Spell_en-US.dct") Me.C1RichTextBox.SpellChecker = spell End Sub C# public MainPage() { InitializeComponent(); var spell = new C1SpellChecker(); spell.MainDictionary.LoadAsync("C1Spell_en-US.dct"); this.c1RichTextBox.SpellChecker = spell; }

This code adds spell-checking ­ including as-you-type spell-checking ­ to the application. What You've Accomplished In this step you added spell-checking to your C1RichTextBox application. Type in the C1RichTextBox and notice that as-you-type spell-checking is initialized and misspelled words appear with a red line underneath. If you click the Spell Check button in the C1RichTextBoxToolbar, notice that the Spelling dialog box now appears.

116

Information

ComponentOne RichTextBox for Silverlight

122 pages

Report File (DMCA)

Our content is added by our users. We aim to remove reported files within 1 working day. Please use this link to notify us:

Report this file as copyright or inappropriate

189348


You might also be interested in

BETA
ComponentOne RichTextBox for Silverlight