Scripts discussion (2)

Discuss and announce AkelPad plugins
Locked
  • Author
  • Message
Offline
Posts: 670
Joined: Thu Jun 03, 2010 8:47 am
Location: Сочи, Хоста
Contact:

Post by Andrey_A_A »

Instructor, хочу установить закладки 2, 4, 6 строке, а получается:

Image

Code: Select all

Call AkelPad.Call("LineBoard::Main", 13, hEditWnd, hDocEdit, "2,4,6")
так же приходит список со смещением:

Code: Select all

  
lpBookLen = AkelPad.MemAlloc(4)
  hMainWnd=AkelPad.GetMainWnd()
  hEditWnd = AkelPad.GetEditWnd()
Call AkelPad.CallW("LineBoard::Main", 12, hEditWnd, 0, 0, lpBookLen)
  lpBookStr = AkelPad.MemAlloc(AkelPad.MemRead(lpBookLen, 3) * 2)

  Call AkelPad.CallW("LineBoard::Main", 12, hEditWnd, 0, lpBookStr, 0)
  sBooks = AkelPad.MemRead(lpBookStr, 1)

KDJ
Offline
Posts: 1949
Joined: Sat Mar 06, 2010 7:40 pm
Location: Poland

Post by KDJ »

Andrey_A_A wrote:...хочу установить закладки 2, 4, 6 строке...

Code: Select all

AkelPad.Call("LineBoard::Main", 13, hEditWnd, hDocEdit, "1,3,5")
Internally, the lines are numbered from zero.

Offline
Posts: 670
Joined: Thu Jun 03, 2010 8:47 am
Location: Сочи, Хоста
Contact:

Post by Andrey_A_A »

Internally, the lines are numbered from zero.
Я это уже понял, но как-то нелогично - в плагине нумерация строк с единицы на панели нумерации, а в методах с 0...
Кстати у всех с единицы или есть какая-то настройка, чтобы нумеровалось с 0?

KDJ
Offline
Posts: 1949
Joined: Sat Mar 06, 2010 7:40 pm
Location: Poland

Post by KDJ »

Andrey_A_A wrote:в скрипте AkelPadMethodsView.js можно ли:
...
3. Можно что-то придумать, чтобы фразу/слово из буфера обмена искать по всему тексту.
...
This is already done. Example:
- run AkelPadMethodsView.js,
- press Tab to activate edit window,
- press Ctrl+F (find text - down from beginning),
- press Ctrl+V to paste text from clipboard,
- press Enter to find the text,
- press F3 to find next,
- press Shift+F3 to find previous.

KDJ
Offline
Posts: 1949
Joined: Sat Mar 06, 2010 7:40 pm
Location: Poland

Post by KDJ »

AkelPadMethodsView.js
Added:
- possibility to translate the interface,
- context menu in panel with methods list (options "Copy to clipboard" and "Insert to AkelPad"),
- context menu in edit window,
- hotkey Ctrl(+Shift)+Tab.

Offline
Posts: 670
Joined: Thu Jun 03, 2010 8:47 am
Location: Сочи, Хоста
Contact:

Post by Andrey_A_A »

Instructor, всегда возникал вопрос по поводу вашего скрипта SearchReplace.js, а с годами всё чаще.
Вот в чём дело: Со временем список сохранённых шаблонов растёт и получается длинющий список. Нельзя ли сделать "подменюшные папки", в которые можно было класть (записывать) шаблоны рег. выражений.



KDJ не успел потестировать AkelPadMethodsView.js, спасибо, на днях скажу своё мнение.

Offline
Posts: 119
Joined: Sat Jan 12, 2008 10:16 am
Location: Shantou, China

Post by cnnnc »

KDJ wrote:AkelPadMethodsView.js
...
Hi, KDJ. This script unable to use Scripts-Chs.txt for view. I replaced the string(s) "Scripts-Eng.txt" and/or "Scripts-Rus.txt" with "Scripts-Chs.txt". I run the script, then AkelPad crach and exit. Then I checked the script, it seem the problem at line:

Code: Select all

  AkelPad.MemCopy(lpTextA, sText, 0 /*DT_ANSI*/);
.
This is a sample of

Code: Select all

*****************************************************************
***                 Scripts AkelPad plugin v13.1              ***
*****************************************************************

2014 Shengalts Aleksander aka Instructor (Shengalts@mail.ru)


*** 描述 ***

脚本插件基于 Windows 脚本宿主 (WSH) 引擎,因此您可以使用各种各样的 Windows 组件对象模型 (COM) 的对象。
例如,您可以使用 RegExp 对象来执行正则表达式搜索,
使用 FileSystemObject 对象来操作文件,创建快捷方式,
使用 WshShell 对象来操作 Windows 注册表,
或使用 WshNetwork 对象来运行网络功能。
此外,您可以创建和执行利用一个支持自动化的外部应用程序 (如 Word 和 Excel) 脚本。
插件的源码基于 Jeff Glatt 的 "COM in C"。


*** 包括脚本 ***

SearchReplace.js      -使用正则表达式的 搜索/替换。
LinesFilter.js        -使用正则表达式来过滤行。
Test.js               -测试 JScript 的脚本。
Test.vbs              -测试 VBScript 的脚本。


*** 函数 ***

Scripts::Main
主对话框。


*** 外部调用 ***

Call("Scripts::Main", 1, "SCRIPT", "ARGUMENTS")
  参数:
    1
      执行脚本。如果为 "",将使用最近处理过的脚本。
    "SCRIPT"
      脚本文件。
    "ARGUMENTS"
      参数 (默认值为 "")。
  示例:
    Call("Scripts::Main", 1, "InsertDate.js")
    Call("Scripts::Main", 1, "InsertDate.js", `"dd MMMM yyyy"`)

Call("Scripts::Main", 2, "SCRIPT", "ARGUMENTS")
  与上面相同,但等待脚本完成。

Call("Scripts::Main", 3, "SCRIPT")
  参数:
    3
      打开脚本文件来编辑。
    "SCRIPT"
      脚本文件。如果为 "",将使用最近处理过的脚本。


*** 方法列表 (没有连接到 AkelPad 窗口的方法,标记上 +ActiveX) ***

AkelPad.GetMainWnd
AkelPad.GetAkelDir
AkelPad.GetInstanceExe
AkelPad.GetInstanceDll                       +ActiveX
AkelPad.GetLangId                            +ActiveX


*** 方法描述 ***

AkelPad.GetMainWnd
__________________

获取主窗口句柄。

  GetMainWnd();

返回值
  数值。主窗口句柄。

例:
  var hMainWnd=AkelPad.GetMainWnd();


AkelPad.GetAkelDir
__________________

获得 AkelPad 目录或其子目录。

  GetAkelDir([nSubDir]);

参数
  nSubDir
    0  //ADTYPE_ROOT          AkelPad 的文件夹 (默认值)。
    1  //ADTYPE_AKELFILES     "[AkelPad]\AkelFiles".
    2  //ADTYPE_DOCS          "[AkelPad]\AkelFiles\Docs".
    3  //ADTYPE_LANGS         "[AkelPad]\AkelFiles\Langs".
    4  //ADTYPE_PLUGS         "[AkelPad]\AkelFiles\Plugs".
    5  //ADTYPE_SCRIPTS       "[AkelPad]\AkelFiles\Plugs\Scripts".
    6  //ADTYPE_INCLUDE       "[AkelPad]\AkelFiles\Plugs\Scripts\Include".

返回值
  字串。AkelPad 目录或其子目录。

例:
  var pAkelDir=AkelPad.GetAkelDir();


AkelPad.GetInstanceExe
______________________

获取 EXE 实例句柄。

  GetInstanceExe();

返回值
  数值。EXE 实例句柄。

例:
  var hInstance=AkelPad.GetInstanceExe();


AkelPad.GetInstanceDll
______________________

获取 DLL 实例句柄。

  GetInstanceDll();

返回值
  数值。DLL 实例句柄。

例:
  var hInstance=AkelPad.GetInstanceDll();


AkelPad.GetLangId
_________________

获取 AkelPad 语言 ID。

  GetLangId([nType]);

参数
  nType
    0  //LANGID_FULL     完整的语言标识符。这个值是一个主语言标识符和子语言标识符的组合(默认)。
    1  //LANGID_PRIMARY  主语言标识符。
    2  //LANGID_SUB      子语言标识符。

返回值
  数值。AkelPad 语言 ID。

例:
  var nLangID=AkelPad.GetLangId(1 /*LANGID_PRIMARY*/);

  if (nLangID == 0x19) //LANG_RUSSIAN
    WScript.Echo("Russian");
  else
    WScript.Echo("Other");

, save it into a codepage 936 textfile named "Scripts-Chs.txt" for test.

KDJ
Offline
Posts: 1949
Joined: Sat Mar 06, 2010 7:40 pm
Location: Poland

Post by KDJ »

AkelPadMethodsView.js
Added:
- ability to maximize the window,
- memorizing text selection,
Fixed: find text up from current position.

---
cnnnc
Try this:

Code: Select all

// AkelPadMethodsView_Chs.js - ver. 2014-01-29 (x86/x64)
//
// List of AkelPad methods from Scripts-*.txt files
//
// Usage:
// Call("Scripts::Main", 1, "AkelPadMethodsView_Chs.js")
// Required to include: BrowseForFolder_function.js and InputBox_function.js
//
// Hotkeys:
// Tab - rigth <-> left panel
// Ctrl(+Shift)+Tab - next/previous item on methods list
// F1 - menu
// F4 - maximize/restore window
//
// Note:
// The script should be saved in Unicode format

var oSys       = AkelPad.SystemFunction();
var hInstance  = AkelPad.GetInstanceDll();
var sClassName = "AkelPad::Scripts::" + WScript.ScriptName + "::" + hInstance;
var hDlg       = oSys.Call("User32::FindWindowExW", 0, 0, sClassName, 0);

if (hDlg)
{
  if (! oSys.Call("User32::IsWindowVisible", hDlg))
    oSys.Call("User32::ShowWindow", hDlg, 8 /*SW_SHOWNA*/);
  if (oSys.Call("User32::IsIconic", hDlg))
    oSys.Call("User32::ShowWindow", hDlg, 9 /*SW_RESTORE*/);

  oSys.Call("User32::SetForegroundWindow", hDlg);
}
else
{
  if (! (AkelPad.Include("BrowseForFolder_function.js") && AkelPad.Include("InputBox_function.js")))
    WScript.Quit();

  GetLangStrings();

  var hMainWnd     = AkelPad.GetMainWnd();
  var hWndParent   = hMainWnd;
  var hGuiFont     = oSys.Call("Gdi32::GetStockObject", 17 /*DEFAULT_GUI_FONT*/);
  var oFSO         = new ActiveXObject("Scripting.FileSystemObject");
  var nDlgMinW     = 640;
  var nDlgMinH     = 300;
  var oDlgPos      = {"X": 230, "Y": 200, "W": nDlgMinW, "H": nDlgMinH, "Max": 0};
  var bSeparateWnd = false;
  var nAPMSel      = 0;
  var bAPMSort     = true;
  var nAPMLang     = 0;
  var bWordWrap    = false;
  var sFindName    = "";
  var sFindText    = "";
  var sAltDir      = "";
  var aAPM         = [];
  var aAESel       = [{}, {}];
  var aIsLang;
  var sHeader;
  var hSubClass;
  var hFocus;

  ReadIni();
  GetArrayAPM(hMainWnd);
  if (! aAPM.length) WScript.Quit();

  var nTextMax = 512;
  var lpTextLV = AkelPad.MemAlloc(nTextMax * 2);
  var lpLVITEM = AkelPad.MemAlloc(_X64 ? (72) : (60)); //sizeof(LVITEM)
  AkelPad.MemCopy(lpLVITEM, 0x0001 /*LVIF_TEXT*/, 3 /*DT_DWORD*/);
  AkelPad.MemCopy(lpLVITEM + (_X64 ? 24 : 20), lpTextLV, 2 /*DT_QWORD*/);
  AkelPad.MemCopy(lpLVITEM + (_X64 ? 32 : 24), nTextMax, 3 /*DT_DWORD*/);

  var aDlg      = [];
  var IDHEADERS = 1000;
  var IDNAMELV  = 1001;
  var IDTEXTAE  = 1002;
  var IDSORTB   = 1003;
  var IDLANG1B  = 1004;
  var IDLANG2B  = 1005;
  var IDMENUB   = 1006;
  var IDOKB     = 1007;
  var IDCLOSEB  = 1008;

  aDlg[IDHEADERS] = {Txt: sHeader,     Class: "STATIC",        Style: 0x50000001 /*WS_VISIBLE|WS_CHILD|SS_CENTER*/};
  aDlg[IDNAMELV ] = {Txt: "",          Class: "SysListView32", Style: 0x5080800D /*WS_VISIBLE|WS_CHILD|WS_BORDER|LVS_NOSORTHEADER|LVS_SHOWSELALWAYS|LVS_SINGLESEL|LVS_REPORT*/};
  aDlg[IDTEXTAE ] = {Txt: "",          Class: "AkelEditW",     Style: 0x50B00804 /*WS_VISIBLE|WS_CHILD|WS_BORDER|WS_VSCROLL|WS_HSCROLL|ES_READONLY|ES_MULTILINE*/};
  aDlg[IDSORTB  ] = {Txt: sTxtSort,    Class: "BUTTON",        Style: 0x50000003 /*WS_VISIBLE|WS_CHILD|BS_AUTOCHECKBOX*/};
  aDlg[IDLANG1B ] = {Txt: sTxtEnglish, Class: "BUTTON",        Style: 0x50000009 /*WS_VISIBLE|WS_CHILD|BS_AUTORADIOBUTTON*/};
  aDlg[IDLANG2B ] = {Txt: sTxtRussian, Class: "BUTTON",        Style: 0x50000009 /*WS_VISIBLE|WS_CHILD|BS_AUTORADIOBUTTON*/};
  aDlg[IDMENUB  ] = {Txt: sTxtMenu,    Class: "BUTTON",        Style: 0x50000000 /*WS_VISIBLE|WS_CHILD*/};
  aDlg[IDOKB    ] = {Txt: sTxtOK,      Class: "BUTTON",        Style: 0x50000001 /*WS_VISIBLE|WS_CHILD|BS_DEFPUSHBUTTON*/};
  aDlg[IDCLOSEB ] = {Txt: sTxtClose,   Class: "BUTTON",        Style: 0x50000000 /*WS_VISIBLE|WS_CHILD*/};

  AkelPad.WindowRegisterClass(sClassName);

  hDlg = oSys.Call("User32::CreateWindowExW",
    0,              //dwExStyle
    sClassName,     //lpClassName
    sTxtDlgTitle,   //lpWindowName
    0x80CF0000,     //dwStyle=WS_POPUP|WS_CAPTION|WS_SYSMENU|WS_SIZEBOX|WS_MINIMIZEBOX|WS_MAXIMIZEBOX
    oDlgPos.X,      //x
    oDlgPos.Y,      //y
    oDlgPos.W,      //nWidth
    oDlgPos.H,      //nHeight
    hWndParent,     //hWndParent
    0,              //ID
    hInstance,      //hInstance
    DialogCallback);//Script function callback. To use it class must be registered by WindowRegisterClass.

  oSys.Call("User32::ShowWindow", hDlg, oDlgPos.Max ? 3 /*SW_MAXIMIZE*/ : 1 /*SW_SHOWNORMAL*/);

  AkelPad.ScriptNoMutex();
  AkelPad.WindowGetMessage();

  AkelPad.WindowUnregisterClass(sClassName);
  AkelPad.MemFree(lpTextLV);
  AkelPad.MemFree(lpLVITEM);

  if (! oSys.Call("User32::IsWindowVisible", hMainWnd))
    oSys.Call("User32::ShowWindow", hMainWnd, 8 /*SW_SHOWNA*/);
  if (oSys.Call("User32::IsIconic", hMainWnd))
    oSys.Call("User32::ShowWindow", hMainWnd, 9 /*SW_RESTORE*/);

  oSys.Call("User32::SetForegroundWindow", hMainWnd);
}

function DialogCallback(hWnd, uMsg, wParam, lParam)
{
  if (uMsg == 1) //WM_CREATE
  {
    var i;

    for (i = IDHEADERS; i < aDlg.length; ++i)
    {
      aDlg[i].Handle = oSys.Call("User32::CreateWindowExW",
        0,            //dwExStyle
        aDlg[i].Class,//lpClassName
        aDlg[i].Txt,  //lpWindowName
        aDlg[i].Style,//dwStyle
        0, 0, 0, 0,   //x, y, nWidth, nHeight
        hWnd,         //hWndParent
        i,            //ID
        hInstance,    //hInstance
        0);           //lpParam
      SetWindowFont(aDlg[i].Handle, hGuiFont);
    }

    CheckButtons();

    hSubClass = AkelPad.WindowSubClass(aDlg[IDTEXTAE].Handle, EditCallback, 135 /*WM_GETDLGCODE*/, 256 /*WM_KEYDOWN*/);
    SetOptionsAE();

    InsertColumnLV();
    FillLV(nAPMSel, AkelPad.GetSelText(), true);

    oSys.Call("User32::SetFocus", aDlg[IDTEXTAE].Handle);
    oSys.Call("User32::SetFocus", aDlg[IDNAMELV].Handle);

    PostMessage(hWnd, 0x8000 /*WM_APP*/, 0, 0);
  }

  else if (uMsg == 0x8000 /*WM_APP*/)
  {
    if (aAESel[nAPMLang][aAPM[nAPMSel][0]])
      SetSelAE(aAESel[nAPMLang][aAPM[nAPMSel][0]][0], aAESel[nAPMLang][aAPM[nAPMSel][0]][1]);
  }

  else if (uMsg == 7) //WM_SETFOCUS
    oSys.Call("User32::SetFocus", hFocus);

  else if (uMsg == 36) //WM_GETMINMAXINFO
  {
    AkelPad.MemCopy(lParam + 24, nDlgMinW, 3 /*DT_DWORD*/); //ptMinTrackSize_x
    AkelPad.MemCopy(lParam + 28, nDlgMinH, 3 /*DT_DWORD*/); //ptMinTrackSize_y
  }

  else if (uMsg == 3) //WM_MOVE
  {
    if (! (oSys.Call("User32::IsZoomed", hWnd) || oSys.Call("User32::IsIconic", hWnd)))
      GetWindowPos(hWnd, oDlgPos);
  }

  else if (uMsg == 5) //WM_SIZE
  {
    if (wParam == 0 /*SIZE_RESTORED*/)
      GetWindowPos(hWnd, oDlgPos);

    ResizeDlg(LoWord(lParam), HiWord(lParam));
  }

  else if (uMsg == 15) //WM_PAINT
    PaintSizeGrip();

  else if (uMsg == 256) //WM_KEYDOWN
  {
    if (wParam == 9 /*VK_TAB*/)
    {
      if (Ctrl())
      {
        if (Shift())
        {
          if (nAPMSel > 0)
            --nAPMSel;
          else
            nAPMSel = aAPM.length - 1;
        }
        else
        {
          if (nAPMSel < aAPM.length - 1)
            ++nAPMSel;
          else
            nAPMSel = 0;
        }
        SetCurSelLV(nAPMSel);
        oSys.Call("User32::SetFocus", hFocus);
      }
      else
      {
        if (hFocus == aDlg[IDNAMELV].Handle)
          oSys.Call("User32::SetFocus", aDlg[IDTEXTAE].Handle);
        else
          oSys.Call("User32::SetFocus", aDlg[IDNAMELV].Handle);
      }
    }
    else if ((wParam >= 0x21 /*VK_PRIOR*/) && (wParam <= 0x28 /*VK_DOWN*/))
    {
      if (Ctrl() && (! Shift()) && Alt())
        MoveDlg(wParam);
    }
    else if (wParam == 0x43 /*C key*/)
    {
      if  (Ctrl() && (! Alt()))
      {
        if (hFocus == aDlg[IDNAMELV].Handle)
        {
          if (Shift())
            InsertNameToAP();
          else
            InsertNameToCB();
        }
        else
          InsertTextTo(! Shift());
      }
    }
    else if (wParam == 0x46 /*F key*/)
    {
      if (Ctrl() && (! Alt()))
      {
        if (hFocus == aDlg[IDNAMELV].Handle)
          FindName(Shift() ? 2 : 0);
        else
          FindText(Shift() ? 2 : 0);
      }
    }
    else if (wParam == 0x55 /*U key*/)
    {
      if (Ctrl() && (! Shift()) && (! Alt()))
      {
        bWordWrap = ! bWordWrap;
        SetWordWrapAE();
      }
    }
    else if (wParam == 0x70 /*VK_F1*/)
    {
      if ((! Ctrl()) && (! Shift()))
        MenuMain();
    }
    else if (wParam == 0x72 /*VK_F3*/)
    {
      if (! Ctrl())
      {
        if (hFocus == aDlg[IDNAMELV].Handle)
          FindNameNext(Shift() ? 3 : 1);
        else
          FindTextNext(Shift() ? 3 : 1);
      }
    }
    else if (wParam == 0x73 /*VK_F4*/)
    {
      if ((! Ctrl()) && (! Shift()))
        oSys.Call("User32::ShowWindow", hWnd, oSys.Call("User32::IsZoomed", hWnd) ? 9 /*SW_RESTORE*/ : 3 /*SW_MAXIMIZE*/);
    }
    else if (wParam == 13 /*VK_RETURN*/)
    {
      if ((! Ctrl()) && (! Shift()) && (oSys.Call("User32::GetDlgCtrlID", oSys.Call("User32::GetFocus")) < IDMENUB))
        PostMessage(hWnd, 273 /*WM_COMMAND*/, IDOKB, 0);
    }
    else if (wParam == 27 /*VK_ESCAPE*/)
      PostMessage(hWnd, 16 /*WM_CLOSE*/, 0, 0);
  }

  else if (uMsg == 260) //WM_SYSKEYDOWN
  {
    if (wParam == 0x46 /*F key*/)
    {
      if (hFocus == aDlg[IDNAMELV].Handle)
        FindName(Shift() ? 3 : 1);
      else
        FindText(Shift() ? 3 : 1);
    }
    else if (wParam == 13 /*VK_RETURN*/)
    {
      if (! Shift())
        oSys.Call("User32::ShowWindow", hWnd, oSys.Call("User32::IsZoomed", hWnd) ? 9 /*SW_RESTORE*/ : 3 /*SW_MAXIMIZE*/);
    }
  }

  else if ((uMsg == 0x004E /*WM_NOTIFY*/) && (wParam == IDNAMELV))
  {
    switch (AkelPad.MemRead(lParam + (_X64 ? 16 : 8), 3 /*DT_DWORD*/))
    {
      case -101 : //LVN_ITEMCHANGED
        if (AkelPad.MemRead(lParam + (_X64 ? 32 : 20) /*NMLISTVIEW.uNewState*/, 3 /*DT_DWORD*/) & 0x2 /*LVIS_SELECTED*/)
        {
          nAPMSel = GetCurSelLV();
          SetWindowText(aDlg[IDTEXTAE].Handle, aAPM[nAPMSel][1]);

          if (aAESel[nAPMLang][aAPM[nAPMSel][0]])
            SetSelAE(aAESel[nAPMLang][aAPM[nAPMSel][0]][0], aAESel[nAPMLang][aAPM[nAPMSel][0]][1]);
        }
        break;
      case -3 : //NM_DBLCLK
        if (AkelPad.MemRead(lParam + (_X64 ? 24 : 12) /*NMITEMACTIVATE.iItem*/, 3 /*DT_DWORD*/) == -1)
          SetCurSelLV(GetCurFocLV());
        else
          PostMessage(hWnd, 273 /*WM_COMMAND*/, IDOKB, 0);
        break;
      case -2 : //NM_CLICK
      case -5 : //NM_RCLICK
      case -6 : //NM_RDBLCLK
        if (AkelPad.MemRead(lParam + (_X64 ? 24 : 12) /*NMITEMACTIVATE.iItem*/, 3 /*DT_DWORD*/) == -1)
          SetCurSelLV(GetCurFocLV());
        break;
      case -7 : //NM_SETFOCUS
        hFocus = aDlg[IDNAMELV].Handle;
        break;
    }
  }

  else if (uMsg == 123) //WM_CONTEXTMENU
  {
    if (wParam == aDlg[IDNAMELV].Handle)
      MenuName(LoWord(lParam), HiWord(lParam));
    else if (wParam == aDlg[IDTEXTAE].Handle)
    {
      oSys.Call("User32::SetFocus", aDlg[IDTEXTAE].Handle);
      MenuText(LoWord(lParam), HiWord(lParam));
    }
  }

  else if (uMsg == 273) //WM_COMMAND
  {
    var nLowParam = LoWord(wParam);
    var nHiwParam = HiWord(wParam);
    var sFind;

    if (nLowParam == IDTEXTAE)
    {
      if (nHiwParam == 0x0100 /*EN_SETFOCUS*/)
      {
        if (SendMessage(AkelPad.GetEditWnd(), 3227 /*AEM_GETOPTIONS*/, 0, 0) & 0x00000800 /*AECO_ACTIVELINE*/)
          SendMessage(lParam, 3228 /*AEM_SETOPTIONS*/, 2 /*AECOOP_OR*/, 0x00000800 /*AECO_ACTIVELINE*/);
        hFocus = lParam;
      }
      if (nHiwParam == 0x0200 /*EN_KILLFOCUS*/)
      {
        SendMessage(lParam, 3228 /*AEM_SETOPTIONS*/, 4 /*AECOOP_XOR*/, 0x00000800 /*AECO_ACTIVELINE*/);
        aAESel[nAPMLang][aAPM[nAPMSel][0]] = [GetSelStartAE(), GetSelEndAE()];
      }
    }
    else if ((nLowParam >= IDSORTB) && (nLowParam <= IDLANG2B))
    {
      if (aAPM[nAPMSel][0].charAt(0) != "*")
        sFind = aAPM[nAPMSel][0];

      CheckButtons(nLowParam);
      GetArrayAPM(hWnd);

      if (aAPM.length)
      {
        CheckButtons();
        SetWindowText(aDlg[IDHEADERS].Handle, sHeader);
        FillLV(nAPMSel, sFind, false);
        oSys.Call("User32::SetFocus", hFocus);
      }
      else
        PostMessage(hWnd, 16 /*WM_CLOSE*/, 0, 0);
    }
    else if (nLowParam == IDMENUB)
    {
      oSys.Call("User32::DefDlgProcW", hWnd, 1025 /*DM_SETDEFID*/, IDMENUB, 0);
      oSys.Call("User32::DefDlgProcW", hWnd, 1025 /*DM_SETDEFID*/, IDOKB, 0);
      oSys.Call("User32::SetFocus", hFocus);
      MenuMain();
    }
    else if (nLowParam == IDOKB)
      PostMessage(hWnd, 16 /*WM_CLOSE*/, 1, 0);
    else if (nLowParam == IDCLOSEB)
      PostMessage(hWnd, 16 /*WM_CLOSE*/, 0, 0);
  }

  else if (uMsg == 16) //WM_CLOSE
  {
    if (wParam)
      InsertNameToAP();

    aAESel[nAPMLang][aAPM[nAPMSel][0]] = [GetSelStartAE(), GetSelEndAE()];
    WriteIni();
    AkelPad.WindowUnsubClass(aDlg[IDTEXTAE].Handle);
    oSys.Call("User32::DestroyWindow", hWnd);
  }

  else if (uMsg == 2) //WM_DESTROY
    oSys.Call("User32::PostQuitMessage", 0);

  return 0;
}

function EditCallback(hWnd, uMsg, wParam, lParam)
{
  if (uMsg == 135) //WM_GETDLGCODE
  {
    AkelPad.WindowNoNextProc(hSubClass);
    return 0x1; //DLGC_WANTARROWS
  }

  if (uMsg == 256) //WM_KEYDOWN
  {
    if ((wParam >= 0x21 /*VK_PRIOR*/) && (wParam <= 0x28 /*VK_DOWN*/) && Ctrl() && (!Shift()) && Alt())
      AkelPad.WindowNoNextProc(hSubClass);
  }

  return 0;
}

function SendMessage(hWnd, uMsg, wParam, lParam)
{
  return oSys.Call("User32::SendMessageW", hWnd, uMsg, wParam, lParam);
}

function PostMessage(hWnd, uMsg, wParam, lParam)
{
  return oSys.Call("User32::PostMessageW", hWnd, uMsg, wParam, lParam);
}

function LoWord(nDwNum)
{
  return nDwNum & 0xFFFF;
}

function HiWord(nDwNum)
{
  return (nDwNum >> 16) & 0xFFFF;
}

function MkLong(nLoWord, nHiWord)
{
  return (nLoWord & 0xFFFF) | (nHiWord << 16);
}

function Ctrl()
{
  return Boolean(oSys.Call("User32::GetKeyState", 0x11 /*VK_CONTROL*/) & 0x8000);
}

function Shift()
{
  return Boolean(oSys.Call("User32::GetKeyState", 0x10 /*VK_SHIFT*/) & 0x8000);
}

function Alt()
{
  return Boolean(oSys.Call("user32::GetKeyState", 0x12 /*VK_MENU*/) & 0x8000);
}

function GetWindowPos(hWnd, oRect)
{
  var lpRect = AkelPad.MemAlloc(16); //sizeof(RECT)

  if (hWnd)
    oSys.Call("User32::GetWindowRect", hWnd, lpRect);
  else
    oSys.Call("User32::SystemParametersInfoW", 0x30 /*SPI_GETWORKAREA*/, 0, lpRect, 0);

  oRect.X = AkelPad.MemRead(lpRect,      3 /*DT_DWORD*/);
  oRect.Y = AkelPad.MemRead(lpRect +  4, 3 /*DT_DWORD*/);
  oRect.W = AkelPad.MemRead(lpRect +  8, 3 /*DT_DWORD*/) - oRect.X;
  oRect.H = AkelPad.MemRead(lpRect + 12, 3 /*DT_DWORD*/) - oRect.Y;

  AkelPad.MemFree(lpRect);
}

function SetWindowText(hWnd, sText)
{
  oSys.Call("User32::SetWindowTextW", hWnd, sText);
}

function SetWindowFont(hWnd, hFont)
{
  SendMessage(hWnd, 48 /*WM_SETFONT*/, hFont, true);
}

function GetSelStartAE()
{
  AkelPad.SetEditWnd(aDlg[IDTEXTAE].Handle);
  var nSelStart = AkelPad.GetSelStart();
  AkelPad.SetEditWnd(0);
  return nSelStart;
}

function GetSelEndAE()
{
  AkelPad.SetEditWnd(aDlg[IDTEXTAE].Handle);
  var nSelEnd = AkelPad.GetSelEnd();
  AkelPad.SetEditWnd(0);
  return nSelEnd;
}

function SetSelAE(nSelStart, nSelEnd)
{
  AkelPad.SetEditWnd(aDlg[IDTEXTAE].Handle);
  AkelPad.SetSel(nSelStart, nSelEnd);
  AkelPad.SetEditWnd(0);
}

function GetSelTextAE()
{
  AkelPad.SetEditWnd(aDlg[IDTEXTAE].Handle);
  var sText = AkelPad.GetSelText(0);
  AkelPad.SetEditWnd(0);
  return sText;
}

function SetWordWrapAE()
{
  SendMessage(aDlg[IDTEXTAE].Handle, 0x0CAA /*AEM_SETWORDWRAP*/, bWordWrap ? 1 /*AEWW_WORD*/ : 0 /*AEWW_NONE*/, 0);
}

function SetOptionsAE()
{
  var hEditWnd = AkelPad.GetEditWnd();

  SetWindowFont(aDlg[IDTEXTAE].Handle, SendMessage(hMainWnd, 1233 /*AKD_GETFONTW*/, 0, 0));
  SetWordWrapAE();

  var lpRect = AkelPad.MemAlloc(16); //sizeof(RECT)
  AkelPad.MemCopy(lpRect,      4, 3 /*DT_DWORD*/);
  AkelPad.MemCopy(lpRect +  4, 4, 3 /*DT_DWORD*/);
  AkelPad.MemCopy(lpRect +  8, 4, 3 /*DT_DWORD*/);
  AkelPad.MemCopy(lpRect + 12, 4, 3 /*DT_DWORD*/);
  SendMessage(aDlg[IDTEXTAE].Handle, 3178 /*AEM_SETRECT*/, 0x03 /*AERC_MARGINS|AERC_UPDATE*/, lpRect);
  AkelPad.MemFree(lpRect);

  if (hEditWnd)
  {
    var lpAECOLORS = AkelPad.MemAlloc(17 * 4);
    AkelPad.MemCopy(lpAECOLORS, 0x0001FFFE /*AECLR_ALL*/, 3 /*DT_DWORD*/);
    SendMessage(hEditWnd, 3231 /*AEM_GETCOLORS*/, 0, lpAECOLORS);
    SendMessage(aDlg[IDTEXTAE].Handle, 3232 /*AEM_SETCOLORS*/, 0, lpAECOLORS);
    AkelPad.MemFree(lpAECOLORS);

    if (SendMessage(hEditWnd, 3227 /*AEM_GETOPTIONS*/, 0, 0) & 0x00001000 /*AECO_ACTIVELINEBORDER*/)
      SendMessage(aDlg[IDTEXTAE].Handle, 3228 /*AEM_SETOPTIONS*/, 2 /*AECOOP_OR*/, 0x00001000 /*AECO_ACTIVELINEBORDER*/);

    var lpPOINT = AkelPad.MemAlloc(8);
    SendMessage(hEditWnd, 3237 /*AEM_GETCARETWIDTH*/, 0, lpPOINT);
    SendMessage(aDlg[IDTEXTAE].Handle, 3238 /*AEM_SETCARETWIDTH*/, 0, lpPOINT);
    AkelPad.MemFree(lpPOINT);

    SendMessage(aDlg[IDTEXTAE].Handle, 3260 /*AEM_SETLINEGAP*/, SendMessage(hEditWnd, 3259 /*AEM_GETLINEGAP*/, 0, 0), 0);
  }
}

function GetCurFocLV()
{
  return SendMessage(aDlg[IDNAMELV].Handle, 0x100C /*LVM_GETNEXTITEM*/, -1, 0x0001 /*LVNI_FOCUSED*/);
}

function GetCurSelLV()
{
  return SendMessage(aDlg[IDNAMELV].Handle, 0x100C /*LVM_GETNEXTITEM*/, -1, 0x0002 /*LVNI_SELECTED*/);
}

function SetCurSelLV(nItem)
{
  AkelPad.MemCopy(lpLVITEM + 12, 0x0003 /*LVIS_SELECTED|LVIS_FOCUSED*/, 3 /*DT_DWORD*/);
  AkelPad.MemCopy(lpLVITEM + 16, 0x0003 /*LVIS_SELECTED|LVIS_FOCUSED*/, 3 /*DT_DWORD*/);
  SendMessage(aDlg[IDNAMELV].Handle, 0x102B /*LVM_SETITEMSTATE*/, nItem, lpLVITEM);
  SendMessage(aDlg[IDNAMELV].Handle, 0x1013 /*LVM_ENSUREVISIBLE*/, nItem, false);
}

function InsertColumnLV()
{
  var lpLVCOLUMN = AkelPad.MemAlloc(_X64 ? 56 : 44); //sizeof(LVCOLUMN)

  AkelPad.MemCopy(lpLVCOLUMN, 4 /*mask=LVCF_TEXT*/, 3 /*DT_DWORD*/);
  AkelPad.MemCopy(lpLVCOLUMN + (_X64 ? 16 : 12), lpTextLV, 2 /*DT_QWORD*/);
  AkelPad.MemCopy(lpTextLV, sTxtName, 1 /*DT_UNICODE*/);

  SendMessage(aDlg[IDNAMELV].Handle, 0x1036 /*LVM_SETEXTENDEDLISTVIEWSTYLE*/, 0x0020 /*LVS_EX_FULLROWSELECT*/, 0x0020);
  SendMessage(aDlg[IDNAMELV].Handle, 0x1061 /*LVM_INSERTCOLUMNW*/, 0, lpLVCOLUMN);
  AkelPad.MemFree(lpLVCOLUMN);
}

function FillLV(nSel, sFind, bFindOnStart)
{
  var i;

  SendMessage(aDlg[IDNAMELV].Handle, 0x000B /*WM_SETREDRAW*/, false, 0);
  SendMessage(aDlg[IDNAMELV].Handle, 0x1009 /*LVM_DELETEALLITEMS*/, 0, 0);

  for (i = 0; i < aAPM.length; ++i)
  {
    AkelPad.MemCopy(lpLVITEM + 4, i, 3 /*DT_DWORD*/);
    AkelPad.MemCopy(lpTextLV, aAPM[i][0].replace(/^AkelPad\./, ""), 1 /*DT_UNICODE*/);
    SendMessage(aDlg[IDNAMELV].Handle, 0x104D /*LVM_INSERTITEMW*/, 0, lpLVITEM);

    if (sFind)
    {
      if ((bFindOnStart && (aAPM[i][0].indexOf(sFind) > -1)) || ((! bFindOnStart) && (aAPM[i][0] == sFind)))
      {
        if (bFindOnStart)
          sFindName = sFind;

        nSel  = i;
        sFind = "";
      }
    }
  }

  if (nSel >= aAPM.length)
    nSel = aAPM.length - 1;
  if (nSel < 0)
    nSel = 0;

  SetCurSelLV(nSel);
  SendMessage(aDlg[IDNAMELV].Handle, 0x000B /*WM_SETREDRAW*/, true, 0);
}

function GetArrayAPM(hWnd)
{
  var sDocsDir  = AkelPad.GetAkelDir(2 /*ADTYPE_DOCS*/) + "\\";
//  var aDocFile  = ["Scripts-Eng.txt", "Scripts-Rus.txt"];
//  var nCodePage = 1251 /*ANSI Cyrillic*/;
  var aDocFile  = ["Scripts-Eng.txt", "Scripts-Chs.txt"];
  var nCodePage = 936 /*ANSI Chinese Simplified*/;
  var sText;
  var lpTextA;
  var lpTextW;
  var nTextWLen;
  var aExec;
  var oRE;
  var i;

  aIsLang     = [false, false];
  sHeader     = "";
  aAPM.length = 0;

  while (! (aIsLang[0] || aIsLang[1]))
  {
    if (sAltDir)
    {
      for (i = 0; i < 2; ++i)
        aIsLang[i] = oFSO.FileExists(sAltDir + aDocFile[i]);
    }

    if (aIsLang[0] || aIsLang[1])
      sDocsDir = sAltDir;
    else
    {
      for (i = 0; i < 2; ++i)
        aIsLang[i] = oFSO.FileExists(sDocsDir + aDocFile[i]);

      if (! (aIsLang[0] || aIsLang[1]))
      {
        AkelPad.MessageBox(hWnd, sTxtNoFiles + "\n" + ((sAltDir && (sAltDir.toUpperCase() != sDocsDir.toUpperCase())) ? (sAltDir + aDocFile[0] + "\n" + sAltDir + aDocFile[1] + "\n") : "") + sDocsDir + aDocFile[0] + "\n" + sDocsDir + aDocFile[1], sTxtDlgTitle, 0x30 /*MB_ICONWARNING*/);

        if (! sAltDir)
          sAltDir = AkelPad.GetAkelDir(1 /*ADTYPE_AKELFILES*/) + "\\";

        sAltDir = BrowseForFolder(hWnd, sTxtChooseDir, sAltDir);

        if (! sAltDir)
          return;
        else if (sAltDir.slice(-1) != "\\")
          sAltDir += "\\";
      }
    }
  }

  if (! aIsLang[nAPMLang])
    nAPMLang = Number(! nAPMLang);

  oFile = oFSO.OpenTextFile(sDocsDir + aDocFile[nAPMLang], 1, false, 0 /*ASCII*/);
  sText = oFile.ReadAll().replace(/\r\n/g, "\n");
  oFile.Close();

  if (nAPMLang == 1)
  {
    //convert ANSII to UTF-16LE
    lpTextA = AkelPad.MemAlloc(sText.length + 1);
    AkelPad.MemCopy(lpTextA, sText, 0 /*DT_ANSI*/);
    if (nTextWLen = oSys.Call("Kernel32::MultiByteToWideChar", nCodePage, 0, lpTextA, -1, 0, 0))
    {
      lpTextW = AkelPad.MemAlloc(nTextWLen * 2);
      oSys.Call("Kernel32::MultiByteToWideChar", nCodePage, 0, lpTextA, -1, lpTextW, nTextWLen);
      sText = AkelPad.MemRead(lpTextW, 1 /*DT_UNICODE*/);
      AkelPad.MemFree(lpTextW);
    }
    AkelPad.MemFree(lpTextA);
  }

  //methods and constants
  oRE = /^(([\w.()]+)\n_+\n+[\s\S]+?\n)\n*(?=[\w.()]+\n_+)|^(([\w.()]+)\n_+\n+[\s\S]+?\n)\n*(?=\*{3} \S.+\S \*{3}\n)/gm
  while (aExec = oRE.exec(sText))
  {
    if (aExec[1])
      aAPM.push([aExec[2], aExec[1]]);
    else if (aExec[3])
      aAPM.push([aExec[4], aExec[3]]);
  }

  if (bAPMSort)
    aAPM.sort(
      function(a1, a2)
      {
        if (a1[0] < a2[0])
          return -1;
        else if (a1[0] > a2[0])
          return 1;
        else
          return 0;
      });

  //Scripts-*.txt
  //first char in Name must be "*"
  if (aExec = /(^\*{4,}\n\*{3} +(\S.+\S) +\*{3}\n\*{4,}\n+[\s\S]+?\n)/m.exec(sText))
  {
    sHeader = aExec[2];
    aAPM.push(["*** " + aDocFile[nAPMLang] + " ***", aExec[1]]);
  }

  oRE = /^((\*{3} \S.+\S \*{3})\n+[\s\S]+?\n)\n*(?=\*{3} \S.+\S \*{3}\n)|(^(\*{3} \S.+\S \*{3})\n+[\s\S]+)/gm;
  while (aExec = oRE.exec(sText))
  {
    if (aExec[1])
      aAPM.push([aExec[2].replace(/ \(.+\)/, ""), aExec[1]]);
    else if (aExec[3])
      aAPM.push([aExec[4].replace(/ \(.+\)/, ""), aExec[3]]);
  }
}

function CheckButtons(nButton)
{
  if (nButton == IDSORTB)
    bAPMSort = ! bAPMSort;
  else if ((nButton == IDLANG1B) || (nButton == IDLANG2B))
    nAPMLang = nButton - IDLANG1B;

  SendMessage(aDlg[IDSORTB ].Handle, 241 /*BM_SETCHECK*/, bAPMSort, 0);
  SendMessage(aDlg[IDLANG1B].Handle, 241 /*BM_SETCHECK*/, (nAPMLang == 0), 0);
  SendMessage(aDlg[IDLANG2B].Handle, 241 /*BM_SETCHECK*/, (nAPMLang == 1), 0);

  oSys.Call("User32::EnableWindow", aDlg[IDLANG1B].Handle, aIsLang[0]);
  oSys.Call("User32::EnableWindow", aDlg[IDLANG2B].Handle, aIsLang[1]);
}

function PaintSizeGrip()
{
  var lpPaint = AkelPad.MemAlloc(_X64 ? 72 : 64); //sizeof(PAINTSTRUCT)
  var lpRect  = AkelPad.MemAlloc(16); //sizeof(RECT)
  var hDC;

  if (hDC = oSys.Call("User32::BeginPaint", hDlg, lpPaint))
  {
    oSys.Call("User32::GetClientRect", hDlg, lpRect);

    AkelPad.MemCopy(lpRect,     AkelPad.MemRead(lpRect +  8, 3 /*DT_DWORD*/) - oSys.Call("User32::GetSystemMetrics",  2 /*SM_CXVSCROLL*/), 3 /*DT_DWORD*/);
    AkelPad.MemCopy(lpRect + 4, AkelPad.MemRead(lpRect + 12, 3 /*DT_DWORD*/) - oSys.Call("User32::GetSystemMetrics", 20 /*SM_CYVSCROLL*/), 3 /*DT_DWORD*/);

    oSys.Call("User32::DrawFrameControl", hDC, lpRect, 3 /*DFC_SCROLL*/, 0x8 /*DFCS_SCROLLSIZEGRIP*/);
    oSys.Call("User32::EndPaint", hDlg, lpPaint);
  }

  AkelPad.MemFree(lpPaint);
  AkelPad.MemFree(lpRect);
}

function ResizeDlg(nW, nH)
{
  var nFlags = 0x14; //SWP_NOACTIVATE|SWP_NOZORDER
  var nLVW   = 205;
  var nAEW   = nW - nLVW - 30;
  var i;

  oSys.Call("User32::SetWindowPos",
    aDlg[IDHEADERS].Handle, 0,
    nW - nAEW - 10,
    13,
    nAEW,
    13,
    nFlags);
  oSys.Call("User32::SetWindowPos",
    aDlg[IDNAMELV].Handle, 0,
    10,
    10,
    nLVW,
    nH - 53,
    nFlags);
  oSys.Call("User32::SetWindowPos",
    aDlg[IDTEXTAE].Handle, 0,
    nW - nAEW - 10,
    30,
    nAEW,
    nH - 73,
    nFlags);
  oSys.Call("User32::SetWindowPos",
    aDlg[IDSORTB].Handle, 0,
    10,
    nH - 30,
    100,
    16,
    nFlags);
  for (i = IDLANG1B; i <= IDLANG2B; ++i)
  {
    oSys.Call("User32::SetWindowPos",
      aDlg[i].Handle, 0,
      20 + nLVW + 75 * (i - IDLANG1B),
      nH - 30,
      70,
      16,
      nFlags);
  }
  for (i = IDMENUB; i <= IDCLOSEB; ++i)
  {
    oSys.Call("User32::SetWindowPos",
      aDlg[i].Handle, 0,
      nW - (70 + 10) * (IDCLOSEB - i + 1),
      nH - 33,
      70,
      23,
      nFlags);
  }

  SendMessage(aDlg[IDNAMELV].Handle, 0x101E /*LVM_SETCOLUMNWIDTH*/, 0, -2 /*LVSCW_AUTOSIZE_USEHEADER*/);
  SendMessage(aDlg[IDNAMELV].Handle, 0x1013 /*LVM_ENSUREVISIBLE*/, GetCurSelLV(), false);
}

function MoveDlg(nKey)
{
  var oRectWA = {};
  var oRect   = {};

  GetWindowPos(0, oRectWA);
  GetWindowPos(hDlg, oRect);

  if (nKey == 0x21 /*VK_PRIOR*/)
    oRect.Y = oRectWA.Y;
  else if (nKey == 0x22 /*VK_NEXT*/)
    oRect.Y = oRectWA.Y + oRectWA.H - oRect.H;
  else if (nKey == 0x23 /*VK_END*/)
    oRect.X = oRectWA.X + oRectWA.W - oRect.W;
  else if (nKey == 0x24 /*VK_HOME*/)
    oRect.X = oRectWA.X;
  else if (nKey == 0x25 /*VK_LEFT*/)
  {
    if (oRect.X > oRectWA.X)
      oRect.X = (oRect.X - oRectWA.X > 20) ? oRect.X - 20 : oRectWA.X;
  }
  else if (nKey == 0x26 /*VK_UP*/)
  {
    if (oRect.Y > oRectWA.Y)
      oRect.Y = (oRect.Y - oRectWA.Y > 20) ? oRect.Y - 20 : oRectWA.Y;
  }
  else if (nKey == 0x27 /*VK_RIGHT*/)
  {
    if (oRect.X + oRect.W < oRectWA.X + oRectWA.W)
      oRect.X = (oRectWA.X + oRectWA.W - oRect.X - oRect.W > 20) ? oRect.X + 20 : oRectWA.X + oRectWA.W - oRect.W;
  }
  else if (nKey == 0x28 /*VK_DOWN*/)
  {
    if (oRect.Y + oRect.H < oRectWA.Y + oRectWA.H)
      oRect.Y = (oRectWA.Y + oRectWA.H - oRect.Y - oRect.H > 20) ? oRect.Y + 20 : oRectWA.Y + oRectWA.H - oRect.H;
  }

  oSys.Call("user32::SetWindowPos", hDlg, 0, oRect.X, oRect.Y, 0, 0, 0x15 /*SWP_NOZORDER|SWP_NOACTIVATE|SWP_NOSIZE*/);
}

function FindName(nDirection)
{
  InputBox(aDlg[IDNAMELV].Handle, sTxtFindName + " - " + [sTxtDownFromBeg, sTxtDownFromCur, sTxtUpFromEnd, sTxtUpFromCur][nDirection], sTxtName + ":", sFindName, 0, CheckFindName, nDirection);
}

function CheckFindName(hWnd, aName, nDirection)
{
  if (aName[0])
  {
    sFindName = aName[0];
    if (! FindNameNext(nDirection))
    {
      AkelPad.MessageBox(hWnd, sTxtNotFound, sTxtDlgTitle, 0x30 /*MB_ICONWARNING*/);
      return 0;
    }
  }

  return -1;
}

function FindNameNext(nDirection)
{
  var bFound = false;
  var nStart;
  var i;

  if (nDirection < 2)
  {
    if (nDirection == 0)
      nStart = 0;
    else
      nStart = GetCurSelLV() + 1;

    for (i = nStart; i < aAPM.length; ++i)
    {
      if (aAPM[i][0].indexOf(sFindName) > -1)
      {
        SetCurSelLV(i);
        bFound = true;
        break;
      }
    }
  }
  else
  {
    if (nDirection == 2)
      nStart = aAPM.length - 1;
    else
      nStart = GetCurSelLV() - 1;

    for (i = nStart; i >= 0; --i)
    {
      if (aAPM[i][0].indexOf(sFindName) > -1)
      {
        SetCurSelLV(i);
        bFound = true;
        break;
      }
    }
  }

  return bFound;
}

function FindText(nDirection)
{
  var sText = GetSelTextAE();

  if (! sText)
    sText = sFindText;

  InputBox(aDlg[IDTEXTAE].Handle, sTxtFindText + " - " + [sTxtDownFromBeg, sTxtDownFromCur, sTxtUpFromEnd, sTxtUpFromCur][nDirection], sTxtText + ":", sText, 0, CheckFindText, nDirection);
}

function CheckFindText(hWnd, aText, nDirection)
{
  if (aText[0])
  {
    sFindText = aText[0];
    if (! FindTextNext(nDirection))
    {
      AkelPad.MessageBox(hWnd, sTxtNotFound, sTxtDlgTitle, 0x30 /*MB_ICONWARNING*/);
      return 0;
    }
  }

  return -1;
}

function FindTextNext(nDirection)
{
  var bFound = false;
  var nNameStart;
  var nTextStart;
  var nSel;
  var i;

  if (nDirection < 2)
  {
    if (nDirection == 0)
    {
      nNameStart = 0;
      nTextStart = 0;
    }
    else
    {
      nNameStart = GetCurSelLV();
      nTextStart = GetSelEndAE();
    }

    for (i = nNameStart; i < aAPM.length; ++i)
    {
      nSel = aAPM[i][1].indexOf(sFindText, (i == nNameStart) ? nTextStart : 0);

      if (nSel > -1)
      {
        SetCurSelLV(i);
        SetSelAE(nSel, nSel + sFindText.length);
        bFound = true;
        break;
      }
    }
  }
  else
  {
    if (nDirection == 2)
    {
      nNameStart = aAPM.length - 1;
      nTextStart = aAPM[nNameStart][1].length;
    }
    else
    {
      nNameStart = GetCurSelLV();
      nTextStart = GetSelStartAE() - sFindText.length;

      if ((nTextStart < 0) && (--nNameStart >= 0))
        nTextStart = aAPM[nNameStart][1].length;
    }

    for (i = nNameStart; i >= 0; --i)
    {
      nSel = aAPM[i][1].lastIndexOf(sFindText, (i == nNameStart) ? nTextStart : aAPM[i][1].length);

      if (nSel > -1)
      {
        SetCurSelLV(i);
        SetSelAE(nSel, nSel + sFindText.length);
        bFound = true;
        break;
      }
    }
  }

  return bFound;
}

function InsertNameToCB()
{
  if ((nAPMSel >= 0) && (aAPM[nAPMSel][0].charAt(0) != "*"))
    AkelPad.SetClipboardText(aAPM[nAPMSel][0] + ((aAPM[nAPMSel][0].substr(0, 8) == "AkelPad.") ? "()" : ""));
}

function InsertNameToAP()
{
  if ((nAPMSel >= 0) && (aAPM[nAPMSel][0].charAt(0) != "*") && AkelPad.GetEditWnd() && (! AkelPad.GetEditReadOnly(0)))
  {
    if (aAPM[nAPMSel][0].substr(0, 8) == "AkelPad.")
    {
      var sSelText = AkelPad.GetSelText(0);
      AkelPad.ReplaceSel(aAPM[nAPMSel][0] + "(" + sSelText + ")");
      AkelPad.SetSel(AkelPad.GetSelEnd() - sSelText.length - 1, AkelPad.GetSelEnd() - 1);
    }
    else
      AkelPad.ReplaceSel(aAPM[nAPMSel][0], true);
  }
}

function InsertTextTo(bClipboard)
{
  var sText = GetSelTextAE();

  if (sText)
  {
    if (bClipboard)
      AkelPad.SetClipboardText(sText);
    else
      AkelPad.ReplaceSel(sText, true);
  }
}

function MenuMain()
{
  var MF_STRING    = 0x0000;
  var MF_CHECKED   = 0x0008;
  var MF_POPUP     = 0x0010;
  var MF_SEPARATOR = 0x0800;
  var hMenu1 = oSys.Call("User32::CreatePopupMenu");
  var hMenu2 = oSys.Call("User32::CreatePopupMenu");
  var hMenu3 = oSys.Call("User32::CreatePopupMenu");
  var hMenu  = oSys.Call("User32::CreatePopupMenu");
  var aMenu  = [hMenu1, hMenu2];
  var oRect  = {};
  var nCmd;
  var nCmd1;
  var i;

  for (i = 1; i <= 2; ++i)
  {
    oSys.Call("User32::AppendMenuW", aMenu[i - 1], MF_STRING, 0x0000 | i, sTxtDownFromBeg + "\tCtrl+F");
    oSys.Call("User32::AppendMenuW", aMenu[i - 1], MF_STRING, 0x0200 | i, sTxtUpFromEnd   + "\tCtrl+Shift+F");
    oSys.Call("user32::AppendMenuW", aMenu[i - 1], MF_SEPARATOR, 0);
    oSys.Call("User32::AppendMenuW", aMenu[i - 1], MF_STRING, 0x0100 | i, sTxtDownFromCur + "\tAlt+F");
    oSys.Call("User32::AppendMenuW", aMenu[i - 1], MF_STRING, 0x0300 | i, sTxtUpFromCur   + "\tShift+Alt+F");
    oSys.Call("user32::AppendMenuW", aMenu[i - 1], MF_SEPARATOR, 0);
    oSys.Call("User32::AppendMenuW", aMenu[i - 1], MF_STRING, 0x0400 | i, sTxtNext     + "\tF3");
    oSys.Call("User32::AppendMenuW", aMenu[i - 1], MF_STRING, 0x0500 | i, sTxtPrevious + "\tShift+F3");
  }

  oSys.Call("User32::AppendMenuW", hMenu3, MF_STRING, 0x2503 /*VK_LEFT*/,  sTxtLeft  + "\tCtrl+Alt+Left");
  oSys.Call("User32::AppendMenuW", hMenu3, MF_STRING, 0x2703 /*VK_RIGHT*/, sTxtRight + "\tCtrl+Alt+Right");
  oSys.Call("User32::AppendMenuW", hMenu3, MF_STRING, 0x2603 /*VK_UP*/,    sTxtUp    + "\tCtrl+Alt+Up");
  oSys.Call("User32::AppendMenuW", hMenu3, MF_STRING, 0x2803 /*VK_DOWN*/,  sTxtDown  + "\tCtrl+Alt+Down");
  oSys.Call("user32::AppendMenuW", hMenu3, MF_SEPARATOR, 0);
  oSys.Call("User32::AppendMenuW", hMenu3, MF_STRING, 0x2403 /*VK_HOME*/,  sTxtToLeftEdge   + "\tCtrl+Alt+Home");
  oSys.Call("User32::AppendMenuW", hMenu3, MF_STRING, 0x2303 /*VK_END*/,   sTxtToRightEdge  + "\tCtrl+Alt+End");
  oSys.Call("User32::AppendMenuW", hMenu3, MF_STRING, 0x2103 /*VK_PRIOR*/, sTxtToTopEdge    + "\tCtrl+Alt+PgUp");
  oSys.Call("User32::AppendMenuW", hMenu3, MF_STRING, 0x2203 /*VK_NEXT*/,  sTxtToBottomEdge + "\tCtrl+Alt+PgDn");

  oSys.Call("User32::AppendMenuW", hMenu, MF_POPUP,  hMenu1, sTxtFindName);
  oSys.Call("User32::AppendMenuW", hMenu, MF_POPUP,  hMenu2, sTxtFindText);
  oSys.Call("User32::AppendMenuW", hMenu, MF_POPUP,  hMenu3, sTxtMoveWindow);
  oSys.Call("user32::AppendMenuW", hMenu, MF_SEPARATOR, 0);
  oSys.Call("User32::AppendMenuW", hMenu, (bWordWrap ? MF_CHECKED : MF_STRING), 0x0004, sTxtWrapLines + "\tCtrl+U");
  oSys.Call("User32::AppendMenuW", hMenu, (bSeparateWnd ? MF_CHECKED : MF_STRING), 0x0005, sTxtSeparateWnd);

  GetWindowPos(aDlg[IDMENUB].Handle, oRect);

  nCmd = oSys.Call("User32::TrackPopupMenu", hMenu, 0x01A8 /*TPM_NONOTIFY|TPM_RETURNCMD|TPM_BOTTOMALIGN|TPM_RIGHTALIGN*/, oRect.X + oRect.W, oRect.Y, 0, hDlg, 0);

  oSys.Call("User32::DestroyMenu", hMenu1);
  oSys.Call("User32::DestroyMenu", hMenu2);
  oSys.Call("User32::DestroyMenu", hMenu3);
  oSys.Call("User32::DestroyMenu", hMenu);

  nCmd1 = (nCmd >> 8) & 0xFF;
  nCmd  = nCmd & 0xFF;

  if (nCmd == 1)
  {
    oSys.Call("User32::SetFocus", aDlg[IDNAMELV].Handle);
    if (nCmd1 < 4)
      FindName(nCmd1);
    else if (nCmd1 == 4)
      FindNameNext(1);
    else if (nCmd1 == 5)
      FindNameNext(3);
  }
  else if (nCmd == 2)
  {
    oSys.Call("User32::SetFocus", aDlg[IDTEXTAE].Handle);
    if (nCmd1 < 4)
      FindText(nCmd1);
    else if (nCmd1 == 4)
      FindTextNext(1);
    else if (nCmd1 == 5)
      FindTextNext(3);
  }
  else if (nCmd == 3)
    MoveDlg(nCmd1);
  else if (nCmd == 4)
  {
    bWordWrap = ! bWordWrap;
    SetWordWrapAE();
  }
  else if (nCmd == 5)
    bSeparateWnd = ! bSeparateWnd;
}

function MenuName(nX, nY)
{
  var lpRect;
  var nX1, nY1, nY2;
  var hMenu;
  var nCmd;

  if ((nAPMSel < 0) || (aAPM[nAPMSel][0].charAt(0) == "*"))
    return;

  //menu from keyboard
  if (nX == 0xFFFF)
    SendMessage(aDlg[IDNAMELV].Handle, 0x1013 /*LVM_ENSUREVISIBLE*/, nAPMSel, false);

  lpRect = AkelPad.MemAlloc(16 /*sizeof(RECT)*/);
  SendMessage(aDlg[IDNAMELV].Handle, 0x100E /*LVM_GETITEMRECT*/, nAPMSel, lpRect);
  oSys.Call("User32::ClientToScreen", aDlg[IDNAMELV].Handle, lpRect);
  oSys.Call("User32::ClientToScreen", aDlg[IDNAMELV].Handle, lpRect + 8);
  nX1 = AkelPad.MemRead(lpRect,      3 /*DT_DWORD*/);
  nY1 = AkelPad.MemRead(lpRect +  4, 3 /*DT_DWORD*/);
  nY2 = AkelPad.MemRead(lpRect + 12, 3 /*DT_DWORD*/);
  AkelPad.MemFree(lpRect);

  if (nX == 0xFFFF)
  {
    nX = nX1;
    nY = nY2;
  }
  else if ((nY < nY1) || (nY > nY2))
    return;

  hMenu = oSys.Call("User32::CreatePopupMenu");
  oSys.Call("User32::AppendMenuW", hMenu, 0 /*MF_STRING*/, 1, sTxtCopyToCB + "\tCtrl+C");
  oSys.Call("User32::AppendMenuW", hMenu, AkelPad.GetEditWnd() && (! AkelPad.GetEditReadOnly(0)) ? 0 /*MF_STRING*/ : 0x01 /*MF_GRAYED*/, 2, sTxtInsertToAP + "\tCtrl+Shift+C");

  nCmd = oSys.Call("User32::TrackPopupMenu", hMenu, 0x0180 /*TPM_NONOTIFY|TPM_RETURNCMD*/, nX, nY, 0, hDlg, 0);

  oSys.Call("User32::DestroyMenu", hMenu);

  if (nCmd == 1)
    InsertNameToCB();
  else if (nCmd == 2)
    InsertNameToAP();
}

function MenuText(nX, nY)
{
  var bSel  = SendMessage(aDlg[IDTEXTAE].Handle, 3125 /*AEM_GETSEL*/, 0, 0);
  var hMenu = oSys.Call("User32::CreatePopupMenu");
  var lpPoint;
  var nCmd;

  //menu from keyboard
  if (nX == 0xFFFF)
  {
    lpPoint = AkelPad.MemAlloc(8 /*sizeof(POINT)*/);
    oSys.Call("User32::GetCaretPos", lpPoint);
    oSys.Call("User32::ClientToScreen", aDlg[IDTEXTAE].Handle, lpPoint);
    nX = AkelPad.MemRead(lpPoint,     3 /*DT_DWORD*/);
    nY = AkelPad.MemRead(lpPoint + 4, 3 /*DT_DWORD*/) + SendMessage(aDlg[IDTEXTAE].Handle, 3188 /*AEM_GETCHARSIZE*/, 0 /*AECS_HEIGHT*/, 0);
    AkelPad.MemFree(lpPoint);
  }

  oSys.Call("User32::AppendMenuW", hMenu, bSel ? 0 /*MF_STRING*/ : 0x01 /*MF_GRAYED*/, 1, sTxtCopyToCB + "\tCtrl+C");
  oSys.Call("User32::AppendMenuW", hMenu, AkelPad.GetEditWnd() && (! AkelPad.GetEditReadOnly(0)) && bSel ? 0 /*MF_STRING*/ : 0x01 /*MF_GRAYED*/, 2, sTxtInsertToAP + "\tCtrl+Shift+C");
  oSys.Call("user32::AppendMenuW", hMenu, 0x0800 /*MF_SEPARATOR*/, 0);
  oSys.Call("User32::AppendMenuW", hMenu, 0 /*MF_STRING*/, 3, sTxtSelectAll + "\tCtrl+A");

  nCmd = oSys.Call("User32::TrackPopupMenu", hMenu, 0x0180 /*TPM_NONOTIFY|TPM_RETURNCMD*/, nX, nY, 0, hDlg, 0);

  oSys.Call("User32::DestroyMenu", hMenu);

  if (nCmd == 1)
    InsertTextTo(true);
  else if (nCmd == 2)
    InsertTextTo(false);
  else if (nCmd == 3)
    SetSelAE(0, -1);
}

function ReadIni()
{
  var sIniFile = WScript.ScriptFullName.substring(0, WScript.ScriptFullName.lastIndexOf(".")) + ".ini";

  if (oFSO.FileExists(sIniFile))
  {
    try
    {
      eval(AkelPad.ReadFile(sIniFile));
    }
    catch (oError)
    {}
  }

  oDlgPos.W = Math.max(oDlgPos.W, nDlgMinW);
  oDlgPos.H = Math.max(oDlgPos.H, nDlgMinH);
  if (bSeparateWnd) hWndParent = 0;
}

function WriteIni()
{
  var oFile   = oFSO.OpenTextFile(WScript.ScriptFullName.substring(0, WScript.ScriptFullName.lastIndexOf(".")) + ".ini", 2, true, -1);
  var sIniTxt = "";
  var i;

  oDlgPos.Max = oSys.Call("User32::IsZoomed", hDlg);

  for (i in oDlgPos)
    sIniTxt += 'oDlgPos.' + i + '=' + oDlgPos[i] + ';\r\n';

  sIniTxt +=
    'bSeparateWnd=' + bSeparateWnd + ';\r\n' +
    'nAPMSel='      + nAPMSel + ';\r\n' +
    'bAPMSort='     + bAPMSort + ';\r\n' +
    'nAPMLang='     + nAPMLang + ';\r\n' +
    'bWordWrap='    + bWordWrap + ';\r\n' +
    'sFindName="'   + EscapeStr(sFindName) + '";\r\n' +
    'sFindText="'   + EscapeStr(sFindText) + '";\r\n' +
    'sAltDir="'     + EscapeStr(sAltDir) + '";\r\n' +
    'aAESel[0]={';

  for (i in aAESel[0])
    sIniTxt += '"' + i + '":[' + aAESel[0][i] + '],';

  if (sIniTxt.slice(-1) == ',')
    sIniTxt = sIniTxt.slice(0, -1);

  sIniTxt += '};\r\naAESel[1]={';

  for (i in aAESel[1])
    sIniTxt += '"' + i + '":[' + aAESel[1][i] + '],';

  if (sIniTxt.slice(-1) == ',')
    sIniTxt = sIniTxt.slice(0, -1);

  sIniTxt += '};';
	
  oFile.Write(sIniTxt);
  oFile.Close();
}

function EscapeStr(sText)
{
  return sText.replace(/[\\"]/g, '\\$&').replace(/\n/g, '\\n').replace(/\r/g, '\\r');
}

function GetLangStrings()
{
//  if (AkelPad.GetLangId(0 /*LANGID_FULL*/) == 1049 /*Russian*/)
//  {
//  }
//  else
  {
    sTxtDlgTitle     = "AkelPad methods view";
    sTxtNoFiles      = "Files not found:";
    sTxtChooseDir    = "Choose directory with documentation of Scripts plugin:";
    sTxtSort         = "&Sort methods";
    sTxtEnglish      = "&English";
//    sTxtRussian      = "&Russian";
    sTxtRussian      = "&Chinese";
    sTxtMenu         = "&Menu";
    sTxtOK           = "OK";
    sTxtClose        = "Close";
    sTxtName         = "Name";
    sTxtText         = "Text";
    sTxtFindName     = "Find name";
    sTxtFindText     = "Find text";
    sTxtDownFromBeg  = "Down from beginning";
    sTxtDownFromCur  = "Down from current position";
    sTxtUpFromEnd    = "Up from end";
    sTxtUpFromCur    = "Up from current position";
    sTxtNext         = "Next";
    sTxtPrevious     = "Previous";
    sTxtNotFound     = "Not found.";
    sTxtMoveWindow   = "Move window";
    sTxtLeft         = "Left";
    sTxtRight        = "Right";
    sTxtUp           = "Up";
    sTxtDown         = "Down";
    sTxtToLeftEdge   = "To left edge";
    sTxtToRightEdge  = "To right edge";
    sTxtToTopEdge    = "To top edge";
    sTxtToBottomEdge = "To bottom edge";
    sTxtWrapLines    = "Wrap lines";
    sTxtSeparateWnd  = "Run in separate window";
    sTxtCopyToCB     = "Copy to clipboard";
    sTxtInsertToAP   = "Insert to AkelPad";
    sTxtSelectAll    = "Select all";
  }
}

I changed Russian language into Chinese (codepage 1251 -> 936).

KDJ
Offline
Posts: 1949
Joined: Sat Mar 06, 2010 7:40 pm
Location: Poland

Post by KDJ »

FeyFre
The following files are encoded in UTF-8:
Speech-Eng.txt,
Speech-Rus.txt,
SpellCheck-Eng.txt,
SpellCheck-Rus.txt.
Can you recode them to ANSI, like other documents *.txt in the directory ...\Docs\?
The point is that they are improperly displayed by the script AkelPadDocsView.js.

Offline
Site Admin
Posts: 6311
Joined: Thu Jul 06, 2006 7:20 am

Post by Instructor »

KDJ
You can set codepage to 1251, if file not unicode:

Code: Select all

var hMainWnd=AkelPad.GetMainWnd();
var aCP=[];

aCP.nCodePage=0;
aCP.bBOM=0;
if (!DetectFile("c:\\TC\\AkelPad\\AkelFiles\\Docs\\SpellCheck-Rus.txt", 1024, 0xD, aCP))
  WScript.Echo("CodePage=" + aCP.nCodePage + "\nBOM=" + aCP.bBOM);

function DetectFile(pFile, dwBytesToCheck, dwFlags, aCP)
{
  var lpInputFile;
  var lpDetectFile;
  var nResult=-2 /*EDT_ALLOC*/;

  if (lpInputFile=AkelPad.MemAlloc(256 * 2 /*sizeof(wchar_t)*/))
  {
    if (lpDetectFile=AkelPad.MemAlloc(_X64?24:20 /*sizeof(DETECTFILEW)*/))
    {
      //Detect codepage
      AkelPad.MemCopy(lpInputFile, pFile, 1 /*DT_UNICODE*/);
      AkelPad.MemCopy(lpDetectFile + 0 /*offsetof(DETECTFILEW, pFile)*/, lpInputFile, 2 /*DT_QWORD*/);
      AkelPad.MemCopy(lpDetectFile + (_X64?8:4) /*offsetof(DETECTFILEW, dwBytesToCheck)*/, 1024, 3 /*DT_DWORD*/);
      AkelPad.MemCopy(lpDetectFile + (_X64?12:8) /*offsetof(DETECTFILEW, dwFlags)*/, dwFlags, 3 /*DT_DWORD*/);
      AkelPad.MemCopy(lpDetectFile + (_X64?16:12) /*offsetof(DETECTFILEW, nCodePage)*/, aCP.nCodePage, 3 /*DT_DWORD*/);
      AkelPad.MemCopy(lpDetectFile + (_X64?20:16) /*offsetof(DETECTFILEW, bBOM)*/, aCP.bBOM, 3 /*DT_DWORD*/);

      if ((nResult=AkelPad.SendMessage(hMainWnd, 1177 /*AKD_DETECTFILEW*/, 0, lpDetectFile)) == 0 /*EDT_SUCCESS*/)
      {
        aCP.nCodePage=AkelPad.MemRead(lpDetectFile + (_X64?16:12) /*offsetof(DETECTFILEW, nCodePage)*/, 3 /*DT_DWORD*/);
        aCP.bBOM=AkelPad.MemRead(lpDetectFile + (_X64?20:16) /*offsetof(DETECTFILEW, bBOM)*/, 3 /*DT_DWORD*/);
      }
      AkelPad.MemFree(lpDetectFile);
    }
    AkelPad.MemFree(lpInputFile);
  }
  return nResult;
}

Offline
Posts: 1161
Joined: Sun Oct 20, 2013 11:44 am

Post by Skif_off »

Если у кого-нибудь найдется время и возможность, напишите, пожалуйста, скрипт (желательно JavaScript, а не VBScript), который будет копировать выделенный текст в буфер обмена, запускать внешнюю утилиту и после ее завершения выдавать диалог "Вставить текст?" и если да - вставлять вместо выделения, если нет - завершиться и оставить текст в буфере.

Offline
Site Admin
Posts: 6311
Joined: Thu Jul 06, 2006 7:20 am

Post by Instructor »

Skif_off

Code: Select all

var hMainWnd=AkelPad.GetMainWnd();
var pSelText;
var pClipText;

if (pSelText=AkelPad.GetSelText())
{
  AkelPad.SetClipboardText(pSelText);
  AkelPad.Exec("notepad.exe", "", 1);
  pClipText=AkelPad.GetClipboardText();

  if (pClipText != pSelText && AkelPad.MessageBox(hMainWnd, "Вставить текст?", WScript.ScriptName, 36 /*MB_ICONQUESTION|MB_YESNO*/) == 6 /*IDYES*/)
    AkelPad.ReplaceSel(pClipText, true);
}

Offline
Posts: 1161
Joined: Sun Oct 20, 2013 11:44 am

Post by Skif_off »

Instructor
Спасибо, работает. Рабочую директорию не обязательно указывать?

Добавлено:
Разобрался, не обязательно.
Last edited by Skif_off on Fri Jan 31, 2014 9:07 pm, edited 1 time in total.

KDJ
Offline
Posts: 1949
Joined: Sat Mar 06, 2010 7:40 pm
Location: Poland

Post by KDJ »

Instructor wrote:KDJ
You can set codepage to 1251, if file not unicode:
...
Excellent idea, thank you very much.
Already done (code page detection): AkelPadDocsView.js.

Offline
Posts: 1161
Joined: Sun Oct 20, 2013 11:44 am

Post by Skif_off »

Возможно ли изменить темы подсветки на заданную для всех открытых файлов, в т.ч. не сохраненных?
Locked