As you may notice from version numbers, we do not consider this update as a major update. However, many interesting new features are implemented.
Some of them:
- image activation/deactivation to save memory and resources
- text fields
- controlling image file names on import
- seamless integration of HTML reading and XML components in RichViewActions,
and more

Like before, there are two versions of the trial Setup.
The first version installs the components in Delphi (and also in C++Builder, if available). It supports both 32-bit and 64-bit platforms.(important!) This version can install even in C++Builder without Delphi personality, if command line Delphi compilers are available (and they should). This is the recommended way to install.
The second version installs C++Builder only packages. This version of the installer is mainly provided for a backward compatibility (or use it, if you need to install in C++Builder 6).

Image activation/deactivation

Since this version, only 100 images in each TRichView are stored as TGraphic objects. All other images are "deactivated" (destroyed and saved to a memory stream, to be recreated again when they are needed). This mechanism allows saving memory and (the most important) GDI resources. It works for pictures, hot-pictures, background images of tables and table cells.
In previous version, application crashed if you tried to add several thousand of images. Now you can add 10000 images, without any problem.
Obvious compatibility issues:
1) You cannot add an image to TRichView and store a link to its TGraphic object for a later use. After redrawing or adding other images, this object may be destroyed.
2) All TGraphic classes used in TRichView must implement SaveToStream and LoadToStream correctly (there are some third-party graphic classes that implement only LoadToStream).
Otherwise, this feature is completely transparent to the application and end-users.

Text fields

This update introduces a new feature: text items that are not deleted when they become empty. They can be used to implement text fields.
Text styles have new property: EmpyWidth. By default, it is zero, so text items work as before.
If you assign a positive value to this property, it defines width of empty text items of this style. Such items are not deleted when all item characters are deleted (when pressing Delete or Backspace key, or deleting selection), but they can be deleted when they are empty (unless protected).
Recommendations: I recommend to use background color for these items. You can assign a small width (less than space characters). Or you can assign large value (to attract attention to unfilled fields).
I have more ideas to improve this feature in future.
The demo Demos\DelphiUnicode\Assorted\Fields\FillInGaps is changed to use this new property.

Controlling image file names on import

A new option is added in for TRichView.Options: rvoAssignImageFileNames.
If included, the components assign "image file name properties" when importing external images.
In other words, this options defines whether the file name (or URL) of the image source will be stored together with imported images.

The following properties are affected:
- rvespImageFileName item property of pictures, hot-pictures, tables (for tables, it is also accessible as table.BackgroundImageFileName property)
- cell.BackgroundImageFileName.

Previously, the behavior was either hard-coded (usually, file names were not stored), or was controlled by various different properties. Now, everything is centralized in this option.

A new event is added: TRichView.OnAssignImageFileName event. This event allows changing image file name before assigning (for example, you can convert full paths to relative paths). It occurs on all cases listed above.

We noticed that when dragging images from modern browsers in TRichViewEdit, images were not inserted as images. They are inserted as a plain text from Edge, and as a link from Chrome (and other Chrome-based browsers).
We made the following changes to fix these problems.

1. Priorities of formats are changed when accepting drag&drop.
Since this version, files (CF_HDROP) have higher priority than URL, text, bitmap or metafile.
So now, when you drag an image from Internet Explorer or Edge, it is inserted as an image, not as a text containing its URL (these browsers provide images as links to cached image files).

2. A new option is added, it allows inserting URLs to images as an image, not as URL (when accepting drag&drop).
To activate this feature, include rvoDragDropPicturesFromLinks in TRichViewEdit.EditorOption.
This change allows accepting images dragged from FireFox, Chrome and other browsers using the Chrome engine.

The most probably, this is a link to a remote image (on an HTTP server). TRichView cannot download this image automatically, so you need to do it yourself in OnImportPicture event, or use RichViewActions downloader.
However, there is a problem: RichViewActions downloader is used when an importing procedure (loading or inserting files, or pasting) is initiated by RichViewActions. But drag&drop is not initiated by an action! To solve this problem, we added new events for TRichViewEdit: OnBeforeOleDrop and OnAfterOleDrop. They occur before and after the insertion when accepting drag&drop. You can use these events to initialize and finalize image reading by RichViewActions, see the help file.

In previous updates, we concentrated on integration of additional components (both our components and third-party components) with RichViewActions.
Downloaders, spelling checkers, custom color dialogs now can be used in RichViewActions "out of the box", without $ifdefs.

In this update, we continued this work.
Now you can use HTML importers and RichViewXML in RichViewActions.

TRVAControlPanel has new properties:
- XMLComponent. Assign TRichViewXML to allow loading, saving, inserting XML files (alternative to RVF)
- HTMLComponent. Assign either TRvHtmlImporter or TRvHtmlViewImporter to allow loading, inserting and pasting HTML (using TRvHtmlImporter for opening is not recommended, so this function is disabled by default).

This change affects compatibility: in older version of RichViewActions, the properties that were added after activating $defines had different names.

TRVAControlPanel.OnGetHeaderFooterCode event is added.
This event allows implementing custom codes when processing text displayed in headers and footers. RichViewActions automatically process the following codes:
&p - page number,
&P - page count,
&d - current date,
&t - current time.
You can implement your own one-letter codes (for example, &f - file name).
This feature is useful when header and footer are drawn as a plain text strings by RichViewActions.
They are not used in ScaleRichView, where headers and footers are created by users directly in the WYSIWYG editing components.

Changing widths of controls according to document width

"PercentWidth" property is added to control items. If the value is in the range 1..100, it defines the width of the control in % of document width.

Borders around label items

Label items (non-editable objects looking like text) now may have borders around them, like pictures and controls. This border is supported when exporting to HTML, RTF and DocX.

The demos were changed, they use EmptyWidth property now.
You can see that field editing is much more convenient now: previously, to prevent field deletion, the component did not allow to delete the last field character. Now fields can be empty but they still exist.

ReportWorkshop

New set of demos:
ReportWorkshop\Demos\CBuilderUnicode\FireDAC\
C++Builder version of FireDAC demo projects for Report Workshop (the same demos as for Delphi, except for the ReportEditor demo; it will be created later)

function GetCharCount(RVData: TCustomRVData): Integer;
var i,r,c:Integer;
table:TRVTableItemInfo;
begin
Result:=0;
for i:=0 to RVData.Items.Count-1 do
if RVData.GetItemStyle(i)>=0 then // this is a text item
Inc(Result, RVData.ItemLength(i))
else if RVData.GetItemStyle(i)=rvsTab then Inc(Result)
else if RVData.GetItemStyle(i)=rvsTable then begin
table:=TRVTableItemInfo(RVData.GetItem(i));
for r:=0 to table.Rows.Count-1 do
for c:=0 to table.Rows[r].Count-1 do
if table.Cells[r,c]<>nil then
Inc(Result,GetCharCount(table.Cells[r,c].GetRVData));
end;
end;