Створення нового типу довідника аналітики

Скачать: 

Давайте якісно проаналізуємо попередню статтю (“Створення простого довідника”). В цій статті ми вирішили питання ведення реєстру комп'ютерів. Але чи повністю? Зрозуміло, що ПК має набагато більше характеристик, ніж ми передбачили. Це і список комплектуючих, і підключені до нього периферійні пристрої. Комплектуючі теж відрізняються своїми параметрами.

Очевидно, ці всі дані потрібно реєструвати в системі.

Для того, щоби доповнити наш довідник, нам необхідно створити список цих комплектуючих. По суті, він вже існує в довіднику номенклатури. Проте до вже існуючих даних потрібно додати технічні характеристики кожного комплектуючого. Для цього, нам потрібно створити такий довідник аналітики, який би містив список комплектуючих (взятих з довідника номенклатури) розбитих на групи і технічні характеристики, записаних окремим списком.

Для реалізації цього ми створимо новий тип довідника аналітики.

Створений на основі цього типу довідник аналітика буде містити список комплектуючих в одній таблиці, а їхніх характеристик – в іншій. Відображати на екрані ми будемо за допомогою двох списків. В одному комплектуючі, а в другому характеристики, при чому при переміщенні по списку комплектуючих їхні характеристики будуть змінюватись автоматично.

Почнемо...

Трошки теорії про створення типів довідників аналітики.Типи довідників аналітики зберігаються в папціScripts/Cls. Для кожного типу створюється окрема папка. Її назва і буде позначенням нового типу. В цій папці можуть бути наступні файли:

  • class.xml – тут описуються змінні довідника аналітики;

  • dpmapping.xml – тут ці змінні прив’язуються до полів таблиці;

  • form.xml – описується форма для додавання даних в довідник;

  • *.js – оброблювач подій на формі;

  • list.xml – описуються відображення списку;

  • list.js – описуються оброблювач подій списку (не обов’язкове);

Якщо довідник з рядками, то в цю ж папку треба помістити файл *.xml з описом цього Grid`а і окрему папку, в якій будуть міститись файли для оброблення даних в цьому списку:

  • class.xml – тут описуються змінні довідника аналітики;

  • dpmapping.xml – тут ці змінні прив’язуються до полів таблиці;

  • form.xml – описується форма для додавання даних в довідник;

  • *.js – оброблювач подій на формі;

Все просто і зрозуміло. Достатньо уважно описати змінні і поля, створити довідник аналітики потрібного (створеного) типу і сміливо користуватись.

Створення таблиць. Як створювати таблиці в існуючій базі даних ми знаємо. Тому тут я просто наведу назви таблиць і списки полів.

Нам потрібна одна таблиця, де ми опишемо код, назву і серійний номер деталі. Назвемо її CL_KOMPL. Поля, що входять:FKOD, FNAME, FSERNOM.

В другій нам потрібно лише два поля (потім зрозуміємо чому так). Цю таблицю назвемо CL_KOMPL_ROW. Поля, що входять: FPARNAME, FPARZNACH.

Таблиці створено і до цього більше не будемо звертатись. Просто навожу в лістингу 1 текст файлу для їх створення.

Лістинг 1

<?xml version="1.0" encoding="UTF-8"?>

<STRU>

<TABLES>

<table attr="" dospath="cdbf" path="cl_mdb" pattern="CL_KOMPL" sys="com" table="CL_KOMPL"></table>

<table attr="" dospath="cdbf" path="cl_mdb" pattern="CL_KOMPL_ROW" sys="com" table="CL_KOMPL_ROW"></table>

</TABLES>

<PATTERNS>

<CL_KOMPL>

<PARENTS>

<PARENT pattern="FWIDPARENT"/>

</PARENTS>

<FIELDS>

<FWID_CL attr=" " type="long"/>

<FKOD attr=" " type="text"/>

<FNAME attr=" " type="text"/>

<FSERNOM attr=" " type="text"/>

<FREM attr=" " type="longtext"/>

</FIELDS>

</CL_KOMPL>

<CL_KOMPL_ROW>

<PARENTS>

<PARENT pattern="FWIDPARENT"/>

</PARENTS>

<FIELDS>

<FWID_CL attr=" " type="long"/>

<FPARNAME attr=" " type="long"/>

<FPARZNACH attr=" " type="text"/>

</FIELDS>

</CL_KOMPL_ROW>

</PATTERNS>

</STRU>

Для створення нового типу довідника виконаємо наступні дії:

  1. В Scripts/Cls створимо папку з іменем довідника (наприклад, clkompl);

  2. Створимо всі необхідні файли в цій папці.

Описання типу довідника (class.xml). Отже, поля таблиць створені, можна описувати клас довідника. Нагадую, що в класі ми описуємо змінні довідника. Імена цим змінним ми будемо давати такі, як і імена полів, замінюючи першу літеру F на H.

Лістинг 2

<?xml version="1.0" encoding="UTF-8"?>

<DpCL type="clkompl" name="Комплектуючі|Комплектующие" sys="COM">

<Parents>

<parent classid="cls.CL1"/>

</Parents>

<Header>

<var name="HKOD" datatype="text"/>

<var name="HNAME" datatype="text"/>

<var name="HSERNOM" datatype="text"/>

<var name="HREM" datatype="text"/>

</Header>

<rows>

<row id="KLROWS" classid="KLROWS"/>

</rows>

</DpCL>

 

В лістингу 2 не складно розібратись самостійно. Тут описано текст файлу class.xml. Все ж дам деякі пояснення.

<Header> - описує основні змінні довідника. Тут вказується і тип цієї змінної.

<rows> - прив'язує до основного класу рядки. Classid - ідентифікатор класу рядків. Папку з такою ж назвою потрібно створити в папці Scripts/Cls/Назва довідника.

Зв'язок змінних з полями таблиці (dpmapping.xml). Тепер “прив'яжемо” змінні довідника до полів таблиці. В системі “Дебет Плюс V12” це здійснюеться за допомогою файлу dpmapping.xml, який описано в лістингу 3.

Лістинг 3

<?xml version="1.0" encoding="UTF-8"?>

<DpCL type="clkompl">

<Header>

<Tables>

<table name="CL" />

<table name="CLRELCLCL" ID="FWID_CL" />

<table name="CL_KOMPL" ID="FWID_CL" />

</Tables>

<Fields>

<field name="FWID" table="CL" var="ID" />

<field name="FTXT" table="CL" var="HTXT" />

<field name="FTXTS" table="CL" var="HTXTS" />

<field name="FCOD" table="CLRELCLCL" var="HCOD" />

<field name="FCL" table="CLRELCLCL" var="HCL" />

<field name="FWID_CL" table="CLRELCLCL" var="ID" />

<field name="FWID" table="CL_KOMPL" var="ID" />

<field name="FKOD" table="CL_KOMPL" var="HKOD" />

<field name="FNAME" table="CL_KOMPL" var="HNAME" />

<field name="FSERNOM" table="CL_KOMPL" var="HSERNOM" />

<field name="FREM" table="CL_KOMPL" var="HREM" />

</Fields>

</Header>

<Rows>

<Tables>

<table name="CL_KOMPL_ROW" reffield="FWID_CL"/>

</Tables>

</Rows>

</DpCL>

Тут name –ім'я поля, table –ім'я таблиці, в якій це поле знаходиться,var – ім'я змінної. Якщо все зрозуміло – йдемо далі.

Тепер потрібно описати grid.

Файл list.xml. Як описувати відображення таблиці на екрані ми вже знаємо. Тому просто навожу лістинг цього файлу.

Лістинг 4

<?xml version="1.0" encoding="UTF-8"?>

<list>

<grid>

<field field="kompl.FKOD" text="Код|Код" width="20" />

<field field="kompl.FNAME" text="Назва|Название" width="40" />

<field field="kompl.FSERNOM" text="Серійний номер|Серийный номер" width="20" />

<field field="kompl.FREM" text="Примітка|Примечание" width="70" />

</grid>

</list>


 

В цьому коді kompl.FKOD означає <псевдонім таблиці>.<назва поля>. Така комбінація утворилась в результаті використання функції tie. Ця функція приєднує до основної таблиці іншу по вибраних полях. Її використано в файлі list.js.

Файл list.js.

Лістинг 5

function clAfterLoad()

{

this.addTies = clAddTies;

}


 

function clAddTies()

{

this.extTie("CL",Fcl);

this.extTieEx("ext0","fwid","CL","0");

this.subTie("CL_KOMPL", "kompl", "FWID_CL", "Fwid");

}

Функція є clAfterLoad()обов’язковою. В ній описуються методи і властивості таблиці, яка відображається на гріді.

Я спробую пояснити тільки останній рядок функції clAddTies(). Тут:

  • "CL_KOMPL" – ім'я таблиці, що приєднується.

  • "kompl" – псевдонім цієї таблиці.

  • "FWID_CL", "Fwid" – поля таблиць, за якими ці таблиці об'єднуються.


 

Все доволі просто. Якщо ви створили і цей файл, то можемо йти далі.

Тепер потрібно створити форму для заповнення таблиці. Знову ж таки ми це вже з вами робили. Я зупинюсь тільки на використанні гріда.

Файл form.js і form.xml.

Лістинг 6

<?xml version="1.0" encoding="utf-8"?>

<Form>

<Controls col="3">

<Label text="№" width="80" gridwidth="1"/>

<TextField ID="FKOD" width="80" gridwidth="2"/>

<Label text="Назва:|Название:" gridwidth="1"/>

<TextField ID="FNAME" width="450" gridwidth="2"/>

<Label text="Серійний номер:|Серийный номер:" gridwidth="1"/>

<TextField ID="FSERNOM" width="450" gridwidth="2"/>

<Label text="Примітка:|Примечание:" gridwidth="1"/>

<TextField ID="FREM" width="450" gridwidth="2"/>

<grid ID="grid" width="700" height="250" gridwidth="3" align="fill" valign1="fill"/>

</Controls>

<script languige="JavaScript" src="form.js"/>

</Form>


 

Лістинг 7


 

include("objects//DpCl.js");

include("gridedit.js");


 

var sDir = rootDirectory() + "cls/clkompl/";

var sTmpTbl = "TMP_KOMPL_ROW";

var sRowTbl = "CL_KOMPL_ROW";

var sRowClass = "KLROWS";

var objCl = extPar.dpObj;

var ctrlLinker;

var gridTbl;

var oGridEdit;


 

function onLoad()

{

this.onEscape = exit;

Caption(ru("Комплектующие", "Комплектуючі") +": "+ modeName(this.sMode));

ctrlLinker = new DpCtrlLinker(objCl);

FKOD.setMask("######");

FKOD.setFocus();

ctrlLinker.addLink("HKOD", FKOD);

ctrlLinker.addLink("HNAME", FNAME);

ctrlLinker.addLink("HSERNOM", FSERNOM);

ctrlLinker.addLink("HREM", FREM);

ctrlLinker.toControls();

loadGrid(this.sMode);

}


 

function loadGrid(sMode)

{

DropTable(sTmpTbl);

var sSQL = "SELECT * "

+ " INTO " + sTmpTbl

+ " FROM ^"+ sRowTbl;

var sWhere = " WHERE 1<>1 ";

if (sMode != "ADD")

sWhere = " WHERE FWID_CL="+ sqlTo(objCl.getID());

sSQL += sWhere;

ExecuteSQL(sSQL);

gridTbl = OpenTable("m", "SELECT * FROM "+ sTmpTbl);

clTie(gridTbl,"kk","="+250+",FPARNAME");

//browse(gridTbl);

grid.setXMLDir(sDir);

grid.setXMLFile("l_kompllist.xml");

grid.setTable(gridTbl);

grid.build();

grid.setData(sRowClass);

this.gridMenuInit = gridMenuInit;

this.gridMenuRum = gridMenuRum;

grid.loadMenuHandler(this,"gridMenuInit");

grid.selectMenuHandler(this,"gridMenuRum");


 

oGridEdit = new DpGridEdit(grid);

oGridEdit.canEdit = canEditRecord;

oGridEdit.saveRecord = saveRecord;

}


 


 

function saveRecord()

{

var rowID = parseInt(grid.getTable().getValue("fwid"));

var oRow = objCl.getRow(sRowClass, rowID);

if (oRow == null)

{

oRow = objCl.createRow(sRowClass);

oRow.setID(rowID);

objCl.appendRow(sRowClass, oRow);

}

with (oRow)

{

setVar("RPARNAME", gridTbl.getValue("FPARNAME"));

setVar("RPARZNACH", gridTbl.getValue("FPARZNACH"));

}

return true;

}


 

function canEditRecord()

{

return true;

}


 

function gridMenuInit(grid)

{

grid.AddMenuItem("ADD","Додати|Добавить");

if (!grid.getTable().isEmpty())

{

grid.AddMenuItem("EDIT","Редагувати|Редактировать");

grid.AddMenuItem("COPY","Копіювати|Копировать");

grid.AddMenuItem("DEL","Видалити|Удалить");

}

}


 

function gridMenuRum(sID, grid)

{

var tbl = grid.getTable();

var tName = tbl.getTableName();

var rowID = tbl.getValue("FWID");

switch(sID)

{

case "DEL":

var nGridPos = grid.getRowSelected();

ExecuteSQL("delete From "+ tName

+" where Fwid="+ sqlTo(rowID));

objCl.deleteRow(sRowClass, rowID);

tbl.requery();

tbl.setAbsolute(nGridPos-1);

grid.refresh();

break;

case "ADD": case "EDIT": case "COPY":

var oRow;

if(sID == "ADD")

oRow = objCl.createRow(sRowClass);

else if(sID == "EDIT")

oRow = objCl.getRow(sRowClass, rowID);

else if(sID == "COPY")

oRow = objCl.copyRow(sRowClass, rowID);

if(!oRow)

break;

if (!rowEdit(sID, oRow))

break;

tbl.requery();

grid.refresh();

break;

}

return true;

}


 

function onSave()

{

ctrlLinker.toVars();

storeToDb(sRowTbl, sTmpTbl);

exit();

}


 

function rowEdit(sMode, oRow)

{

var par = new Object();

par.dpObj = oRow;

par.mode = sMode;

par.tblName = sTmpTbl;

par.dpObj.hasExt = hasExt;

par.formFile = "cls/"+ objCl.sClassId +"/KLROWS/form.xml";


 

showWindow(par.formFile, "XMLDLG", par);

if(par.escape)

return false;

var id = oRow.getID();

if(inList(sMode, "ADD", "COPY"))

objCl.appendRow(sRowClass, oRow);

obj2DB(id, oRow.jObj, null, sTmpTbl);

return true;

}


 

function hasExt()

{

return false;

}


 

function storeToDb(sTbl, tmpTbl)

{

var sFld = GetPatternIntersection (sTbl, sTbl);

ExecuteSQL("DELETE FROM ^"+ sTbl +" WHERE FWID_CL="+ sqlTo(objCl.getID()));

ExecuteSQL("UPDATE "+ tmpTbl +" SET Fwid_cl="+ sqlTo(objCl.getID()));

ExecuteSQL("INSERT INTO ^"+ sTbl +" ("+ sFld +")"

+" SELECT "+ sFld +" FROM "+ tmpTbl);

}


 

function exit()

{

gridTbl.close();

DropTable(sTmpTbl);

}


 

include("sys/DpBaseDlg.js");


 

Грід завантажується на форму та ініціалізується функцією loadGrid. Поля на формі прив'язуються до змінних класу з допомогою об'єкту ctrlLinker. Це дає можливість зручного збереження даних та завантаження даних на форму. Все інше – це оброблення даних. Шукайте описання об'єктів і функцій в файлах бізнес-логіки системи “Дебет Плюс V12”.

Один момент. Описання гріду, який знаходиться на формі знаходиться в файлі l_kompllist.xml. Ось його літинг.

Лістинг 8

<?xml version="1.0" encoding="UTF-8"?>

<grid>

<field field="=tcl('CL','TXT',250,FPARNAME)" text="Параметр|Параметр" width="20" />

<field field="FPARZNACH" text="Значення|Значение" width="30" />

</grid>


 

Для успішного виконання коду потрібно створити довідник аналітики №250 “Характеристики комплектуючих”.

<Тепер створимо клас для додавання рядків. Оскільки ми повністю розробили один клас , то нема проблеми розібратись як зробити інший.

В папці Scripts/Cls/Назва довідника стпоримо папку KLROWS. В ній чотири файли. Навожу без коментарів.

class.xml

<?xml version="1.0" encoding="utf-8"?>

<DpCl type="KLROWS">

<Header>

<var name="RWID_CL" datatype="long"/>

<var name="RPARNAME" datatype="text"/>

<var name="RPARZNACH" datatype="text"/>

</Header>

</DpCl>

dpmapping.xml

<?xml version="1.0" encoding="utf-8"?>

<DpCl type="KLROWS">

<Header>

<Tables>

<table name="CL_KOPML_ROWS"/>

</Tables>

<Fields>

<field name="FWID_CL" table="CL_KOMPL_ROWS" var="RWID_CL"/>

<field name="FPARNAME" table="CL_KOPML_ROWS" var="RPARNAME"/>

<field name="FPARZNACH" table="CL_KOPML_ROWS" var="RPARZNACH"/>

</Fields>

</Header>

</DpCl>

form.xml

<?xml version="1.0" encoding="utf-8" ?>

<Form>

<Controls col="4" >

<ComboBox ID="FPARNAME">

<option selected="true" value="-">---</option>

</ComboBox>

<Label text="Значення|Значение"/>

<TextField ID="FPARZNACH" width="130" colspan="2"/>

</Controls>

<script languige="JavaScript" src="form.js"/>

</Form>


 

form.js

include("Objects/DpVal.js");

include("Objects/DpBank.js");


 

var obj = extPar.dpObj;

var oVal;

var ctrlLinker;


 

function onLoad()

{

Caption(ru("Комплектующие", "Комплектуючі")

+ ": " + modeName(extPar.mode));

//Блок для заповнення списку ComboBox з довідника аналітики № 250

var tt = OpenTable("Select a.FCOD,b.FWID,b.FTXT, a.FWID_CL From ^CL b, ^CLRELCLCL a WHERE b.FWID=a.FWID_CL and a.FCL=250 ORDER BY b.FTXT");

for(tt.MoveFirst();!tt.IsEOF();tt.MoveNext())

{

var sVal = tt.getValue("FCOD");

var sTxt = tt.getValue("FTXT");

FPARNAME.addItem(sVal,sTxt);

}

FPARNAME.selectedIndex = obj.getVar("RPARNAME");

//showObject(obj);

//Кінець блоку

ctrlLinker = new DpCtrlLinker(obj);

ctrlLinker.addLink("RPARNAME", FPARNAME);

ctrlLinker.addLink("RPARZNACH", FPARZNACH);

ctrlLinker.updateData(false);

}


 

function onSave()

{

ctrlLinker.updateData(true);

}


 

function hasExt()

{

// return false;

}


 

include("sys\\DpBaseDlg.js");


 


 

Тепер додамо довідник аналітики створеного типу і от, що в нас вийшло: