logger
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © GETpacman

//@version=5

// @description A dual logging library for developers.
library("logger")

GETpacman =
 "\n          
 				 logger  Library
   Import the Library and Call docs(), and hover mouse over docs() to see Docs in Editor! 
	 		 
			   import GETpacman/logger/3 as logger
               logger.usage()       =>  Sample Code Usage
               logger.fields()      =>  For listing all fields
               logger.methods()     =>  For listing of all methods
	 		   logger.docs()        =>  All documentation in one go

               Code demo => 'https://www.tradingview.com/script/wITCQP6R-libhs-log-DEMO/'
 "

// Credits
//  QuantNomad - For his idea on logging messages as Error/Warnings and displaying the color based on the type of the message. This got me started on my own private logging library.
//  RicardoSantos - When I was new to pine and looked up some of his code on how to pass arrays created within function as init.
//  Tradingview - For implementing UDTs. This single feature has made it possible for me to migrate my library for public use, leading to less complex code.
//  HoanGhetti  - For markdown explanation. This explanation has helped me provide an exhaustive help lookup/markup for all methods, right within the code editor window
//  FFriZz      - For the concept of having a docs() method, just to show the documentation, using markdown.
//  kaigouthro  - Cast Improvements - Some of the exports I had come up independently as part of my own quick logging requirement. Then I discovered  kaigouthro's conversions and copied some here (float with decimals, rounding float to float, rounding string when converting to float, and converting string to int)

export type log
	color			HeaderColor
	color			HeaderColorBG
	color			StatusColor
	color			StatusColorBG
	color			TextColor
	color			TextColorBG
	color			FrameColor
	int 			FrameSize		= 1 
	int 			CellBorderSize	= 0
	color 			CellBorderColor
    color           SeparatorColor  = color.gray
    bool iq                 = false
	bool IsConsole			= true
	bool ShowHeader			= true
	bool HeaderAtTop		= true
	bool ShowStatusBar		= true
	bool StatusBarAtBottom	= true
	bool ShowMetaStatus     = true
	string HeaderQbarIndex  = 'Bar#'
	string HeaderQdateTime  = 'Date'
	string HeaderQLevelCode	= 'Code'
	string HeaderQLogLevel	= 'LvL'
	string HeaderQ1			= '[.q1]'
	string HeaderQ2			= '<.q2>'
	string HeaderQ3			= '(.q3)'
	string HeaderQ4			= ''
	string HeaderQ5			= ''
	string HeaderQ6			= ''
    string Status           = ''
    string HeaderTooltip    = 'Header'
    string StatusTooltip    = 'Status'
    string MetaStatusTooltip= 'Meta Info'
	bool ShowBarIndex       = false
	bool ShowDateTime       = false
	bool ShowLogLevels    	= false         //Shows the debug log level as a column in Logx or as meta tab in Console
	bool ShowQ1             = true
	bool ShowQ2             = true
	bool ShowQ3             = true
	bool ShowQ4             = false
	bool ShowQ5             = false
	bool ShowQ6             = false
	int TabSizeQ1	        = 0
	int TabSizeQ2           = 0
	int TabSizeQ3           = 0
	int TabSizeQ4           = 0
	int TabSizeQ5           = 0
	int TabSizeQ6           = 0
    int PageHistory         = 0
	bool PageOnEveryBar     = false
	bool MoveLogUp          = true
	bool ColorText     		= true
	bool HighlightText      = false
	bool ReplaceWithCodes=false
    bool RestrictLevelsToKey7     = false
	bool MarkNewBar			= true
	int MinWidth       		= 40
	bool AutoMerge          = true
	bool PrefixLogLevel     = false
    int ShowMinimumLevel     = 0
    matrix<string>  mqx
    matrix<int>     hqx
	matrix<color>	cqx
    matrix<bool>    bqx
    array<int>     	intDB
    array<bool>     boolDB
    array<string>  	stringDB
    matrix<color>   colorDB
	array<string>  	levelDB
    array<string>   fontDB
	matrix<color>	cfgx
	matrix<color>	cbgx
	table			tbx
    table           cbx

// @function   
//  convert to upper string\
//  convert to upper string from bool
export method upper(string this) => str.upper(this)
// @function   
//  convert to lower string\
//  convert to lower string from bool
export method lower(string this) => str.lower(this)
// @function   convert bool to string upper
export method upper(bool this) => str.upper(str.tostring(this))
// @function   convert bool to string lower
export method lower(bool this) => str.lower(str.tostring(this))

// @function   
//  convert to float from bool\
//  convert to float from string\
//  convert to float from int
//  rounds float to specified decimals `.f(int deciimals=6)`
export method f(bool this) => 	this ? 1.0 : 0.0
export method f(string this, int decimals=6) =>
// export method f(string this) => str.tonumber(this)
    math.round(str.tonumber(this), decimals)
export method f(int this) => 	float(this)
export method f(float this, int decimals = 6 ) => math.round(this, decimals)

// @function   
//  convert to int from bool\
//  convert to int from string\
//  convert to int from float
export method i(bool this) => 	this ? 1 : 0
export method i(string this) => 
// export method i(string this) => int(str.tonumber(this))
    switch 
        na(str.match(this,'[^\\d]')) => int(str.tonumber(this))
        => int(na)
export method i(float this) => 	int(this)

// @function    
//  convert to string from bool\
//  convert to string from int\
//  convert to string from float
export method s(bool this) => 	str.tostring(this)
export method s(int this) => 	str.tostring(this)
export method s(float this) => 	str.tostring(this)

// @function   
//  convert to bool from int\
//  convert to bool from float\
//  convert to bool from string
export method b(int this) => 	this!=0?true:false
export method b(float this) => 	this!=0.0?true:false
export method b(string this) => 
// export method b(string this) => str.upper(this)=='TRUE' ? true : false
    varip _false = array.from('n','no','nan','0','0.0','f','false','fail','failed','x')
    varip _true  = array.from('y','yes','1','1.0','t','true','pass','passed','p')
    float snum=str.tonumber(this)
    if na(snum)
        switch
            array.includes(_false,str.lower(this)) => false
            array.includes(_true ,str.lower(this)) => true
            => bool(na)
    else
        snum!=0.0

// @function Returns TV compliant Text Alignment, that can be used in TV functions
// @param  align,   string:     alignment in human readable form. Deafult is left
// @returns text alignment
export method getTextAlign(string name) =>
    var _style = switch str.lower(name)
        'left'   => text.align_left
        'right'  => text.align_right
        'top'    => text.align_top
        'bottom' => text.align_bottom
        'center' => text.align_center
    _style
    
// @function Returns TV compliant Text size, that can be used in TV functions
// @param  size,   string:     size in human readable form. Deafult is auto
// @returns text alignment
export method getTextSize(string name) =>
    var _style = switch str.lower(name)
        'auto'   => size.auto
        'tiny'   => size.tiny
        'small'  => size.small
        'normal' => size.normal
        'large'  => size.large
        'huge'   => size.huge
    _style
    
// @function Returns TV compliant Table position, that can be used in TV functions
// @param  position,   string:     position in human readable form. Deafult is top left
// @returns Table position
export method getTablePosition(string name) =>
    var _position= switch str.lower(name)
        'top right' =>      position.top_right
        'top center' =>     position.top_center
        'top left' =>       position.top_left
        'middle right' =>   position.middle_right
        'middle center' =>  position.middle_center
        'middle left' =>    position.middle_left
        'bottom right' =>   position.bottom_right
        'bottom center' =>  position.bottom_center
        'bottom left' =>    position.bottom_left
    _position

//====================

__consolePosition(int position) =>
    _position=switch position
        1 =>  'top'
        2 =>  'right'
        4 =>  'left'
        =>  'bottom'
__consolePosition(string position='anywhere') =>
    _position = switch str.lower(position)
        'top'   =>  1
        'right' =>  2
        'left'  =>  4
        => 3
    _position

method __resetLocations(log this) =>
    this.intDB.set(17,0), this.intDB.set(18,0), this.intDB.set(19,1), this.intDB.set(20,8)
    this.intDB.set(13,0), this.intDB.set(14,10), this.intDB.set(15,this.intDB.get(1)-1+(this.ShowHeader?1:0) + (this.ShowStatusBar?1:0)), this.intDB.set(16,18)
    this.intDB.set(11,3)

method __switchMode(log this)=>
    if this.boolDB.get(1) and not this.IsConsole
        string _metaLog='', string _toLog='', int oldm1Len=0, int m1Len=0, int lvl=0
        for x=0 to this.mqx.rows()>0 ? (this.mqx.rows()-1) : na
            oldm1Len:=str.length(this.mqx.get(x,1))
            if str.contains(this.mqx.get(x,8),'New Bar')
                _metaLog:=''
                _toLog:=this.mqx.get(x,1)
                m1Len:=this.hqx.get(x,3)
            else
                lvl:=this.hqx.get(x,0)
                _metaLog:=(this.ShowBarIndex ? (str.tostring(bar_index)+', ') : '') + 
                          (this.ShowDateTime ? (str.format('{0,date,'+this.stringDB.get(4)+'}',this.hqx.get(x,2))+'  ') : '') + 
                          ((this.TabSizeQ1>0 and lvl>1 and lvl<=7)? str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,this.TabSizeQ1)):'') +
                          ( (this.PrefixLogLevel and lvl>=0 and lvl<=this.levelDB.size())? (this.levelDB.get(lvl) +': ' ):'')
                _toLog:=str.substring(this.mqx.get(x,1),0,4096-str.length(_metaLog))
                m1Len:=str.length(_metaLog)+str.length(_toLog)
            this.hqx.set(x,3,m1Len), this.mqx.set(x,0,_metaLog), this.mqx.set(x,1,_toLog)
    this.boolDB.set(1, this.IsConsole)

method __MarkNewBar(log this, int lvl=0, int ccode=0, string font=na, int tv=time, int q=0)=>
    if (this.MarkNewBar and this.intDB.get(4)!=bar_index)
        int _txn    = (q>=1 and q<=6)?this.intDB.get(25+q):math.max(this.intDB.get(0),this.intDB.get(26),this.intDB.get(27),this.intDB.get(28),this.intDB.get(29),this.intDB.get(30),this.intDB.get(31))
        // int _qsize  = this.intDB.get(1)
        int _qn     = ((_txn+1)%this.intDB.get(1))
        _logMark='#.'+str.tostring(bar_index)+' '+this.stringDB.get(1)
        _markLen=str.length(_logMark)
        this.hqx.set(_qn,0, lvl),this.hqx.set(_qn,1, bar_index),this.hqx.set(_qn,2, tv),this.hqx.set(_qn,3, _markLen),this.hqx.set(_qn,4, _markLen),this.hqx.set(_qn,5, this.intDB.get(6)),this.hqx.set(_qn,6, font==font.family_monospace?1:0)
        this.mqx.set(_qn,0, ''),this.mqx.set(_qn,1, _logMark),this.mqx.set(_qn,2, ''),this.mqx.set(_qn,3, ''),this.mqx.set(_qn,4, ''),this.mqx.set(_qn,5, ''),this.mqx.set(_qn,6, ''),this.mqx.set(_qn,7, '')
        this.mqx.set(_qn,8,'New Bar #.'+str.tostring(bar_index))
        this.cqx.set(_qn,0,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(ccode,0) : this.HighlightText ? this.colorDB.get(ccode, 2) : this.TextColor)
        this.cqx.set(_qn,1,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(ccode,1) : this.HighlightText ? this.colorDB.get(ccode, 0) : this.TextColorBG)
        this.cfgx.set(_qn,0,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(ccode,0) : this.HighlightText ? this.colorDB.get(ccode, 2) : this.TextColor)
        this.cfgx.set(_qn,1,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(ccode,0) : this.HighlightText ? this.colorDB.get(ccode, 2) : this.TextColor)
        this.cfgx.set(_qn,2,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(ccode,0) : this.HighlightText ? this.colorDB.get(ccode, 2) : this.TextColor)
        this.cfgx.set(_qn,3,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(ccode,0) : this.HighlightText ? this.colorDB.get(ccode, 2) : this.TextColor)
        this.cfgx.set(_qn,4,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(ccode,0) : this.HighlightText ? this.colorDB.get(ccode, 2) : this.TextColor)
        this.cfgx.set(_qn,5,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(ccode,0) : this.HighlightText ? this.colorDB.get(ccode, 2) : this.TextColor)
        this.cbgx.set(_qn,0,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(ccode,1) : this.HighlightText ? this.colorDB.get(ccode, 0) : this.TextColorBG)
        this.cbgx.set(_qn,1,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(ccode,1) : this.HighlightText ? this.colorDB.get(ccode, 0) : this.TextColorBG)
        this.cbgx.set(_qn,2,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(ccode,1) : this.HighlightText ? this.colorDB.get(ccode, 0) : this.TextColorBG)
        this.cbgx.set(_qn,3,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(ccode,1) : this.HighlightText ? this.colorDB.get(ccode, 0) : this.TextColorBG)
        this.cbgx.set(_qn,4,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(ccode,1) : this.HighlightText ? this.colorDB.get(ccode, 0) : this.TextColorBG)
        this.cbgx.set(_qn,5,(ccode<0 or ccode>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(ccode,1) : this.HighlightText ? this.colorDB.get(ccode, 0) : this.TextColorBG)

        this.bqx.set(_qn,0,true), this.bqx.set(_qn,1,true)
        if q>=1 and q<=6
            this.intDB.set(25+q,this.intDB.get(25+q)+1)
        else
            this.intDB.set(0,this.intDB.get(0)+1)


// @function 
//  Clears all the queue, including bar_index and time queues, of existing messages
//```
//  method clear()
//```
//___
export method clear (log this)=> 
    this.mqx.fill( '', 0, this.mqx.rows(), 0, this.mqx.columns())
    this.hqx.fill( -1, 0, this.hqx.rows(), 0, this.hqx.columns())
    this.bqx.fill(true,0, this.bqx.rows(), 0, this.bqx.columns())
    this.hqx.fill( 0,  0, this.hqx.rows(), 6,7)
    this.hqx.fill( 0,  0, this.hqx.rows(), 3,5)
    this.hqx.fill( this.intDB.get(6),  0, this.hqx.rows(), 5,6)
    this.cfgx.fill(chart.fg_color,0,this.cfgx.rows(),0,this.cfgx.columns())
    this.cbgx.fill(chart.bg_color,0,this.cbgx.rows(),0,this.cbgx.columns())

    this.intDB.set(7,0),this.intDB.set(0,-1),this.intDB.set(26,-1),this.intDB.set(27,-1),this.intDB.set(28,-1),this.intDB.set(29,-1),this.intDB.set(30,-1),this.intDB.set(31,-1),this.intDB.set(12,-1)

// @function 
//  Resizes the message queues. If size is decreased then removes the oldest message.
//```
//  method resize (int rows=40)
//```
//  #### *Parameters*
//>  int `rows`=*40*     Number of rows to be resized to
//___
// @param rows The new size needed for the queues. Default value is 40.
export method resize (log this, int rows=40) =>
    int _txn    = this.intDB.get(0)
    int _qsize  = this.intDB.get(1)
    int _qc     = (_txn<=-1 or _qsize<1) ? na : (_txn%_qsize)
    int _qn     = (_txn<=-1 or _qsize<1) ? na : ((_txn+1)%_qsize)
    int _rows   = math.min(1000,rows)

    if _rows<=0
        this.clear()
    else
        if _qsize > _rows and _qsize != _rows
            for x = 1 to (_qsize - _rows)
                this.mqx.remove_row(_qn),this.hqx.remove_row(_qn),this.cqx.remove_row(_qn),this.bqx.remove_row(_qn)
                _qn := (_txn<=-1) ? na : ((_txn+1)%_qsize)
                if _qn>_qc
                    _qn := (_qc+1 > (_qsize-1-x)) ? 0 : _qn 
                else
                    _qc -= 1
        if _qsize < _rows and _qsize != _rows
            for x =1 to (_rows - _qsize)
                this.mqx.add_row(_qn,array.new_string(this.mqx.columns(),'')),this.hqx.add_row(_qn,array.new_int(this.hqx.columns(),-1)),this.cqx.add_row(_qn,array.new_color(this.cqx.columns(),na)),this.bqx.add_row(_qn,array.new_bool(this.bqx.columns(),true)),this.cfgx.add_row(_qn,array.new_color(this.cfgx.columns(),na)),this.cbgx.add_row(_qn,array.new_color(this.cbgx.columns(),na))
                this.hqx.set(_qn+1,3,0),this.hqx.set(_qn+1,4,0),this.hqx.set(_qn+1,6,0),this.hqx.set(_qn+1,5,this.intDB.get(6))
        this.intDB.set(1, _rows)
        _txn := (_txn+1) < _qsize ? _txn : (_rows-1+_qn)
        this.intDB.set(0, _txn),this.intDB.set(12, _txn),this.intDB.set(26, _txn),this.intDB.set(27, _txn),this.intDB.set(28, _txn),this.intDB.set(29, _txn),this.intDB.set(30, _txn),this.intDB.set(31, _txn)
        this.intDB.set(15, _rows-1+(this.ShowHeader?1:0)+(this.ShowStatusBar?1:0) + (this.intDB.get(11)==1 ? 2 : 0))

//  @function 
//  Undo messages logged. Will not undo when messages have been logged asynchronously
//```
//  method undo (int rows=1)
//```
//  #### *Parameters*
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  @param  rows    Default is 1
export method undo(log this, int rows=1) =>
    int _txn    = this.intDB.get(0)
    int _rows   = math.min(this.intDB.get(1),math.max(0,rows))
    _rows := (_txn+1)>=_rows ? _rows : this.intDB.get(1)

    if _rows==this.intDB.get(1)
        this.clear()
    else if _rows>0
        int wx=0
        int del=0
        while wx<=(_rows-1)
            _qu=(_txn-wx)%this.intDB.get(1)
            if this.bqx.get(_qu,0)!=this.bqx.get(_qu,1)
                break
            this.hqx.set(_qu,1,-1),this.hqx.set(_qu,3,0),this.hqx.set(_qu,4,0),this.hqx.set(_qu,6,0),this.hqx.set(_qu,5,this.intDB.get(6))
            wx+=1
            del+=1


        this.intDB.set(7,this.intDB.get(7)-del),this.intDB.set(0,this.intDB.get(0)-del)
        this.intDB.set(26,this.intDB.get(26)-del),this.intDB.set(27,this.intDB.get(27)-del),this.intDB.set(28,this.intDB.get(28)-del),this.intDB.set(29,this.intDB.get(29)-del),this.intDB.set(30,this.intDB.get(30)-del),this.intDB.set(31,this.intDB.get(31)-del),this.intDB.set(12,this.intDB.get(12)-del)

//  @function 
//  Undo asynchronously logged messages. Will not undo normally logged messages.
//```
//  method undoq (int q, int rows=1)
//```
//  #### *Parameters*
//>  int `q`           Q number whose messages are to be reverted\
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  @param  q       The Q number to remove messages from
//  @param  rows    Default is 1
export method undoq(log this, int q, int rows=1) =>
    bool _undo=(q<1 or q>6)?false:this.intDB.get(25+q)>this.intDB.get(12)?true:false
    if _undo
        int _txn    = this.intDB.get(12)
        int _txnQ    = this.intDB.get(25+q)
        // int _qsize  = this.intDB.get(1)
        int _rows   = math.min(this.intDB.get(1),math.max(0,rows),this.intDB.get(25+q)-this.intDB.get(12))

        if _rows>0
            int wx=0
            int _qu=_txnQ%this.intDB.get(1)
            while wx<=(_rows-1) and _txnQ>_txn and this.bqx.get(_qu,0)!=this.bqx.get(_qu,1)
                this.mqx.set(_qu,q,'')
                this.cfgx.set(_qu,q-1,na)
                this.cbgx.set(_qu,q-1,chart.bg_color)

                _txnQ-=1
                this.intDB.set(25+q,_txnQ)
                if _txnQ == math.max(this.intDB.get(26),this.intDB.get(27),this.intDB.get(28),this.intDB.get(29),this.intDB.get(30),this.intDB.get(31))
                    this.hqx.set(_qu,1,-1)
                    this.bqx.set(_qu,0,true)
                    this.bqx.set(_qu,1,true)
                wx+=1
                _qu:=_txnQ%this.intDB.get(1)

            this.intDB.set(0,math.max(this.intDB.get(26),this.intDB.get(27),this.intDB.get(28),this.intDB.get(29),this.intDB.get(30),this.intDB.get(31)))

//  @function 
//  Undo asynchronously logged messages from Q1. Will not undo normally logged messages.
//```
//  method undo1 (int rows=1)
//```
//  #### *Parameters*
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  @param  rows    Default is 1
export method undo1(log this, int rows=1) => this.undoq(1,rows)
//  @function 
//  Undo asynchronously logged messages from Q2. Will not undo normally logged messages.
//```
//  method undo2 (int rows=1)
//```
//  #### *Parameters*
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  @param  rows    Default is 1
export method undo2(log this, int rows=1) => this.undoq(2,rows)
//  @function 
//  Undo asynchronously logged messages from Q3. Will not undo normally logged messages.
//```
//  method undo3 (int rows=1)
//```
//  #### *Parameters*
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  @param  rows    Default is 1
export method undo3(log this, int rows=1) => this.undoq(3,rows)
//  @function 
//  Undo asynchronously logged messages from Q4. Will not undo normally logged messages.
//```
//  method undo4 (int rows=1)
//```
//  #### *Parameters*
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  @param  rows    Default is 1
export method undo4(log this, int rows=1) => this.undoq(4,rows)
//  @function 
//  Undo asynchronously logged messages from Q5. Will not undo normally logged messages.
//```
//  method undo5 (int rows=1)
//```
//  #### *Parameters*
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  @param  rows    Default is 1
export method undo5(log this, int rows=1) => this.undoq(5,rows)
//  @function 
//  Undo asynchronously logged messages from Q6. Will not undo normally logged messages.
//```
//  method undo6 (int rows=1)
//```
//  #### *Parameters*
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  @param  rows    Default is 1
export method undo6(log this, int rows=1) => this.undoq(6,rows)

__getFont(string font=na)=>font==font.family_monospace?font.family_monospace:font.family_default
// @function 
// Re/set the date time format used for displaying date and time. Default resets to dd.MMM.yy HH:mm\
//```
//  method dateTimeFormat(string format='')
//```
//  #### *Parameters*
//>  string `format`*=''*     Date time format. If passed as empty (not as na) then resets teh format to d.MMM.yy H:mm, which would look as 9.Aug.23 9:01
//___
// @param   format  time format to be used for displaying the date. If empty then reverts to dd.MMM.yy HH:mm
export method dateTimeFormat(log this, string format='') =>this.stringDB.set(4, format==''?'d.MMM.yy H:mm':format)

// @function
// Sets up font to be used for Header (only on Logx)\
//```
//  method setFontHeader(string font=na)
//```
//  #### *Parameters*
//>  string `font`*=na*     Font to be used for Logx header. If it is not font.family_monospace then it is set to font.family_default
//___
// @param   font    Font to be used for Header. If nothing is specified then defaults to font.family_default
export method setFontHeader(log this, string font=na)=>this.stringDB.set(6,__getFont(font))

// @function 
// Sets up font to be used for Status\
//```
//  method setFontStatus(string font=na)
//```
//  #### *Parameters*
//>  string `font`*=na*     Font to be used for Console/Logx status bar. If it is not font.family_monospace then it is set to font.family_default
//___
// @param   font    Font to be used for Status. If nothing is specified then defaults to font.family_default
export method setFontStatus(log this, string font=na)=>this.stringDB.set(7,__getFont(font))

// @function 
// Sets up font to be used for meta info in Status\
//```
//  method setFontMetaStatus(string font=na)
//```
//  #### *Parameters*
//>  string `font`*=na*     Font to be used for Console/Logx status bar. If it is not font.family_monospace then it is set to font.family_default
//___
// @param   font    Font to be used for Meta Status. If nothing is specified then defaults to font.family_default
export method setFontMetaStatus(log this, string font=na)=>this.stringDB.set(8,__getFont(font))
// @function 
//  Resets the text color of the log to library default.
//```
//  method resetTextColor()
//```
//___
export method resetTextColor(log this) =>this.TextColor := color.new(chart.fg_color,60)
// @function 
//  Resets the background color of the log to library default.
//```
//  method resetTextColorBG()
//```
//___
export method resetTextColorBG(log this) =>this.TextColorBG := chart.bg_color
// @function 
//  Resets the color used for Headers, to library default.
//```
//  method resetHeaderColor()
//```
//___
export method resetHeaderColor(log this) =>this.TextColor := color.new(chart.fg_color,30)
// @function 
//  Resets the background color used for Headers, to library default.
//```
//  method resetHeaderColorBG()
//```
//___
export method resetHeaderColorBG(log this) =>this.HeaderColorBG := color.new(#434651,80)
// @function 
//  Resets the text color of the status row, to library default.
//```
//  method resetStatusColor()
//```
//___
export method resetStatusColor(log this) =>this.StatusColor := color.new(#9598a1,50)
// @function 
//  Resets the background color of the status row, to library default.
//```
//  method resetStatusColorBG()
//```
//___
export method resetStatusColorBG(log this) =>this.StatusColorBG := color.new(#434651,70)
// @function
//  Resets the color used for the frame around the log table, to library default.
//```
//  method resetFrameColor()
//```
//___
export method resetFrameColor(log this) =>this.FrameColor := chart.bg_color



// @function 
//  Resets the color used for the highlighting when Highlight Text option is used, to library default
//```
//  method resetColorsHC()
//```
//___
export method resetColorsHC(log this) =>
    if this.colorDB.rows()<37
        for x=1 to 37-this.colorDB.rows()
            this.colorDB.add_row(0)
    this.colorDB.fill(color.new(color.white,10),0,this.colorDB.rows(),2,3)
    this.colorDB.set(5, 2,color.new(color.black,10)),this.colorDB.set(6, 2,color.new(color.black,10)),this.colorDB.set(14,2,color.new(color.black,10)),this.colorDB.set(21,2,color.new(color.black,10)),this.colorDB.set(22,2,color.new(color.black,10)),this.colorDB.set(26,2,color.new(color.black,10)),this.colorDB.set(34,2,color.new(color.black,10)),this.colorDB.set(35,2,color.new(color.black,10))
    this.intDB.set(21,this.colorDB.rows())

// @function 
//  Resets the background color used for setting the background color, when the Color Text option is used, to library default
//```
//  method resetColorsBG()
//```
//___
export method resetColorsBG(log this) =>
    if this.colorDB.rows()<37
        for x=1 to 37-this.colorDB.rows()
            this.colorDB.add_row(0)

	for x=0 to this.colorDB.rows()-1
		this.colorDB.set(x,1,chart.bg_color)
    this.intDB.set(21,this.colorDB.rows())

// @function 
//  Resets the color used for respective color code, when the ColorText option is used, to library default
//```
//  method resetColors()
//```
//___
export method resetColors(log this) =>
    if this.colorDB.rows()<37
        for x=1 to 37-this.colorDB.rows()
            this.colorDB.add_row(0)

    this.colorDB.set(3, 0, color.new(#2196f3,10)),this.colorDB.set(2, 0, color.new(#4caf50,10)),this.colorDB.set(1, 0, color.new(#9598a1,20)),this.colorDB.set(4, 0, color.new(#c29857,20)),this.colorDB.set(5, 0, color.new(#fbc02d,10)),this.colorDB.set(6, 0, color.new(#f57f17,00)),this.colorDB.set(7, 0, color.new(#f44336,10))
    this.colorDB.set(8, 0, color.new(color.aqua,10)),this.colorDB.set(9, 0, color.new(color.blue,10)),this.colorDB.set(10,0, color.new(color.red,10)),this.colorDB.set(11,0, color.new(color.fuchsia,10)),this.colorDB.set(12,0, color.new(color.gray,10)),this.colorDB.set(13,0, color.new(color.green,10)),this.colorDB.set(14,0, color.new(color.lime,10))
    this.colorDB.set(15,0, color.new(color.maroon,10)),this.colorDB.set(16,0, color.new(color.navy,10)),this.colorDB.set(17,0, color.new(color.olive,10)),this.colorDB.set(18,0, color.new(color.purple,10)),this.colorDB.set(19,0, color.new(color.silver,10)),this.colorDB.set(20,0, color.new(color.teal,10)),this.colorDB.set(21,0, color.new(color.white,10))
    this.colorDB.set(22,0, color.new(color.yellow,10)),this.colorDB.set(23,0, color.new(#9C6E1B,00)),this.colorDB.set(24,0, color.new(#AA00FF,10)),this.colorDB.set(25,0, color.new(#673ab7,10)),this.colorDB.set(26,0, color.new(#CCCC00,10)),this.colorDB.set(27,0, color.new(#c29857,10)),this.colorDB.set(28,0, color.new(#5d606b,00))
    this.colorDB.set(29,0, color.new(#fc5d07,10)),this.colorDB.set(30,0, color.new(#004d40,10)),this.colorDB.set(31,0, color.new(#b71c1c,10)),this.colorDB.set(32,0, color.new(#7e57c2,50)),this.colorDB.set(33,0, color.new(#388e3c,20)),this.colorDB.set(34,0, color.new(#ffeb3b,00)),this.colorDB.set(35,0, color.new(#fbc02d,00))
    this.colorDB.set(36,0, color.new(#ff9850,10))
    this.resetColorsHC(),this.resetColorsBG()

// @function 
//  Sets the colors corresponding to color codes. Index 0 of input array c is color is reserved for future use\
//  Index 1 of input array c is color for color code 1\
//  Index 2 of input array c is color for color code 2 and so on.\
//  There are 2 modes of coloring
//  1. Using the Foreground color
//  2. Using the Foreground color as background color and a white/black/gray color as foreground color
//  - This is denoting or highlighting. Which effectively puts the foreground color as background color
//```
//  method setColors(color[] c)
//```
//  #### *Parameters*
//>  color[ ] `c`     Color Array to be used for corresponding color codes. If the corresponding code is not found, then text color is used
//___
// @param c Array of colors to be used for corresponding color codes. If the corresponding code is not found, then text color is used
export method setColors(log this, color[] c) =>
    sc=c.size()
    sq=this.colorDB.rows()
    if sq<sc
        trow=this.colorDB.row(0)
        for x=1 to sc-sq
            this.colorDB.add_row(0)
    if sq>sc and sc>0
        for x=1 to sq-sc
            this.colorDB.remove_row(0)
    for x=0 to (sc > 0 ? sc-1 : na)
        this.colorDB.set(x,0,c.get(x))
	this.intDB.set(21,this.colorDB.rows())

// @function 
//  Sets the highlight colors corresponding to color codes. Index 0 of input array c is color is reserved for future use\
//  Index 1 of input array c is color for color code 1\
//  Index 2 of input array c is color for color code 2 and so on.\
//  There are 2 modes of coloring
//  1. Using the Foreground color
//  2. Using the Foreground color as background color and a white/black/gray color as foreground color
//  - This is denoting or highlighting. Which effectively puts the foreground color as background color
//```
//  method setColorsHC(color[] c)
//```
//  #### *Parameters*
//>  color[ ] `c`     Color Array to be used for corresponding color codes. If the corresponding code is not found, then text color BG is used
//___
// @param c Array of highlight colors to be used for corresponding color codes. If the corresponding code is not found, then text color BG is used
export method setColorsHC(log this, color[] c) =>
    sc=c.size()
    sq=this.colorDB.rows()
    if sq<sc
        trow=this.colorDB.row(0)
        for x=1 to sc-sq
            this.colorDB.add_row(0)
    if sq>sc and sc>0
        for x=1 to sq-sc
            this.colorDB.remove_row(0)
    for x=0 to (sc > 0 ? sc-1 : na)
        this.colorDB.set(x,2,c.get(x))
	this.intDB.set(21,this.colorDB.rows())

// @function 
//  Sets the background colors corresponding to color codes. Index 0 of input array c is color is reserved for future use\
//  Index 1 of input array c is color for color code 1\
//  Index 2 of input array c is color for color code 2 and so on.\
//  There are 2 modes of coloring
//  1. Using the Foreground color
//  2. Using the Foreground color as background color and a white/black/gray color as foreground color
//  - This is denoting or highlighting. Which effectively puts the foreground color as background color
//```
//  method setColorsBG(color[] c)
//```
//  #### *Parameters*
//>  color[ ] `c`     Color Array to be used for corresponding color codes. If the corresponding code is not found, then text color BG is used
//___
// @param c Array of background colors to be used for corresponding color codes. If the corresponding code is not found, then text color BG is used
export method setColorsBG(log this, color[] c) =>
    sc=c.size()
    sq=this.colorDB.rows()
    if sq<sc
        trow=this.colorDB.row(0)
        for x=1 to sc-sq
            this.colorDB.add_row(0)
    if sq>sc and sc>0
        for x=1 to sq-sc
            this.colorDB.remove_row(0)
    for x=0 to (sc > 0 ? sc-1 : na)
        this.colorDB.set(x,1,c.get(x))
	this.intDB.set(21,this.colorDB.rows())

// @function 
//  Sets the color corresponding to color code
//```
//  method setColor(int e, color c)
//  method setColor(int e, color fg, color bg, color hc)
//```
//  #### *Parameters*
//>  int `e`       Color code whose color needs to be changed. If this code is not found, then color array will be expanded\
//>  color `c`     Color corresponding to code supplied.
//  #### *Parameters*
//>  color `fg`     Foreground Color corresponding to code supplied\
//>  color `bg`     Background Color corresponding to code supplied\
//>  color `hc`     Highlight Color corresponding to code supplied.
//___
// @param e Color code number whose color needs to be changed. If this code is not found, then color array will be expanded.
// @param c Color corresponding to code supplied. 
export method setColor(log this, int e, color c) =>
    if e>=0
        if e>(this.colorDB.rows()-1)
            ca=array.from(this.TextColor,this.TextColorBG,color.white)
            while e>(this.colorDB.rows()-1)
                this.colorDB.add_row(this.intDB.get(21)-1,ca)
	        this.intDB.set(21,this.colorDB.rows())
        this.colorDB.set(e,0,c)

// @function Sets the color corresponding to error code
// @param e Error code whose color needs to be changed. If this error code is not found, then error color array will be expanded.
// @param fg Foreground Color corresponding to error code supplied. 
// @param bg Background Color corresponding to error code supplied. 
// @param hc Highlight Color corresponding to error code supplied. 
export method setColor(log this, int e, color fg, color bg, color hc) =>
    if e>=0
        if e>(this.colorDB.rows()-1)
            ca=array.from(this.TextColor,this.TextColorBG,color.white)
            while e>(this.colorDB.rows()-1)
                this.colorDB.add_row(this.intDB.get(21),ca)
	        this.intDB.set(21,this.colorDB.rows())
        this.colorDB.set(e,0,fg)
        this.colorDB.set(e,1,bg)
        this.colorDB.set(e,2,hc)

// @function 
// Sets the highlight color corresponding to error code
//```
//  method setColorHC(int e, color c)
//```
//  #### *Parameters*
//>  int `e`       Color code whose highlight color needs to be changed. If this code is not found, then color array will be expanded\
//>  color `c`     Color corresponding to code supplied.
//___
// @param e Color code number whose highlight color needs to be changed. If this code is not found, then color array will be expanded.
// @param c Color corresponding to code supplied. 
export method setColorHC(log this, int e, color c) =>
    if e>=0
        if e>(this.colorDB.rows()-1)
            ca=array.from(this.TextColor,this.TextColorBG,color.white)
            while e>(this.colorDB.rows()-1)
                this.colorDB.add_row(this.intDB.get(21),ca)
	        this.intDB.set(21,this.colorDB.rows())
        this.colorDB.set(e,2,c)

// @function 
//  Sets the background color corresponding to error code
//```
//  method setColorBG(int e, color c)
//```
//  #### *Parameters*
//>  int `e`       Color code whose background color needs to be changed. If this code is not found, then color array will be expanded\
//>  color `c`     Color corresponding to code supplied.
//___
// @param e Color code number whose background color needs to be changed. If this code is not found, then color array will be expanded.
// @param c Color corresponding to code supplied. 
export method setColorBG(log this, int e, color c) =>
    if e>=0
        if e>(this.colorDB.rows()-1)
            ca=array.from(this.TextColor,this.TextColorBG,color.white)
            while e>(this.colorDB.rows()-1)
                this.colorDB.add_row(this.intDB.get(21),ca)
	        this.intDB.set(21,this.colorDB.rows())
        this.colorDB.set(e,1,c)

// @function 
//  Returns the color corresponding to color code
//```
//  method getColor(int e)
//```
//  #### *Parameters*
//>  int `e`       Color Code whose color needs to be extracted. If this code is not found, then na will be returned.\
//  #### Returns    
//> **`color`**      The color corresponding to color code supplied. If this code is not found, then na will be returned.
//___
// @param e Code whose color needs to be extracted. If this code is not found, then na will be returned.
export method getColor(log this, int e) =>
    if e>=0 and e<this.intDB.get(21)
        this.colorDB.get(e,0)

// @function 
//  Returns the highlight color corresponding to color code
//```
//  method getColorHC(int e)
//```
//  #### *Parameters*
//>  int `e`       Color Code whose highlight color needs to be extracted. If this code is not found, then na will be returned.\
//  #### Returns    
//> **`color`**      The highlight color corresponding to color code supplied. If this code is not found, then na will be returned.
//___
// @param e Code whose highlight color needs to be extracted. If this code is not found, then na will be returned.
export method getColorHC(log this, int e) =>
    if e>=0 and e<this.intDB.get(21)
        this.colorDB.get(e,2)

// @function 
//  Returns the background color corresponding to color code
//```
//  method getColorBG(int e)
//```
//  #### *Parameters*
//>  int `e`       Color Code whose background color needs to be extracted. If this code is not found, then na will be returned.\
//  #### Returns    
//> **`color`**      The background color corresponding to color code supplied. If this code is not found, then na will be returned.
//___
// @param e Code whose background color needs to be extracted. If this code is not found, then na will be returned.
export method getColorBG(log this, int e) =>
    if e>=0 and e<this.intDB.get(21)
        this.colorDB.get(e,1)

// @function 
//  Resets the log level names used for corresponding level codes\
// With prefix/suffix, the default Level name will be like => prefix + Code + suffix
//```
//  method resetLevelNames(string prefix='Level ', string suffix='')
//```
//  #### *Parameters*
//>  string `prefix`=*'Level'*   Prefix to use when resetting level names\
//>  string `suffix`=*''*        Suffix to use when resetting level names
//___
// @param prefix    Prefix to use when resetting level names
// @param suffix    Suffix to use when resetting level names
export method resetLevelNames(log this, string prefix='Level ', string suffix='') =>
    this.levelDB.clear()
    this.levelDB:=array.new_string(this.colorDB.rows()<8 ? 8 : (this.colorDB.rows()))

    this.levelDB.set(0,''),this.levelDB.set(1,'TRACE'),this.levelDB.set(2,'DEBUG'),this.levelDB.set(3,'INFO'),this.levelDB.set(4,'WARNING'),this.levelDB.set(5,'ERROR'),this.levelDB.set(6,'CRITICAL'),this.levelDB.set(7,'FATAL')
    for x=8 to this.levelDB.size() > 8 ? (this.levelDB.size()-1) : na
        this.levelDB.set(x,prefix+str.tostring(x)+suffix)

// @function 
//  Resets the log level names used for corresponding level codes\
//  Index 0 of input array names is reserved for future use\
//  Index 1 of input array names is name used for level code 1.\
//  Index 2 of input array names is name used for level code 2 and so on.
//```
//  method setLevelNames(string[] names)
//```
//  #### *Parameters*
//>  string[ ] `names`   Array of log level names be used for corresponding level odes. If the corresponding code is not found, then an empty string is used
//___
// @param names Array of log level names be used for corresponding level odes. If the corresponding code is not found, then an empty string is used
export method setLevelNames(log this, string[] names) =>
    if names.size()>0
        this.levelDB.clear()
        this.levelDB:=array.new_string(names.size()<8 ? 8 : names.size())
        this.levelDB.set(0,''),this.levelDB.set(1,''),this.levelDB.set(2,''),this.levelDB.set(3,''),this.levelDB.set(4,''),this.levelDB.set(5,''),this.levelDB.set(6,''),this.levelDB.set(7,'')
        for x=0 to  names.size()-1
            this.levelDB.set(x+1,names.get(x))

// @function 
//  Sets the Log level name corresponding to code supplied.
//```
//  method setLevelName(int e, string levelName)
//```
//  #### *Parameters*
//>  int `e`                Code whose log level name needs to be changed. If this code is not found, then log level names array will be expanded.\
//>  string `levelName`   Level name corresponding to code supplied.
//___
// @param e         Error code whose log level name needs to be changed. If this code is not found, then log level names array will be expanded.
// @param levelName Log level name corresponding to code supplied. 
export method setLevelName(log this, int e, string levelName) =>
    if e>=0
        while e>(this.levelDB.size()-1)
            this.levelDB.push('LVL <'+str.tostring(this.levelDB.size())+'>')
        this.levelDB.set(e,levelName)

// @function 
//  Gets the Log level name corresponding to error code supplied.
//```
//  method getLevelName(int e)
//```
//  #### *Parameters*
//>  int `e`       Code whose log level name needs to be extracted. If this error code is not found, then na will be returned.\
//  #### Returns    
//> **`string`**    The log level name corresponding to code supplied. If this code is not found, then na will be returned.
//___
// @param e         Code whose log level name needs to be extracted. If this error code is not found, then na will be returned.
export method getLevelName(log this, int e) =>
    if e>=0 and e<this.levelDB.size()
        this.levelDB.get(e)

// @function
//  Sets up data for logging. It consists of 6 separate message queues, and 3 additional queues for bar index, time and log level/error code. Do not directly alter the contents, as library could break.
//```
//  method init (int rows=50, isConsole=true)
//```
//  #### *Parameters*
//>  int `rows`*=50*             Number of rows to start with\
//>  bool `isConsole`*=true*    Whether to initialise as Console or Logx. If true will setup as Console.
//___
// @param rows Log size, excluding the header/status. Default value is 50.
// @param isConsole Whether to init the log as console or logx. True= as console, False = as Logx. Default is true, hence init as console.
export method init(log this, int rows=50, bool isConsole=true) =>
    var bool  _init       = false
    if not _init and barstate.isfirst
        _rows=math.max(1,math.min(1000,rows))
	    this.IsConsole:=isConsole

		this.mqx:= matrix.new<string>	(_rows,9,'')
    	this.hqx:= matrix.new<int>		(_rows,7,-1)
    	this.bqx:= matrix.new<bool>   	(_rows,2,true)
    	this.cqx:= matrix.new<color>   	(_rows,2)
    	this.cfgx:= matrix.new<color>   (_rows,6)
    	this.cbgx:= matrix.new<color>   (_rows,6)

		this.intDB			:= array.new<int>  		(40,0)
		this.boolDB			:= array.new<bool>  	(10,false)
		this.stringDB		:= array.new<string>  	(10,'')
    	this.colorDB		:= matrix.new<color>   	(37,3)
		this.levelDB		:= array.new<string> 	(37,'')
        this.fontDB         := array.from(font.family_default,font.family_monospace)
		this.intDB.set(21,this.colorDB.rows())


        this.resetColors()
        this.dateTimeFormat()
        this.resetLevelNames('LVL <','>')

        this.HeaderColor	:= color.new(chart.fg_color,30)
        this.HeaderColorBG	:= color.new(#434651,80)

        this.StatusColor	:= color.new(#9598a1,50)
        this.StatusColorBG	:= color.new(#434651,70)

        this.TextColor		:= color.new(chart.fg_color,60)
        this.TextColorBG	:= chart.bg_color

        this.FrameColor		:= chart.bg_color
        this.CellBorderColor:= chart.bg_color

        this.stringDB.set(0,'                                                                                                                                                                                                                                                                                                                                                                                                                ')
        this.stringDB.set(1,'______________')
        this.intDB.set(22,str.length(this.stringDB.get(0))),this.intDB.set(23,str.length(this.stringDB.get(1)) )
        this.stringDB.set(3,'                            ')
        this.stringDB.set(6,font.family_default),this.stringDB.set(7,font.family_default),this.stringDB.set(8,font.family_default)

        this.intDB.set(1, math.max(0,rows)),this.intDB.set(6,0),this.intDB.set(5,0),this.intDB.set(7,0)
        // this.hqx.fill(0,0, this.hqx.rows(), 6,7),this.hqx.fill(0,0, this.hqx.rows(), 3,5),this.hqx.fill(0,0, this.hqx.rows(), 5,6)
        this.hqx.fill(0,0, this.hqx.rows(), 3,7)

        this.boolDB.set(1,this.IsConsole)
        this.stringDB.set(4, 'dd.MMM.yy HH:mm'),this.stringDB.set(5, position.top_right)
        
        this.intDB.set(24,80),this.intDB.set(25,40)
        this.__resetLocations(),this.setFontHeader(),this.setFontStatus(),this.setFontMetaStatus()
    
		_init:=true
        this.boolDB.set(0,_init)

        this.SeparatorColor:=color.new(#c29857,20)
        this.MarkNewBar:=this.IsConsole?true:false
        this.ShowBarIndex:=this.IsConsole?false:true

// @function 
//  Sets up logger as Console. It consists of one message queue, and 3 additional queues for bar index, time and log level/error code.
//```
//  method initConsole (int rows=50)
//```
//  #### *Parameters*
//>  int `rows`*=50*             Number of rows to start with
//  #### Override default settings with following
//> `MarkNewBar` =*true*\
//> `ShowBarIndex`= *false*
//___
// @param rows Log size, excluding status. Default value is 50.
export method initConsole(log this, int rows=50)=>
    this.init(rows,isConsole=true)
    this.MarkNewBar     := true
    this.ShowBarIndex   := false

// @function 
//  Sets up logger as Logx. It consists of six message queues, and 3 additional queues for bar index, time and log level/error code.
//```
//  method initLogx (int rows=50)
//```
//  #### *Parameters*
//>  int `rows`*=50*             Number of rows to start with
//  #### Override default settings with following
//> `MarkNewBar` =*false*\
//> `ShowBarIndex` =*true*
//___
// @param rows Log size, excluding status. Default value is 50.
export method initLogx(log this, int rows=50)=>
    this.init(rows,isConsole=false)
    this.MarkNewBar     := false
    this.ShowBarIndex   := true

// @function 
//  Logs messages asyncronously to the queue, including, time/date, bar_index, and error code
//```
//  method alog (                string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method alog (int lvl,        string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method alog (int lvl, int c, string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7\
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`     (Optional) Log Level of the message.If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`       (Optional) Color Code to be used for the row being logged. Not used for messages, but for other fields such as Bar Index, if they are displayed. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `msg`  Message to be logged\
//>  int `q`*=1*     Q number the message to be logged to\
//>  int `cq`      (Optional) Color Code to be used for the message being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//  #### *Note 1:*
//  When logging to a console, color code parameter `c` is ignored and color coding of messages is via c1. This is due to Console not having multiple cells, and all data being fit into single table cell.\
//  Hence, to keep logging behaviour consistent with Logx logging, the message colouring is via `c1` - `c6`, however for Console, the row color parameter `c` is not used for coloring.
//  #### *Note 2:*
//  When logging to console, the colour is picked from the last message logged\
//  Sometimes, this can get confusing when (empty) messages are logged with a different colour and one would expect console to show a different color.
//___
// @param lvl       (Optional) Log Level to be assigned.
// @param c         (Optional) Color code of the row being logged. Not used for messages, but for other fields such as Bar Index, if they are displayed. If not specified, uses lvl as color code
// @param m         Message needed to be logged to Q.
// @param q         Which Q should this message be logged to. Default is 1. If not in between 1 and 6, this message will not be logged.
// @param cq        (Optional) Color code to be used for the message being logged. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param font      Font to be used for this message row, when its displayed in the table. Accepts either font.family_default or font.family_monospace
// @param tooltip   Tooltip to display over each row when mouse hovers over it
// @param tv        Time to be used. Default value is time, which logs the start time of bar.
// @param log       Whether to log the message or not. Default is true.
export method alog (log this, int lvl, int c, string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)=>
    _mq='',_metaC='',_m1Len=0,_tabSize=0, _ccode=c<0?lvl:c, _ccodeq=na(cq)?_ccode:cq<0?lvl:cq>this.colorDB.rows()?lvl:cq
    this.PageHistory:=this.PageHistory < 0 ? 0 : this.PageHistory
    if this.PageOnEveryBar and bar_index-this.intDB.get(3) > this.PageHistory
        if this.PageHistory==0
            this.clear()
        else if this.intDB.get(1)>0
            for x=0 to this.intDB.get(1)-1
                this.hqx.set(x,1,(bar_index-this.hqx.get(x,1)) > this.PageHistory ? -1 :  this.hqx.get(x,1))
                this.hqx.set(x,3,(bar_index-this.hqx.get(x,1)) > this.PageHistory ? 0  :  this.hqx.get(x,3))
        this.intDB.set(3, bar_index - this.PageHistory)
    if this.IsConsole!=this.boolDB.get(1)
        this.__switchMode()

    if log and q>0 and q<7
        int _txnLeader = math.max(this.intDB.get(26),this.intDB.get(27),this.intDB.get(28),this.intDB.get(29),this.intDB.get(30),this.intDB.get(31))
        int _txn    = this.intDB.get(12)
        // int _qsize  = this.intDB.get(1)
        int _qn     = ((_txn+1)%this.intDB.get(1))
        int _txnQ   = this.intDB.get(25+q)
        int _qnQ    = ((_txnQ+1)%this.intDB.get(1))

        // _qnQ+=str.contains(this.mqx.get(_qnQ,8),'New Bar')?1:0
        if _txnQ==_txnLeader
            _gap=(_txnQ+1)-(_txn+1)
            _itn=((_gap-(_gap%this.intDB.get(1)))/this.intDB.get(1))%2
            if this.bqx.get(_qnQ,_itn)
                this.bqx.set(_qnQ,_itn,false),this.bqx.set(_qnQ,1-_itn,true)
                this.mqx.set(_qnQ,1,''),this.mqx.set(_qnQ,2,''),this.mqx.set(_qnQ,3,''),this.mqx.set(_qnQ,4,''),this.mqx.set(_qnQ,5,''),this.mqx.set(_qnQ,6,'')

        if (_txnLeader+1)-(_txnQ+1)<=this.intDB.get(1) and _txnLeader>=_txnQ
            if not this.IsConsole
                _tabSize:=switch q
                    1 => this.TabSizeQ1
                    2 => this.TabSizeQ2
                    3 => this.TabSizeQ3
                    4 => this.TabSizeQ4
                    5 => this.TabSizeQ5
                    6 => this.TabSizeQ6
                    => 0
                _mq := (lvl>1 and lvl<=7 and str.length(msg)>0)?str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,_tabSize)):''
                _mq += str.substring(msg,0,4096-str.length(_mq))
                _metaC:=''
            if this.IsConsole       
                _metaC:= (this.ShowBarIndex ? (str.tostring(bar_index)+', ') : '') + 
                         (this.ShowDateTime ? (str.format('{0,date,'+this.stringDB.get(4)+'}',tv)+'  ') : '') + 
                         ((this.TabSizeQ1>0 and lvl>1 and lvl<=7)? str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,this.TabSizeQ1)):'') +
                         ( (this.PrefixLogLevel and lvl>=0 and lvl<=this.levelDB.size())? (this.levelDB.get(lvl) +': ' ):'')
                _storedLen=str.length(_metaC)+str.length(this.mqx.get(_qnQ,1))+str.length(this.mqx.get(_qnQ,2))+str.length(this.mqx.get(_qnQ,3))+str.length(this.mqx.get(_qnQ,4))+str.length(this.mqx.get(_qnQ,5))+str.length(this.mqx.get(_qnQ,6))
                _mq:= _storedLen<4096?str.substring(msg,0,4096-_storedLen):''
        
            this.mqx.set(_qnQ,0, _metaC),this.mqx.set(_qnQ,q, _mq)
            this.hqx.set(_qnQ,3, str.length(_metaC)+str.length(this.mqx.get(_qnQ,1))+str.length(this.mqx.get(_qnQ,2))+str.length(this.mqx.get(_qnQ,3))+str.length(this.mqx.get(_qnQ,4))+str.length(this.mqx.get(_qnQ,5))+str.length(this.mqx.get(_qnQ,6)))
            this.hqx.set(_qnQ,0, lvl),this.hqx.set(_qnQ,1, bar_index),this.hqx.set(_qnQ,2, tv),this.hqx.set(_qnQ,5, this.intDB.get(6)),this.hqx.set(_qnQ,6,font==font.family_monospace?1:0)
            this.mqx.set(_qnQ,7, (lvl<0 or lvl>this.levelDB.size())?'':this.levelDB.get(lvl)),this.mqx.set(_qnQ,8,tooltip)

            this.cqx.set(_qnQ,0,(_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(_ccode,0) : this.HighlightText ? this.colorDB.get(_ccode, 2) : this.TextColor)
            this.cqx.set(_qnQ,1,(_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(_ccode,1) : this.HighlightText ? this.colorDB.get(_ccode, 0) : this.TextColorBG)
            this.cfgx.set(_qnQ,q-1,(_ccodeq<0 or _ccodeq>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(_ccodeq,0) : this.HighlightText ? this.colorDB.get(_ccodeq, 2) : this.TextColor)
            this.cbgx.set(_qnQ,q-1,(_ccodeq<0 or _ccodeq>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(_ccodeq,1) : this.HighlightText ? this.colorDB.get(_ccodeq, 0) : this.TextColorBG)

            // this.cqx.set(_qnQ,0,this.ColorText ? ((_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColor   : this.colorDB.get(_ccode,0)) : this.HighlightText ? ((_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode, 2)) : this.TextColor )
            // this.cqx.set(_qnQ,1,this.ColorText ? ((_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColorBG : this.colorDB.get(_ccode,1)) : this.HighlightText ? ((_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode, 0)) : this.TextColorBG)

            // this.cfgx.set(_qnQ,q-1,this.ColorText ? ((_ccodeq<0 or _ccodeq>this.colorDB.rows() ) ? this.TextColor   : this.colorDB.get(_ccodeq,0)) : this.HighlightText ? ((_ccodeq<0 or _ccodeq>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccodeq, 2)) : this.TextColor )
            // this.cbgx.set(_qnQ,q-1,this.ColorText ? ((_ccodeq<0 or _ccodeq>this.colorDB.rows() ) ? this.TextColorBG : this.colorDB.get(_ccodeq,1)) : this.HighlightText ? ((_ccodeq<0 or _ccodeq>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccodeq, 0)) : this.TextColorBG)

            this.intDB.set(4,bar_index)
        this.intDB.set(25+q, _txnQ+1),this.intDB.set(0,math.max(this.intDB.get(26),this.intDB.get(27),this.intDB.get(28),this.intDB.get(29),this.intDB.get(30),this.intDB.get(31)))
    else if this.IsConsole
        this.stringDB.set(2, ' +'+str.tostring(4096-this.intDB.get(5)) + (this.PageOnEveryBar ? ' ● ' : ' ') + '◼︎'   )

// @function
//  Logs messages to the queues , including, time/date, bar_index, and error code
//```
//  method log (                string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log (int lvl,        string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log (int lvl, int c, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.AutoMerge`           Automatically merges the right most columns into left if there is no text logged.\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7
//  #### *Properties used*
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`           (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`             (Optional) Color Code to be used for the row being logged. Not used for messages, but for other fields such as Bar Index, if they are displayed. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `m1`         Message needed to be logged to Q1, or for console\
//>  string `m2` - `m6`   Message needed to be logged to Q2 to Q6. Not used/ignored when in console mode\
//>  int `c1` - `c6`      (Optional) Color Code to be used for the messages being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//  #### *Note 1:*
//  When logging to a console, color code parameter `c` is ignored and color coding of messages is via c1. This is due to Console not having multiple cells, and all data being fit into single table cell.\
//  Hence, to keep logging behaviour consistent with Logx logging, the message colouring is via `c1` - `c6`, however for Console, the row color parameter `c` is not used for coloring.
//  #### *Note 2:*
//  When logging to console, the colour is picked from the last message logged\
//  Sometimes, this can get confusing when (empty) messages are logged with a different colour and one would expect console to show a different color.
//___
// @param lvl   (Optional) Log Level to be assigned.
// @param c     (Optional) Color code of the row being logged. Not used for messages, but for other fields such as Bar Index, if they are displayed. If not specified, uses lvl as color code
// @param m1    Message needed to be logged to Q1, or for console.
// @param m2    Message needed to be logged to Q2. Not used/ignored when in console mode
// @param m3    Message needed to be logged to Q3. Not used/ignored when in console mode
// @param m4    Message needed to be logged to Q4. Not used/ignored when in console mode
// @param m5    Message needed to be logged to Q5. Not used/ignored when in console mode
// @param m6    Message needed to be logged to Q6. Not used/ignored when in console mode
// @param c1    (Optional) Color code to be used for the message being logged to Q1. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c2    (Optional) Color code to be used for the message being logged to Q2. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c3    (Optional) Color code to be used for the message being logged to Q3. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c4    (Optional) Color code to be used for the message being logged to Q4. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c5    (Optional) Color code to be used for the message being logged to Q5. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c6    (Optional) Color code to be used for the message being logged to Q6. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param tooltip   Tooltip to display over each row when mouse hovers over it
// @param font  Font to be used for this message row, when its displayed in the table. Accepts either font.family_default or font.family_monospace
// @param tv    Time to be used. Default value is time, which logs the start time of bar.
// @param log   Whether to log the message or not. Default is true.
export method log (log this, int lvl, int c, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)=>
    _mq1='',_mq2='',_mq3='',_mq4='',_mq5='',_mq6='',_m1Len=0,_metaC='', _ccode=c<0?lvl:c
    cdb=this.colorDB.rows()
    _ccode1=na(c1)?_ccode:c1<0?lvl:c1>cdb?lvl:c1
    _ccode2=na(c2)?_ccode:c2<0?lvl:c2>cdb?lvl:c2
    _ccode3=na(c3)?_ccode:c3<0?lvl:c3>cdb?lvl:c3
    _ccode4=na(c4)?_ccode:c4<0?lvl:c4>cdb?lvl:c4
    _ccode5=na(c5)?_ccode:c5<0?lvl:c5>cdb?lvl:c5
    _ccode6=na(c6)?_ccode:c6<0?lvl:c6>cdb?lvl:c6

    this.PageHistory:=this.PageHistory < 0 ? 0 : this.PageHistory
    if this.PageOnEveryBar and bar_index-this.intDB.get(3) > this.PageHistory
        if this.PageHistory==0
            this.clear()
        else if this.intDB.get(1)>0
            for x=0 to this.intDB.get(1)-1
                this.hqx.set(x,1,     (bar_index-this.hqx.get(x,1)) > this.PageHistory ? -1 :  this.hqx.get(x,1))
                this.hqx.set(x,3,   (bar_index-this.hqx.get(x,1)) > this.PageHistory ? 0  :  this.hqx.get(x,3))
        this.intDB.set(3, bar_index - this.PageHistory)

    if this.IsConsole!=this.boolDB.get(1)
        this.__switchMode()

    if log
        this.__MarkNewBar(lvl,_ccode,font,tv,0)
        int _txn    = this.intDB.get(0)
        // int _qsize  = this.intDB.get(1)
        int _qn     = ((_txn+1)%this.intDB.get(1))

        if not this.IsConsole
            _mq1    := ( (lvl>1 and lvl<=7 and str.length(m1)>0)?str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,this.TabSizeQ1)):'')
            _mq2    := ( (lvl>1 and lvl<=7 and str.length(m2)>0)?str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,this.TabSizeQ2)):'')
            _mq3    := ( (lvl>1 and lvl<=7 and str.length(m3)>0)?str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,this.TabSizeQ3)):'')
            _mq4    := ( (lvl>1 and lvl<=7 and str.length(m4)>0)?str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,this.TabSizeQ4)):'')
            _mq5    := ( (lvl>1 and lvl<=7 and str.length(m5)>0)?str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,this.TabSizeQ5)):'')
            _mq6    := ( (lvl>1 and lvl<=7 and str.length(m6)>0)?str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,this.TabSizeQ6)):'')


            _mq1+=str.substring(m1,0,4096-str.length(_mq1))
            _mq2+=str.substring(m2,0,4096-str.length(_mq2))
            _mq3+=str.substring(m3,0,4096-str.length(_mq3))
            _mq4+=str.substring(m4,0,4096-str.length(_mq4))
            _mq5+=str.substring(m5,0,4096-str.length(_mq5))
            _mq6+=str.substring(m6,0,4096-str.length(_mq6))
            _m1Len:=0
			_metaC:=''

        if this.IsConsole
            _totalLen=array.sum(this.hqx.col(3))
            _metaC:= (this.ShowBarIndex ? (str.tostring(bar_index)+', ') : '') + 
                     (this.ShowDateTime ? (str.format('{0,date,'+this.stringDB.get(4)+'}',tv)+'  ') : '') + 
                     ((this.TabSizeQ1>0 and lvl>1 and lvl<=7)? str.substring(this.stringDB.get(3),0,(math.min(7,lvl)-1)*math.min(4,this.TabSizeQ1)):'') +
                     ( (this.PrefixLogLevel and lvl>=0 and lvl<=this.levelDB.size())? (this.levelDB.get(lvl) +': ' ):'')
            _mq1:=str.substring(m1,0,4096-str.length(_metaC))
            _m1Len:=str.length(_metaC)+str.length(_mq1)

        this.hqx.set(_qn,0, lvl),this.hqx.set(_qn,1, bar_index),this.hqx.set(_qn,2, tv),this.hqx.set(_qn,3, _m1Len),this.hqx.set(_qn,5, this.intDB.get(6)),this.hqx.set(_qn,6,font==font.family_monospace?1:0)
		this.cqx.set(_qn,0,(_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(_ccode,0) : this.HighlightText ? this.colorDB.get(_ccode, 2) : this.TextColor)
		this.cqx.set(_qn,1,(_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(_ccode,1) : this.HighlightText ? this.colorDB.get(_ccode, 0) : this.TextColorBG)

        this.cfgx.set(_qn,0,(_ccode1<0 or _ccode1>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(_ccode1,0) : this.HighlightText ? this.colorDB.get(_ccode1, 2) : this.TextColor)
        this.cfgx.set(_qn,1,(_ccode2<0 or _ccode2>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(_ccode2,0) : this.HighlightText ? this.colorDB.get(_ccode2, 2) : this.TextColor)
        this.cfgx.set(_qn,2,(_ccode3<0 or _ccode3>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(_ccode3,0) : this.HighlightText ? this.colorDB.get(_ccode3, 2) : this.TextColor)
        this.cfgx.set(_qn,3,(_ccode4<0 or _ccode4>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(_ccode4,0) : this.HighlightText ? this.colorDB.get(_ccode4, 2) : this.TextColor)
        this.cfgx.set(_qn,4,(_ccode5<0 or _ccode5>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(_ccode5,0) : this.HighlightText ? this.colorDB.get(_ccode5, 2) : this.TextColor)
        this.cfgx.set(_qn,5,(_ccode6<0 or _ccode6>this.colorDB.rows() ) ? this.TextColor   : this.ColorText ? this.colorDB.get(_ccode6,0) : this.HighlightText ? this.colorDB.get(_ccode6, 2) : this.TextColor)

        this.cbgx.set(_qn,0,(_ccode1<0 or _ccode1>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(_ccode1,1) : this.HighlightText ? this.colorDB.get(_ccode1, 0) : this.TextColorBG)
        this.cbgx.set(_qn,1,(_ccode2<0 or _ccode2>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(_ccode2,1) : this.HighlightText ? this.colorDB.get(_ccode2, 0) : this.TextColorBG)
        this.cbgx.set(_qn,2,(_ccode3<0 or _ccode3>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(_ccode3,1) : this.HighlightText ? this.colorDB.get(_ccode3, 0) : this.TextColorBG)
        this.cbgx.set(_qn,3,(_ccode4<0 or _ccode4>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(_ccode4,1) : this.HighlightText ? this.colorDB.get(_ccode4, 0) : this.TextColorBG)
        this.cbgx.set(_qn,4,(_ccode5<0 or _ccode5>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(_ccode5,1) : this.HighlightText ? this.colorDB.get(_ccode5, 0) : this.TextColorBG)
        this.cbgx.set(_qn,5,(_ccode6<0 or _ccode6>this.colorDB.rows() ) ? this.TextColorBG : this.ColorText ? this.colorDB.get(_ccode6,1) : this.HighlightText ? this.colorDB.get(_ccode6, 0) : this.TextColorBG)

        // this.cqx.set(_qn,0,this.ColorText ? ((_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColor   : this.colorDB.get(_ccode,0)) : this.HighlightText ? ((_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode, 2)) : this.TextColor )
        // this.cqx.set(_qn,1,this.ColorText ? ((_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColorBG : this.colorDB.get(_ccode,1)) : this.HighlightText ? ((_ccode<0 or _ccode>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode, 0)) : this.TextColorBG)
    
        // this.cfgx.set(_qn,0,this.ColorText ? ((_ccode1<0 or _ccode1>this.colorDB.rows() ) ? this.TextColor   : this.colorDB.get(_ccode1,0)) : this.HighlightText ? ((_ccode1<0 or _ccode1>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode1, 2)) : this.TextColor )
        // this.cfgx.set(_qn,1,this.ColorText ? ((_ccode2<0 or _ccode2>this.colorDB.rows() ) ? this.TextColor   : this.colorDB.get(_ccode2,0)) : this.HighlightText ? ((_ccode2<0 or _ccode2>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode2, 2)) : this.TextColor )
        // this.cfgx.set(_qn,2,this.ColorText ? ((_ccode3<0 or _ccode3>this.colorDB.rows() ) ? this.TextColor   : this.colorDB.get(_ccode3,0)) : this.HighlightText ? ((_ccode3<0 or _ccode3>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode3, 2)) : this.TextColor )
        // this.cfgx.set(_qn,3,this.ColorText ? ((_ccode4<0 or _ccode4>this.colorDB.rows() ) ? this.TextColor   : this.colorDB.get(_ccode4,0)) : this.HighlightText ? ((_ccode4<0 or _ccode4>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode4, 2)) : this.TextColor )
        // this.cfgx.set(_qn,4,this.ColorText ? ((_ccode5<0 or _ccode5>this.colorDB.rows() ) ? this.TextColor   : this.colorDB.get(_ccode5,0)) : this.HighlightText ? ((_ccode5<0 or _ccode5>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode5, 2)) : this.TextColor )
        // this.cfgx.set(_qn,5,this.ColorText ? ((_ccode6<0 or _ccode6>this.colorDB.rows() ) ? this.TextColor   : this.colorDB.get(_ccode6,0)) : this.HighlightText ? ((_ccode6<0 or _ccode6>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode6, 2)) : this.TextColor )

        // this.cbgx.set(_qn,0,this.ColorText ? ((_ccode1<0 or _ccode1>this.colorDB.rows() ) ? this.TextColorBG : this.colorDB.get(_ccode1,1)) : this.HighlightText ? ((_ccode1<0 or _ccode1>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode1, 0)) : this.TextColorBG)
        // this.cbgx.set(_qn,1,this.ColorText ? ((_ccode2<0 or _ccode2>this.colorDB.rows() ) ? this.TextColorBG : this.colorDB.get(_ccode2,1)) : this.HighlightText ? ((_ccode2<0 or _ccode2>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode2, 0)) : this.TextColorBG)
        // this.cbgx.set(_qn,2,this.ColorText ? ((_ccode3<0 or _ccode3>this.colorDB.rows() ) ? this.TextColorBG : this.colorDB.get(_ccode3,1)) : this.HighlightText ? ((_ccode3<0 or _ccode3>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode3, 0)) : this.TextColorBG)
        // this.cbgx.set(_qn,3,this.ColorText ? ((_ccode4<0 or _ccode4>this.colorDB.rows() ) ? this.TextColorBG : this.colorDB.get(_ccode4,1)) : this.HighlightText ? ((_ccode4<0 or _ccode4>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode4, 0)) : this.TextColorBG)
        // this.cbgx.set(_qn,4,this.ColorText ? ((_ccode5<0 or _ccode5>this.colorDB.rows() ) ? this.TextColorBG : this.colorDB.get(_ccode5,1)) : this.HighlightText ? ((_ccode5<0 or _ccode5>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode5, 0)) : this.TextColorBG)
        // this.cbgx.set(_qn,5,this.ColorText ? ((_ccode6<0 or _ccode6>this.colorDB.rows() ) ? this.TextColorBG : this.colorDB.get(_ccode6,1)) : this.HighlightText ? ((_ccode6<0 or _ccode6>this.colorDB.rows() ) ? this.TextColor : this.colorDB.get(_ccode6, 0)) : this.TextColorBG)

        this.mqx.set(_qn,0, _metaC),this.mqx.set(_qn,1, _mq1),this.mqx.set(_qn,2, _mq2),this.mqx.set(_qn,3, _mq3),this.mqx.set(_qn,4, _mq4),this.mqx.set(_qn,5, _mq5),this.mqx.set(_qn,6, _mq6),this.mqx.set(_qn,7, (lvl<0 or lvl>this.levelDB.size())?'':this.levelDB.get(lvl)),this.mqx.set(_qn,8,tooltip)
        this.bqx.set(_qn,0,true),this.bqx.set(_qn,1,true)
        this.intDB.set(4,bar_index)
        _txn+=1
        this.intDB.set(0, _txn),this.intDB.set(12, _txn),this.intDB.set(26, _txn),this.intDB.set(27, _txn),this.intDB.set(28, _txn),this.intDB.set(29, _txn),this.intDB.set(30, _txn),this.intDB.set(31, _txn)
    else if this.IsConsole
        this.stringDB.set(2, ' +'+str.tostring(4096-this.intDB.get(5)) + (this.PageOnEveryBar ? ' ● ' : ' ') + '◼︎'   )

// @function 
//  Logs messages to the queues , including, time/date, bar_index, and error code. All messages from previous bars are cleared
//```
//  method page (                string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)
//  method page (int lvl,        string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)
//  method page (int lvl, int c, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    `not used`\
//> `.PageHistory`        `not used`\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.AutoMerge`           Automatically merges the right most columns into left if there is no text logged.\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7
//  #### *Properties used*
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`           (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`             (Optional) Color Code to be used for the row being logged. Not used for messages, but for other fields such as Bar Index, if they are displayed. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `m1`         Message needed to be logged to Q1, or for console\
//>  string `m2` - `m6`   Message needed to be logged to Q2 to Q6. Not used/ignored when in console mode\
//>  int `c1` - `c6`      (Optional) Color Code to be used for the messages being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `page`*=true*        Whether to page the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//  #### *Note 1:*
//  When logging to a console, color code parameter `c` is ignored and color coding of messages is via c1. This is due to Console not having multiple cells, and all data being fit into single table cell.\
//  Hence, to keep logging behaviour consistent with Logx logging, the message colouring is via `c1` - `c6`, however for Console, the row color parameter `c` is not used for coloring.
//  #### *Note 2:*
//  When logging to console, the colour is picked from the last message logged\
//  Sometimes, this can get confusing when (empty) messages are logged with a different colour and one would expect console to show a different color.
//___
// @param lvl   (Optional) Log Level to be assigned.
// @param c     (Optional) Color code to be used for logging. If not specified, uses lvl as color code
// @param m1    Message needed to be logged to Q1, or for console.
// @param m2    Message needed to be logged to Q2. Not used/ignored when in console mode
// @param m3    Message needed to be logged to Q3. Not used/ignored when in console mode
// @param m4    Message needed to be logged to Q4. Not used/ignored when in console mode
// @param m5    Message needed to be logged to Q5. Not used/ignored when in console mode
// @param m6    Message needed to be logged to Q6. Not used/ignored when in console mode
// @param c1    (Optional) Color code to be used for the message being logged to Q1. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c2    (Optional) Color code to be used for the message being logged to Q2. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c3    (Optional) Color code to be used for the message being logged to Q3. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c4    (Optional) Color code to be used for the message being logged to Q4. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c5    (Optional) Color code to be used for the message being logged to Q5. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param c6    (Optional) Color code to be used for the message being logged to Q6. If negative, uses lvl to determine color code. If omitted, uses row color code (parameter c). 
// @param tooltip   Tooltip to display over each row when mouse hovers over it
// @param font  Font to be used for this message row, when its displayed in the table. Accepts either font.family_default or font.family_monospace
// @param tv    Time to be used. Default value is time, which logs the start time of bar.
// @param page  Whether to log the message or not. Default is true.
export method page (log this, int lvl, int c, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)=> 
    if this.intDB.get(3)!=bar_index and page
        this.clear()
        this.intDB.set(3, bar_index )
    this.log(lvl,c,m1,m2,m3,m4,m5,m6,c1,c2,c3,c4,c5,c6,font,tooltip,tv,log=page)

// @function 
//  Set the messages to be on a new page, clearing messages from previous page.
//  This is not dependent on PageHistory option, as this export method simply just clears all the messages, like turning old pages onto a new page.
//```
//  method turnPage (bool turn=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    `not used`\
//> `.PageHistory`        `not used`
//  #### *Parameters*
//>  bool `turn`=*true*     //>  bool `turn`=*true*     Whether to turn the page or not
//___
//@param    turn    default is true. If set then will turn the page when called.
export method turnPage (log this, bool turn=true)=>
    this.intDB.set(6, this.intDB.get(6)+1)
    for x=0 to (turn and this.intDB.get(1)>0)?(this.intDB.get(1)-1):na
        this.hqx.set(x,1, (this.intDB.get(6)-this.hqx.get(x,5)) > this.PageHistory ? -1 :  this.hqx.get(x,1))


export method alog(log this,          string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)=> this.alog(3,1,msg,q,cq,tooltip,font,tv,log)
export method alog(log this, int lvl, string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)=> this.alog(lvl,-1,msg,q,cq,tooltip,font,tv,log)
export method log (log this,          string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.log(3,1,m1,m2,m3,m4,m5,m6,c1,c2,c3,c4,c5,c6,tooltip,font,tv,log)
export method log (log this, int lvl, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.log(lvl,-1,m1,m2,m3,m4,m5,m6,c1,c2,c3,c4,c5,c6,tooltip,font,tv,log)
export method page(log this,          string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true) => this.page(3,3,m1,m2,m3,m4,m5,m6,c1,c2,c3,c4,c5,c6,tooltip,font,tv,page)
export method page(log this, int lvl, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true) => this.page(lvl,-1,m1,m2,m3,m4,m5,m6,c1,c2,c3,c4,c5,c6,tooltip,font,tv,page)

// @function
//  Logs messages asyncronously to the queue 1, including, time/date, bar_index, and error code
//```
//  method log1(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log1(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log1(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7\
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`     (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`       (Optional) Color Code to be used for the message. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `msg`  Message to be logged\
//>  int `cq`      (Optional) Color Code to be used for the message being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
export method log1(log this, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(3,0,msg,1,cq,tooltip,font,tv,log)
export method log1(log this, int lvl, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,-1,msg,1,cq,tooltip,font,tv,log)
export method log1(log this, int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,c,msg,1,cq,tooltip,font,tv,log)

// @function
//  Logs messages asyncronously to the queue 2, including, time/date, bar_index, and error code
//```
//  method log2(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log2(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log2(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7\
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`     (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`       (Optional) Color Code to be used for the message. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `msg`  Message to be logged\
//>  int `cq`      (Optional) Color Code to be used for the message being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
export method log2(log this, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(3,0,msg,2,cq,tooltip,font,tv,log)
export method log2(log this, int lvl, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,-1,msg,2,cq,tooltip,font,tv,log)
export method log2(log this, int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,c,msg,2,cq,tooltip,font,tv,log)

// @function
//  Logs messages asyncronously to the queue 3, including, time/date, bar_index, and error code
//```
//  method log3(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log3(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log3(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7\
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`     (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`       (Optional) Color Code to be used for the message. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `msg`  Message to be logged\
//>  int `cq`      (Optional) Color Code to be used for the message being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
export method log3(log this, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(3,0,msg,3,cq,tooltip,font,tv,log)
export method log3(log this, int lvl, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,-1,msg,3,cq,tooltip,font,tv,log)
export method log3(log this, int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,c,msg,3,cq,tooltip,font,tv,log)

// @function
//  Logs messages asyncronously to the queue 4, including, time/date, bar_index, and error code
//```
//  method log4(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log4(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log4(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7\
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`     (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`       (Optional) Color Code to be used for the message. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `msg`  Message to be logged\
//>  int `cq`      (Optional) Color Code to be used for the message being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
export method log4(log this, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(3,0,msg,4,cq,tooltip,font,tv,log)
export method log4(log this, int lvl, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,-1,msg,4,cq,tooltip,font,tv,log)
export method log4(log this, int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,c,msg,4,cq,tooltip,font,tv,log)

// @function
//  Logs messages asyncronously to the queue 5, including, time/date, bar_index, and error code
//```
//  method log5(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log5(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log5(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7\
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`     (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`       (Optional) Color Code to be used for the message. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `msg`  Message to be logged\
//>  int `cq`      (Optional) Color Code to be used for the message being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
export method log5(log this, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(3,0,msg,5,cq,tooltip,font,tv,log)
export method log5(log this, int lvl, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,-1,msg,5,cq,tooltip,font,tv,log)
export method log5(log this, int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,c,msg,5,cq,tooltip,font,tv,log)

// @function
//  Logs messages asyncronously to the queue 6, including, time/date, bar_index, and error code
//```
//  method log6(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log6(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log6(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7\
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`     (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`       (Optional) Color Code to be used for the message. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `msg`  Message to be logged\
//>  int `cq`      (Optional) Color Code to be used for the message being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
export method log6(log this, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(3,0,msg,6,cq,tooltip,font,tv,log)
export method log6(log this, int lvl, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,-1,msg,6,cq,tooltip,font,tv,log)
export method log6(log this, int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true) => this.alog(lvl,c,msg,6,cq,tooltip,font,tv,log)

__display (table tt, log this, string hhalign=text.align_left, string hvalign=text.align_top, string hsize=size.auto, string thalign=text.align_left, string tvalign=text.align_top, string tsize=size.auto) =>
    if barstate.islast
        int _txn    = this.intDB.get(0)
        // int _qsize  = this.intDB.get(1)
        int _txnS   = (_txn<=-1 or this.intDB.get(1)<1) ? na : _txn<this.intDB.get(1) ? 0 : (_txn - this.intDB.get(1) + 1)
        int _txnLen = (_txn<=-1 or this.intDB.get(1)<1) ? na : _txn<this.intDB.get(1) ? _txn : (this.intDB.get(1) - 1)

        int _qS  = this.MoveLogUp ? _txnS :_txn
        int _dx  = this.MoveLogUp ? 1 : -1
        int _qc = (_qS%this.intDB.get(1))
        int _qn=na

        int _hqcolBar       = this.intDB.get(14)-1+(this.ShowBarIndex?1:0)
        int _hqcolDateTime  = _hqcolBar+(this.ShowDateTime?1:0)
        int _hqcolEC        = _hqcolDateTime+(this.ShowLogLevels?1:0)
        int _mqcolQ1        = _hqcolEC+(this.ShowQ1?1:0)
        int _mqcolQ2        = _mqcolQ1+(this.ShowQ2?1:0)
        int _mqcolQ3        = _mqcolQ2+(this.ShowQ3?1:0)
        int _mqcolQ4        = _mqcolQ3+(this.ShowQ4?1:0)
        int _mqcolQ5        = _mqcolQ4+(this.ShowQ5?1:0)
        int _mqcolQ6        = _mqcolQ5+(this.ShowQ6?1:0)

        int _logx_headerRowDelta = this.intDB.get(13) + ((this.ShowHeader and this.HeaderAtTop) ? 1 : 0) + ((this.ShowStatusBar and not this.StatusBarAtBottom) ? 1 : 0)
        int _hrow   = 0
        string _toShow=''
        
        if this.ShowHeader and not this.IsConsole
            _hrow := this.intDB.get(13) + (this.HeaderAtTop ?  (this.ShowStatusBar ? (this.StatusBarAtBottom ? 0 : 1) : 0) : (this.intDB.get(1) + (this.ShowStatusBar ? (this.StatusBarAtBottom ? 0 : 1 ) : 0)))
            if this.ShowBarIndex
                tt.cell(column=_hqcolBar,      row=_hrow, text=this.HeaderQbarIndex,     text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if this.ShowDateTime
                tt.cell(column=_hqcolDateTime, row=_hrow, text=this.HeaderQdateTime,   text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if this.ShowLogLevels and this.ReplaceWithCodes
                tt.cell(column=_hqcolEC,       row=_hrow, text=this.HeaderQLevelCode,   text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if this.ShowLogLevels and not this.ReplaceWithCodes
                tt.cell(column=_hqcolEC,       row=_hrow, text=this.HeaderQLogLevel,   text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if this.ShowQ1
                tt.cell(column=_mqcolQ1,       row=_hrow, text=this.HeaderQ1,           text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if this.ShowQ2
                tt.cell(column=_mqcolQ2,       row=_hrow, text=this.HeaderQ2,           text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if this.ShowQ3
                tt.cell(column=_mqcolQ3,       row=_hrow, text=this.HeaderQ3,           text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if this.ShowQ4
                tt.cell(column=_mqcolQ4,       row=_hrow, text=this.HeaderQ4,           text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if this.ShowQ5
                tt.cell(column=_mqcolQ5,       row=_hrow, text=this.HeaderQ5,           text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if this.ShowQ6
                tt.cell(column=_mqcolQ6,       row=_hrow, text=this.HeaderQ6,           text_halign=hhalign, text_valign=hvalign, text_size=hsize, text_color=this.HeaderColor , bgcolor=this.HeaderColorBG, text_font_family = this.stringDB.get(6), tooltip=this.HeaderTooltip)
            if _mqcolQ6<this.intDB.get(16)
                tt.merge_cells(start_column=_mqcolQ6, start_row=_hrow, end_column=this.intDB.get(16), end_row=_hrow)
		if not this.IsConsole
			for x=0 to _txnLen
				_qc := (_qS%this.intDB.get(1))
				_qS += _dx
				if this.hqx.get(_qc,1) >=0 and not this.IsConsole and this.hqx.get(_qc,0)>=this.ShowMinimumLevel
					if this.ShowBarIndex
						tt.cell(column=_hqcolBar,       row=x+_logx_headerRowDelta, text=str.tostring( this.hqx.get(_qc,1)),    text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.ShowDateTime
						tt.cell(column=_hqcolDateTime,  row=x+_logx_headerRowDelta, text=str.format('{0,date,'+this.stringDB.get(4)+'}',this.hqx.get(_qc,2)), 
																																	  text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.ShowLogLevels and this.ReplaceWithCodes
						tt.cell(column=_hqcolEC,        row=x+_logx_headerRowDelta, text=str.tostring(this.hqx.get(_qc,0)),      text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.ShowLogLevels and not this.ReplaceWithCodes
						tt.cell(column=_hqcolEC,        row=x+_logx_headerRowDelta, text=((this.RestrictLevelsToKey7 and this.hqx.get(_qc,0) >=0 and this.hqx.get(_qc,0) <=7) or not this.RestrictLevelsToKey7)? this.mqx.get(_qc,7) : '' , 
																																	  text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.ShowQ1
						// tt.cell(column=_mqcolQ1,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,1),                    text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
						tt.cell(column=_mqcolQ1,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,1),                    text_color=this.cfgx.get(_qc,0), bgcolor=this.cbgx.get(_qc,0), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.ShowQ2
						// tt.cell(column=_mqcolQ2,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,2),                    text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
						tt.cell(column=_mqcolQ2,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,2),                    text_color=this.cfgx.get(_qc,1), bgcolor=this.cbgx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.ShowQ3
						// tt.cell(column=_mqcolQ3,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,3),                    text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
						tt.cell(column=_mqcolQ3,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,3),                    text_color=this.cfgx.get(_qc,2), bgcolor=this.cbgx.get(_qc,2), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.ShowQ4
						// tt.cell(column=_mqcolQ4,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,4),                    text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
						tt.cell(column=_mqcolQ4,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,4),                    text_color=this.cfgx.get(_qc,3), bgcolor=this.cbgx.get(_qc,3), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.ShowQ5
						// tt.cell(column=_mqcolQ5,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,5),                    text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
						tt.cell(column=_mqcolQ5,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,5),                    text_color=this.cfgx.get(_qc,4), bgcolor=this.cbgx.get(_qc,4), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.ShowQ6
						// tt.cell(column=_mqcolQ6,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,6),                    text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
						tt.cell(column=_mqcolQ6,        row=x+_logx_headerRowDelta, text=this.mqx.get(_qc,6),                    text_color=this.cfgx.get(_qc,5), bgcolor=this.cbgx.get(_qc,5), text_halign=thalign, text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8) )
					if this.AutoMerge
						if str.length(this.mqx.get(_qc,6))==0
							if str.length(this.mqx.get(_qc,5))==0
								if str.length(this.mqx.get(_qc,4))==0
									if str.length(this.mqx.get(_qc,3))==0
										if str.length(this.mqx.get(_qc,2))==0
											tt.merge_cells( start_column = _mqcolQ1, end_column = this.intDB.get(16), start_row = x+_logx_headerRowDelta, end_row = x+_logx_headerRowDelta)
										else
											tt.merge_cells( start_column = _mqcolQ2, end_column = this.intDB.get(16), start_row = x+_logx_headerRowDelta, end_row = x+_logx_headerRowDelta)
									else
										tt.merge_cells( start_column = _mqcolQ3, end_column = this.intDB.get(16), start_row = x+_logx_headerRowDelta, end_row = x+_logx_headerRowDelta)
								else
									tt.merge_cells( start_column = _mqcolQ4, end_column = this.intDB.get(16), start_row = x+_logx_headerRowDelta, end_row = x+_logx_headerRowDelta)
							else
								tt.merge_cells( start_column = _mqcolQ5, end_column = this.intDB.get(16), start_row = x+_logx_headerRowDelta, end_row = x+_logx_headerRowDelta)
						else if _mqcolQ6<this.intDB.get(16)
							tt.merge_cells( start_column = _mqcolQ6, end_column = this.intDB.get(16), start_row = x+_logx_headerRowDelta, end_row = x+_logx_headerRowDelta)
					else if _mqcolQ6<this.intDB.get(16)
						tt.merge_cells(start_column=_mqcolQ6, start_row=x+_logx_headerRowDelta, end_column=this.intDB.get(16), end_row=x+_logx_headerRowDelta)
        if this.IsConsole
            _totalLen=array.sum(this.hqx.col(3))
            _overflow= (_totalLen+this.intDB.get(1)-1) > 4096 ? true : false
            _freeup = _overflow ?( _totalLen + this.intDB.get(1) - 1 - 4096): 0
            _rowsout=1
            while _freeup > 0 and _rowsout <= this.intDB.get(1)
                _qn:=((_txn+_rowsout)%this.intDB.get(1))
                _freeup -= this.hqx.get(_qn,3)
                this.hqx.set(_qn,0,0),this.hqx.set(_qn,1, -1),this.hqx.set(_qn,2, 0),this.hqx.set(_qn,3,0),this.hqx.set(_qn,4,0)
                this.mqx.set(_qn,1,''),this.mqx.set(_qn,2,''),this.mqx.set(_qn,3,''),this.mqx.set(_qn,4,''),this.mqx.set(_qn,5,''),this.mqx.set(_qn,6,'')
                _rowsout+=1            
            _totalLen:=array.sum(this.hqx.col(3))
            this.intDB.set(5,  _totalLen)
            this.stringDB.set(2, ' +'+str.tostring(4096-_totalLen)+(this.PageOnEveryBar ? ' ● ' : ' ')+(_overflow ? 'x' : '') )      
			for x=0 to _txnLen
				_qc := (_qS%this.intDB.get(1))
				_qS += _dx
				_toShow+=((this.hqx.get(_qc,1) >=0  and this.hqx.get(_qc,0)>=this.ShowMinimumLevel)? (this.mqx.get(_qc,0)+this.mqx.get(_qc,1) + 
						 ((not(this.bqx.get(_qc,0) and this.bqx.get(_qc,1)))?(this.mqx.get(_qc,2)+this.mqx.get(_qc,3)+this.mqx.get(_qc,4)+this.mqx.get(_qc,5)+this.mqx.get(_qc,6)):'') + 
						 (x==_txnLen ? '' : '\n') ): '')
            int _crowUP = this.intDB.get(17) + (this.ShowStatusBar ? (this.StatusBarAtBottom? 0 : 1) : 0)
            int _crowDN = this.intDB.get(19) - (this.ShowStatusBar ? (this.StatusBarAtBottom? 1 : 0) : 0)
            string _font=this.hqx.get(_qc,1) >=0 ? this.fontDB.get(this.hqx.get(_qc,6)) : __getFont()
            tt.merge_cells(start_column=this.intDB.get(18),   end_column=this.intDB.get(20),   
                                 start_row=_crowUP,      
                                 end_row  =_crowDN)
            // tt.cell(column=this.intDB.get(18), row=_crowUP, text=_toShow, text_color=this.cqx.get(_qc,0), bgcolor=this.cqx.get(_qc,1), text_halign=thalign,text_valign=tvalign, text_size=tsize, text_font_family=this.fontDB.get(this.hqx.get(_qc,6)), tooltip=this.mqx.get(_qc,8))
            tt.cell(column=this.intDB.get(18), row=_crowUP, text=_toShow, text_color=this.cfgx.get(_qc,0), bgcolor=this.cbgx.get(_qc,0), text_halign=thalign,text_valign=tvalign, text_size=tsize, text_font_family=_font, tooltip=this.mqx.get(_qc,8))

        if this.ShowStatusBar and not this.IsConsole
            int _srow = this.intDB.get(13) + (this.StatusBarAtBottom ? (this.intDB.get(1) + (this.ShowHeader?1:0)) : 0)
            int _endMerge=this.ShowMetaStatus ? ((this.ShowBarIndex?1:0) + (this.ShowDateTime?1:0) + (this.ShowLogLevels?1:0) ) : 0
            _minStatusLen=math.max(this.intDB.get(24),this.MinWidth)-(this.ShowMetaStatus?11:0)
            _status=this.Status + (str.length(this.Status)>_minStatusLen ? '': str.substring(this.stringDB.get(0),0,_minStatusLen-str.length(this.Status)))
            if _endMerge >1 
                tt.merge_cells(start_column=this.intDB.get(14),            start_row=_srow, end_column=this.intDB.get(14)+_endMerge-1, end_row=_srow)
                tt.merge_cells(start_column=this.intDB.get(14)+_endMerge,  start_row=_srow, end_column=this.intDB.get(16),             end_row=_srow)
                tt.cell(column=this.intDB.get(14),           row=_srow, text=(this.PageOnEveryBar?'●':'')+' @'+str.tostring(bar_index)+(this.StatusBarAtBottom?' ▲':' ▼'),  text_halign=text.align_left, text_valign=text.align_center, text_size=tsize, text_color=this.StatusColor , bgcolor=this.StatusColorBG, text_font_family = this.stringDB.get(8), tooltip=this.MetaStatusTooltip)
                tt.cell(column=this.intDB.get(14)+_endMerge, row=_srow, text=_status,        			text_halign=text.align_left, text_valign=text.align_top, 	text_size=tsize, text_color=this.StatusColor , bgcolor=this.StatusColorBG, text_font_family = this.stringDB.get(7), tooltip=this.StatusTooltip)
            else
                tt.merge_cells(start_column=this.intDB.get(14)+(this.ShowMetaStatus?1:0), start_row=_srow, end_column=this.intDB.get(16), end_row=_srow)
                if this.ShowMetaStatus
                    tt.cell(column=this.intDB.get(14),   	row=_srow, 					text=(this.PageOnEveryBar?'●':'')+' @'+str.tostring(bar_index)+(this.StatusBarAtBottom?' ▲':' ▼'),  	text_halign=text.align_left, text_valign=text.align_center, text_size=tsize, text_color=this.StatusColor , bgcolor=this.StatusColorBG, text_font_family = this.stringDB.get(8), tooltip=this.MetaStatusTooltip)
                tt.cell(column=this.intDB.get(14)+(this.ShowMetaStatus?1:0), row=_srow,  text=_status,        			text_halign=text.align_left, text_valign=text.align_top, 	text_size=tsize, text_color=this.StatusColor , bgcolor=this.StatusColorBG, text_font_family = this.stringDB.get(7), tooltip=this.StatusTooltip)
        
        if this.ShowStatusBar and this.IsConsole
            int _srow   = this.StatusBarAtBottom? this.intDB.get(19) : this.intDB.get(17)
            _hideECmeta= (this.hqx.get(_qc,0)<=0 or (not this.ShowLogLevels) or (this.ShowLogLevels and this.hqx.get(_qc,0)>this.levelDB.size()) or (this.ShowLogLevels and this.RestrictLevelsToKey7 and this.hqx.get(_qc,0)>7))
            
            _minStatusLen=math.max(this.intDB.get(25),this.MinWidth)-(this.ShowMetaStatus?20:0)
            if _hideECmeta
                _status=this.Status + (str.length(this.Status)>_minStatusLen ? '': str.substring(this.stringDB.get(0),0,_minStatusLen-str.length(this.Status)))
                tt.merge_cells(start_column=this.intDB.get(18),start_row=_srow, end_column=this.intDB.get(20)-(this.ShowMetaStatus?1:0),end_row=_srow)
                if this.ShowMetaStatus
                    tt.cell(column=this.intDB.get(20), row=_srow, text=(this.StatusBarAtBottom?'▲':'▼')+' @'+str.tostring(bar_index)+this.stringDB.get(2) ,  text_halign=text.align_right, text_valign=text.align_top,   text_size=tsize, text_color=this.StatusColor, bgcolor=this.StatusColorBG, text_font_family = this.stringDB.get(8), tooltip=this.MetaStatusTooltip)
                tt.cell(column=this.intDB.get(18), row=_srow, text=_status ,  text_halign=text.align_left, text_valign=text.align_top,   text_size=tsize, text_color=this.StatusColor, bgcolor=this.StatusColorBG, text_font_family = this.stringDB.get(7), tooltip=this.StatusTooltip)
            else
                string _lvlText    = this.levelDB.get(this.hqx.get(_qc,0))
                color _lvlColor    = (this.hqx.get(_qc,0)>0 and this.hqx.get(_qc,0)<=this.levelDB.size())? this.colorDB.get(this.hqx.get(_qc,0),0) : this.StatusColorBG
                color _lvlColorHC  = (this.hqx.get(_qc,0)>0 and this.hqx.get(_qc,0)<=this.levelDB.size())? this.colorDB.get(this.hqx.get(_qc,0),2) : this.StatusColor
                // color _lvlColor    = (this.hqx.get(_qc,0)>0 and this.hqx.get(_qc,0)<=this.levelDB.size())? this.cqx.get(_qc,1) : this.StatusColorBG
                // color _lvlColorHC  = (this.hqx.get(_qc,0)>0 and this.hqx.get(_qc,0)<=this.levelDB.size())? this.cqx.get(_qc,0) : this.StatusColor
                _minStatusLen-=str.length(_lvlText)
                _status=this.Status + (str.length(this.Status)>_minStatusLen ? '': str.substring(this.stringDB.get(0),0,_minStatusLen-str.length(this.Status)))
                tt.cell(column=this.intDB.get(18),    row=_srow, text=_lvlText,                                    text_halign=text.align_center, text_valign=text.align_top, text_size=tsize, text_color=_lvlColorHC,         bgcolor=_lvlColor, text_font_family = this.stringDB.get(8))

                tt.merge_cells(start_column=this.intDB.get(18)+1,start_row=_srow, end_column=this.intDB.get(20)-(this.ShowMetaStatus?1:0),end_row=_srow)
                if this.ShowMetaStatus
                    tt.cell(column=this.intDB.get(20), row=_srow, text=(this.StatusBarAtBottom?'▲':'▼')+' @'+str.tostring(bar_index)+this.stringDB.get(2) ,  text_halign=text.align_right, text_valign=text.align_top,   text_size=tsize, text_color=this.StatusColor, bgcolor=this.StatusColorBG,text_font_family = this.stringDB.get(8), tooltip=this.MetaStatusTooltip)
                tt.cell(column=this.intDB.get(18)+1,  row=_srow, text=_status,    text_halign=text.align_left, text_valign=text.align_top,   text_size=tsize, text_color=this.StatusColor, bgcolor=this.StatusColorBG, text_font_family = this.stringDB.get(7), tooltip=this.StatusTooltip)

// @function 
//  Display Message Q, Index Q, Time Q, and Log Levels
//```
//  method show (string position=position.bottom_right, string hhalign=text.align_left, string hvalign=text.align_top, string hsize=size.auto, string thalign=text.align_left, string tvalign=text.align_top, string tsize=size.auto, bool show=true, log attach=na)
//```
// #### *Note*
//>  All options for postion/alignment accept TV values, such as position.bottom_right, text.align_left, size.auto etc.\
//>  Use getTablePosition() / getTextAlign() / getTextSize() methods to get the TV accepted names.
// #### *Example:*
//```
//  ip_TablePosition = input.string('Top Right',   'Position',  options=['Top Left','Top Center','Top Right','Middle Left','Middle Center','Middle Right','Bottom Left','Bottom Center','Bottom Right'])
//  ip_TextSize      = input.string('Small',       'Size',      options=['Auto','Tiny','Small','Normal','Large','Huge'])
//  ip_Align         = input.string('Left',        'Alignment', options=['Left','Center','Right'])
//  .show(position=ip_TablePosition.getTablePosition(), thalign=ip_Align.getTextAlign(), tsize=ip_TextSize.getTextSize() )
//```
//  #### *Properties impacting how log is displayed*
//> `ColorText`               Color Code will be used only if ColorText has been set to true\
//> `HighlightText`          Color Code will be used only if HighlightText has been set to true\
//> `MoveLogUp`               Reverse the direction of the log scrolling. The usual direction is scrolling up. False will scroll down\
//> `ShowMinimumLevel`       The Log level upto which the messages will be shown. All messages below this level will not be displayed, even if logged\
//> `MinWidth`                Sometimes the text displayed goes over table edges. Setting this property ensures a minumum width is always displayed
//  #### *Properties impacting how log is displayed*
//> `ReplaceWithCodes`          (Logx Only) When displaying the Q with Log Level names, you can display Log level codes instead\
//> `RestrictLevelsToKey7`     When displaying Log Level names, only first seven (TRACE to CRITICAL) will be displayed and rest ignored
//  #### *Parameters*
//>  string `position`=*position.bottom_right*     Position of the logger table.\
//>  string `hhalign`=*text.align_left*             Header text's horizontal alignment\
//>  string `hvalign`=*text.align_top*             Header text's vertical alignment\
//>  string `hhsize`=*size.auto*                   Header text size
//  #### *Parameters*
//>  string `thalign`=*text.align_left*             Text's horizontal alignment of each cell within the log table\
//>  string `tvalign`=*text.align_top*             Text's vertical alignment of each cell within the log table\
//>  string `thsize`=*size.auto*                   Logger cell's text size
//  #### *Parameters*
//>  bool `show`=*true*                          Whether to show the log table or not\
//>  log `attach`                              (Optional) Console that has been attached before using logger.attach() method
//___
// @param  position         Position of the table used for displaying the messages. Default is Bottom Right.
// @param  hhalign          Horizontal alignment of Header columns 
// @param  hvalign          Vertical alignment of Header columns
// @param  hsize            Size of Header text Options
// @param  thalign          Horizontal alignment of all messages
// @param  tvalign          Vertical alignment of all messages
// @param  tsize            Size of text across the table
// @param  show             Whether to display the logs or not. Default is true.
export method show (log this, string position=position.bottom_right, string hhalign=text.align_left, string hvalign=text.align_top, string hsize=size.auto, string thalign=text.align_left, string tvalign=text.align_top, string tsize=size.auto, bool show=true, log attach=na) =>
    this.stringDB.set(5,position)
    if barstate.islast
        if this.IsConsole!=this.boolDB.get(1)
            this.__switchMode()
    if barstate.islast and not show and not na(this.tbx)
        this.tbx.delete()
    if barstate.islast and show and not this.boolDB.get(3)
        this.__resetLocations()
    if barstate.islast and show and not this.boolDB.get(2)
		this.tbx := table.new(frame_color=this.FrameColor, border_color=this.CellBorderColor, position=position, columns=19, rows=   2 + 2+this.intDB.get(1)+1, frame_width=this.FrameSize, border_width=this.CellBorderSize)
        if not na(attach)
            if attach.intDB.get(2)!=-1
                attach.resize(this.intDB.get(1))

            if this.boolDB.get(3) and not na(this.SeparatorColor)
                this.tbx.merge_cells(start_column=  this.intDB.get(11)==1? this.intDB.get(14)   :this.intDB.get(11)==2?(this.intDB.get(16)+1):this.intDB.get(11)==4?(this.intDB.get(14)-1): this.intDB.get(14), 
                                     start_row=     this.intDB.get(11)==1?(this.intDB.get(13)-1):this.intDB.get(11)==2? this.intDB.get(13)   :this.intDB.get(11)==4? this.intDB.get(13)   :(this.intDB.get(15)+1), 
                                     end_column=    this.intDB.get(11)==1? this.intDB.get(16)   :this.intDB.get(11)==2?(this.intDB.get(16)+1):this.intDB.get(11)==4?(this.intDB.get(14)-1):this.intDB.get(16),
                                     end_row=       this.intDB.get(11)==1?(this.intDB.get(13)-1):this.intDB.get(11)==2? this.intDB.get(15)   :this.intDB.get(11)==4? this.intDB.get(15)   :(this.intDB.get(15)+1))
                this.tbx.cell(text=' ',bgcolor=this.SeparatorColor, text_color=this.SeparatorColor,
                                             row=   this.intDB.get(11)==1?(this.intDB.get(13)-1):this.intDB.get(11)==2? this.intDB.get(13)   :this.intDB.get(11)==4? this.intDB.get(13)   :(this.intDB.get(15)+1),
                                             column=this.intDB.get(11)==1? this.intDB.get(14)   :this.intDB.get(11)==2?(this.intDB.get(16)+1):this.intDB.get(11)==4?(this.intDB.get(14)-1):this.intDB.get(14))
            if attach.boolDB.get(2)
                __display(this.tbx, attach, hhalign=hhalign, hvalign=hvalign, hsize=hsize, thalign=thalign, tvalign=tvalign, tsize=tsize)
        __display(this.tbx, this, hhalign=hhalign, hvalign=hvalign, hsize=hsize, thalign=thalign, tvalign=tvalign, tsize=tsize)

// @function 
//  Attaches a console to Logx, or moves already attached console around Logx
//```
//  method attach(log attach, string position='anywhere')
//```
//  #### *Parameters*
//>  log `attach`                 Console object that to be attached.\
//>  string `position`=*anywhere*  Position of Console relative to Logx. Can be Top, Right, Bottom, Left. Default is Bottom. If unknown specified then defaults to Bottom
//___
// @param attach        Console object that has been previously attached.
// @param position      Position of Console in relation to Logx. Can be Top, Right, Bottom, Left. Default is Bottom. If unknown specified then defaults to bottom.
export method attach(log this,log attach, string position='anywhere')=>
    if not this.boolDB.get(3) 
        if (this.intDB.get(11)%2==0)
            attach.intDB.set(2,attach.intDB.get(1)),attach.resize(this.intDB.get(1))
        else
            attach.intDB.set(2,-1)

    if this.boolDB.get(3)
        if __consolePosition(position)%2!=this.intDB.get(11)%2
            if attach.intDB.get(2)==-1 
                attach.intDB.set(2,attach.intDB.get(1)), attach.resize(this.intDB.get(1))
            else
                attach.resize(attach.intDB.get(2)),attach.intDB.set(2,-1)
    attach.tbx.delete()
    this.intDB.set(11,__consolePosition(position))
    this.IsConsole:=false
    attach.IsConsole:=true
    this.boolDB.set(2,false),this.boolDB.set(3,true),attach.boolDB.set(2,true),attach.boolDB.set(3,false)

    _ate=not(na(this.SeparatorColor))
    int _czeroRow = this.intDB.get(11)==3 ? (this.intDB.get(1)+(this.ShowHeader?1:0)+(this.ShowStatusBar?1:0) + (_ate?1:0) ) :  0

    int _czeroCol = this.intDB.get(11)==2 ? (9 + (_ate?1:0)) : 0
    int _clastCol = _czeroCol + 8
    int _clastRow = _czeroRow + (this.intDB.get(11)%2==1 ? 1 : (this.intDB.get(1)-1+(this.ShowHeader?1:0)+(this.ShowStatusBar?1:0)))

    int _lzeroRow = this.intDB.get(11)==1 ? (_clastRow+1+(_ate?1:0)) : 0
    int _lzeroCol = this.intDB.get(11)==4? (_clastCol+1+(_ate?1:0)): 0
    int _llastRow = _lzeroRow + this.intDB.get(1)-1+(this.ShowHeader?1:0)+(this.ShowStatusBar?1:0)
    int _llastCol = _lzeroCol + 8

    this.intDB.set(14,_lzeroCol),this.intDB.set(16,_llastCol),this.intDB.set(13,_lzeroRow),this.intDB.set(15,_llastRow)
    attach.intDB.set(14,_lzeroCol),attach.intDB.set(16,_llastCol),attach.intDB.set(13,_lzeroRow),attach.intDB.set(15,_llastRow)
    attach.intDB.set(18,_czeroCol),attach.intDB.set(20,_clastCol),attach.intDB.set(17,_czeroRow),attach.intDB.set(19,_clastRow)

// @function 
//  Detaches the attached console from Logx.
//```
//  method detach(log attachment)
//```
//  #### *Parameters*
//>  log `attachment`        Console object to be detached.
//___
// @param attachment         Console object that has been previously attached.
export method detach(log this,log attachment)=>
    this.boolDB.set(2,false),this.boolDB.set(3,false),attachment.boolDB.set(2,false),attachment.boolDB.set(3,false)
    this.__resetLocations(),attachment.__resetLocations()

    if attachment.intDB.get(2)!=-1
        attachment.resize(attachment.intDB.get(2))

// @function 
//  Displays a separate table, showing what Error Colors (maximum 200 colors)
//```
//  method showColors (string position=position.bottom_left,bool showColors=true)
//```
//  #### *Parameters*
//>  string `position`=*position.bottom_left*     Position of the logger table.\
//>  bool `showColors`=*true*                   Whether to show Colors table or not. Default is true.\
//___
// @param position         Position of the table used for displaying the messages. Default is Bottom Left. Accepts TV string for position.
// @param showColors       Whether to show Colors table or not. Default is true.
export method showColors (log this,string position=position.bottom_left,bool showColors=true) =>
    var int dataCols=3
    var int dataRows=206

    if barstate.islast and not showColors and not na(this.cbx)
        this.cbx.delete()

    if barstate.islast and showColors
        this.cbx := table.new(columns=dataCols,rows=dataRows,position=position)
        this.cbx.merge_cells(start_column=dataCols-2, start_row=0, end_column=dataCols-1, end_row=0)
        this.cbx.cell(column=dataCols-2,   row=0,    text='Frame =>',    text_halign=text.align_right, text_size=size.small, text_color=chart.fg_color, bgcolor=chart.bg_color)
        this.cbx.cell(column=dataCols-1,   row=0,    text='Frame Color', text_halign=text.align_left, text_size=size.small, text_color=this.FrameColor, bgcolor=chart.bg_color)
        this.cbx.cell(column=dataCols-2,   row=1,    text='Header =>',           text_halign=text.align_right, text_size=size.small, text_color=chart.fg_color, bgcolor=chart.bg_color)
        this.cbx.cell(column=dataCols-1,   row=1,    text='Header Color + BG',   text_halign=text.align_left, text_size=size.small, text_color=this.HeaderColor, bgcolor=this.HeaderColorBG)
        this.cbx.cell(column=dataCols-2,   row=2,    text='Status =>',           text_halign=text.align_right, text_size=size.small, text_color=chart.fg_color, bgcolor=chart.bg_color)
        this.cbx.cell(column=dataCols-1,   row=2,    text='Status Color + BG',   text_halign=text.align_left, text_size=size.small, text_color=this.StatusColor, bgcolor=this.StatusColorBG)
        this.cbx.cell(column=dataCols-2,   row=3,    text='Text =>',         text_halign=text.align_right, text_size=size.small, text_color=chart.fg_color, bgcolor=chart.bg_color)
        this.cbx.cell(column=dataCols-1,   row=3,    text='Text Color + BG', text_halign=text.align_left, text_size=size.small, text_color=this.TextColor, bgcolor=this.TextColorBG)
        this.cbx.cell(column=dataCols-2,   row=4,    text='Cell Border =>',    text_halign=text.align_right, text_size=size.small, text_color=chart.fg_color, bgcolor=chart.bg_color)
        this.cbx.cell(column=dataCols-1,   row=4,    text='Cell Border Color', text_halign=text.align_left, text_size=size.small, text_color=this.CellBorderColor, bgcolor=this.CellBorderColor)
        this.cbx.cell(column=dataCols-2,   row=5,    text='Separator =>',    text_halign=text.align_right, text_size=size.small, text_color=chart.fg_color, bgcolor=chart.bg_color)
        this.cbx.cell(column=dataCols-1,   row=5,    text='Separator Color', text_halign=text.align_left, text_size=size.small, text_color=this.SeparatorColor, bgcolor=this.SeparatorColor)
        for x=0 to math.min(this.colorDB.rows(),200)-1
            this.cbx.cell(column=dataCols-2,   row=x+6,    text='Color #'   +str.tostring(x)+'      '+(x<this.levelDB.size()?this.levelDB.get(x):'No Level Name')+'  ',  text_halign=text.align_left, text_size=size.small, text_color=this.colorDB.get(x,0), bgcolor=this.colorDB.get(x,1))
            this.cbx.cell(column=dataCols-1,   row=x+6,    text='Highlight '+str.tostring(x)+'      '+(x<this.levelDB.size()?this.levelDB.get(x):'No Level Name')+'  ',  text_halign=text.align_left, text_size=size.small, text_color=this.colorDB.get(x,2), bgcolor=this.colorDB.get(x,0))

// @function
//  Library demo link => https://www.tradingview.com/script/wITCQP6R-libhs-log-DEMO/
//___
//  ### **init**()
//  Sets up data for logging. It consists of 6 separate message queues, and 3 additional queues for bar index, time and log level/error code. Do not directly alter the contents, as library could break.
//```
//  method init (int rows=50, isConsole=true)
//```
//  #### *Parameters*
//>  int `rows`*=50*             Number of rows to start with\
//>  bool `isConsole`*=true*    Whether to initialise as Console or Logx. If true will setup as Console.
//___
//  ### **initConsole**()
//```
//  method initConsole (int rows=50)
//```
//  Sets up logger as Console. It consists of one message queue, and 3 additional queues for bar index, time and log level/error code.
//  #### *Parameters*
//>  int `rows`*=50*             Number of rows to start with
//  #### Override default settings with following
//> `MarkNewBar` =*true*\
//> `ShowBarIndex`= *false*
//___
//  ### **initLogx**()
//```
//  method initLogx (int rows=50)
//```
//  Sets up logger as Logx. It consists of six message queues, and 3 additional queues for bar index, time and log level/error code.
//  #### *Parameters*
//>  int `rows`*=50*             Number of rows to start with
//  #### Override default settings with following
//> `MarkNewBar` =*false*\
//> `ShowBarIndex` =*true*
//___
//  ### **clear**()
//```
//  method clear()
//```
//  Clears all the queue, including bar_index and time queues, of existing messages
//___
//  ### **resize**()
//```
//  method resize (int rows=40)
//```
//  Resizes the message queues. If size is decreased then removes the oldest message.
//  #### *Parameters*
//>  int `rows`=*40*     Number of rows to be resized to
//___
//  ### **undo**()
//```
//  method undo (int rows=1)
//```
//  Undo messages logged. Will not undo when messages have been logged asynchronously
//  #### *Parameters*
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  ### **undoq**()
//```
//  method undoq (int q, int rows=1)
//```
//  Undo asynchronously logged messages. Will not undo normally logged messages.
//  #### *Parameters*
//>  int `q`           Q number whose messages are to be reverted\
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  ### **undo1**(), **undo2**(), **undo3**(), **undo4**(), **undo5**(), **undo6**()
//  Undo asynchronously logged messages from Q1/2/3/4/5/6. Will not undo normally logged messages.
//```
//  method undo1 (int rows=1)
//  method undo2 (int rows=1)
//  method undo3 (int rows=1)
//  method undo4 (int rows=1)
//  method undo5 (int rows=1)
//  method undo6 (int rows=1)
//```
//  #### *Parameters*
//>  int `rows`*=1*     Number of rows to be reverted
//___
//  ### **log**()
//  Logs messages to the queues , including, time/date, bar_index, and error code
//```
//  method log (                string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log (int lvl,        string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log (int lvl, int c, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.AutoMerge`           Automatically merges the right most columns into left if there is no text logged.\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7
//  #### *Properties used*
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`           (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`             (Optional) Color Code to be used for the row being logged. Not used for messages, but for other fields such as Bar Index, if they are displayed. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `m1`         Message needed to be logged to Q1, or for console\
//>  string `m2` - `m6`   Message needed to be logged to Q2 to Q6. Not used/ignored when in console mode\
//>  int `c1` - `c6`      (Optional) Color Code to be used for the messages being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
//  ### **page**()
//  Logs messages to the queues , including, time/date, bar_index, and error code. All messages from previous bars are cleared
//```
//  method page (                string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)
//  method page (int lvl,        string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)
//  method page (int lvl, int c, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    `not used`\
//> `.PageHistory`        `not used`\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.AutoMerge`           Automatically merges the right most columns into left if there is no text logged.\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7
//  #### *Properties used*
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`           (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`             (Optional) Color Code to be used for the row being logged. Not used for messages, but for other fields such as Bar Index, if they are displayed. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `m1`         Message needed to be logged to Q1, or for console\
//>  string `m2` - `m6`   Message needed to be logged to Q2 to Q6. Not used/ignored when in console mode\
//>  int `c1` - `c6`      (Optional) Color Code to be used for the messages being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `page`*=true*        Whether to page the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
//  ### **turnPage**()
//```
//  method turnPage (bool turn=true)
//```
//  Set the messages to be on a new page, clearing messages from previous page.
//  This is not dependent on PageHistory option, as this export method simply just clears all the messages, like turning old pages onto a new page.
//  #### *Properties used*
//> `.PageOnEveryBar`    `not used`\
//> `.PageHistory`        `not used`
//  #### *Parameters*
//>  bool `turn`=*true*     Whether to turn the page or not
//___
//  ### **alog**()
//  Logs messages asyncronously to the queue, including, time/date, bar_index, and error code
//```
//  method alog (                string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method alog (int lvl,        string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method alog (int lvl, int c, string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7\
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`     (Optional) Log Level of the message.If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`       (Optional) Color Code to be used for the message. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `msg`  Message to be logged\
//>  int `q`*=1*     Q number the message to be logged to\
//>  int `cq`      (Optional) Color Code to be used for the message being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
//  ### **log1**(), **log2**(), **log3**(), **log4**(), **log5**(), **log6**()
//  Logs messages asyncronously to the queue 1/2/3/4/5/6, including, time/date, bar_index, and error code
//```
//  method log1(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log1(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log1(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  method log2(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log2(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log2(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  method log3(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log3(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log3(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  method log4(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log4(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log4(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  method log5(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log5(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log5(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  method log6(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log6(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log6(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//  #### *Properties used*
//> `.PageOnEveryBar`    Paging will be done on each bar only if this property has been set to true\
//> `.PageHistory`        Number of bars that will be retained, if paging is on. Defalut is 0, which mean only messages from current bar will be retained\
//> `.MarkNewBar`         First on each new bar will be marked, only if this property has been set to true\
//> `.TabSizeQ1-6`        Adds a tab of the size specified to start of each message in each cell, if using log levels 1 - 7\
//> `.PrefixLogLevel`     (Console Only) Prefix the log level name before the messages (in Q1, when logging asynchronously)
//  #### *Parameters*
//>  int `lvl`     (Optional) Log Level of the message. If omitted, defaults to Level 3 = Info / Color Code = 1/Off White. Refer to levels/colors below\
//>  int `c`       (Optional) Color Code to be used for the message. If omitted or negative, uses lvl to determine color code. Color code 0 will hide the message\
//>  string `msg`  Message to be logged\
//>  int `cq`      (Optional) Color Code to be used for the message being logged. If negative, uses `lvl` to determine color code. If omitted, uses row color code (parameter `c`). Color code 0 will hide the message
//  #### *Parameters*
//>  string `tooltip`*=na*    Tooltip for the row\
//>  string `font`*=na*        Font to be used for the row\
//>  int `tv`*=time*           Time value to be logged\
//>  bool `log`*=true*         Whether to log the message or not
//  #### *Log Levels*
//  `1 = TRACE  Off White`    
//  `2 = DEBUG  Green`    
//  `3 = INFO  Blue`    
//  `4 = WARNING  Cream`    
//  `5 = ERROR  Yellow`    
//  `6 = CRITICAL  Orange`    
//  `7 = FATAL  Red`    
//___
// ### **show**()
//```
//  method show (string position=position.bottom_right, string hhalign=text.align_left, string hvalign=text.align_top, string hsize=size.auto, string thalign=text.align_left, string tvalign=text.align_top, string tsize=size.auto, bool show=true, log attach=na)
//```
//  Display Message Q, Index Q, Time Q, and Log Levels
// #### *Note*
//>  All options for postion/alignment accept TV values, such as position.bottom_right, text.align_left, size.auto etc.\
//>  Use getTablePosition() / getTextAlign() / getTextSize() methods to get the TV accepted names.
// #### *Example:*
//```
//  ip_TablePosition = input.string('Top Right',   'Position',  options=['Top Left','Top Center','Top Right','Middle Left','Middle Center','Middle Right','Bottom Left','Bottom Center','Bottom Right'])
//  ip_TextSize      = input.string('Small',       'Size',      options=['Auto','Tiny','Small','Normal','Large','Huge'])
//  ip_Align         = input.string('Left',        'Alignment', options=['Left','Center','Right'])
//  .show(position=ip_TablePosition.getTablePosition(), thalign=ip_Align.getTextAlign(), tsize=ip_TextSize.getTextSize() )
//```
//  #### *Properties impacting how log is displayed*
//> `.ColorText`               Color Code will be used only if ColorText has been set to true\
//> `.HighlightText`          Color Code will be used only if HighlightText has been set to true\
//> `.MoveLogUp`               Reverse the direction of the log scrolling. The usual direction is scrolling up. False will scroll down\
//> `.ShowMinimumLevel`       The Log level upto which the messages will be shown. All messages below this level will not be displayed, even if logged\
//> `.MinWidth`                Sometimes the text displayed goes over table edges. Setting this property ensures a minumum width is always displayed
//  #### *Properties impacting how log is displayed*
//> `.ReplaceWithCodes`          (Logx Only) When displaying the Q with Log Level names, you can display Log level codes instead\
//> `.RestrictLevelsToKey7`     When displaying Log Level names, only first seven (TRACE to CRITICAL) will be displayed and rest ignored
//  #### *Parameters*
//>  string `position`=*position.bottom_right*     Position of the logger table.\
//>  string `hhalign`=*text.align_left*             Header text's horizontal alignment\
//>  string `hvalign`=*text.align_top*             Header text's vertical alignment\
//>  string `hhsize`=*size.auto*                   Header text size
//  #### *Parameters*
//>  string `thalign`=*text.align_left*             Text's horizontal alignment of each cell within the log table\
//>  string `tvalign`=*text.align_top*             Text's vertical alignment of each cell within the log table\
//>  string `thsize`=*size.auto*                   Logger cell's text size
//  #### *Parameters*
//>  bool `show`=*true*                          Whether to show the log table or not\
//>  log `attach`                              (Optional) Console that has been attached before using logger.attach() method
//___
// ### **attach**()
//```
//  method attach(log attach, string position='anywhere')
//```
//  Attaches a console to Logx, or moves already attached console around Logx
//  #### *Parameters*
//>  log `attach`                 Console object that to be attached.\
//>  string `position`=*anywhere*  Position of Console relative to Logx. Can be Top, Right, Bottom, Left. Default is Bottom. If unknown specified then defaults to Bottom
//___
// ### **detach**()
//```
//  method detach(log attachment)
//```
//  Detaches the attached console from Logx.
//  #### *Parameters*
//>  log `attachment`        Console object to be detached.
//___
// ### **showColors**()
//```
//  method showColors (string position=position.bottom_left,bool showColors=true)
//```
//  Displays a separate table, showing what Error Colors (maximum 200 colors)
//  #### *Parameters*
//>  string `position`=*position.bottom_left*     Position of the logger table.\
//>  bool `showColors`=*true*                   Whether to show Colors table or not. Default is true.
//___
// ### **dateTimeFormat**()
//```
//  method dateTimeFormat(string format='')
//```
// Re/set the date time format used for displaying date and time. Default resets to dd.MMM.yy HH:mm\
//  #### *Parameters*
//>  string `format`*=''*     Date time format. If passed as empty (not as na) then resets teh format to d.MMM.yy H:mm, which would look as 9.Aug.23 9:01
//___
// ### **setFontHeader**()
//```
//  method setFontHeader(string font=na)
//```
// Sets up font to be used for Header (only on Logx)
//  #### *Parameters*
//>  string `font`*=na*     Font to be used for Logx header. If it is not font.family_monospace then it is set to font.family_default
//___
// ### **setFontStatus**()
//```
//  method setFontStatus(string font=na)
//```
// Sets up font to be used for Status
//  #### *Parameters*
//>  string `font`*=na*     Font to be used for Console/Logx status bar. If it is not font.family_monospace then it is set to font.family_default
//___
// ### **setFontMetaStatus**()
//```
//  method setFontMetaStatus(string font=na)
//```
// Sets up font to be used for meta info in Status
//  #### *Parameters*
//>  string `font`*=na*     Font to be used for Console/Logx status bar. If it is not font.family_monospace then it is set to font.family_default
//___
// ### **resetXX**()
//```
//  method resetTextColor()     =>  //  Resets the text color of the log to library default.
//  method resetTextColorBG()   =>  //   Resets the background color of the log to library default.
//  method resetHeaderColor()   =>  //  Resets the color used for Headers, to library default.
//  method resetHeaderColorBG() =>  //  Resets the background color used for Headers, to library default.
//  method resetStatusColor()   =>  //  Resets the text color of the status row, to library default.
//  method resetStatusColorBG() =>  //  Resets the background color of the status row, to library default.
//  method resetFrameColor()    =>  //  Resets the color used for the frame around the log table, to library default.
//  method resetColorsHC()      =>  //  Resets the color used for the highlighting when Highlight Text option is used, to library default
//  method resetColorsBG()      =>  //  Resets the background color used for setting the background color, when the Color Text option is used, to library default
//  method resetColors()        =>  //  Resets the color used for respective color code, when the Color Text option is used, to library default
//```
//___
// ### **setColors**()
//  Sets the colors corresponding to color codes. 
//```
//  method setColors(color[] c)
//```
//  Index 0 of input array c is color is reserved for future use\
//  Index 1 of input array c is color for color code 1\
//  Index 2 of input array c is color for color code 2 and so on.\
//  There are 2 modes of coloring
//  1. Using the Foreground color
//  2. Using the Foreground color as background color and a white/black/gray color as foreground color
//  - This is denoting or highlighting. Which effectively puts the foreground color as background color
//  #### *Parameters*
//>  color[ ] `c`     Color Array to be used for corresponding color codes. If the corresponding code is not found, then text color is used
//___
// ### **setColorsHC**()
//  Sets the highlight colors corresponding to color codes. 
//```
//  method setColorsHC(color[] c)
//```
//  Index 0 of input array c is color is reserved for future use\
//  Index 1 of input array c is color for color code 1\
//  Index 2 of input array c is color for color code 2 and so on.\
//  There are 2 modes of coloring
//  1. Using the Foreground color
//  2. Using the Foreground color as background color and a white/black/gray color as foreground color
//  - This is denoting or highlighting. Which effectively puts the foreground color as background color
//  #### *Parameters*
//>  color[ ] `c`     Color Array to be used for corresponding color codes. If the corresponding code is not found, then text color BG is used
//___
// ### **setColorsBG**()
//```
//  method setColorsBG(color[] c)
//```
//  Sets the background colors corresponding to color codes. Index 0 of input array c is color is reserved for future use\
//  Index 1 of input array c is color for color code 1\
//  Index 2 of input array c is color for color code 2 and so on.\
//  There are 2 modes of coloring
//  1. Using the Foreground color
//  2. Using the Foreground color as background color and a white/black/gray color as foreground color
//  - This is denoting or highlighting. Which effectively puts the foreground color as background color
//  #### *Parameters*
//>  color[ ] `c`     Color Array to be used for corresponding color codes. If the corresponding code is not found, then text color BG is used
//___
// ### **setColor**()
//  Sets the color corresponding to color code
//```
//  method setColor(int e, color c)
//  method setColor(int e, color fg, color bg, color hc)
//```
//  #### *Parameters*
//>  int `e`       Color code whose color needs to be changed. If this code is not found, then color array will be expanded\
//>  color `c`     Color corresponding to code supplied.
//  #### *Parameters*
//>  color `fg`     Foreground Color corresponding to code supplied\
//>  color `bg`     Background Color corresponding to code supplied\
//>  color `hc`     Highlight Color corresponding to code supplied.
//___
// ### **setColorHC**()
// Sets the highlight color corresponding to error code
//```
//  method setColorHC(int e, color c)
//```
//  #### *Parameters*
//>  int `e`       Color code whose highlight color needs to be changed. If this code is not found, then color array will be expanded\
//>  color `c`     Color corresponding to code supplied.
//___
// ### **setColorBG**()
//```
//  method setColorBG(int e, color c)
//```
//  Sets the background color corresponding to error code
//  #### *Parameters*
//>  int `e`       Color code whose background color needs to be changed. If this code is not found, then color array will be expanded\
//>  color `c`     Color corresponding to code supplied.
//___
// ### **getColor**()
//```
//  method getColor(int e)
//```
//  Returns the color corresponding to color code
//  #### *Parameters*
//>  int `e`       Color Code whose color needs to be extracted. If this code is not found, then na will be returned.\
//  #### Returns    
//> **`color`**      The color corresponding to color code supplied. If this code is not found, then na will be returned.
//___
// ### **getColorHC**()
//```
//  method getColorHC(int e)
//```
//  Returns the highlight color corresponding to color code
//  #### *Parameters*
//>  int `e`       Color Code whose highlight color needs to be extracted. If this code is not found, then na will be returned.\
//  #### Returns    
//> **`color`**      The highlight color corresponding to color code supplied. If this code is not found, then na will be returned.
//___
// ### **getColorBG**()
//```
//  method getColorBG(int e)
//```
//  Returns the background color corresponding to color code
//  #### *Parameters*
//>  int `e`       Color Code whose background color needs to be extracted. If this code is not found, then na will be returned.\
//  #### Returns    
//> **`color`**      The background color corresponding to color code supplied. If this code is not found, then na will be returned.
//___
// ### **resetLevelNames**()
//```
//  method resetLevelNames(string prefix='Level ', string suffix='')
//```
//  Resets the log level names used for corresponding level codes\
// With prefix/suffix, the default Level name will be like => prefix + Code + suffix
//  #### *Parameters*
//>  string `prefix`=*'Level'*   Prefix to use when resetting level names\
//>  string `suffix`=*''*        Suffix to use when resetting level names
//___
// ### **setLevelNames**()
//```
//  method setLevelNames(string[] names)
//```
//  Resets the log level names used for corresponding level codes\
//  Index 0 of input array names is reserved for future use\
//  Index 1 of input array names is name used for level code 1.\
//  Index 2 of input array names is name used for level code 2 and so on.
//  #### *Parameters*
//>  string[ ] `names`   Array of log level names be used for corresponding level odes. If the corresponding code is not found, then an empty string is used
//___
// ### **setLevelName**()
//```
//  method setLevelName(int e, string levelName)
//```
//  Sets the Log level name corresponding to code supplied.
//  #### *Parameters*
//>  int `e`                Code whose log level name needs to be changed. If this code is not found, then log level names array will be expanded.\
//>  string `levelName`   Level name corresponding to code supplied.
//___
// ### **getLevelName**()
//```
//  method getLevelName(int e)
//```
//  Gets the Log level name corresponding to error code supplied.
//  #### *Parameters*
//>  int `e`       Code whose log level name needs to be extracted. If this error code is not found, then na will be returned.\
//  #### Returns    
//> **`string`**    The log level name corresponding to code supplied. If this code is not found, then na will be returned.
//___
//> import GETpacman/logger/3 as logger\
//> `logger.usage()`\
//> `logger.fields()`\
//> `logger.methods()`\
//> `logger.docs()`        
//___
export docs()=>
    ''


//  @function
//  `Color Settings`
// ```
// 	color	HeaderColor
// 	color	HeaderColorBG
// 	color	StatusColor
// 	color	StatusColorBG
// 	color	TextColor
// 	color	TextColorBG
// 	color	FrameColor
// 	int 	FrameSize	= 1 
// 	int 	CellBorderSize	= 0
// 	color 	CellBorderColor
//  color   SeparatorColor  = color.gray
// ```
//  `Header/Status Bar settings`
// ```
// 	bool    IsConsole	= true
// 	bool    ShowHeader	= true
// 	bool    HeaderAtTop	= true
//  string  HeaderTooltip   = 'Header'
// 	bool    ShowStatusBar	= true
// 	bool    StatusBarAtBottom= true
//  string  Status          = ''
//  string  StatusTooltip   = 'Status'
// 	bool    ShowMetaStatus  = true
//  string  MetaStatusTooltip= 'Meta Info'
// ```
//  `Columns settings`
// ```
// 	bool    ShowBarIndex    = false
// 	bool    ShowDateTime    = false
// 	bool    ShowLogLevels   = false     //Shows the debug log level as a column in Logx or as meta tab in Console
// 	bool    ShowQ1          = true
// 	bool    ShowQ2          = true
// 	bool    ShowQ3          = true
// 	bool    ShowQ4          = false
// 	bool    ShowQ5          = false
// 	bool    ShowQ6          = false
// 	string  HeaderQbarIndex = 'Bar#'
// 	string  HeaderQdateTime = 'Date'
// 	string  HeaderQLevelCode= 'Code'
// 	string  HeaderQLogLevel	= 'LvL'
// 	string  HeaderQ1	= 'h.Q1'    //Header Text
// 	string  HeaderQ2	= 'h.Q2'
// 	string  HeaderQ3	= 'h.Q3'
// 	string  HeaderQ4	= ''
// 	string  HeaderQ5	= ''
// 	string  HeaderQ6	= ''
// 	int     TabSizeQ1	= 0     //Q Tabe size
// 	int     TabSizeQ2       = 0
// 	int     TabSizeQ3       = 0
// 	int     TabSizeQ4       = 0
// 	int     TabSizeQ5       = 0
// 	int     TabSizeQ6       = 0
// ```
//  `General settings`
// ```
//  int     ShowMinimumLevel= 0    //Shows log messages at or above this level
// 	bool    AutoMerge       = true
// 	bool    ColorText     	= true  //Text coloring requires this setting to be on
// 	bool    HighlightText   = false //Text highlighting requires this setting to be on
// 	bool    MarkNewBar	= true
// 	bool    PageOnEveryBar  = false
//  int     PageHistory     = 0     //Used with PageOnEveryBar, how many bars of messages will be retained when paging on every bar
// 	bool    PrefixLogLevel  = false //Only for Console, to prefix all messages with Log Level
// 	bool    MoveLogUp       = true  //Reverses the direction of log scrolling
// 	int     MinWidth       	= 40    //Minumum width to display for Logx/Console. 
// 	bool    ReplaceWithCodes= false    //When used with ShowLogLevels in Logx, replaces log level codes with log level names.
//  bool    RestrictLevelsToKey7 = false    //If set to true, will only record log levels from TRACE to CRITICAL and rest levels will not be logged with message.
// ```
// #### `Field Methods`
//```
//  method dateTimeFormat(string format='') =>  // Re/set the date time format used for displaying date and time. Default resets to dd.MMM.yy HH:mm
//  method setFontHeader(string font=na)    =>  // Sets up font to be used for Header (only on Logx)
//  method setFontStatus(string font=na)    =>  // Sets up font to be used for Status
//  method setFontMetaStatus(string font=na)=>  // Sets up font to be used for meta info in Status
//```
//```
//  method resetTextColor()                 =>  // Resets the text color of the log to library default
//  method resetTextColorBG()               =>  // Resets the background color of the log to library default
//  method resetHeaderColor()               =>  // Resets the color used for Headers, to library default.
//  method resetHeaderColorBG()             =>  // Resets the background color used for Headers, to library default.
//  method resetStatusColor()               =>  // Resets the text color of the status row, to library default.
//  method resetStatusColorBG()             =>  // Resets the background color of the status row, to library default.
//  method resetFrameColor()                =>  // Resets the color used for the frame around the log table, to library default.
//```
//```
//  method setColors(color[] c)             =>  // Sets the colors corresponding to color codes.
//  method setColorsHC(color[] c)           =>  // Sets the highlight colors corresponding to color codes.
//  method setColorsBG(color[] c)           =>  // Sets the background colors corresponding to color codes.
//  method setColor(int e, color c)         =>  // Sets the color corresponding to color code
//  method setColor(int e, color fg, color bg, color hc)    
//  method setColorHC(int e, color c)       =>  // Sets the highlight color corresponding to error code
//  method setColorBG(int e, color c)       =>  // Sets the background color corresponding to error code
//  method getColor(int e)                  =>  // Returns the color corresponding to color code
//  method getColorHC(int e)                =>  // Returns the highlight color corresponding to color code
//  method getColorBG(int e)                =>  // Returns the background color corresponding to color code
//```
//```
//  method resetLevelNames(prefix='Level ', suffix='')=>  // Resets the log level names used for corresponding level codes
//  method setLevelNames(string[] names)    =>  // Resets the log level names used for corresponding level codes
//  method setLevelName(int e, string levelName)=>  // Sets the Log level name corresponding to code supplied.
//  method getLevelName(int e)              =>  // Gets the Log level name corresponding to error code supplied.
//```
//___
//> import GETpacman/logger/3 as logger\
//> `logger.usage()`\
//> `logger.fields()`\
//> `logger.methods()`\
//> `logger.docs()`    
//___
export fields()=>
    ''

//  @function
// #### `Helper String Overloads`
//```
// method getTextAlign(string)  => ('Top').getTextAlign()
// method getTextSize()         => ('Small').getTextSize()
// method getTablePosition()    => ('Bottom Right').getTablePosition()
//```
// #### `Helper conversions`   
//```
// method upper(string this)    => // convert to upper string
// method upper(bool this)      => // convert to upper string from bool
//```
//```
// method lower(string this)    => // convert to lower string
// method lower(bool this)      => // convert to lower string from bool
//```
//```
// method f(bool this)                      => // convert to float from bool
// method f(string this, int decimals=6)    => // convert to float from string
// method f(int this)                       => // convert to float from int
// method f(float this, int decimals=6)     => // rounds float to specified decimals `.f(int deciimals=6)
//```
//```
// method i(bool this)          =>  // convert to int from bool
// method i(string this)        =>  // convert to int from string
// method i(float this)         =>  // convert to int from float
//```
//```
// method s(bool this)          =>  // convert to string from bool
// method s(int this)           =>  // convert to string from int
// method s(float this)         =>  // convert to string from float
//```
//```
// method b(int this)           =>  // convert to bool from int
// method b(float this)         =>  // convert to bool from float
// method b(string this)        =>  // convert to bool from string
//```
// ### `Logger Methods`
// #### `Initialise`
//```
//  method init (int rows=50, isConsole=true)   =>  //  Sets up data for logging. It consists of 6 separate message queues, and 3 additional queues for bar index, time and log level/error code. Do not directly alter the contents, as library could break.
//  method initConsole (int rows=50)            =>  //  Sets up logger as Console. It consists of one message queue, and 3 additional queues for bar index, time and log level/error code.
//  method initLogx (int rows=50)               =>  //  Sets up logger as Logx. It consists of six message queues, and 3 additional queues for bar index, time and log level/error code.
//```
// #### `Clear / Resize / Undo`
//```
//  method clear()                   =>  // Clears all the queue, including bar_index and time queues, of existing messages
//  method resize (int rows=40)      =>  // Resizes the message queues. If size is decreased then removes the oldest message.
//  method undo (int rows=1)         =>  // Undo messages logged. Will not undo when messages have been logged asynchronously
//  method undoq (int q, int rows=1) =>  // Undo asynchronously logged messages. Will not undo normally logged messages.
//```
//```
//  method undo1 (int rows=1)        =>  // Undo asynchronously logged messages from Q1. Will not undo normally logged messages.
//  method undo2 (int rows=1)        =>  // Undo asynchronously logged messages from Q2. Will not undo normally logged messages.
//  method undo3 (int rows=1)        =>  // Undo asynchronously logged messages from Q3. Will not undo normally logged messages.
//  method undo4 (int rows=1)        =>  // Undo asynchronously logged messages from Q4. Will not undo normally logged messages.
//  method undo5 (int rows=1)        =>  // Undo asynchronously logged messages from Q5. Will not undo normally logged messages.
//  method undo6 (int rows=1)        =>  // Undo asynchronously logged messages from Q6. Will not undo normally logged messages.
//```
// #### `Logging messages`
//```
//  // Logs messages to the queues , including, time/date, bar_index, and error code
//  method log (                string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log (int lvl,        string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log (int lvl, int c, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  // Logs messages to the queues , including, time/date, bar_index, and error code. All messages from previous bars are cleared
//  method page (                string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)
//  method page (int lvl,        string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)
//  method page (int lvl, int c, string m1=na, string m2=na, string m3=na, string m4=na, string m5=na, string m6=na, int c1=na, int c2=na, int c3=na, int c4=na, int c5=na, int c6=na, string tooltip=na, string font=na, int tv=time, bool page=true)
//  
//  method turnPage (bool turn=true)    =>  //  Set the messages to be on a new page, clearing messages from previous page.
//```
//```
//  // Logs messages asyncronously to the queue, including, time/date, bar_index, and error code
//  method alog (                string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method alog (int lvl,        string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method alog (int lvl, int c, string msg=na, int q=1, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  // Logs messages asyncronously to the queue 1/2/3/4/5/6, including, time/date, bar_index, and error code
//  method log1(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log2(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log3(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log4(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log5(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log6(int lvl, int c, string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  method log1(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log2(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log3(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log4(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log5(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log6(int lvl,        string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  method log1(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log2(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log3(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log4(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log5(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//  method log6(                string msg=na, int cq=na, string tooltip=na, string font=na, int tv=time, bool log=true)
//```
//```
//  method attach(log attach, string position='anywhere')   =>  //  Attaches a console to Logx, or moves already attached console around Logx
//  method detach(log attachment)                           =>  //  Detaches the attached console from Logx.
//```
//```
//  // Display Message Q, Index Q, Time Q, and Log Levels
//  method show (string position=position.bottom_right, string hhalign=text.align_left, string hvalign=text.align_top, string hsize=size.auto, string thalign=text.align_left, string tvalign=text.align_top, string tsize=size.auto, bool show=true, log attach=na)
//```
//```
//  // Displays a separate table, showing what Error Colors (maximum 200 colors)
//  method showColors (string position=position.bottom_left,bool showColors=true)
//```
// #### `Settings`
//```
//  method dateTimeFormat(string format='') =>  // Re/set the date time format used for displaying date and time. Default resets to dd.MMM.yy HH:mm
//  method setFontHeader(string font=na)    =>  // Sets up font to be used for Header (only on Logx)
//  method setFontStatus(string font=na)    =>  // Sets up font to be used for Status
//  method setFontMetaStatus(string font=na)=>  // Sets up font to be used for meta info in Status
//```
//```
//  method resetTextColor()                 =>  // Resets the text color of the log to library default
//  method resetTextColorBG()               =>  // Resets the background color of the log to library default
//  method resetHeaderColor()               =>  // Resets the color used for Headers, to library default.
//  method resetHeaderColorBG()             =>  // Resets the background color used for Headers, to library default.
//  method resetStatusColor()               =>  // Resets the text color of the status row, to library default.
//  method resetStatusColorBG()             =>  // Resets the background color of the status row, to library default.
//  method resetFrameColor()                =>  // Resets the color used for the frame around the log table, to library default.
//```
//```
//  method setColors(color[] c)             =>  // Sets the colors corresponding to color codes.
//  method setColorsHC(color[] c)           =>  // Sets the highlight colors corresponding to color codes.
//  method setColorsBG(color[] c)           =>  // Sets the background colors corresponding to color codes.
//  method setColor(int e, color c)         =>  // Sets the color corresponding to color code
//  method setColor(int e, color fg, color bg, color hc)    
//  method setColorHC(int e, color c)       =>  // Sets the highlight color corresponding to error code
//  method setColorBG(int e, color c)       =>  // Sets the background color corresponding to error code
//  method getColor(int e)                  =>  // Returns the color corresponding to color code
//  method getColorHC(int e)                =>  // Returns the highlight color corresponding to color code
//  method getColorBG(int e)                =>  // Returns the background color corresponding to color code
//```
//```
//  method resetLevelNames(prefix='Level ', suffix='')  =>  // Resets the log level names used for corresponding level codes
//  method setLevelNames(string[] names)                =>  // Resets the log level names used for corresponding level codes
//  method setLevelName(int e, string levelName)        =>  // Sets the Log level name corresponding to code supplied.
//  method getLevelName(int e)                          =>  // Gets the Log level name corresponding to error code supplied.
//```
//___
//> import GETpacman/logger/3 as logger\
//> `logger.usage()`\
//> `logger.fields()`\
//> `logger.methods()`\
//> `logger.docs()`    
//___
export methods()=>
    ''

// @function
//  Library demo link => https://www.tradingview.com/script/wITCQP6R-libhs-log-DEMO/
//___
// ## **Console Sample Code**
// Console = A sleek single cell logging with a limit of 4096 characters. When you dont need a large logging capability.
//```
// //@version=5
// indicator("demo.Console", overlay=true)
// plot(na)
//```
//```
// ipdc_showTable      = input.bool  (true,          'Show Console?  ',inline='console1', group='Console')
// ipdc_position       = input.string('Bottom Left', 'Position',       inline='console1', group='Console', options=['Top Left','Top Center','Top Right','Middle Left','Middle Center','Middle Right','Bottom Left','Bottom Center','Bottom Right'])
// ipdc_tsize          = input.string('Auto',        'Text Size',      inline='console1', group='Console', options=['Auto','Tiny','Small','Normal','Large','Huge'])
// ipdc_hsize          = ipdc_tsize
// ipdc_hhalign        = 'Left'
// ipdc_hvalign        = 'Top'
// ipdc_thalign        = 'Left'
// ipdc_tvalign        = 'Top'
//```
//```
// import GETpacman/logger/3 as logger
//```
//```
// var console = logger.log.new()      
// console.init()  // init() should be called as first line after variable declaration
// console.MarkNewBar:=false
// console.PageOnEveryBar:=true
//```
//```
// console.FrameColor:=color.green
// console.log(' ')
// console.log(' ')
// console.log('Hello World')
// console.log(' ')
// console.log(' ',c1=2)
//```
//```
// console.FrameColor:=color.blue
// console.ShowHeader:=false             //this wont throw error but is not used for console
//```
//```
// console.show(ipdc_position.getTablePosition(),ipdc_hhalign.getTextAlign(), ipdc_hvalign.getTextAlign(), ipdc_tsize.getTextSize(),ipdc_thalign.getTextAlign(), ipdc_tvalign.getTextAlign(), ipdc_tsize.getTextSize(),show=ipdc_showTable)
//```
//>
//>
//___
//  
// ## **Logx Sample Code**
// Logx = Multiple columns logging with a limit of 4096 characters each message. When you need to log large number of messages.
//```
// //@version=5
// indicator("demo.Logx", overlay=true)
// plot(na)
//```
//```
// ipdd_showTable = input.bool  (true,          'Show Logx?  ',inline='logx1', group='Logx')
// ipdd_position  = input.string('Bottom Right','Position',    inline='logx1', group='Logx', options=['Top Left','Top Center','Top Right','Middle Left','Middle Center','Middle Right','Bottom Left','Bottom Center','Bottom Right'])
// ipdd_tsize     = input.string('Auto',        'Text Size',   inline='logx1', group='Logx', options=['Auto','Tiny','Small','Normal','Large','Huge'])
// ipdd_hsize     = ipdd_tsize
// ipdd_hhalign   = 'Left'
// ipdd_hvalign   = 'Top'
// ipdd_thalign   = 'Left'
// ipdd_tvalign   = 'Top'
//```
//```
// import GETpacman/logger/3 as logger
//```
//```
// var logx = logger.log.new()      
// logx.init(isConsole=false)  // init() should be called as first line after variable declaration
// logx.MarkNewBar:=false
// logx.PageOnEveryBar:=true
// logx.ShowBarIndex:=false
//```
//```
// logx.FrameColor:=color.green
// logx.log(' ')
// logx.log(' ')
// logx.log(m2='Hello',m3='World',c2=2,c3=3)
// logx.log(' ')
// logx.log(' ')
//```
//```
// logx.HeaderQ1:=''
// logx.HeaderQ2:=''
// logx.HeaderQ3:=''
// logx.FrameColor:=color.olive       //settings can be changed anytime before show method is called. Even twice. The last call will set the final value
//```
//```
// logx.show(ipdd_position.getTablePosition(),ipdd_hhalign.getTextAlign(), ipdd_hvalign.getTextAlign(), ipdd_tsize.getTextSize(),ipdd_thalign.getTextAlign(), ipdd_tvalign.getTextAlign(), ipdd_tsize.getTextSize(),show=ipdd_showTable) //this should be the last line of your code, after all methods and settings have been dealt with.
//```
//___
//> import GETpacman/logger/3 as logger\
//> `logger.usage()`\
//> `logger.fields()`\
//> `logger.methods()`\
//> `logger.docs()`    
//___
export usage()=>
    ''

//  this.v3 libhs.logger.rcUAT.v34  libhs.logger.rcSIT.45/dev.110/SITdev.v78