NAT Documentation


Getting Started

Main NAT Window Interface

Automatic Buy/Sell Button Location

About Log Files

Creating
News Scripts

Custom News Sources

 

Creating News Scripts


Getting Started, Basics

NAT includes scripts for most tradable economic indicators. To trade other news releases you can create your own scripts, if your news sources provide the necessary economic data. You can also modify the trade logic of existing scripts.

NAT allows to use many of the Object Pascal / Delphi language features within scripts. Complete language documentation is not provided in this help file, however, to create news scripts, usually very little of available features are necessary. Documentation is included mostly only for things specific to NAT (special variables, constants, objects, useful functions).
You can probably learn enough from included news scripts, but if you need more Pascal or Perl regular expression knowledge, read some online tutorials (note: Pascal pointers are not supported).

The scripting engine used by NAT is RemObjects Pascal Script.

Use NSEditor (News Script Editor) to edit and compile the scripts.

Example script with extra comments:
 

const SYSTEMTITLE='News Trading System'; // SYSTEMTITLE is required for every news script

      cns=1.45; // some global constant
                // ...

var   // global variables...
      i:integer;
      b:boolean;
      d:double;   // floating point variable
      c:currency; // 'currency' type is recommended in most cases instead of 'double',
                  // unless the values need more than 4 digits after point accuracy, because
                  // then simple comparisons like 'if (c>=0.1) ...' can be done correctly. With
                  // 'double' type such comparisons can give incorrect results because of
                  // inaccuracies caused by internal floating point representation.

      s:string;

procedure Init();
  // use const/var to define local constants/variables
begin
  // lbl1 - lbl6 are predefined labels (cns, act, dev, pre, rev, rdev) you can reuse
  lbl1.Caption:=lbl1.Caption+FloatToStrFixed(cns,2);
  // regexp, regexp2,..., regexp10 are predefined regular expression objects you can reuse
  regexp.Pattern:='value is ([+-]?\d+\.\d+) for (\w+)'; // Perl compatible regular expression
end;

// DeInit() is usually not even needed, unless you create dynamic arrays or objects (labels, reg.
// expressions, etc.) which need to be freed/destroyed. Predefined objects(lbl1-lbl6, regexp-
// regexp10) should not be freed, this is done automatically if necessary.

procedure DeInit();
begin
end;

procedure Start(headline:string; source:string);
begin
  // "not signaled" means that Buy(), StrongBuy(), Sell(), StrongSell(), NoTrade() or CancelTrade()
  // was not executed before

  if not signaled and regexp.Match(headline) then
  begin
    c:=StrToFloat(regexp.Sub[1]); // get number from headline
    s:=regexp.Sub[2]; // get second, string value from headline
    if c-cns>100 then Buy() else NoTrade(); // generate trade signal
    lbl2.Caption:=lbl2.Caption+FloatToStrFixed(c,2); // add value to 'act' in results panel
    lbl3.Caption:=lbl3.Caption+FloatToStrFixed(c-cns,2); // add value to 'dev' in results panel
    WriteLn(FloatToStrFixed(c,3)+' '+s); // debug output to headline box
 
end;
end;

Every script should include a global constant SYSTEMTITLE with the string value that will be used in main NAT window title.

Procedure Init() is called once when the script is attached to NAT, similarly DeInit() is called when removing the attached script.

Procedure Start(headline:string; source:string) is called on each headline received, this is where the system logic is implemented and trade signals generated. Parameter "headline" is the received news headline and "source" is the news source (broker short name for MT4 sources).

About NSEditor

When a script is compiled/attached the compiler generates a file with .exn extension with the same file name as the script, at the same directory. If you make changes to the script it needs to be recompiled and reattached for changes to be reflected in NAT. Attaching a script automatically recompiles it if it was modified.

If NSEditor is launched separately, before NAT is launched, any attached script will be automatically removed(detached).

To test the script with example/made-up headlines use the "Testing sandbox". In testing mode no simulated mouse pointer movement and no automated mouse clicks will be done.

The "Reset" button does almost the same as "Remove", except Init() will be executed if it was not done before (script not running) and NAT window is always shown (if clicking "Remove" while NAT is closed the script will be removed silently, without showing the NAT window).


Displaying Info in Results Panel

Results panel can be useful to display economic data consensus numbers, actual numbers, deviations, and other info that you want to be quickly readable. By default it includes 6 predefined labels, which you can reuse (or you can create your own labels):



The label with caption 'cns:' can be accessed from scripts with name lbl1, similarly: 'act:' => lbl2, 'dev:' => lbl3, 'pre:' => lbl4, 'rev:' => lbl5, 'rdev:' => lbl6.

<LabelName>.Caption:='<string>'; - changes label caption text.

<LabelName>.Hide; - hides the label (useful to hide the predefined labels you don't need).

<LabelName>.Left:=<integer>; - sets label Left pixel position within the results panel.

<LabelName>.Top:=<integer>; - sets label Top pixel position within the results panel.

<LabelName>.Font.Color:=<color>; - sets font color. Example color values: clRed, clGreen, clBlue, clYellow, clAqua, $00FF00 (hex. constant).

<LabelName>.Font.Height:=<integer>; - sets the font height in pixels. You can also use <LabelName>.Font.Size:=..., however then the actual size will depend on system DPI setting and this can be undesirable because the results panel is not rescaled.

<LabelName>.Font.Name:='<font name>'; - sets font face. Example: 'Arial'.

Note: by default labels have font smoothing disabled. After changing the font height/size or name it will be automatically re-enabled. If you use font smoothing such as ClearType and want it disabled, after font updates add code "
DisableFontSmoothing(<LabelName>);"

<LabelName>.Color:=<integer>; - sets label background color.

<LabelName>.Width:=<integer>; - sets label width (usually not necessary, it's updated automatically when caption is updated).

<LabelName>.Height:=<integer>; - sets label height (usually not necessary, it's updated automatically when caption is updated).

If you need more space for results panel, to display more info, it can be resized:

ResPanel.Width:=<width in pixels>;

ResPanel.Height:=<height in pixels>;

You can also change the panel color:

ResPanel.Color:=<color>;

Creating Additional Labels

Additional labels can be created by using the TLabel type. Example:

var MyLabel:TLabel;

procedure
Init();
begin
    MyLabel:=TLabel.Create(nil);
    MyLabel.Parent:=ResPanel; // required
    MyLabel.Left:=20;
    MyLabel.Top:=20;
    MyLabel.Caption:='TEST';
    MyLabel.Font.Name:='Courier New';
    MyLabel.Font.Color:=clWhite;
end;

In this case the label object also needs to be freed within DeInit(), otherwise it will not be removed when the attached script is removed:

procedure DeInit();
begin
    MyLabel.Free;
end;

Alternatively, to create the label object and initialize the caption and position you can use function CreateLabel:

function CreateLabel(const Caption: string; Xpos: integer; Ypos: integer): TLabel;

Example:

procedure Init();
begin
    MyLabel:=CreateLabel('TEST', 20, 20);
end;

 

Using Regular Expressions


regexp
, regexp2, ..., regexp10 are predefined regular expression objects you can reuse.

To set the regular expression pattern, use:

<RegExpName>.Pattern:='<pattern>';

This is usually done within Init() procedure. <pattern> is Perl compatible regular expression.

For extended info about regular expressions check the Perl documentation: http://perldoc.perl.org/perlre.html

The following pattern components are most useful:

(word1|word2|multiple words|etc...) - use to match either of the words or phrases. Example: regexp.Pattern:='(bank of england|boe)';

([+-]?\d+)
- match an integer number with optional sign.

(\d+) - match an integer number without sign.

([+-]?\d+\.\d+) - match a real number (with digits after dot) with optional sign.

(\d+\.\d+) - match a real number (with digits after dot), no sign.

(\w+) - match a word.

^ - match must be at the beginning of string.

$ - match must be at the end of string.

Example:

regexp.Pattern:='US (\w+) Nonfarm Payrolls ([+-]?\d+)K; Consensus ([+-]?\d+)K';

will match the text "US Jun Nonfarm Payrolls +115K; Consensus +15K".

To verify if a string matches the pattern use method Match:

<RegExpName>.Match(headline:string):boolean

Example:

if regexp.Match(headline) then ...

Now, if there is a match, you can extract the individual components (values in parentheses) by using method Sub:

<RegExpName>.Sub[<index from 1>]:string

Example:

regexp.Pattern:='US (\w+) Nonfarm Payrolls ([+-]?\d+)K; Consensus ([+-]?\d+)K';
if regexp.Match(headline) then
begin
    // get month
    month:=regexp.Sub[1];
    // get actual NFP number (as string) and convert it to integer
    actual:=StrToInt(regexp.Sub[2]);
    // get NFP consensus number (as string) and convert it to integer
    consensus:=StrToInt(regexp.Sub[3]);
end
;

To create additional regular expression objects, use the TRegExp type. Example:

var MyRegExp:TRegExp;

procedure
Init();
begin
    MyRegExp:=TRegExp.Create(nil);
    // MyRegExp.Pattern:='...';
end;


In this case the objects also need to be freed within DeInit():

procedure DeInit();
begin
    MyRegExp.Free;
end;

Note: predefined regular expression objects don't need to be freed, it's done automatically when the attached script is removed.
 

Trade Signal Functions


procedure Buy();

   
- generates a BUY signal and displays it in signal panel. If autoclick is enabled, a left mouse click is simulated at configured Buy button location(s).

procedure StrongBuy();

    - generates a BUY+ signal and displays it in signal panel. If autoclick is enabled, a left mouse click is simulated at configured Buy+ button location(s). If Buy+ button coordinates are not set, mouse click will be done at Buy button location(s).

procedure Sell();

    - generates a SELL signal and displays it in signal panel. If autoclick is enabled, a left mouse click is simulated at configured Sell button location(s).

procedure StrongSell();

    - generates a SELL+ signal and displays it in signal panel. If autoclick is enabled, a left mouse click is simulated at configured Sell+ button location(s). If Sell+ button coordinates are not set, mouse click will be done at Sell button location(s).

procedure NoTrade();

    - generates a "No Trade" signal and displays it in signal panel. No mouse clicks are done.

procedure CancelTrade();

    - generates a "Cancel" signal and displays it in signal panel. No mouse clicks are done.

function LastSignal():integer;

    - returns the signal constant of last generated signal: CBUY, CSTRONGBUY, CSELL, CSTRONGSELL, CNOTRADE, or CCANCEL. If no signal was generated returns CNONE (equals 0).

function Signaled():boolean;

    - returns TRUE if any signal was previously generated, otherwise returns FALSE.
 

Other Useful Functions


procedure WriteLn(text:string);

   
- writes a line of text to headline box. Example: WriteLn('test');

procedure WriteLnLog(text:string);

   
- writes a line of text to current log file (date/time info added). Example: WriteLnLog('test');

function ReadLn(const question: string): string;

   
- ask for user input in a dialog box. Example: answer:=ReadLn('Parameter X?');

function FloatToStr(value: double/currency): string;

   
- converts double/currency type number to string.

function FloatToStrFixed(value: double/currency; digits:integer): string;

   
- converts double/currency type number to string with specified digits after point precision (rounded). With FloatToStr there can be many unneeded 0's added.

function FloatToStrFixedS(value: double/currency; digits:integer): string;

   
- like FloatToStrFixed, but will also add a "+" sign for positive numbers.

function IntToStr(value: integer): string;

   
- converts integer type number to string.

function IntToStrS(value: integer): string;

   
- like IntToStr, but will also add a "+" sign for positive numbers.

function StrToFloat(value: string): double/currency;

   
- converts string to double/currency type number.

function StrReplace(const S, OldPattern, NewPattern: string; ReplaceAll: boolean; IgnoreCase:boolean): string;

   
- replaces substring OldPattern in string S with substring NewPattern and returns the resulting string.

function LowerCase(value: string): string;

   
- converts string to lowercase.

function UpperCase(value: string): string;

   
- converts string to uppercase.

function Abs(value: integer/double/currency): integer/double/currency;

   
- converts number to absolute number (without minus sign).

function Now():TDateTime;

   
- returns current date and time.

function MilliSecondOf(datetime:TDateTime):Word;

   
- returns the millisecond of the second represented in TDateTime value.

function SecondOf(datetime:TDateTime):Word;

   
- returns the second of the minute represented in TDateTime value.

function MinuteOf(datetime:TDateTime):Word;

   
- returns the minute of the hour represented in TDateTime value.

function HourOf(datetime:TDateTime):Word;

   
- returns the hour of the day represented in TDateTime value.

function DayOf(datetime:TDateTime):Word;

   
- returns the day of the month represented in TDateTime value.

function DayOfWeek(datetime:TDateTime):Word;

   
- returns the day of the week represented in TDateTime value.

function DateToStr(datetime:TDateTime):string;

   
- converts TDateTime value to string (date only).

function DateTimeToStr(datetime:TDateTime):string;

   
- converts TDateTime value to string (date and time).

function StrToDate(const s:string):TDateTime;

   
- converts string (date) to TDateTime.

function StrToDateTime(const s:string):TDateTime;

   
- converts string (date and time) to TDateTime.

procedure Exit();

   
- exit from current function or procedure
 

Calling External DLL Functions


Example:

 

const SYSTEMTITLE='DLL Test';

function MessageBox(hWnd: Longint; lpText, lpCaption: PChar; uType: Longint): Longint; external 'MessageBoxA@user32.dll stdcall';

procedure Init();
begin
  MessageBox(0,'Hello','DLL Test',0);
end;
 


Custom News Sources...