Stay in touch

Add your e-mail address here to receive the monthly TMS Software alerts.


Product releases
Product articles
Technical articles
Website changes
Software development


<< >>
April 2015

Friday, March 27, 2015

Latest Additions to TMS Workflow

TMS products could be categorized by "application user-oriented" or "application developer-oriented".

Products like TMS Aurelius are heavily developer-oriented: it's the developer that "uses" the product during most of development time and the application user have no idea it even exists. Products like TAdvStringGrid stays in the middle: programming effort might be required to achieve the desired behavior of the grid, but at the same time the application user benefits from grid features, viewing data, interacting with the grid, etc..

TMS Workflow is in the "user-oriented" extreme: it's the application user, that will mostly use it. You will do the effort to do some initial setup, setup some configuration, build some initial integration, and that's it: now it's up to your user to benefit and live with TMS Workflow for the rest of your application life.

This post shows the new features introduced in most recent release of TMS Workflow, version 2.1. And you will see how it's heavily user-oriented and focused to make the life of application user - your customer! - easier.

Variables Tool Window
When building the workflow definition, there are many parameters that can use expressions and thus workflow or system variables. With this new helper tool, users can see all the existing variables that can be used in expressions, and can drag a variable name and drop in a control that accepts expressions to create an expression with the variable name. It's even useful to know which parameters can accept expressions.

Transition Scripts
TMS Workflow provides the Script Block to allow users to execute scripts when the workflow reaches a specified point in the diagram flowchart. But it's often not very productive to create the block, connect lines, etc.. And it also pollutes the workflow diagram with irrelevant information (most managers and workflow developers don't want to a script block in the middle of the process indicating that some low level stuff is being done).
To improve that TMS Workflow 2.1 introduces transition scripts: each transition can have a script associated to it. If the execution flow goes through a specified transition, the script associated with it (if any) is executed. Much easier to setup and makes your workflow diagram display only the relevant parts of the business process.

Send Mail Block
A block to send an e-mail notification. In addition to the automatic e-mail notification about tasks, if the user one to send a custom e-mail to someone, this is a very straightforward way to do it.

Database SQL Block
Executes an SQL statement in the database. Users don't need to create datasets or wait for you to build custom functions. If they just want to update some status in database or set some field value, that's an easy way to do so.

Status Templates
When creating tasks, users need to specify the list of valid status for the task. In many cases, the status are the same: "open/closed", or "pending/approved/rejected". Although TMS Workflow already has the Approval Task Block that automatically creates "approved/rejected" status, your user might have other needs for a different list of status, and still use it to create several different tasks. With status templates, you can predefine a list of status under a specified name, and your user can just choose from those predefined templates to quickly create the list of status in a task.

Comment and Text Blocks
Visual blocks to display information in the workflow diagram. The nice thing about text blocks is that they are dynamic, so your user can build a definition that shows a date, a task status, or other relevant information that changes as the workflow is being executed and tasks are being completed.


Wagner Landgraf

This blog post has received 2 comments. Add a comment.

Monday, March 23, 2015

From Lego to TComponent...

In my childhood, I was always fascinated by Lego. I spent countless hours building all kinds of things with Lego, many times a town, all kinds of houses but never forgetting a few sporty cars to accompany each house. What I could build with Lego was mostly limited by my imagination and the number of blocks I had (which was eventually quite a lot as I didn't let any anniversary or special celebration go by to ask for more Lego blocks as a gift). What is so nice about Lego is the easy to use interface between all kinds of blocks. All blocks fit on other blocks and can be effortlessly put together.

From my Lego time, fast-forward about 20 years, in 1995 Delphi brought us the concept of TComponent, an evolution of the TObject originated in Turbo Pascal. TComponent was an invention as magic as the Lego building block. While seamlessly interfacing with its parent, siblings, childs, the major difference with the basic Lego block is that a component can be heavily characterized through its properties. This makes 'playing' with components even more fun, interesting & challenging than playing with Lego was. At TMS software, it is always my objective to build interesting components that are as intuitive as possible to use and that could do interesting things while requiring to write a minimum amount of plumbing code to use them. With a wave of new components we released in the past quarter, I set a challenge for myself to explore and smoothen the ways to interface these building blocks to each other. In this article I wanted to highlight the easiness of bringing together quite sophisticated stand-alone components or building blocks to create powerful solutions.
To demonstrate this, we start with the versatile TMS TAdvStringGrid. With a few properties, this turns into an editable 2D data structure. In our sample, the grid is used to present or capture sales information for a 12 month period. The majority of the effort to write code for this sample goes into initializing the grid. In this case, all we still need to do in code is initialize the data contained in the grid:
  i: integer;
  AdvStringGrid1.EditLink := AdvRichEditorEditLink1;
  AdvStringGrid1.Cells[1,1] := '';
  AdvStringGrid1.Cells[2,1] := 'Sales of development tools products per month';
  AdvStringGrid1.Cells[0,1] := 'Name';
  AdvStringGrid1.Cells[0,0] := 'Month';
  AdvStringGrid1.Cells[1,0] := 'Units';
  AdvStringGrid1.Cells[2,0] := 'Sales';
  AdvStringGrid1.Cells[3,0] := '% Market';

  for i := 2 to 13 do
    AdvStringGrid1.Cells[0,i] := FormatSettings.ShortMonthNames[i - 1];
    AdvStringGrid1.Ints[1,i] := Random(100);
    AdvStringGrid1.Ints[2,i] := Random(10000);
    AdvStringGrid1.Ints[3,i] := Random(50);
All other settings are done by setting properties at design-time. Now, what we want to do is represent the information entered in the grid in a chart. The 3 columns of sales related data are represented in 3 series bar charts in TAdvChartView, the TMS chart component. With the easy interfaces of Lego in mind, we also want and can do this without writing much code (3 lines actually to be exact). We drop a TAdvChartView on the form and also 3 TAdvChartLink components. The TAdvChartLink is a component that takes on the interface between the grid data and a chart series data. The TAdvChartLink is so smart to update the chart series when the grid data changes through editing. All we need to do is setup the relationship between a specific range of cells and a series. Grid and chart are connected by assigning the grid to AdvChartLink.Grid and the chart to AdvChartLink.ChartView. What data from the grid is connected to what series is also configured at design-time via properties through the AdvChartLink.GridValues property. The chart itself can be configured at design-time with a special pane and series design-time editor that allows to customize the X-axis, Y-axis, colors, markers, ... everything about the chart actually. So, the only code left to write is the activation of the chartlink after the data is set in the grid:
  AdvChartLink1.Active := true;
  AdvChartLink2.Active := true;
  AdvChartLink3.Active := true;
Next step, we want to do is display the chart within an editable rich formatted document as we want to allow the user to create a customizable sales report that includes the chart. To do this, TAdvRichEditor is put on the form as well as a TAdvRichEditorEditToolBar and TAdvRichEditorFormatToolBar. We could have opted for a ribbon UI as well with TAdvRichEditorClipboardRibbonToolBar, TAdvRichEditorFontRibbonToolBar, TAdvRichEditorParagraphRibbonToolBar. TAdvRichEditorEditToolBar and TAdvRichEditorFormatToolBar or the ribbon toolbars are building blocks derived from our TMS Advanced ToolBars & Menus product that provides docking toolbars or ribbon controls. These 3 components together are already sufficient to have a rich formatted document editor without needing to write a single line of code.

All we do is initialize the content of the document a little bit with:
  AdvRichEditor1.InsertMultiLineText('Dear Mr. NAME'#13);
  AdvRichEditor1.SelStart := 9;
  AdvRichEditor1.SelLength := 4;

  AdvRichEditor1.InsertMultiLineText('Included is the chart of sales for our development tool product.'#13#13);
With this initialization, we have inserted a merge field and a chart instance in the document. The merge field will be used to insert the addressee name with data from the grid.

The chart is added with initial dimensions 500 x 400px and with ID CHART. To have the chart displayed in the document, the event handler to draw custom graphic objects in the document needs to be coded:
procedure TForm1.AdvRichEditor1DrawGraphic(Sender: TObject; ACanvas: TCanvas;
  ARect: TRect; AID: string);
  if AID = 'CHART' then
    AdvChartView1.PrintAllPanes(ACanvas, ARect);
The merge of the addressee, NAME merge field in the document is done from the grid's OnCellValidate event for the cell 1,1 that holds the name. The code in this event handler is:
procedure TForm1.AdvStringGrid1CellValidate(Sender: TObject; ACol,
  ARow: Integer; var Value: string; var Valid: Boolean);
  sl: TStringList;
  if (ACol = 1) and (ARow = 1) then
    sl := TStringList.Create;
      sl.Values['NAME'] := Value;
But we are not satisfied yet. Wanting to generate a PDF document from the TAdvRichEditor content, a TAdvRichEditorPDFIO component is dropped on the form and connected to the TAdvRichEditor. All we need to do to get the PDF document from the TAdvRichEditor is add the code:
This will prompt for the filename to use and can optionally automatically display the generated PDF in the Windows default PDF viewer, again all without needing to write any additional code.

While not really functionally used in the sample, we just wanted to show yet another seamless integration between the TAdvRichEditor and TAdvStringGrid. In this case, the integration means we can use the TAdvRichEditor as inplace editor in the grid. And here comes yet another integration as this inplace TAdvRichEditor can optionally have a popup formatting toolbar for on-the-fly formatting of the editor content without the need for extra screen estate to put another toolbar or ribbon.

Get started by playing with these building blocks with the sample you can download here and the latest versions of TMS Component Pack and TMS Advanced Charts. We hope this article is an inspiration to have you create other powerful integrations. We're curious to see your results and hear about any suggestions you might have for new integrations or things that can make the integrations even smoother.


Bruno Fierens

This blog post has received 1 comment. Add a comment.

Friday, February 27, 2015

A customer speaks out on TMS components ...

To our big surprise, we found out yesterday a customer gave his feedback in the Embarcadero thirdpartytools forum (nntp://embarcadero.public.thirdpartytools.general) when asked for experiences with our ORM and related products;
The saying is, "a picture is worth a thousand words", but in this case, I would rather say "thousand positive words from a customer are priceless". It speaks for itself that our team was delighted to find out about this posting and it's an incredible motivation and boost to continue the development of our components.

The original post is here in its entirety and unedited:

I can tell you about my experience with Aurelius and other TMS products.

One year ago I started a new project for a ERP and needed to have it in a 
more modernized way. Pretty much the way you intend to do.

I had some goals:

- using modern Delphi language features. I had no need to be compatible with 
anything from previous versions.

- capable of going crossplatform (so it is FIREMONKEY): in my case i have 
an entire ERP running on android :) very nice this. This is important since 
we are now in a multi OS era. There is no guarantee on wich platform will 
remain in 10 years.

- possibility of isolate modules, or even replace them in case of the vendor/open 
source gets out of the market (or just not get more updates)

- something I could understand withou need to be a phD on the area.

I choose the TMS products because they met this parameters for me.

This is my current result:

I have Aurelius as my ORM layer. I have an application based on MVP, so my 
Model part understands Aurelius entities. That are plain simple classes. 
I have created my base class with all funcionality needed and Aurelius does 
the rest.

It is fast, and it is bugs free. I have it working on real conditions for 
1 year now and did not get any problem at all. 

The Idea is simple, the code is modern, and it relies on the new delphi language 

It is compatible with mobile and then you can have all the functionality 
on Android or whatever you need. Using most of the important databases, including 

I am using frames to create the view part of my MVP. I wire everything with 
LiveBInding and Aurelius provides to you a TAureliusDataSet, a fantastic 
TDataSet descendant that publish by several ways the entities you get from 
the ORM.

Right now it is very handy to me, since I have my data prepared on a parallel 
thread and when done it is set to the TAureliusDataSet. The result is a fluid 

You can Edit one entity, a TLIST<> or a Cursor to your database. You can 
access all the properties of your Entity as fields on the Dataset. It is 
very handy to deal with LiveBindings. 

See, since it is Firemonkey this is the only way if not manual). But I can 
tell you, after getting some experience it is reliable and fast enought for 
work based on XE7 


it is the product that permit you connect remotely, you have a server based 
on the http.sys that is the core windows http service and you "write" a server 
based on the documentation. I could add some flavors of my interest of the 
comunication between client and server. (there is another layer called Sparkle 
that is the real http transport here, but just to be simple)

The good thing is that you isolate the native database drivers and you can 
have either mobile using it to connect to your database


I am about to move my application to use it. In my case I am waiting for 
a new feature where I would be capable to use Aurelius over XData. XData 
is a OData standard way to share your data. You create your own server following 
the examples and you can use Aurelius in the server side to create your business 

With eh upcoming feature you will be also possible to use Aurelius with the 
Xdata result. Then you can hide business logic on the server side and publish 
only what is relevant.


This is the way to go for Reporting. It is not only reporting, but for me 
is a fantastic tool.

It has a core based on excel spreadsheet, you can load, create, change, save 
them, in ANY Platform.

But there is a way to use TEMPLATES. So in my ERP i have created XLS templates 
that are embeded on the exe as resources (25k), then I load it and pass the 
Aurelius results from queries based on Linq. The result is commonly a TList 
or can be anything else. But the Entity objects can be directly accessed 
from the Excel Template!

And the good thing is that it works on any platform! it is very fast. Much 
better than FastReports. Easier to work. You can do a lot more, and you can 
even let your customer create Excel templates (wich customer you have that 
does not know how to use them?)
My ERP is already in use on a big chain pilot project. No trouble at all.

I do not work for TMS, but their support was so help ful for me in many cases 
that I have to give you this information.

I am extremelly satisfied. The price is not high for the product benefits, 
and the result is professional.

Any other specific question please let me know...

Eduardo Elias

Well, what more can I say than a big thanks to Eduardo Elias and many other customers who help shape our products every day, 7 by 7, year in, year out and who steer our developments!


Bruno Fierens

This blog post has not received any comments yet. Add a comment.

Friday, December 19, 2014

WYSIWYG formatted text & images editor for VCL & FireMonkey

Early this year, our team started the challenging task to create a new component for WYSIWYG editing of formatted text & images for Delphi. From the start, we want to create a control for FireMonkey that would fit neatly the FMX paradigm of one source code to rule all platforms (Windows, iOS, Android, Mac OSX at this time) but realising this would be a huge effort, we wanted that this effort would also be usable for VCL developers targetting Windows only.

After a lot of research was done on performance (as we knew from our experience with other FMX controls this would be difficult) we decided on what we internally disrespectfully call a sandwich architecture. This sandwich architecture should enable us to isolate a core formatted text handling layer from the framework, i.e. the VCL and FireMonkey framework. The benefit clearly is that work on the core only needs to be done once and further evolutions of the core and its maintenance automatically benefits both VCL and FireMonkey framework versions. Visually, this can be seen as:

The core middle layer not only deals with rendering the formatted text and images but also with all the manipulations that can happen with it. Non-trivial areas in this core middle layer abstraction are: dealing with font handling, coordinates and images that are all treated in a different way in VCL and FireMonkey frameworks. Between this architecture and its final implementation is of course lots and lots of hard work both in development and testing. The final result in VCL and FireMonkey platform running on Windows looks like:

TAdvRichEditor : VCL component from TMS Component Pack

TTMSFMXRichEditor : FireMonkey component from TMS Pack for FireMonkey

To whet your appetite to get started with the new editors regardless of what platform or framework you want to use, here is a short feature list:

  • Compact light-weight WYSIWYG editor for formatted text
  • Supports formatted text with bullets, hyperlinks, images, indenting
  • Paragraphs with left,center,right alignment
  • Support for images, plain text and formatted text on clipboard
  • Undo/redo support
  • Find & replace + text highlighting
  • Mailmerge function
  • Printing (on Windows)
  • Exports to .TXT, .RTF, .HTML files.


Bruno Fierens

This blog post has received 6 comments. Add a comment.

Using the new iOS Sprite Kit from Delphi, a little XMas gift from the TMS team

With iOS 7, Apple introduced the new SpriteKit framework for game development on iOS 7. This framework manages things like graphics, animation, physics, particle effects, gravity, ... all things typically needed for game development. The full documentation for SpriteKit can be found in the "SpriteKit Programming Guide"

We did some research here on using the SpriteKit framework from Delphi XE7 and that triggered the idea of creating a small demo with it in XMas spirit as it is the time of the year for it.

In the little demo, we use an XMas tree with gifts under it as background. This is provided as 4 PNG files, a retina and non-retina version for both portrait and landscape mode. The snowflakes in the demo are particles and therefore we need to create a SpriteKit particle file which can be done from XCode. The SpriteKit particle file contains the PNG for a snow flake and the "snow" particle type is chosen. The result is a .SKS file that is linked as resource with the application.
To make the app a little fun, we added a MotionManager. The snow starts falling when you first shake the device. This is accomplished by handling the motionEnded method at UIViewController level. The motion manager is used to make the snow fall faster according to the angle with which you hold the device. The Delphi TMotionSensor makes this possible.
Finally, to stay in the XMas spirit, we added an MP3 files as resource that plays Jingle Bells as background music.

Video demonstration of the application:

Have fun exploring the iOS SpriteKit framework with the full source code for Delphi XE7* of this gift you can download here.

Note: you'll need to add the SpriteKit framework to the Delphi XE7 IDE to compile the app


Bruno Fierens

This blog post has received 1 comment. Add a comment.

Previous  |  Next  |  Index

Copyright © 1995 - 2015 TMS Software v4.0