From 3eba0a52f01a3f0be4fe26c8b57ba5a2e4f0abf2 Mon Sep 17 00:00:00 2001 From: Mikhail Chechnev Date: Wed, 5 Mar 2025 14:17:25 +0300 Subject: [PATCH] =?UTF-8?q?WEBAPP:=20=D0=9D=D0=BE=D0=B2=D0=B0=D1=8F=20?= =?UTF-8?q?=D0=BF=D0=B0=D0=BD=D0=B5=D0=BB=D1=8C=20-=20"=D0=98=D0=BD=D1=84?= =?UTF-8?q?=D0=BE=D1=80=D0=BC=D0=B0=D1=86=D0=B8=D1=8F=20=D0=BE=20=D0=BF?= =?UTF-8?q?=D1=80=D0=BE=D0=B5=D0=BA=D1=82=D0=B0=D1=85"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/panels/prj_info/filter.js | 170 +++ app/panels/prj_info/filter_dialog.js | 147 +++ app/panels/prj_info/index.js | 16 + app/panels/prj_info/layouts.js | 168 +++ app/panels/prj_info/prj_info.js | 27 + app/panels/prj_info/projects.js | 70 ++ app/panels/prj_info/projects_hooks.js | 82 ++ app/panels/prj_info/projects_layouts.js | 96 ++ app/panels/prj_info/stage_detail.js | 173 +++ app/panels/prj_info/stage_detail_hooks.js | 126 +++ app/panels/prj_info/stage_detail_layouts.js | 148 +++ app/panels/prj_info/stages.js | 95 ++ app/panels/prj_info/stages_hooks.js | 78 ++ app/panels/prj_info/stages_layouts.js | 86 ++ db/PKG_P8PANELS_PROJECTS.pck | 1087 ++++++++++++++++++- img/prj_info.jpg | Bin 0 -> 136923 bytes p8panels.config | 11 + 17 files changed, 2578 insertions(+), 2 deletions(-) create mode 100644 app/panels/prj_info/filter.js create mode 100644 app/panels/prj_info/filter_dialog.js create mode 100644 app/panels/prj_info/index.js create mode 100644 app/panels/prj_info/layouts.js create mode 100644 app/panels/prj_info/prj_info.js create mode 100644 app/panels/prj_info/projects.js create mode 100644 app/panels/prj_info/projects_hooks.js create mode 100644 app/panels/prj_info/projects_layouts.js create mode 100644 app/panels/prj_info/stage_detail.js create mode 100644 app/panels/prj_info/stage_detail_hooks.js create mode 100644 app/panels/prj_info/stage_detail_layouts.js create mode 100644 app/panels/prj_info/stages.js create mode 100644 app/panels/prj_info/stages_hooks.js create mode 100644 app/panels/prj_info/stages_layouts.js create mode 100644 img/prj_info.jpg diff --git a/app/panels/prj_info/filter.js b/app/panels/prj_info/filter.js new file mode 100644 index 0000000..3642f49 --- /dev/null +++ b/app/panels/prj_info/filter.js @@ -0,0 +1,170 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Фильтр +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React, { useState } from "react"; //Классы React +import PropTypes from "prop-types"; //Контроль свойств компонента +import { Grid, Chip, Stack, Input, InputAdornment, IconButton, Icon } from "@mui/material"; //Интерфейсные элементы +import { FILTER_INITIAL, FILTER_ITEMS, PRICE_STRUCT_STATUS, PROJECT_STATE, FilterDialog } from "./filter_dialog"; //Компонент "Диалог фильтра" + +//--------- +//Константы +//--------- + +//Стили +const STYLES = { + CONTAINER: { paddingTop: "10px" }, + FILTER: { maxWidth: "99vw" }, + SEARCH_GRID_ITEM: { paddingRight: "15px" } +}; + +//------------------------------------ +//Вспомогательные функции и компоненты +//------------------------------------ + +//Элемент фильтра +const FilterItem = ({ caption, value, defaultValue, onClick, onDelete }) => { + //При нажатии на элемент + const handleClick = () => (onClick ? onClick() : null); + + //При нажатии на удаление элемента + const handleDelete = () => (onDelete ? onDelete() : null); + + //Генерация содержимого + return ( + + {caption}: {value || defaultValue} + + } + variant="outlined" + onClick={handleClick} + onDelete={onDelete ? handleDelete : null} + /> + ); +}; + +//Контроль свойств компонента - Элемент фильтра +FilterItem.propTypes = { + caption: PropTypes.string.isRequired, + value: PropTypes.any, + defaultValue: PropTypes.string.isRequired, + onClick: PropTypes.func, + onDelete: PropTypes.func +}; + +//----------- +//Тело модуля +//----------- + +//Фильтр +const Filter = ({ values, onChange }) => { + //Собственное состояние - отображение диалога ввода значений фильтра + const [isOpen, setIsOpen] = useState(false); + + //Собственное состояние - строка поиска + const [search, setSearch] = useState(values.search); + + //Передача сообщения об измении фильтра родителю + const notifyChange = values => (onChange ? onChange(values) : null); + + //При закрытии диалога с сохранением значений + const handleFilterDialogOk = values => { + setIsOpen(false); + notifyChange(values); + }; + + //При закрытии диалога без сохранения значений + const handleFilterDialogCancel = () => setIsOpen(false); + + //При нажатии на фильтр + const handleClick = () => setIsOpen(true); + + //При выполнении поиска + const handleDoSearch = (clear = false) => { + if (clear === true) setSearch(""); + notifyChange({ ...values, search: clear === true ? "" : search }); + }; + + //При изменении значения в строке поиска + const handleSearchChange = e => setSearch(e.target.value); + + //При нажатии клавиши в строке поиска + const handleSearchKeyPress = e => ([13, 27].includes(e.keyCode) ? handleDoSearch(e.keyCode == 27) : null); + + //Формирование функции обработки очистки элемента фильтар + const buildFilterItemClearHandler = сode => + values[сode] != FILTER_INITIAL[сode] ? () => notifyChange({ ...values, [сode]: FILTER_INITIAL[сode] }) : null; + + //Генерация содержимого + return ( + + + {isOpen ? : null} + + + + item.value == values.priceStructStatus)?.name} + onDelete={buildFilterItemClearHandler("priceStructStatus")} + /> + item.value == values.prjState)?.name} + onDelete={buildFilterItemClearHandler("prjState")} + /> + + + + + handleDoSearch(true)}> + clear + + + search + + + } + onKeyDown={handleSearchKeyPress} + onChange={handleSearchChange} + /> + + + ); +}; + +//Контроль свойств компонента - Фильтр +Filter.propTypes = { + values: FILTER_ITEMS.isRequired, + onChange: PropTypes.func +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { FILTER_INITIAL, Filter }; diff --git a/app/panels/prj_info/filter_dialog.js b/app/panels/prj_info/filter_dialog.js new file mode 100644 index 0000000..c9d8f90 --- /dev/null +++ b/app/panels/prj_info/filter_dialog.js @@ -0,0 +1,147 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Диалог фильтра +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React, { useState, useContext } from "react"; //Классы React +import PropTypes from "prop-types"; //Контроль свойств компонента +import { Button, Dialog, DialogTitle, DialogContent, DialogActions } from "@mui/material"; //Интерфейсные элементы +import { ApplicationСtx } from "../../context/application"; //Контекст приложения +import { BUTTONS } from "../../../app.text"; //Типовые тексты +import { APP_STYLES } from "../../../app.styles"; //Типовые стили +import { FormField } from "./layouts"; //Общие компоненты панели + +//--------- +//Константы +//--------- + +//Стили +const STYLES = { + DIALOG_CONTENT: { overflowY: "auto", ...APP_STYLES.SCROLL } +}; + +//Структура фильтра +const FILTER_ITEMS = PropTypes.shape({ + prjType: PropTypes.string, + insDep: PropTypes.string, + priceStructStatus: PropTypes.number.isRequired, + prjState: PropTypes.number.isRequired, + search: PropTypes.string +}); + +//Начальное состояние фильтра +const FILTER_INITIAL = { prjType: "", insDep: "", priceStructStatus: 0, prjState: 0, search: "" }; + +//Статусы структуры цены +const PRICE_STRUCT_STATUS = [ + { value: 0, name: "Все" }, + { value: 1, name: "Есть статьи с расходом больше 90%" }, + { value: 2, name: "Есть статьи с перерасходом" } +]; + +//Состояния проекта +const PROJECT_STATE = [ + { value: 0, name: "Все" }, + { value: 1, name: "Открытые" }, + { value: 2, name: "Неоткрытые" } +]; + +//----------- +//Тело модуля +//----------- + +//Диалог фильтра +const FilterDialog = ({ valuesInitial, onOk, onCancel }) => { + //Собственное состояние элементов фильтра + const [values, setValues] = useState({ ...valuesInitial }); + + //Подключение к контексту приложения + const { pOnlineShowDictionary } = useContext(ApplicationСtx); + + //Изменение элемента формы фильтра + const handleValueChanged = (name, value) => setValues(pv => ({ ...pv, [name]: value })); + + //Сброс настроек фильтра + const handleResetClick = () => setValues({ ...FILTER_INITIAL }); + + //Сохранение фильтра + const handleOkClick = () => (onOk ? onOk(values) : null); + + //Отмена фильтра + const handleCancelClick = () => (onCancel ? onCancel() : null); + + //Выбор значения элемента формы из словаря + const selectFromDictionary = (unitCode, name, applyValue) => { + pOnlineShowDictionary({ + unitCode, + showMethod: "main", + inputParameters: [{ name: "in_CODE", value: values[name] }], + callBack: res => applyValue(res.success ? [{ name, value: res.outParameters.out_CODE }] : null) + }); + }; + + //Генерация содержимого + return ( + + Фильтр отбора + + selectFromDictionary("ProjectTypes", "prjType", applyValue)} + /> + selectFromDictionary("INS_DEPARTMENT", "insDep", applyValue)} + /> + + + + + + + + + + ); +}; + +//Контроль свойств компонента - Диалог фильтра +FilterDialog.propTypes = { + valuesInitial: FILTER_ITEMS.isRequired, + onOk: PropTypes.func, + onCancel: PropTypes.func +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { FILTER_ITEMS, FILTER_INITIAL, PRICE_STRUCT_STATUS, PROJECT_STATE, FilterDialog }; diff --git a/app/panels/prj_info/index.js b/app/panels/prj_info/index.js new file mode 100644 index 0000000..2a01b83 --- /dev/null +++ b/app/panels/prj_info/index.js @@ -0,0 +1,16 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Панель мониторинга: точка входа +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import { PrjInfo } from "./prj_info"; //Корневая панель информации о проектах + +//---------------- +//Интерфейс модуля +//---------------- + +export const RootClass = PrjInfo; diff --git a/app/panels/prj_info/layouts.js b/app/panels/prj_info/layouts.js new file mode 100644 index 0000000..bd65b4c --- /dev/null +++ b/app/panels/prj_info/layouts.js @@ -0,0 +1,168 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Общие дополнительная разметка и вёрстка клиентских элементов +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React, { useState, useEffect } from "react"; //Классы React +import PropTypes from "prop-types"; //Контроль свойств компонента +import { Box, Icon, Input, InputAdornment, FormControl, Select, InputLabel, MenuItem, IconButton, Typography, Switch, Stack } from "@mui/material"; //Интерфейсные компоненты + +//--------- +//Константы +//--------- + +//Стили +const STYLES = { + STATE: value => ({ color: value === 1 ? "green" : "black" }), + COST_STATUS: color => ({ color, verticalAlign: "middle" }), + COST_READY: value => ({ color: value <= 30 ? "red" : value >= 80 ? "green" : "#e2af00" }), + TOGGLE_COLOR: checked => ({ color: checked ? "#006dd9" : "lightgrey" }) +}; + +//----------- +//Тело модуля +//----------- + +//Поле ввода формы +const FormField = ({ elementCode, elementValue, labelText, onChange, dictionary, list, type, ...other }) => { + //Значение элемента + const [value, setValue] = useState(elementValue); + + //При получении нового значения из вне + useEffect(() => { + setValue(elementValue); + }, [elementValue]); + + //Выбор значения из словаря + const handleDictionaryClick = () => + dictionary ? dictionary(res => (res ? res.map(i => handleChange({ target: { name: i.name, value: i.value } })) : null)) : null; + + //Изменение значения элемента (по событию) + const handleChange = e => { + setValue(e.target.value); + if (onChange) onChange(e.target.name, e.target.value); + }; + + //Генерация содержимого + return ( + + + {list ? ( + <> + + {labelText} + + + + ) : ( + <> + + {labelText} + + + + list + + + ) : null + } + {...(type ? { type } : {})} + onChange={handleChange} + /> + + )} + + + ); +}; + +//Контроль свойств - Поле ввода формы +FormField.propTypes = { + elementCode: PropTypes.string.isRequired, + elementValue: PropTypes.oneOfType([PropTypes.number, PropTypes.string, PropTypes.instanceOf(Date)]), + labelText: PropTypes.string.isRequired, + onChange: PropTypes.func, + dictionary: PropTypes.func, + list: PropTypes.array, + type: PropTypes.string +}; + +//Переключатель +const Toggle = ({ labels, checked, onChange }) => { + //Обработка переключения + const handleChange = event => (onChange ? onChange(event.target.checked) : null); + + //Генерация содержимого + return ( + + {labels[0]} + + {labels[1]} + + ); +}; + +//Контроль свойств компонента - Переключатель +Toggle.propTypes = { + labels: PropTypes.arrayOf(PropTypes.string).isRequired, + checked: PropTypes.bool.isRequired, + onChange: PropTypes.func +}; + +//Формирование значения для колонки "Статус структуры цены" +const formatCostStatusValue = ({ value, onClick, type = 1 }) => { + const [text, color] = + value == 0 + ? ["Без отклонений", "lightgreen"] + : value == 1 + ? [type == 1 ? "Есть статьи с расходом более 90%" : "Расход более 90%", "#ffdf71"] + : value == 2 + ? [type == 1 ? "Есть статьи с перерасходом" : "Перерасход", "#eb6b6b"] + : ["Не определено", "lightgray"]; + return onClick ? ( + + + circle + + + ) : ( + + circle + + ); +}; + +//Формирование значения для колонки "Готов (%, зтраты)" +const formatCostReadyValue = value => { + return {value}; +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { STYLES as COMMON_STYLES, FormField, Toggle, formatCostStatusValue, formatCostReadyValue }; diff --git a/app/panels/prj_info/prj_info.js b/app/panels/prj_info/prj_info.js new file mode 100644 index 0000000..46b6737 --- /dev/null +++ b/app/panels/prj_info/prj_info.js @@ -0,0 +1,27 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Корневой компонент панели +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React from "react"; //Классы React +import { Projects } from "./projects"; //Список проектов + +//----------- +//Тело модуля +//----------- + +//Корневой компонент панели "Информация о проектах" +const PrjInfo = () => { + //Генерация содержимого + return ; +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { PrjInfo }; diff --git a/app/panels/prj_info/projects.js b/app/panels/prj_info/projects.js new file mode 100644 index 0000000..76b4776 --- /dev/null +++ b/app/panels/prj_info/projects.js @@ -0,0 +1,70 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Список проектов +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React, { useState, useContext } from "react"; //Классы React +import { P8PDataGrid } from "../../components/p8p_data_grid"; //Таблица данных +import { P8P_DATA_GRID_CONFIG_PROPS } from "../../config_wrapper"; //Подключение компонентов к настройкам приложения +import { ApplicationСtx } from "../../context/application"; //Контекст приложения +import { useProjectsDataGrid } from "./projects_hooks"; //Хуки списка проектов +import { FILTER_INITIAL, Filter } from "./filter"; //Компонент "Фильтр" +import { PROJECTS_STYLES, projectDataCellRender, projectRowExpandRender } from "./projects_layouts"; //Дополнительная разметка и вёрстка клиентских элементов + +//----------- +//Тело модуля +//----------- + +//Список проектов +const Projects = () => { + //Собственное состояние + const [projects, setProjects] = useState({ pageNumber: 1, orders: [], filter: { ...FILTER_INITIAL } }); + + //Состояние таблицы проектов + const [projectsDataGrid] = useProjectsDataGrid({ ...projects.filter, pageNumber: projects.pageNumber, orders: projects.orders }); + + //Подключение к контексту приложения + const { pOnlineShowDocument } = useContext(ApplicationСtx); + + //Отображение записи проекта в штатном разделе + const showProject = async rn => pOnlineShowDocument({ unitCode: "Projects", document: rn, modal: false }); + + //При изменении количества отображаемых страниц + const handlePagesCountChanged = () => setProjects(pv => ({ ...pv, pageNumber: pv.pageNumber + 1 })); + + //При изменении состояния сортировки + const handleOrderChanged = ({ orders }) => setProjects(pv => ({ ...pv, orders: [...orders], pageNumber: 1 })); + + //При изменении фильтра + const handleFilterChanged = values => setProjects(pv => ({ ...pv, filter: { ...values }, pageNumber: 1 })); + + //Генерация содержимого + return ( + <> + + {projectsDataGrid.init ? ( + projectDataCellRender({ ...prms, showProject })} + rowExpandRender={projectRowExpandRender} + /> + ) : null} + + ); +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { Projects }; diff --git a/app/panels/prj_info/projects_hooks.js b/app/panels/prj_info/projects_hooks.js new file mode 100644 index 0000000..667f0bc --- /dev/null +++ b/app/panels/prj_info/projects_hooks.js @@ -0,0 +1,82 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Список проектов: пользовательские хуки для взаимодействия с сервером +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import { useState, useContext, useEffect } from "react"; //Классы React +import { BackEndСtx } from "../../context/backend"; //Контекст взаимодействия с сервером +import { object2Base64XML, formatDateRF } from "../../core/utils"; //Вспомогательные функции +import config from "../../../app.config"; //Настройки приложения + +//--------- +//Константы +//--------- + +//Размер страницы данных +const DATA_GRID_PAGE_SIZE = config.SYSTEM.PAGE_SIZE; + +//----------- +//Тело модуля +//----------- + +//Получение данных проектов с сервера +const useProjectsDataGrid = ({ prjType, insDep, priceStructStatus, prjState, search, pageNumber, orders }) => { + //Собственное состояние - флаг загрузки + const [isLoading, setLoading] = useState(false); + + //Собственное состояние - таблица данных + const [data, setData] = useState({ init: false, morePages: true }); + + //Подключение к контексту взаимодействия с сервером + const { executeStored, SERV_DATA_TYPE_CLOB } = useContext(BackEndСtx); + + //При необходимости обновить данные таблицы + useEffect(() => { + //Загрузка данных таблицы с сервера + const loadData = async () => { + try { + setLoading(true); + const data = await executeStored({ + stored: "PKG_P8PANELS_PROJECTS.INFO_PROJECTS_DG", + args: { + SPRJ_TYPE: prjType, + SINS_DEPARTMENT: insDep, + NCOST_STATUS: priceStructStatus, + NSTATE: prjState, + SSEARCH: search, + CORDERS: { VALUE: object2Base64XML(orders, { arrayNodeName: "orders" }), SDATA_TYPE: SERV_DATA_TYPE_CLOB }, + NPAGE_NUMBER: pageNumber, + NPAGE_SIZE: DATA_GRID_PAGE_SIZE, + NINCLUDE_DEF: pageNumber == 1 ? 1 : 0 + }, + respArg: "COUT", + loader: true, + attributeValueProcessor: (name, val) => (["DBEGPLAN", "DENDPLAN"].includes(name) ? formatDateRF(val) : val) + }); + setData(pv => ({ + ...pv, + columnsDef: data.XDATA_GRID.columnsDef ? [...data.XDATA_GRID.columnsDef] : pv.columnsDef || [], + rows: pageNumber == 1 ? [...(data.XDATA_GRID.rows || [])] : [...(pv.rows || []), ...(data.XDATA_GRID.rows || [])], + morePages: DATA_GRID_PAGE_SIZE == 0 ? false : (data.XDATA_GRID.rows || []).length >= DATA_GRID_PAGE_SIZE, + init: true + })); + } finally { + setLoading(false); + } + }; + loadData(); + }, [prjType, insDep, priceStructStatus, prjState, search, pageNumber, orders, executeStored, SERV_DATA_TYPE_CLOB]); + + //Возвращаем интерфейс хука + return [data, isLoading]; +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { useProjectsDataGrid }; diff --git a/app/panels/prj_info/projects_layouts.js b/app/panels/prj_info/projects_layouts.js new file mode 100644 index 0000000..0fe7af6 --- /dev/null +++ b/app/panels/prj_info/projects_layouts.js @@ -0,0 +1,96 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Список проектов: дополнительная разметка и вёрстка клиентских элементов +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React from "react"; //Классы React +import { Icon, Stack, Paper, Link } from "@mui/material"; //Интерфейсные элементы +import { P8P_DATA_GRID_MORE_HEIGHT } from "../../components/p8p_data_grid"; //Таблица данных +import { APP_BAR_HEIGHT } from "../../components/p8p_app_workspace"; //Заголовок страницы +import { APP_STYLES } from "../../../app.styles"; //Типовые стили +import { COMMON_STYLES, formatCostStatusValue, formatCostReadyValue } from "./layouts"; //Общие стили и разметка панели +import { Stages } from "./stages"; //Компонент "Этапы проекта" + +//--------- +//Константы +//--------- + +//Высота фильтра (пиксели) +const FILTER_HEIGHT = "60px"; + +//Стили +const STYLES = { + DATA_GRID_CONTAINER: morePages => ({ + height: `calc(100vh - ${APP_BAR_HEIGHT} - ${FILTER_HEIGHT} - ${morePages ? P8P_DATA_GRID_MORE_HEIGHT : "0px"} - 8px)`, + ...APP_STYLES.SCROLL + }) +}; + +//----------- +//Тело модуля +//----------- + +//Формирование значения для колонки "Состояние" проекта +const formatPrjStateValue = value => { + const [text, icon] = + value == 0 + ? ["Зарегистрирован", "app_registration"] + : value == 1 + ? ["Открыт", "lock_open"] + : value == 2 + ? ["Остановлен", "do_not_disturb_on"] + : value == 3 + ? ["Закрыт", "lock_outline"] + : value == 4 + ? ["Согласован", "thumb_up_alt"] + : ["Исполнение прекращено", "block"]; + return ( + + + {icon} + + + ); +}; + +//Форматирование ячеек таблицы "Проекты" +const projectDataCellRender = ({ row, columnDef, showProject }) => { + //Формирование представлений + switch (columnDef.name) { + case "NCOST_STATUS": + return { cellProps: { align: "center" }, data: formatCostStatusValue({ value: row[columnDef.name] }) }; + case "NCOST_READY": + return { cellProps: { align: "center" }, data: formatCostReadyValue(row[columnDef.name]) }; + case "NSTATE": + return { cellProps: { align: "center" }, data: formatPrjStateValue(row[columnDef.name]) }; + case "SCODE": + return { + data: ( + showProject(row["NRN"])}> + {row[columnDef.name]} + + ) + }; + default: + return { data: row[columnDef.name] }; + } +}; + +//Генерация представления расширения строки таблицы "Проектов" +const projectRowExpandRender = ({ row }) => { + return ( + + + + ); +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { STYLES as PROJECTS_STYLES, projectDataCellRender, projectRowExpandRender }; diff --git a/app/panels/prj_info/stage_detail.js b/app/panels/prj_info/stage_detail.js new file mode 100644 index 0000000..326729a --- /dev/null +++ b/app/panels/prj_info/stage_detail.js @@ -0,0 +1,173 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Детальная информация об этапе проекта +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React, { useState, useContext } from "react"; //Классы React +import PropTypes from "prop-types"; //Контроль свойств компонента +import { Grid, Box, Typography, Paper, Drawer, IconButton, Icon } from "@mui/material"; //Интерфейсные элементы +import { ApplicationСtx } from "../../context/application"; //Контекст приложения +import { BackEndСtx } from "../../context/backend"; //Контекст взаимодействия с сервером +import { MessagingСtx } from "../../context/messaging"; //Контекст сообщений +import { TEXTS } from "../../../app.text"; //Тектовые ресурсы и константы +import { P8PDataGrid, P8P_DATA_GRID_SIZE } from "../../components/p8p_data_grid"; //Таблица данных +import { P8PChart } from "../../components/p8p_chart"; //График +import { P8PAppInlineError } from "../../components/p8p_app_message"; //Встраиваемое сообщение об ошибке +import { P8P_DATA_GRID_CONFIG_PROPS } from "../../config_wrapper"; //Подключение компонентов к настройкам приложения +import { useStageDetailInfoDataGrid, useStageDetailArtsDataGrid, useStageDetailArtsChart } from "./stage_detail_hooks"; //Хуки детализации этапов проекта +import { Toggle } from "./layouts"; //Общая разметка и компоненты панели +import { + STAGE_DETAIL_STYLES, + stageDetailInfoHeadCellRender, + stageDetailInfoDataCellRender, + stageDetailArtsHeadCellRender, + stageDetailArtsDataCellRender +} from "./stage_detail_layouts"; //Дополнительная разметка и вёрстка клиентских элементов + +//------------------------------------ +//Вспомогательные функции и компоненты +//------------------------------------ + +//Данные этапа +const StageDetailData = ({ stageRn }) => { + //Собственное состояние + const [state, setState] = useState({ artsDisplayType: 0, artsChartType: 0 }); + + //Подключение к контексту взаимодействия с сервером + const { executeStored } = useContext(BackEndСtx); + + //Подключение к контексту приложения + const { pOnlineShowUnit } = useContext(ApplicationСtx); + + //Подключение к контексту сообщений + const { showMsgErr } = useContext(MessagingСtx); + + //Отображение журнала затрат (фактического, по рег. номеру ЛС и статьи затрат) + const showCostNotesFact = async ({ faceAccRn, artclRn }) => { + const data = await executeStored({ + stored: "PKG_P8PANELS_PROJECTS.INFO_FCCOSTNOTES_FACT_SELECT", + args: { NFACEACC: faceAccRn, NFPDARTCL: artclRn } + }); + if (data.NIDENT) pOnlineShowUnit({ unitCode: "CostNotes", inputParameters: [{ name: "in_IDENT", value: data.NIDENT }] }); + else showMsgErr(TEXTS.NO_DATA_FOUND); + }; + + //Состояние таблицы с информацией об этапе + const [stageDeatilInfoDataGrid] = useStageDetailInfoDataGrid({ stageRn }); + + //Состояние таблицы с данными структуры цены + const [stageDeatilArtsDataGrid] = useStageDetailArtsDataGrid({ stageRn }); + + //Состояние графика с данными структуры цены + const [stageDeatilArtsChart] = useStageDetailArtsChart({ stageRn, display: state.artsDisplayType == 1, type: state.artsChartType }); + + //При изменении способа отображения структуры цены + const handleArtsDisplayTypeChange = checked => setState(pv => ({ ...pv, artsDisplayType: checked ? 1 : 0 })); + + //При изменении типа данных графика структуры цены + const handleArtsChartTypeChange = checked => setState(pv => ({ ...pv, artsChartType: checked ? 1 : 0 })); + + //Отработка нажатия на график + const handleChartClick = ({ item }) => + state.artsChartType === 1 && item.NFACEACC && item.NFPDARTCL + ? showCostNotesFact({ faceAccRn: item.NFACEACC, artclRn: item.NFPDARTCL }) + : null; + + //Генерация содержимого + return ( + + + + Сведения + + {stageDeatilInfoDataGrid.init ? ( + + ) : null} + + + + + Структура цены + + + + {state.artsDisplayType === 0 ? ( + stageDeatilArtsDataGrid.init ? ( + stageDetailArtsDataCellRender({ ...prms, showCostNotesFact })} + /> + ) : null + ) : ( + + + + {stageDeatilArtsDataGrid?.rows?.length > 0 ? ( + stageDeatilArtsChart.init ? ( + + ) : null + ) : ( + + )} + + + )} + + + ); +}; + +//Контроль свойств компонента - Данные этапа +StageDetailData.propTypes = { + stageRn: PropTypes.number +}; + +//----------- +//Тело модуля +//----------- + +//Детальная информация об этапе проекта +const StageDetail = ({ stageRn, stageName, isOpen, onClose }) => { + return ( + + + + close + + {`Этап: ${stageName}`} + + + + ); +}; + +//Контроль свойств компонента - Детальная информация об этапе проекта +StageDetail.propTypes = { + stageRn: PropTypes.number, + stageName: PropTypes.string, + isOpen: PropTypes.bool.isRequired, + onClose: PropTypes.func +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { StageDetail }; diff --git a/app/panels/prj_info/stage_detail_hooks.js b/app/panels/prj_info/stage_detail_hooks.js new file mode 100644 index 0000000..0a7563a --- /dev/null +++ b/app/panels/prj_info/stage_detail_hooks.js @@ -0,0 +1,126 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Детальная информация об этапе проекта: пользовательские хуки для взаимодействия с сервером +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import { useState, useContext, useEffect } from "react"; //Классы React +import { BackEndСtx } from "../../context/backend"; //Контекст взаимодействия с сервером + +//----------- +//Тело модуля +//----------- + +//Детали этапа проекта - информация об этапе +const useStageDetailInfoDataGrid = ({ stageRn }) => { + //Собственное состояние - флаг загрузки + const [isLoading, setLoading] = useState(false); + + //Собственное состояние - таблица данных + const [data, setData] = useState({ init: false }); + + //Подключение к контексту взаимодействия с сервером + const { executeStored } = useContext(BackEndСtx); + + //При необходимости обновить данные таблицы + useEffect(() => { + //Загрузка данных таблицы с сервера + const loadData = async () => { + try { + setLoading(true); + const data = await executeStored({ + stored: "PKG_P8PANELS_PROJECTS.INFO_STAGE_DTL_DG", + args: { NPROJECTSTAGE: stageRn }, + respArg: "COUT", + loader: true + }); + setData(pv => ({ ...pv, ...data.XDATA_GRID, init: true })); + } finally { + setLoading(false); + } + }; + if (stageRn) loadData(); + }, [stageRn, executeStored]); + + //Возвращаем интерфейс хука + return [data, isLoading]; +}; + +//Детали этапа проекта - структура цены - таблица данных +const useStageDetailArtsDataGrid = ({ stageRn }) => { + //Собственное состояние - флаг загрузки + const [isLoading, setLoading] = useState(false); + + //Собственное состояние - таблица данных + const [data, setData] = useState({ init: false }); + + //Подключение к контексту взаимодействия с сервером + const { executeStored, SERV_DATA_TYPE_CLOB } = useContext(BackEndСtx); + + //При необходимости обновить данные таблицы + useEffect(() => { + //Загрузка данных таблицы с сервера + const loadData = async () => { + try { + setLoading(true); + const artsData = await executeStored({ + stored: "PKG_P8PANELS_PROJECTS.INFO_STAGE_ARTS_DG", + args: { NPROJECTSTAGE: stageRn }, + respArg: "COUT", + loader: true + }); + setData(pv => ({ ...pv, ...artsData.XDATA_GRID, init: true })); + } finally { + setLoading(false); + } + }; + if (stageRn) loadData(); + }, [stageRn, executeStored, SERV_DATA_TYPE_CLOB]); + + //Возвращаем интерфейс хука + return [data, isLoading]; +}; + +//Детали этапа проекта - структура цены - график +const useStageDetailArtsChart = ({ stageRn, display, type }) => { + //Собственное состояние - флаг загрузки + const [isLoading, setLoading] = useState(false); + + //Собственное состояние - график + const [data, setData] = useState({ init: false, currentType: null }); + + //Подключение к контексту взаимодействия с сервером + const { executeStored } = useContext(BackEndСtx); + + //При необходимости обновить данные таблицы + useEffect(() => { + //Загрузка данных таблицы с сервера + const loadData = async () => { + try { + setLoading(true); + const data = await executeStored({ + stored: "PKG_P8PANELS_PROJECTS.INFO_STAGE_ARTS_CHART", + args: { NPROJECTSTAGE: stageRn, NTYPE: type }, + respArg: "COUT", + loader: true + }); + setData(pv => ({ ...pv, ...data.XCHART, currentType: type, init: true })); + } finally { + setLoading(false); + } + }; + if (stageRn && display && data.currentType != type) loadData(); + }, [stageRn, display, type, data.currentType, executeStored]); + + //Возвращаем интерфейс хука + return [data, isLoading]; +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { useStageDetailInfoDataGrid, useStageDetailArtsDataGrid, useStageDetailArtsChart }; diff --git a/app/panels/prj_info/stage_detail_layouts.js b/app/panels/prj_info/stage_detail_layouts.js new file mode 100644 index 0000000..d4b22e2 --- /dev/null +++ b/app/panels/prj_info/stage_detail_layouts.js @@ -0,0 +1,148 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Детальная информация об этапе проекта: дополнительная разметка и вёрстка клиентских элементов +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React from "react"; //Классы React +import { Link } from "@mui/material"; //Интерфейсные элементы +import { APP_STYLES } from "../../../app.styles"; //Типовые стили +import { APP_BAR_HEIGHT } from "../../components/p8p_app_workspace"; //Заголовок страницы +import { formatNumberRFCurrency } from "../../core/utils"; //Вспомогательные функции +import { formatCostStatusValue } from "./layouts"; //Общие стили и разметка панели +import { formatStageStatusValue } from "./stages_layouts"; //Cтили и разметка списка этапов проекта + +//--------- +//Константы +//--------- + +//Высота заголовка информационного блока +const DATA_AREA_HEADER_HEIGHT = "52px"; + +//Стили +const STYLES = { + STAGE_DETAIL_DRAWER: { flexShrink: 0, [`& .MuiDrawer-paper`]: { width: "70%", boxSizing: "border-box", ...APP_STYLES.SCROLL } }, + STAGE_DETAIL_HEADER: { + height: APP_BAR_HEIGHT, + paddingLeft: "24px", + backgroundColor: "#1976d2", + display: "flex", + alignItems: "center", + justifyContent: "flex-start" + }, + STAGE_DETAIL_CLOSE_BUTTON: { color: "white", marginBottom: "3px" }, + DATA_AREA_CONTAINER: { paddingLeft: "10px", paddingRight: "10px" }, + DATA_AREA: { height: `calc(100vh - ${APP_BAR_HEIGHT} - ${DATA_AREA_HEADER_HEIGHT} - 10px)`, overflowY: "auto", ...APP_STYLES.SCROLL }, + DATA_AREA_HEADER_CONTAINER: { display: "flex", justifyContent: "space-between" }, + DATA_AREA_HEADER: { paddingTop: "10px", paddingBottom: "10px" }, + DATA_GRID_HEADER: { fontSize: "10pt", padding: "6px 10px" }, + DATA_GRID_CELL: value => ({ fontSize: "9pt", padding: "6px 10px", ...(value ? { color: value > 0 ? "green" : "red" } : {}) }), + CHART_CONTAINER: { paddingTop: "20px" }, + CHART: { maxHeight: "60vh", display: "flex", justifyContent: "center" } +}; + +//----------- +//Тело модуля +//----------- + +//Форматирование заголовков колонок таблицы "Сведения" +const stageDetailInfoHeadCellRender = ({ columnDef }) => { + //Инициализируем общий стиль ячеек + let cellStyle = STYLES.DATA_GRID_HEADER; + //Формирование представлений + switch (columnDef.name) { + case "SATTR": + return { cellStyle, stackProps: { justifyContent: "left" } }; + case "SVALUE": + return { cellStyle, stackProps: { justifyContent: "right" } }; + default: + return { cellStyle: cellStyle }; + } +}; + +//Форматирование ячеек строк таблицы "Сведения" +const stageDetailInfoDataCellRender = ({ row, columnDef }) => { + //Инициализируем общий стиль ячеек + let cellStyle = STYLES.DATA_GRID_CELL(); + //Формирование представлений + switch (columnDef.name) { + case "SATTR": + return { cellStyle: { ...cellStyle, color: "#1976d2" }, cellProps: { align: "left" } }; + case "SVALUE": { + const res = { cellStyle, cellProps: { align: "right" } }; + if (["NCOST_SUM", "NSTAGE_COST_SUM"].includes(row["SCODE"])) + res.data = row["SVALUE"] || row["SVALUE"] === 0 ? formatNumberRFCurrency(row["SVALUE"]) : "-"; + if (row["SCODE"] == "NSTATE") + res.data = formatStageStatusValue({ value: parseInt(row["SVALUE"]), addText: true, justifyContent: "right" }); + return res; + } + default: + return { cellStyle }; + } +}; + +//Форматирование заголовков колонок таблицы "Структура затрат" +const stageDetailArtsHeadCellRender = ({ columnDef }) => { + //Инициализируем общий стиль ячеек + let cellStyle = STYLES.DATA_GRID_HEADER; + //Формирование представлений + switch (columnDef.name) { + case "NSTATE": + return { cellStyle: { ...cellStyle, justifyContent: "center" }, stackStyle: { justifyContent: "center" } }; + default: + return { cellStyle: cellStyle }; + } +}; + +//Форматирование ячеек строк таблицы "Структура затрат" +const stageDetailArtsDataCellRender = ({ row, columnDef, showCostNotesFact }) => { + //Инициализируем общий стиль ячеек + let cellStyle = STYLES.DATA_GRID_CELL; + //Формирование представлений + switch (columnDef.name) { + case "NCOST_STATUS": + return { + cellProps: { align: "center" }, + data: formatCostStatusValue({ value: row[columnDef.name], type: 0 }) + }; + case "NPLAN_SUM": + case "NPLAN_FACT_SUM": + return { + cellStyle: cellStyle(columnDef.name == "NPLAN_FACT_SUM" ? row[columnDef.name] : null), + data: row[columnDef.name] || row[columnDef.name] === 0 ? formatNumberRFCurrency(row[columnDef.name]) : "-" + }; + case "NFACT_SUM": + return { + cellStyle: cellStyle(), + data: + row[columnDef.name] || row[columnDef.name] === 0 ? ( + row[columnDef.name] > 0 ? ( + showCostNotesFact({ faceAccRn: row["NFACEACC"], artclRn: row["NFPDARTCL"] })}> + {formatNumberRFCurrency(row[columnDef.name])} + + ) : ( + formatNumberRFCurrency(row[columnDef.name]) + ) + ) : ( + "-" + ) + }; + default: + return { cellStyle: cellStyle(), data: row[columnDef.name] }; + } +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { + STYLES as STAGE_DETAIL_STYLES, + stageDetailInfoHeadCellRender, + stageDetailInfoDataCellRender, + stageDetailArtsHeadCellRender, + stageDetailArtsDataCellRender +}; diff --git a/app/panels/prj_info/stages.js b/app/panels/prj_info/stages.js new file mode 100644 index 0000000..5db113b --- /dev/null +++ b/app/panels/prj_info/stages.js @@ -0,0 +1,95 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Список этапов проекта +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React, { useState, useContext } from "react"; //Классы React +import PropTypes from "prop-types"; //Контроль свойств компонента +import { Typography } from "@mui/material"; //Интерфейсные элементы +import { ApplicationСtx } from "../../context/application"; //Контекст приложения +import { P8PDataGrid } from "../../components/p8p_data_grid"; //Таблица данных +import { P8P_DATA_GRID_CONFIG_PROPS } from "../../config_wrapper"; //Подключение компонентов к настройкам приложения +import { useStagesDataGrid } from "./stages_hooks"; //Хуки списка этапов проекта +import { STAGES_STYLES, projectStageDataCellRender } from "./stages_layouts"; //Дополнительная разметка и вёрстка клиентских элементов +import { StageDetail } from "./stage_detail"; //Компонент "Информация об этапе проекта" + +//----------- +//Тело модуля +//----------- + +//Список этапов проекта +const Stages = ({ projectRn, projectCode }) => { + //Собственное состояние + const [stages, setStages] = useState({ pageNumber: 1, orders: [] }); + + //Состояние таблицы этапов + const [stagesDataGrid] = useStagesDataGrid({ ...stages, projectRn }); + + //Состояние информации о этапе + const [stageInfo, setStageInfo] = useState({ showInfo: false, stage: null, sFaceAcc: null }); + + //Подключение к контексту приложения + const { pOnlineShowUnit } = useContext(ApplicationСtx); + + //Отображение записи этапа проекта в штатном разделе + const showProjectStage = (prn, rn) => { + pOnlineShowUnit({ + unitCode: "Projects", + inputParameters: [ + { name: "in_RN", value: prn }, + { name: "in_STAGE_RN", value: rn } + ], + modal: false + }); + }; + + //Отображение деталей этапа + const showStageDetails = stage => setStageInfo(pv => ({ ...pv, showInfo: true, stage: stage["NRN"], sFaceAcc: stage["SFACEACC"] })); + + //При изменении количества отображаемых страниц + const handlePagesCountChanged = () => setStages(pv => ({ ...pv, pageNumber: pv.pageNumber + 1 })); + + //При изменении состояния сортировки + const handleOrderChanged = ({ orders }) => setStages(pv => ({ ...pv, orders: [...orders], pageNumber: 1 })); + + //Генерация содержимого + return stagesDataGrid.init ? ( + <> +
+ + {`Этапы проекта "${projectCode}"`} + + projectStageDataCellRender({ ...prms, showProjectStage, showStageDetails })} + /> +
+ setStageInfo(pv => ({ ...pv, showInfo: false, stage: null, sFaceAcc: null }))} + /> + + ) : null; +}; + +//Контроль свойств компонента - Список этапов проекта +Stages.propTypes = { + projectRn: PropTypes.number.isRequired, + projectCode: PropTypes.string.isRequired +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { Stages }; diff --git a/app/panels/prj_info/stages_hooks.js b/app/panels/prj_info/stages_hooks.js new file mode 100644 index 0000000..fafc828 --- /dev/null +++ b/app/panels/prj_info/stages_hooks.js @@ -0,0 +1,78 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Список этапов проекта: пользовательские хуки для взаимодействия с сервером +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import { useState, useContext, useEffect } from "react"; //Классы React +import { BackEndСtx } from "../../context/backend"; //Контекст взаимодействия с сервером +import { object2Base64XML, formatDateRF } from "../../core/utils"; //Вспомогательные функции +import config from "../../../app.config"; //Настройки приложения + +//--------- +//Константы +//--------- + +//Размер страницы данных +const DATA_GRID_PAGE_SIZE = config.SYSTEM.PAGE_SIZE; + +//----------- +//Тело модуля +//----------- + +//Этапы проекта +const useStagesDataGrid = ({ projectRn, pageNumber, orders }) => { + //Собственное состояние - флаг загрузки + const [isLoading, setLoading] = useState(false); + + //Собственное состояние - таблица данных + const [data, setData] = useState({ init: false, morePages: true }); + + //Подключение к контексту взаимодействия с сервером + const { executeStored, SERV_DATA_TYPE_CLOB } = useContext(BackEndСtx); + + //При необходимости обновить данные таблицы + useEffect(() => { + //Загрузка данных таблицы с сервера + const loadData = async () => { + try { + setLoading(true); + const data = await executeStored({ + stored: "PKG_P8PANELS_PROJECTS.INFO_STAGES_DG", + args: { + NPROJECT: projectRn, + CORDERS: { VALUE: object2Base64XML(orders, { arrayNodeName: "orders" }), SDATA_TYPE: SERV_DATA_TYPE_CLOB }, + NPAGE_NUMBER: pageNumber, + NPAGE_SIZE: DATA_GRID_PAGE_SIZE, + NINCLUDE_DEF: pageNumber == 1 ? 1 : 0 + }, + respArg: "COUT", + loader: true, + attributeValueProcessor: (name, val) => (["DBEGPLAN", "DENDPLAN"].includes(name) ? formatDateRF(val) : val) + }); + setData(pv => ({ + ...pv, + columnsDef: data.XDATA_GRID.columnsDef ? [...data.XDATA_GRID.columnsDef] : pv.columnsDef || [], + rows: pageNumber == 1 ? [...(data.XDATA_GRID.rows || [])] : [...(pv.rows || []), ...(data.XDATA_GRID.rows || [])], + morePages: DATA_GRID_PAGE_SIZE == 0 ? false : (data.XDATA_GRID.rows || []).length >= DATA_GRID_PAGE_SIZE, + init: true + })); + } finally { + setLoading(false); + } + }; + if (projectRn) loadData(); + }, [projectRn, orders, pageNumber, executeStored, SERV_DATA_TYPE_CLOB]); + + //Возвращаем интерфейс хука + return [data, isLoading]; +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { useStagesDataGrid }; diff --git a/app/panels/prj_info/stages_layouts.js b/app/panels/prj_info/stages_layouts.js new file mode 100644 index 0000000..0846ffd --- /dev/null +++ b/app/panels/prj_info/stages_layouts.js @@ -0,0 +1,86 @@ +/* + Парус 8 - Панели мониторинга - ПУП - Информация о проектах + Список этапов проекта: дополнительная разметка и вёрстка клиентских элементов +*/ + +//--------------------- +//Подключение библиотек +//--------------------- + +import React from "react"; //Классы React +import { Icon, Stack, Link } from "@mui/material"; //Интерфейсные элементы +import { formatNumberRFCurrency } from "../../core/utils"; //Спомогательные функции +import { COMMON_STYLES, formatCostStatusValue, formatCostReadyValue } from "./layouts"; //Общие стили и разметка панели + +//--------- +//Константы +//--------- + +//Стили +const STYLES = { + CONTAINER: { textAlign: "center", paddingTop: "10px", backgroundColor: "lightcyan" }, + TITLE: { fontSize: "13pt", paddingBottom: "10px" }, + DATA_GRID_CONTAINER: { backgroundColor: "lightcyan" } +}; + +//----------- +//Тело модуля +//----------- + +//Формирование значения для колонки "Состояние" этапа +const formatStageStatusValue = ({ value, addText = false, justifyContent = "center" }) => { + const [text, icon] = + value == 0 + ? ["Зарегистрирован", "app_registration"] + : value == 1 + ? ["Открыт", "lock_open"] + : value == 2 + ? ["Закрыт", "lock_outline"] + : value == 3 + ? ["Согласован", "thumb_up_alt"] + : value == 4 + ? ["Исполнение прекращено", "block"] + : ["Остановлен", "do_not_disturb_on"]; + return ( + + + {icon} + + {addText == true ? text : null} + + ); +}; + +//Форматирование ячеек таблицы "Этапы проекта" +const projectStageDataCellRender = ({ row, columnDef, showProjectStage, showStageDetails }) => { + //Формирование представлений + switch (columnDef.name) { + case "NCOST_STATUS": + return { + cellProps: { align: "center" }, + data: formatCostStatusValue({ value: row[columnDef.name], onClick: () => showStageDetails(row) }) + }; + case "NCOST_READY": + return { cellProps: { align: "center" }, data: formatCostReadyValue(row[columnDef.name]) }; + case "NSTATE": + return { cellProps: { align: "center" }, data: formatStageStatusValue({ value: row[columnDef.name] }) }; + case "SFACEACC": + return { + data: ( + showProjectStage(row["NPRN"], row["NRN"])}> + {row[columnDef.name]} + + ) + }; + case "NCOST_SUM": + return { data: formatNumberRFCurrency(row[columnDef.name]) }; + default: + return { data: row[columnDef.name] }; + } +}; + +//---------------- +//Интерфейс модуля +//---------------- + +export { STYLES as STAGES_STYLES, projectStageDataCellRender, formatStageStatusValue }; diff --git a/db/PKG_P8PANELS_PROJECTS.pck b/db/PKG_P8PANELS_PROJECTS.pck index 424a7b0..ef88481 100644 --- a/db/PKG_P8PANELS_PROJECTS.pck +++ b/db/PKG_P8PANELS_PROJECTS.pck @@ -17,6 +17,24 @@ create or replace package PKG_P8PANELS_PROJECTS as /* Типы данных - коллекция статей этапа проекта */ type TSTAGE_ARTS is table of TSTAGE_ART; + + /* Типы данных - статьи структуры цены этапа проекта (для панели "Информация о проектах") */ + type TINFO_STAGE_ART is record + ( + NRN CONTRPRCLC.RN%type, -- Рег. номер записи структуры цены + NCOST_STATUS PKG_STD.TNUMBER, -- Состояние затрат статьи (-1 - не определено, 0 - без отклонений, 1 - расходом больше 90%, 2 - перерасход) + NFACEACC FACEACC.RN%type, -- Рег. номер лицевого счёта затрат связанного этапа проекта + NFPDARTCL FPDARTCL.RN%type, -- Рег. номер статьи затрат + SFPDARTCL FPDARTCL.CODE%type, -- Код статьи затрат + NPLAN_SUM PKG_STD.TSUMM, -- Сумма затрат (план) + NFACT_SUM PKG_STD.TSUMM, -- Сумма затрат (факт) + NPLAN_FACT_SUM PKG_STD.TSUMM, -- Отклонение (план - факт) + SCURNAMES CURNAMES.INTCODE%type, -- Код валюты + NCOST_CTL boolean -- Подлежит контролю затрат + ); + + /* Типы данных - коллекция статей структуры цены этапа проекта (для панели "Информация о проектах") */ + type TINFO_STAGE_ARTS is table of TINFO_STAGE_ART; /* Отбор проектов */ procedure COND; @@ -352,7 +370,7 @@ create or replace package PKG_P8PANELS_PROJECTS as COUT out clob -- Сериализованная таблица данных ); - /* Получение списка проектов */ + /* Получение списка проектов */ procedure JB_PRJCTS_LIST ( NIDENT in number, -- Идентификатор процесса @@ -377,7 +395,7 @@ create or replace package PKG_P8PANELS_PROJECTS as COUT out clob -- Список проектов ); - /* Получение списка для детализации трудоёмкости по ФОТ периода балансировки */ + /* Получение списка для детализации трудоёмкости по ФОТ периода балансировки */ procedure JB_PERIODS_PLAN_FOT_LIST ( NJB_PERIODS in number, -- Рег. номер записи периода в буфере балансировки @@ -454,6 +472,89 @@ create or replace package PKG_P8PANELS_PROJECTS as NIDENT in out number, -- Идентификатор процесса (null - сгенерировать новый, !null - удалить старые данные и пересоздать с указанным идентификатором) NRESOURCE_STATUS out number -- Состояние ресурсов (0 - без отклонений, 1 - есть отклонения) ); + + /* Получение состояния структуры цены проекта/этапа проекта */ + function INFO_COST_STATUS_GET + ( + NPROJECT in number, -- Рег. номер проекта + NPROJECTSTAGE in number := null -- Рег. номер этапа (null - по всем) + ) return number; -- Состояние структуры цены (-1 - не определено, 0 - без отклонений, 1 - есть статьи с расходом больше 90%, 2 - есть статьи с перерасходом) + + /* Получение % готовности проекта/этапа проекта (по затратам) */ + function INFO_COST_READY_GET + ( + NPROJECT in number, -- Рег. номер проекта + NPROJECTSTAGE in number := null -- Рег. номер этапа (null - по всем) + ) return number; -- % готовности + + /* Подбор записей журнала затрат (факт) */ + procedure INFO_FCCOSTNOTES_FACT_SELECT + ( + NFACEACC in number, -- Рег. номер лицевого счета + NFPDARTCL in number, -- Рег. номер статьи затрат + NIDENT out number -- Идентификатор буфера подобранных (списка отмеченных записей, null - не найдено) + ); + + /* Поиск активной структуры цены (утвеждена или согласована, актуальна по датам, активна) */ + function INFO_CONTRPRSTRUCT_ACTIVE_FIND + ( + NPROJECTSTAGE in number -- Рег. номер этапа проекта + ) return number; -- Рег. номер записи структуры цены + + /* Список проектов (таблица данных) */ + procedure INFO_PROJECTS_DG + ( + SPRJ_TYPE in varchar2 := null, -- Мнемокод типа проекта + SINS_DEPARTMENT in varchar2 := null, -- Мнемокод штатного подразделения + NCOST_STATUS in number := 0, -- Статус структуры цены (0 - все, 1 - есть статьи с расходом больше 90%, 2 - есть статьи с перерасходом) + NSTATE in number := 0, -- Состояние (0 - все, 1 - открытые, 2 - неоткрытые, т.е. с прочими статусами) + SSEARCH in varchar2 := null, -- Строка поиска + NPAGE_NUMBER in number, -- Номер страницы (игнорируется при NPAGE_SIZE=0) + NPAGE_SIZE in number, -- Количество записей на странице (0 - все) + CORDERS in clob, -- Сортировки + NINCLUDE_DEF in number, -- Признак включения описания колонок таблицы в ответ + COUT out clob -- Сериализованная таблица данных + ); + + /* Список этапов проекта (таблица данных) */ + procedure INFO_STAGES_DG + ( + NPROJECT in number, -- Рег. номер проекта + NPAGE_NUMBER in number, -- Номер страницы (игнорируется при NPAGE_SIZE=0) + NPAGE_SIZE in number, -- Количество записей на странице (0 - все) + CORDERS in clob, -- Сортировки + NINCLUDE_DEF in number, -- Признак включения описания колонок таблицы в ответ + COUT out clob -- Сериализованная таблица данных + ); + + /* Информация об этапе проекта (таблица данных) */ + procedure INFO_STAGE_DTL_DG + ( + NPROJECTSTAGE in number, -- Рег. номер этапа проекта + COUT out clob -- Сериализованная таблица данных + ); + + /* Структура цены этапа проекта (состав статей) */ + procedure INFO_STAGE_ARTS_GET + ( + NPROJECTSTAGE in number, -- Рег. номер этапа проекта + RINFO_STAGE_ARTS out TINFO_STAGE_ARTS -- Список статей структуры цены этапа проекта + ); + + /* Структура цены этапа проекта (таблица данных) */ + procedure INFO_STAGE_ARTS_DG + ( + NPROJECTSTAGE in number, -- Рег. номер этапа проекта + COUT out clob -- Сериализованная таблица данных + ); + + /* Структура цены этапа проекта (график) */ + procedure INFO_STAGE_ARTS_CHART + ( + NPROJECTSTAGE in number, -- Рег. номер этапа проекта + NTYPE in number, -- Тип диаграммы (0 - по плану, 1 - по факту) + COUT out clob -- Сериализованный график + ); end PKG_P8PANELS_PROJECTS; / @@ -6622,5 +6723,987 @@ create or replace package body PKG_P8PANELS_PROJECTS as JB_PERIODS_RECALC(NIDENT => NIDENT, NINITIAL => 1, NRESOURCE_STATUS => NRESOURCE_STATUS); end JB_INIT; + /* Формирование подсказки для колонки "Статус структуры цены" */ + function INFO_COST_STATUS_HINT + ( + NTYPE in number -- Тип подсказки (0 - для статьи, 1 - для проекта/этапа) + ) return varchar2 -- Подсказка + is + SICON_STYLE PKG_STD.TSTRING; -- Стиль иконки + SICON PKG_STD.TSTRING; -- Иконка + begin + SICON_STYLE := 'font-family: ''Material Icons''; font-size: 0.8em;'; + SICON := 'circle'; + if (NTYPE = 0) then + return 'Контроль фактических затрат:
' || + '' || SICON || ' Перерасход - фактические затраты превышают плановые
' || + '' || SICON || ' Расход более 90% - фактические затраты составляют 90% (и более) от плановых
' || + '' || SICON || ' Без отклонений - фактические затраты менее 90% от плановых
' || + '' || SICON || ' Не определено - контроль затрат по статье не проводится'; + else + return 'Контроль фактических затрат в разрезе статей структуры цены:
' || + '' || SICON || ' Есть статьи с перерасходом - в составе структуры цены проекта/этапа есть статьи, фактические затраты по которым превышают плановые
' || + '' || SICON || ' Есть статьи с расходом более 90% - в составе структуры цены проекта/этапа есть статьи, фактические затраты по которым составляют 90% (и более) от плановых
' || + '' || SICON || ' Без отклонений - в составе структуры цены проекта/этапа все статьи, имеют объем фактических затраты менее 90% от плановых
' || + '' || SICON || ' Не определено - в составе структуры цены проекта/этапа нет статей, по которым ведется контроль затрат'; + end if; + end INFO_COST_STATUS_HINT; + + /* Формирование подсказки для колонки "Готов (%, затраты)" */ + function INFO_COST_READY_HINT + return varchar2 -- Подсказка + is + begin + return 'Процент готовности по затратам расчитывается как отношение плановой себестоимости проекта/этапа (по структуре цены) к фактической, зафиксированной на данный момент в разделе "Журнал затрат". Цветом выделены диапазоны:
' || + '30% и менее - низкая степень готовности
' || + 'От 31% до 79% - средняя степень готовности
' || + '80% и более - высокая степень готовности
'; + end INFO_COST_READY_HINT; + + /* Формирование подсказки для колонки "Состояние" */ + function INFO_STATE_HINT + return varchar2 -- Подсказка + is + SCONT_STYLE PKG_STD.TSTRING; -- Стиль контейнера + SICON_STYLE PKG_STD.TSTRING; -- Стиль иконки + begin + SCONT_STYLE := 'display: flex; align-items: center;'; + SICON_STYLE := 'font-family: ''Material Icons''; font-size: 1.5em;'; + return 'app_registration - Зарегистрирован' || + 'lock_open - Открыт' || + 'do_not_disturb_on - Остановлен' || + 'lock_outline - Закрыт' || + 'thumb_up_alt - Согласован' || + 'block - Исполнение прекращено'; + end INFO_STATE_HINT; + + /* Получение состояния структуры цены проекта/этапа проекта */ + function INFO_COST_STATUS_GET + ( + NPROJECT in number, -- Рег. номер проекта + NPROJECTSTAGE in number := null -- Рег. номер этапа (null - по всем) + ) return number -- Состояние структуры цены (-1 - не определено, 0 - без отклонений, 1 - есть статьи с расходом больше 90%, 2 - есть статьи с перерасходом) + is + RINFO_STAGE_ARTS TINFO_STAGE_ARTS; -- Список статей структуры цены + NRES PKG_STD.TNUMBER := -1; -- Состояние структуры цены + begin + /* Обходим этапы проекта */ + for C in (select PS.RN + from PROJECTSTAGE PS + where PS.PRN = NPROJECT + and ((NPROJECTSTAGE is null) or ((NPROJECTSTAGE is not null) and (PS.RN = NPROJECTSTAGE)))) + loop + /* Сформируем список статей структуры цены */ + INFO_STAGE_ARTS_GET(NPROJECTSTAGE => C.RN, RINFO_STAGE_ARTS => RINFO_STAGE_ARTS); + /* Обходим собранные статьи */ + if ((RINFO_STAGE_ARTS is not null) and (RINFO_STAGE_ARTS.COUNT > 0)) then + for I in RINFO_STAGE_ARTS.FIRST .. RINFO_STAGE_ARTS.LAST + loop + /* Чем хуже (выше) отклонение статьи - тем выше оно у этапа/проекта */ + if (RINFO_STAGE_ARTS(I).NCOST_STATUS > NRES) then + NRES := RINFO_STAGE_ARTS(I).NCOST_STATUS; + end if; + /* Если мы уже добрались до самого худшего отклонения - дальше можно не смотреть */ + if (NRES = 2) then + return NRES; + end if; + end loop; + end if; + end loop; + /* Возвращаем полученное состояние */ + return NRES; + end INFO_COST_STATUS_GET; + + /* Получение % готовности проекта/этапа проекта (по затратам) */ + function INFO_COST_READY_GET + ( + NPROJECT in number, -- Рег. номер проекта + NPROJECTSTAGE in number := null -- Рег. номер этапа (null - по всем) + ) return number -- % готовности + is + RINFO_STAGE_ARTS TINFO_STAGE_ARTS; -- Список статей структуры цены + NCOST_FACT PKG_STD.TLNUMBER := 0; -- Сумма фактических затрат по проекту + NCOST_PLAN PKG_STD.TLNUMBER := 0; -- Сумма плановых затрат по проекту + NRES PKG_STD.TNUMBER := 0; -- Буфер для результата + begin + /* Обходим этапы проекта */ + for C in (select PS.RN + from PROJECTSTAGE PS + where PS.PRN = NPROJECT + and ((NPROJECTSTAGE is null) or ((NPROJECTSTAGE is not null) and (PS.RN = NPROJECTSTAGE)))) + loop + /* Сформируем список статей структуры цены этапа */ + INFO_STAGE_ARTS_GET(NPROJECTSTAGE => C.RN, RINFO_STAGE_ARTS => RINFO_STAGE_ARTS); + /* Обходим собранные статьи */ + if ((RINFO_STAGE_ARTS is not null) and (RINFO_STAGE_ARTS.COUNT > 0)) then + for I in RINFO_STAGE_ARTS.FIRST .. RINFO_STAGE_ARTS.LAST + loop + /* Суммируем затраты по статьям, подлежащим котролю затрат */ + if (RINFO_STAGE_ARTS(I).NCOST_CTL) then + NCOST_PLAN := NCOST_PLAN + RINFO_STAGE_ARTS(I).NPLAN_SUM; + NCOST_FACT := NCOST_FACT + RINFO_STAGE_ARTS(I).NFACT_SUM; + end if; + end loop; + end if; + end loop; + /* Если есть и фактические затраты и плановая себестоимость */ + if ((NCOST_FACT > 0) and (NCOST_PLAN > 0)) then + /* Отношение фактических затрат к плановым - искомый % готовности */ + NRES := ROUND(NCOST_FACT / NCOST_PLAN * 100, 0); + /* Если фактические затраты превысили плановые, то % может быть > 100, но это бессмысленно в данном показателе - откорректируем ситуацию */ + if (NRES > 100) then + NRES := 100; + end if; + end if; + /* Вернём рассчитанное */ + return NRES; + end INFO_COST_READY_GET; + + /* Подбор записей журнала затрат (факт) */ + procedure INFO_FCCOSTNOTES_FACT_SELECT + ( + NFACEACC in number, -- Рег. номер лицевого счета + NFPDARTCL in number, -- Рег. номер статьи затрат + NIDENT out number -- Идентификатор буфера подобранных (списка отмеченных записей, null - не найдено) + ) + is + NSELECTLIST PKG_STD.TREF; -- Рег. номер добавленной записи буфера подобранных + begin + /* Подберём записи журнала затрат */ + for C in (select CN.COMPANY, + CN.RN + from FCCOSTNOTES CN, + FINSTATE FS + where CN.PROD_ORDER = NFACEACC + and CN.COST_ARTICLE = NFPDARTCL + and CN.COST_TYPE = FS.RN + and FS.TYPE = 1 + and exists (select null from V_USERPRIV UP where UP.CATALOG = CN.CRN)) + loop + /* Сформируем идентификатор буфера */ + if (NIDENT is null) then + NIDENT := GEN_IDENT(); + end if; + /* Добавим подобранное в список отмеченных записей */ + P_SELECTLIST_BASE_INSERT(NIDENT => NIDENT, + NCOMPANY => C.COMPANY, + NDOCUMENT => C.RN, + SUNITCODE => 'CostNotes', + SACTIONCODE => null, + NCRN => null, + NDOCUMENT1 => null, + SUNITCODE1 => null, + SACTIONCODE1 => null, + NRN => NSELECTLIST); + end loop; + end INFO_FCCOSTNOTES_FACT_SELECT; + + /* Расчет суммы фактических затрат по журналу затрат */ + function INFO_FCCOSTNOTES_FACT_GET + ( + NFACEACC in number, -- Рег. номер лицевого счета + NFPDARTCL in number -- Рег. номер статьи затрат + ) return number -- Сумма-факт по статье + is + NRES PKG_STD.TNUMBER; -- Буфер для рузультата + begin + /* Суммируем факт по лицевому счёту затрат этапа и указанной статье */ + select COALESCE(sum(CN.COST_BSUM), 0) + into NRES + from FCCOSTNOTES CN, + FINSTATE FS + where CN.PROD_ORDER = NFACEACC + and CN.COST_ARTICLE = NFPDARTCL + and CN.COST_TYPE = FS.RN + and FS.TYPE = 1; + /* Возвращаем результат */ + return NRES; + end INFO_FCCOSTNOTES_FACT_GET; + + /* Поиск активной структуры цены (утвеждена или согласована, актуальна по датам, активна) */ + function INFO_CONTRPRSTRUCT_ACTIVE_FIND + ( + NPROJECTSTAGE in number -- Рег. номер этапа проекта + ) return number -- Рег. номер записи структуры цены + is + begin + /* Подбираем актуальную по дате, активную, утверждённую или согласованную */ + for C in (select CSP.RN + from PROJECTSTAGE PS, + STAGES CS, + CONTRPRSTRUCT CSP + where PS.RN = NPROJECTSTAGE + and PS.FACEACCCUST = CS.FACEACC + and CS.RN = CSP.PRN + and CSP.SIGN_ACT = 1 + and CSP.STATE in (1, 2) + and ((CSP.DATE_FROM is null) or ((CSP.DATE_FROM is not null) and (CSP.DATE_FROM <= sysdate))) + and ((CSP.DATE_TO is null) or ((CSP.DATE_TO is not null) and (CSP.DATE_TO >= sysdate))) + order by CSP.DATE_TO desc) + loop + /* Возвращаем первую */ + return C.RN; + end loop; + /* Ничего не нашли */ + return null; + end INFO_CONTRPRSTRUCT_ACTIVE_FIND; + + /* Получение флага необходимости контроля затрат по статье */ + function INFO_FPDARTCL_COST_IS_CTL + ( + NRN in number -- Рег. номер статьи затрат + ) return boolean -- Признак необходимости контроля затрат + is + NCOMPANY PKG_STD.TREF; -- Рег. номер организации + NCTL_COST_DP PKG_STD.TREF; -- Рег. номер доп. свойства, определяющего необходимость контроля затрат по статье + begin + /* Обратимся к статье затрат */ + for C in (select T.VERSION, + T.RN + from FPDARTCL T + where T.RN = NRN) + loop + /* Определим организацию */ + FIND_COMPANY_BY_VERSION(NVERSION => C.VERSION, SUNITCODE => 'FinPlanArticles', NCOMPANY => NCOMPANY); + /* Определим дополнительные свойства - необходимость контроля затрат */ + FIND_DOCS_PROPS_CODE(NFLAG_SMART => 1, NCOMPANY => NCOMPANY, SCODE => SDP_SCTL_COST, NRN => NCTL_COST_DP); + /* Для статей, подлежащих контролю затрат */ + if (UPPER(F_DOCS_PROPS_GET_STR_VALUE(NPROPERTY => NCTL_COST_DP, SUNITCODE => 'FinPlanArticles', NDOCUMENT => C.RN)) = + UPPER(SYES)) then + return true; + end if; + end loop; + /* Нет статьи (ну или мы раньше не вышли) - нет контроля */ + return false; + end INFO_FPDARTCL_COST_IS_CTL; + + /* Список проектов (таблица данных) */ + procedure INFO_PROJECTS_DG + ( + SPRJ_TYPE in varchar2 := null, -- Мнемокод типа проекта + SINS_DEPARTMENT in varchar2 := null, -- Мнемокод штатного подразделения + NCOST_STATUS in number := 0, -- Статус структуры цены (0 - все, 1 - есть статьи с расходом больше 90%, 2 - есть статьи с перерасходом) + NSTATE in number := 0, -- Состояние (0 - все, 1 - открытые, 2 - неоткрытые, т.е. с прочими статусами) + SSEARCH in varchar2 := null, -- Строка поиска + NPAGE_NUMBER in number, -- Номер страницы (игнорируется при NPAGE_SIZE=0) + NPAGE_SIZE in number, -- Количество записей на странице (0 - все) + CORDERS in clob, -- Сортировки + NINCLUDE_DEF in number, -- Признак включения описания колонок таблицы в ответ + COUT out clob -- Сериализованная таблица данных + ) + is + NCOMPANY PKG_STD.TREF := GET_SESSION_COMPANY(); -- Организация сеанса + RO PKG_P8PANELS_VISUAL.TDG_ORDERS; -- Сортировки + RDG PKG_P8PANELS_VISUAL.TDG; -- Описание таблицы + RDG_ROW PKG_P8PANELS_VISUAL.TDG_ROW; -- Строка таблицы + NROW_FROM PKG_STD.TREF; -- Номер строки с + NROW_TO PKG_STD.TREF; -- Номер строки по + SSEARCH_PREPARED PKG_STD.TSTRING; -- Подготовленная для использования в запросе поисковая строка + CSQL clob; -- Буфер для запроса + ICURSOR integer; -- Курсор для исполнения запроса + begin + /* Читаем сортировки */ + RO := PKG_P8PANELS_VISUAL.TDG_ORDERS_FROM_XML(CORDERS => CORDERS); + /* Преобразуем номер и размер страницы в номер строк с и по */ + PKG_P8PANELS_VISUAL.UTL_ROWS_LIMITS_CALC(NPAGE_NUMBER => NPAGE_NUMBER, + NPAGE_SIZE => NPAGE_SIZE, + NROW_FROM => NROW_FROM, + NROW_TO => NROW_TO); + /* Подготовим поисковую строку для использования в запросе*/ + if (SSEARCH is not null) then + PKG_P8PANELS_BASE.UTL_SEARCH_PREPARE(SSEARCH => SSEARCH, SSEARCH_PREPARED => SSEARCH_PREPARED); + end if; + /* Инициализируем таблицу данных */ + RDG := PKG_P8PANELS_VISUAL.TDG_MAKE(); + /* Добавляем в таблицу описание колонок */ + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NRN', + SCAPTION => 'Рег. номер', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + BVISIBLE => false); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NCOST_STATUS', + SCAPTION => 'Статус', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + SHINT => INFO_COST_STATUS_HINT(NTYPE => 1), + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SCODE', + SCAPTION => 'Код', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SNAME_USL', + SCAPTION => 'Условное наименование', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SNAME', + SCAPTION => 'Наименование', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SEXT_CUST', + SCAPTION => 'Заказчик', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SDOC_OSN', + SCAPTION => 'Договор', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NSTATE', + SCAPTION => 'Состояние', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + SHINT => INFO_STATE_HINT(), + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'DBEGPLAN', + SCAPTION => 'Дата начала', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_DATE, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'DENDPLAN', + SCAPTION => 'Дата окончания', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_DATE, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NCOST_READY', + SCAPTION => 'Готов (%, затраты)', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + SHINT => INFO_COST_READY_HINT(), + BORDER => true); + /* Обходим данные */ + begin + /* Добавляем подсказку совместимости */ + CSQL := PKG_SQL_BUILD.COMPATIBLE(SSQL => CSQL); + /* Формируем запрос */ + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => 'select *'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' from (select D.*,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => PKG_SQL_BUILD.SQLROWNUM() || ' NROW'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' from (select P.RN NRN,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' P.CODE SCODE,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' P.NAME_USL SNAME_USL,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' P.NAME SNAME,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' EC.AGNABBR SEXT_CUST,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' P.DOC_OSN SDOC_OSN,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' P."STATE" NSTATE,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' P.BEGPLAN DBEGPLAN,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' P.ENDPLAN DENDPLAN,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => PKG_SQL_BUILD.PKG_NAME(SNAME => 'PKG_P8PANELS_PROJECTS.INFO_COST_STATUS_GET') || '(P.RN) NCOST_STATUS,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => PKG_SQL_BUILD.PKG_NAME(SNAME => 'PKG_P8PANELS_PROJECTS.INFO_COST_READY_GET') || '(P.RN) NCOST_READY'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' from PROJECT P'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' left outer join AGNLIST EC on P.EXT_CUST = EC.RN'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' left outer join INS_DEPARTMENT SR on P.SUBDIV_RESP = SR.RN,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' PRJTYPE PT'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' where P.COMPANY = :NCOMPANY'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and P.PRJTYPE = PT.RN'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and ((:SPRJ_TYPE is null) or ((:SPRJ_TYPE is not null) and (PT.CODE = :SPRJ_TYPE)))'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and ((:SINS_DEPARTMENT is null) or ((:SINS_DEPARTMENT is not null) and (SR.CODE = :SINS_DEPARTMENT)))'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and ((:NCOST_STATUS = 0) or ((:NCOST_STATUS <> 0) and (' || PKG_SQL_BUILD.PKG_NAME(SNAME => 'PKG_P8PANELS_PROJECTS.INFO_COST_STATUS_GET') || '(P.RN) = :NCOST_STATUS)))'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and ((:NSTATE = 0) or ((:NSTATE <> 0) and (((:NSTATE = 1) and (P.STATE = 1)) or ((:NSTATE = 2) and (P.STATE <> 1)))))'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and ((:SSEARCH_PREPARED is null) or ((:SSEARCH_PREPARED is not null) and (LOWER(P.CODE || P.NAME || P.NAME_USL || EC.AGNABBR) like LOWER(:SSEARCH_PREPARED))))'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and exists (select null from V_USERPRIV UP where UP."CATALOG" = P.CRN)'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and exists (select null from V_USERPRIV UP where UP.JUR_PERS = P.JUR_PERS and UP.UNITCODE = ' || PKG_SQL_BUILD.WRAP_STR(SVALUE => 'Projects') || ')'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' %ORDER_BY%) D) F'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' where F.NROW between :NROW_FROM and :NROW_TO'); + /* Учтём сортировки */ + PKG_P8PANELS_VISUAL.TDG_ORDERS_SET_QUERY(RDATA_GRID => RDG, RORDERS => RO, SPATTERN => '%ORDER_BY%', CSQL => CSQL); + /* Разбираем его */ + ICURSOR := PKG_SQL_DML.OPEN_CURSOR(SWHAT => 'SELECT'); + PKG_SQL_DML.PARSE(ICURSOR => ICURSOR, SQUERY => CSQL); + /* Делаем подстановку параметров */ + PKG_SQL_DML.BIND_VARIABLE_NUM(ICURSOR => ICURSOR, SNAME => 'NCOMPANY', NVALUE => NCOMPANY); + PKG_SQL_DML.BIND_VARIABLE_STR(ICURSOR => ICURSOR, SNAME => 'SPRJ_TYPE', SVALUE => SPRJ_TYPE); + PKG_SQL_DML.BIND_VARIABLE_STR(ICURSOR => ICURSOR, SNAME => 'SINS_DEPARTMENT', SVALUE => SINS_DEPARTMENT); + PKG_SQL_DML.BIND_VARIABLE_NUM(ICURSOR => ICURSOR, SNAME => 'NCOST_STATUS', NVALUE => NCOST_STATUS); + PKG_SQL_DML.BIND_VARIABLE_NUM(ICURSOR => ICURSOR, SNAME => 'NSTATE', NVALUE => NSTATE); + PKG_SQL_DML.BIND_VARIABLE_STR(ICURSOR => ICURSOR, SNAME => 'SSEARCH_PREPARED', SVALUE => SSEARCH_PREPARED); + PKG_SQL_DML.BIND_VARIABLE_NUM(ICURSOR => ICURSOR, SNAME => 'NROW_FROM', NVALUE => NROW_FROM); + PKG_SQL_DML.BIND_VARIABLE_NUM(ICURSOR => ICURSOR, SNAME => 'NROW_TO', NVALUE => NROW_TO); + /* Описываем структуру записи курсора */ + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 1); + PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 2); + PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 3); + PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 4); + PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 5); + PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 6); + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 7); + PKG_SQL_DML.DEFINE_COLUMN_DATE(ICURSOR => ICURSOR, IPOSITION => 8); + PKG_SQL_DML.DEFINE_COLUMN_DATE(ICURSOR => ICURSOR, IPOSITION => 9); + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 10); + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 11); + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 12); + /* Делаем выборку */ + if (PKG_SQL_DML.EXECUTE(ICURSOR => ICURSOR) = 0) then + null; + end if; + /* Обходим выбранные записи */ + while (PKG_SQL_DML.FETCH_ROWS(ICURSOR => ICURSOR) > 0) + loop + /* Добавляем колонки с данными */ + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NRN', ICURSOR => ICURSOR, NPOSITION => 1, BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLS(RROW => RDG_ROW, SNAME => 'SCODE', ICURSOR => ICURSOR, NPOSITION => 2); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLS(RROW => RDG_ROW, SNAME => 'SNAME_USL', ICURSOR => ICURSOR, NPOSITION => 3); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLS(RROW => RDG_ROW, SNAME => 'SNAME', ICURSOR => ICURSOR, NPOSITION => 4); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLS(RROW => RDG_ROW, SNAME => 'SEXT_CUST', ICURSOR => ICURSOR, NPOSITION => 5); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLS(RROW => RDG_ROW, SNAME => 'SDOC_OSN', ICURSOR => ICURSOR, NPOSITION => 6); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NSTATE', ICURSOR => ICURSOR, NPOSITION => 7); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLD(RROW => RDG_ROW, SNAME => 'DBEGPLAN', ICURSOR => ICURSOR, NPOSITION => 8); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLD(RROW => RDG_ROW, SNAME => 'DENDPLAN', ICURSOR => ICURSOR, NPOSITION => 9); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NCOST_STATUS', ICURSOR => ICURSOR, NPOSITION => 10); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NCOST_READY', ICURSOR => ICURSOR, NPOSITION => 11); + /* Добавляем строку в таблицу */ + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + end loop; + /* Освобождаем курсор */ + PKG_SQL_DML.CLOSE_CURSOR(ICURSOR => ICURSOR); + exception + when others then + PKG_SQL_DML.CLOSE_CURSOR(ICURSOR => ICURSOR); + raise; + end; + /* Сериализуем описание */ + COUT := PKG_P8PANELS_VISUAL.TDG_TO_XML(RDATA_GRID => RDG, NINCLUDE_DEF => NINCLUDE_DEF); + end INFO_PROJECTS_DG; + + /* Список этапов проекта (таблица данных) */ + procedure INFO_STAGES_DG + ( + NPROJECT in number, -- Рег. номер проекта + NPAGE_NUMBER in number, -- Номер страницы (игнорируется при NPAGE_SIZE=0) + NPAGE_SIZE in number, -- Количество записей на странице (0 - все) + CORDERS in clob, -- Сортировки + NINCLUDE_DEF in number, -- Признак включения описания колонок таблицы в ответ + COUT out clob -- Сериализованная таблица данных + ) + is + NCOMPANY PKG_STD.TREF := GET_SESSION_COMPANY(); -- Организация сеанса + RO PKG_P8PANELS_VISUAL.TDG_ORDERS; -- Сортировки + RDG PKG_P8PANELS_VISUAL.TDG; -- Описание таблицы + RDG_ROW PKG_P8PANELS_VISUAL.TDG_ROW; -- Строка таблицы + NROW_FROM PKG_STD.TREF; -- Номер строки с + NROW_TO PKG_STD.TREF; -- Номер строки по + CSQL clob; -- Буфер для запроса + ICURSOR integer; -- Курсор для исполнения запроса + begin + /* Читаем сортировки */ + RO := PKG_P8PANELS_VISUAL.TDG_ORDERS_FROM_XML(CORDERS => CORDERS); + /* Преобразуем номер и размер страницы в номер строк с и по */ + PKG_P8PANELS_VISUAL.UTL_ROWS_LIMITS_CALC(NPAGE_NUMBER => NPAGE_NUMBER, + NPAGE_SIZE => NPAGE_SIZE, + NROW_FROM => NROW_FROM, + NROW_TO => NROW_TO); + /* Инициализируем таблицу данных */ + RDG := PKG_P8PANELS_VISUAL.TDG_MAKE(); + /* Добавляем в таблицу описание колонок */ + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NRN', + SCAPTION => 'Рег. номер', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + BVISIBLE => false); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NPRN', + SCAPTION => 'Рег. номер проекта', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + BVISIBLE => false); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NCOST_STATUS', + SCAPTION => 'Статус', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + SHINT => INFO_COST_STATUS_HINT(NTYPE => 1), + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SFACEACC', + SCAPTION => 'Заказ/этап', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'DBEGPLAN', + SCAPTION => 'Начало (план)', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_DATE, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'DENDPLAN', + SCAPTION => 'Окончание (план)', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_DATE, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NCOST_SUM', + SCAPTION => 'Стоимость', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SSUBDIV_RESP', + SCAPTION => 'Исполнитель', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SNAME', + SCAPTION => 'Содержание', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR, + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NCOST_READY', + SCAPTION => 'Готов (%, затраты)', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + SHINT => INFO_COST_READY_HINT(), + BORDER => true); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NSTATE', + SCAPTION => 'Состояние', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + SHINT => INFO_STATE_HINT(), + BORDER => true); + /* Обходим данные */ + begin + /* Добавляем подсказку совместимости */ + CSQL := PKG_SQL_BUILD.COMPATIBLE(SSQL => CSQL); + /* Формируем запрос */ + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => 'select *'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' from (select D.*,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => PKG_SQL_BUILD.SQLROWNUM() || ' NROW'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' from (select T.RN NRN,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' T.PRN NPRN,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' FAC.NUMB SFACEACC,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' T.BEGPLAN DBEGPLAN,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' T.ENDPLAN DENDPLAN,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' T.COST_SUM NCOST_SUM,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' (select I.CODE from INS_DEPARTMENT I where I.RN = T.SUBDIV_RESP) SSUBDIV_RESP,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' T.NAME SNAME,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => PKG_SQL_BUILD.PKG_NAME(SNAME => 'PKG_P8PANELS_PROJECTS.INFO_COST_STATUS_GET') || '(T.PRN, T.RN) NCOST_STATUS,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => PKG_SQL_BUILD.PKG_NAME(SNAME => 'PKG_P8PANELS_PROJECTS.INFO_COST_READY_GET') || '(T.PRN, T.RN) NCOST_READY,'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' T.STATE NSTATE'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' from PROJECTSTAGE T'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' left outer join FACEACC FAC on T.FACEACC = FAC.RN'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' where T.COMPANY = :NCOMPANY'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and T.PRN = :NPROJECT'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and exists (select null from V_USERPRIV UP where UP."CATALOG" = T.CRN)'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and exists (select null from V_USERPRIV UP where UP.JUR_PERS = T.JUR_PERS and UP.UNITCODE = ' || PKG_SQL_BUILD.WRAP_STR(SVALUE => 'Projects') || ')'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' %ORDER_BY%) D) F'); + PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' where F.NROW between :NROW_FROM and :NROW_TO'); + /* Учтём сортировки */ + PKG_P8PANELS_VISUAL.TDG_ORDERS_SET_QUERY(RDATA_GRID => RDG, + RORDERS => RO, + SPATTERN => '%ORDER_BY%', + CSQL => CSQL); + /* Разбираем его */ + ICURSOR := PKG_SQL_DML.OPEN_CURSOR(SWHAT => 'SELECT'); + PKG_SQL_DML.PARSE(ICURSOR => ICURSOR, SQUERY => CSQL); + /* Делаем подстановку параметров */ + PKG_SQL_DML.BIND_VARIABLE_NUM(ICURSOR => ICURSOR, SNAME => 'NCOMPANY', NVALUE => NCOMPANY); + PKG_SQL_DML.BIND_VARIABLE_NUM(ICURSOR => ICURSOR, SNAME => 'NPROJECT', NVALUE => NPROJECT); + PKG_SQL_DML.BIND_VARIABLE_NUM(ICURSOR => ICURSOR, SNAME => 'NROW_FROM', NVALUE => NROW_FROM); + PKG_SQL_DML.BIND_VARIABLE_NUM(ICURSOR => ICURSOR, SNAME => 'NROW_TO', NVALUE => NROW_TO); + /* Описываем структуру записи курсора */ + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 1); + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 2); + PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 3); + PKG_SQL_DML.DEFINE_COLUMN_DATE(ICURSOR => ICURSOR, IPOSITION => 4); + PKG_SQL_DML.DEFINE_COLUMN_DATE(ICURSOR => ICURSOR, IPOSITION => 5); + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 6); + PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 7); + PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 8); + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 9); + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 10); + PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 11); + /* Делаем выборку */ + if (PKG_SQL_DML.EXECUTE(ICURSOR => ICURSOR) = 0) then + null; + end if; + /* Обходим выбранные записи */ + while (PKG_SQL_DML.FETCH_ROWS(ICURSOR => ICURSOR) > 0) + loop + /* Добавляем колонки с данными */ + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NRN', ICURSOR => ICURSOR, NPOSITION => 1, BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NPRN', ICURSOR => ICURSOR, NPOSITION => 2); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLS(RROW => RDG_ROW, SNAME => 'SFACEACC', ICURSOR => ICURSOR, NPOSITION => 3); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLD(RROW => RDG_ROW, SNAME => 'DBEGPLAN', ICURSOR => ICURSOR, NPOSITION => 4); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLD(RROW => RDG_ROW, SNAME => 'DENDPLAN', ICURSOR => ICURSOR, NPOSITION => 5); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NCOST_SUM', ICURSOR => ICURSOR, NPOSITION => 6); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLS(RROW => RDG_ROW, SNAME => 'SSUBDIV_RESP', ICURSOR => ICURSOR, NPOSITION => 7); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLS(RROW => RDG_ROW, SNAME => 'SNAME', ICURSOR => ICURSOR, NPOSITION => 8); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NCOST_STATUS', ICURSOR => ICURSOR, NPOSITION => 9); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NCOST_READY', ICURSOR => ICURSOR, NPOSITION => 10); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_CUR_COLN(RROW => RDG_ROW, SNAME => 'NSTATE', ICURSOR => ICURSOR, NPOSITION => 11); + /* Добавляем строку в таблицу */ + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + end loop; + /* Освобождаем курсор */ + PKG_SQL_DML.CLOSE_CURSOR(ICURSOR => ICURSOR); + exception + when others then + PKG_SQL_DML.CLOSE_CURSOR(ICURSOR => ICURSOR); + raise; + end; + /* Сериализуем описание */ + COUT := PKG_P8PANELS_VISUAL.TDG_TO_XML(RDATA_GRID => RDG, NINCLUDE_DEF => NINCLUDE_DEF); + end INFO_STAGES_DG; + + /* Информация об этапе проекта (таблица данных) */ + procedure INFO_STAGE_DTL_DG + ( + NPROJECTSTAGE in number, -- Рег. номер этапа проекта + COUT out clob -- Сериализованная таблица данных + ) + is + RDG PKG_P8PANELS_VISUAL.TDG; -- Описание таблицы + RDG_ROW PKG_P8PANELS_VISUAL.TDG_ROW; -- Строка таблицы + begin + /* Инициализируем таблицу данных */ + RDG := PKG_P8PANELS_VISUAL.TDG_MAKE(); + /* Добавляем в таблицу описание колонок */ + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SCODE', + SCAPTION => 'Код', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR, + BVISIBLE => false); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SATTR', + SCAPTION => 'Атрибут', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SVALUE', + SCAPTION => 'Значение', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR); + /* Обратимся к данным этапа проекта */ + for REC in (select (select F.NUMB from FACEACC F where F.RN = T.FACEACC) SFACEACC, + trim(T.NUMB) SNUMB, + M.NAME_USL SNAME_USL, + T.NAME SNAME, + (select A.AGNABBR from AGNLIST A where A.RN = M.EXT_CUST) SEXT_CUST, + M.DOC_OSN SDOC_OSN, + (select TO_CHAR(C.DOC_DATE, 'dd.mm.yyyy') + from DOCLINKS DL, CONTRACTS C + where DL.IN_DOCUMENT = M.RN and DL.IN_UNITCODE = 'Projects' and DL.OUT_UNITCODE = 'Contracts' and C.RN = DL.OUT_DOCUMENT and ROWNUM = 1) SDOC_OSN_DATE, + M.COST_SUM NCOST_SUM, + T.COST_SUM NSTAGE_COST_SUM, + (select CUR.INTCODE from CURNAMES CUR where CUR.RN = M.CURNAMES) SCURNAMES, + (select I.CODE from INS_DEPARTMENT I where I.RN = T.SUBDIV_RESP) SSUBDIV_RESP, + (select A.AGNABBR from AGNLIST A where A.RN = T.RESPONSIBLE) SRESPONSIBLE, + TO_CHAR(T.BEGPLAN, 'dd.mm.yyyy') SBEGPLAN, + TO_CHAR(T.ENDPLAN, 'dd.mm.yyyy') SENDPLAN, + T.STATE NSTATE, + T.NAME SCONTENT, + T.NOTE SNOTE + from PROJECTSTAGE T, + PROJECT M + where T.RN = NPROJECTSTAGE + and M.RN = T.PRN) + loop + /* Формируем группу - Общие характеристики */ + PKG_P8PANELS_VISUAL.TDG_ADD_GROUP(RDATA_GRID => RDG, SNAME => 'COMMON', SCAPTION => 'Общие', BEXPANDABLE => true, BEXPANDED => true); + RDG_ROW := PKG_P8PANELS_VISUAL.TDG_ROW_MAKE(SGROUP => 'COMMON'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SFACEACC', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Заказ'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SFACEACC); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SNUMB', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Номер этапа'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SNUMB); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SNAME_USL', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Тема'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SNAME_USL); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SNAME', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Наименование'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SNAME); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SEXT_CUST', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Заказчик'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SEXT_CUST); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SDOC_OSN', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Договор'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SDOC_OSN); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SDOC_OSN_DATE', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Дата договора'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SDOC_OSN_DATE); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'NCOST_SUM', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Стоимость заказа'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.NCOST_SUM); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'NSTAGE_COST_SUM', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Стоимость этапа'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.NSTAGE_COST_SUM); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SCURNAMES', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Валюта'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SCURNAMES); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + /* Формируем группу - Контроль */ + PKG_P8PANELS_VISUAL.TDG_ADD_GROUP(RDATA_GRID => RDG, SNAME => 'CONTROL', SCAPTION => 'Контроль', BEXPANDABLE => true, BEXPANDED => true); + RDG_ROW := PKG_P8PANELS_VISUAL.TDG_ROW_MAKE(SGROUP => 'CONTROL'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SSUBDIV_RESP', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Головной исполнитель'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SSUBDIV_RESP); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SRESPONSIBLE', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Ответственный'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SRESPONSIBLE); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + /* Формируем группу - Работы */ + PKG_P8PANELS_VISUAL.TDG_ADD_GROUP(RDATA_GRID => RDG, SNAME => 'WORKS', SCAPTION => 'Работы', BEXPANDABLE => true, BEXPANDED => true); + RDG_ROW := PKG_P8PANELS_VISUAL.TDG_ROW_MAKE(SGROUP => 'WORKS'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SBEGPLAN', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Начало работ'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SBEGPLAN); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SENDPLAN', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Окончание работ'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SENDPLAN); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'NSTATE', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Состояние'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.NSTATE); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SCONTENT', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Содержание'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SCONTENT); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + /* Формируем группу - Дополнительно */ + PKG_P8PANELS_VISUAL.TDG_ADD_GROUP(RDATA_GRID => RDG, SNAME => 'EXTRA', SCAPTION => 'Дополнительно', BEXPANDABLE => true, BEXPANDED => false); + RDG_ROW := PKG_P8PANELS_VISUAL.TDG_ROW_MAKE(SGROUP => 'EXTRA'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCODE', SVALUE => 'SNOTE', BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SATTR', SVALUE => 'Примечание'); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SVALUE', SVALUE => REC.SNOTE); + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + end loop; + /* Сериализуем описание */ + COUT := PKG_P8PANELS_VISUAL.TDG_TO_XML(RDATA_GRID => RDG, NINCLUDE_DEF => 1); + end INFO_STAGE_DTL_DG; + + /* Структура цены этапа проекта (состав статей) */ + procedure INFO_STAGE_ARTS_GET + ( + NPROJECTSTAGE in number, -- Рег. номер этапа проекта + RINFO_STAGE_ARTS out TINFO_STAGE_ARTS -- Список статей структуры цены этапа проекта + ) + is + I PKG_STD.TNUMBER; -- Счётчик статей в результирующей коллекции + begin + /* Инициализируем коллекцию */ + RINFO_STAGE_ARTS := TINFO_STAGE_ARTS(); + /* Подбираем активную структуру цены этапа проекта и её обходим статьи */ + for C in (select CSPA.RN NRN, + -1 NCOST_STATUS, + PS.FACEACC NFACEACC, + A.RN NFPDARTCL, + A.CODE SFPDARTCL, + CSPA.COST_SUM NPLAN_SUM, + null NFACT_SUM, + null NPLAN_FACT_SUM, + C.INTCODE SCURNAMES + from PROJECTSTAGE PS, + STAGES CS, + FACEACC FC, + CONTRPRSTRUCT CSP, + CONTRPRCLC CSPA, + FPDARTCL A, + CURNAMES C + where PS.RN = NPROJECTSTAGE + and PS.FACEACCCUST = CS.FACEACC + and CS.FACEACC = FC.RN + and FC.CURRENCY = C.RN + and CSP.PRN = CS.RN + and CSP.RN = INFO_CONTRPRSTRUCT_ACTIVE_FIND(PS.RN) + and CSPA.PRN = CSP.RN + and CSPA.COST_ARTICLE = A.RN + and exists (select null from V_USERPRIV UP where UP.CATALOG = PS.CRN) + and exists (select null + from V_USERPRIV UP + where UP.JUR_PERS = PS.JUR_PERS + and UP.UNITCODE = 'Projects') + and exists (select null from V_USERPRIV UP where UP.CATALOG = CS.CRN) + and exists (select null + from V_USERPRIV UP + where UP.JUR_PERS = CS.JUR_PERS + and UP.UNITCODE = 'Contracts') + order by CSPA.NUMB) + loop + /* Добавим строку в коллекцию */ + RINFO_STAGE_ARTS.EXTEND(); + I := RINFO_STAGE_ARTS.LAST; + /* Наполним её значениями из хранилища */ + RINFO_STAGE_ARTS(I).NRN := C.NRN; + RINFO_STAGE_ARTS(I).NCOST_STATUS := C.NCOST_STATUS; + RINFO_STAGE_ARTS(I).NFACEACC := C.NFACEACC; + RINFO_STAGE_ARTS(I).NFPDARTCL := C.NFPDARTCL; + RINFO_STAGE_ARTS(I).SFPDARTCL := C.SFPDARTCL; + RINFO_STAGE_ARTS(I).NPLAN_SUM := C.NPLAN_SUM; + RINFO_STAGE_ARTS(I).NFACT_SUM := C.NFACT_SUM; + RINFO_STAGE_ARTS(I).NPLAN_FACT_SUM := C.NPLAN_FACT_SUM; + RINFO_STAGE_ARTS(I).SCURNAMES := C.SCURNAMES; + RINFO_STAGE_ARTS(I).NCOST_CTL := INFO_FPDARTCL_COST_IS_CTL(NRN => C.NFPDARTCL); + /* Для статей, подлежащих контролю затрат */ + if (RINFO_STAGE_ARTS(I).NCOST_CTL) then + /* Определим фактические затраты */ + RINFO_STAGE_ARTS(I).NFACT_SUM := INFO_FCCOSTNOTES_FACT_GET(NFACEACC => RINFO_STAGE_ARTS(I).NFACEACC, + NFPDARTCL => RINFO_STAGE_ARTS(I).NFPDARTCL); + /* Определим отклонение */ + RINFO_STAGE_ARTS(I).NPLAN_FACT_SUM := RINFO_STAGE_ARTS(I).NPLAN_SUM - RINFO_STAGE_ARTS(I).NFACT_SUM; + /* Определим статус затрат - если сумма фактических затрат больше плановых - это перерасход*/ + if (RINFO_STAGE_ARTS(I).NFACT_SUM > RINFO_STAGE_ARTS(I).NPLAN_SUM) then + RINFO_STAGE_ARTS(I).NCOST_STATUS := 2; + else + /* Если отношение факт/план >= 0.9 - опасность */ + if ((RINFO_STAGE_ARTS(I).NPLAN_SUM <> 0) and + (RINFO_STAGE_ARTS(I).NFACT_SUM / RINFO_STAGE_ARTS(I).NPLAN_SUM >= 0.9)) then + RINFO_STAGE_ARTS(I).NCOST_STATUS := 1; + else + /* Отклонений нет */ + RINFO_STAGE_ARTS(I).NCOST_STATUS := 0; + end if; + end if; + end if; + end loop; + end INFO_STAGE_ARTS_GET; + + /* Структура цены этапа проекта (таблица данных) */ + procedure INFO_STAGE_ARTS_DG + ( + NPROJECTSTAGE in number, -- Рег. номер этапа проекта + COUT out clob -- Сериализованная таблица данных + ) + is + RINFO_STAGE_ARTS TINFO_STAGE_ARTS; -- Список статей структуры цены + RDG PKG_P8PANELS_VISUAL.TDG; -- Описание таблицы + RDG_ROW PKG_P8PANELS_VISUAL.TDG_ROW; -- Строка таблицы + begin + /* Инициализируем таблицу данных */ + RDG := PKG_P8PANELS_VISUAL.TDG_MAKE(); + /* Добавляем в таблицу описание колонок */ + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NRN', + SCAPTION => 'Рег. номер', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + BVISIBLE => false); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NCOST_STATUS', + SCAPTION => 'Статус', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + SHINT => INFO_COST_STATUS_HINT(NTYPE => 0)); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NFACEACC', + SCAPTION => 'Рег. номер лицевого счета затрат', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + BVISIBLE => false); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NFPDARTCL', + SCAPTION => 'Рег. номер статьи', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB, + BVISIBLE => false); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SFPDARTCL', + SCAPTION => 'Статья', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NPLAN_SUM', + SCAPTION => 'План', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NFACT_SUM', + SCAPTION => 'Факт', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'NPLAN_FACT_SUM', + SCAPTION => 'Отклонение', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_NUMB); + PKG_P8PANELS_VISUAL.TDG_ADD_COL_DEF(RDATA_GRID => RDG, + SNAME => 'SCURNAMES', + SCAPTION => 'Валюта', + SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR); + /* Сформируем список статей структуры цены */ + INFO_STAGE_ARTS_GET(NPROJECTSTAGE => NPROJECTSTAGE, RINFO_STAGE_ARTS => RINFO_STAGE_ARTS); + /* Обходим собранные статьи */ + if ((RINFO_STAGE_ARTS is not null) and (RINFO_STAGE_ARTS.COUNT > 0)) then + for I in RINFO_STAGE_ARTS.FIRST .. RINFO_STAGE_ARTS.LAST + loop + /* Добавляем колонки с данными */ + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, + SNAME => 'NRN', + NVALUE => RINFO_STAGE_ARTS(I).NRN, + BCLEAR => true); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, + SNAME => 'NCOST_STATUS', + NVALUE => RINFO_STAGE_ARTS(I).NCOST_STATUS); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'NFACEACC', NVALUE => RINFO_STAGE_ARTS(I).NFACEACC); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'NFPDARTCL', NVALUE => RINFO_STAGE_ARTS(I).NFPDARTCL); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SFPDARTCL', SVALUE => RINFO_STAGE_ARTS(I).SFPDARTCL); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'NPLAN_SUM', NVALUE => RINFO_STAGE_ARTS(I).NPLAN_SUM); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'NFACT_SUM', NVALUE => RINFO_STAGE_ARTS(I).NFACT_SUM); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, + SNAME => 'NPLAN_FACT_SUM', + NVALUE => RINFO_STAGE_ARTS(I).NPLAN_FACT_SUM); + PKG_P8PANELS_VISUAL.TDG_ROW_ADD_COL(RROW => RDG_ROW, SNAME => 'SCURNAMES', SVALUE => RINFO_STAGE_ARTS(I).SCURNAMES); + /* Добавляем строку в таблицу */ + PKG_P8PANELS_VISUAL.TDG_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW); + end loop; + end if; + /* Сериализуем описание */ + COUT := PKG_P8PANELS_VISUAL.TDG_TO_XML(RDATA_GRID => RDG, NINCLUDE_DEF => 1); + end INFO_STAGE_ARTS_DG; + + /* Структура цены этапа проекта (график) */ + procedure INFO_STAGE_ARTS_CHART + ( + NPROJECTSTAGE in number, -- Рег. номер этапа проекта + NTYPE in number, -- Тип диаграммы (0 - по плану, 1 - по факту) + COUT out clob -- Сериализованный график + ) + is + RINFO_STAGE_ARTS TINFO_STAGE_ARTS; -- Список статей структуры цены + RCH PKG_P8PANELS_VISUAL.TCHART; -- График + RCH_DS PKG_P8PANELS_VISUAL.TCHART_DATASET; -- Набор данных + RATTR_VALS PKG_P8PANELS_VISUAL.TCHART_DATASET_ITEM_ATTR_VALS; -- Атрибуты элемента набора данных + begin + /* Сформируем заголовок графика */ + RCH := PKG_P8PANELS_VISUAL.TCHART_MAKE(STYPE => PKG_P8PANELS_VISUAL.SCHART_TYPE_PIE, + SLGND_POS => PKG_P8PANELS_VISUAL.SCHART_LGND_POS_RIGHT); + /* Сформируем набор данных графика */ + RCH_DS := PKG_P8PANELS_VISUAL.TCHART_DATASET_MAKE(SCAPTION => 'Сумма'); + /* Сформируем список статей структуры цены */ + INFO_STAGE_ARTS_GET(NPROJECTSTAGE => NPROJECTSTAGE, RINFO_STAGE_ARTS => RINFO_STAGE_ARTS); + /* Обходим собранные статьи */ + if ((RINFO_STAGE_ARTS is not null) and (RINFO_STAGE_ARTS.COUNT > 0)) then + for I in RINFO_STAGE_ARTS.FIRST .. RINFO_STAGE_ARTS.LAST + loop + /* Только статьи, подлежащие контролю затрат */ + if (INFO_FPDARTCL_COST_IS_CTL(NRN => RINFO_STAGE_ARTS(I).NFPDARTCL)) then + /* Добавим метку для статьи */ + PKG_P8PANELS_VISUAL.TCHART_ADD_LABEL(RCHART => RCH, SLABEL => RINFO_STAGE_ARTS(I).SFPDARTCL); + /* Сформируем дополнительные атрибуты для клиентского приложения - лицевой счет и рег. номер статьи затрат (будут применяться при открытии ЖЗ)*/ + PKG_P8PANELS_VISUAL.TCHART_DATASET_ITM_ATTR_VL_ADD(RATTR_VALS => RATTR_VALS, + SNAME => 'NFACEACC', + SVALUE => TO_CHAR(RINFO_STAGE_ARTS(I).NFACEACC), + BCLEAR => true); + PKG_P8PANELS_VISUAL.TCHART_DATASET_ITM_ATTR_VL_ADD(RATTR_VALS => RATTR_VALS, + SNAME => 'NFPDARTCL', + SVALUE => TO_CHAR(RINFO_STAGE_ARTS(I).NFPDARTCL)); + /* Исходим от типа диаграммы */ + if (NTYPE = 0) then + /* Добавим данные по плану */ + PKG_P8PANELS_VISUAL.TCHART_DATASET_ADD_ITEM(RDATASET => RCH_DS, + NVALUE => RINFO_STAGE_ARTS(I).NPLAN_SUM, + RATTR_VALS => RATTR_VALS); + else + /* Добавим данные по факту */ + PKG_P8PANELS_VISUAL.TCHART_DATASET_ADD_ITEM(RDATASET => RCH_DS, + NVALUE => RINFO_STAGE_ARTS(I).NFACT_SUM, + RATTR_VALS => RATTR_VALS); + end if; + end if; + end loop; + end if; + /* Добавим набор данных в график */ + PKG_P8PANELS_VISUAL.TCHART_ADD_DATASET(RCHART => RCH, RDATASET => RCH_DS); + /* Сериализуем описание */ + COUT := PKG_P8PANELS_VISUAL.TCHART_TO_XML(RCHART => RCH, NINCLUDE_DEF => 1); + end INFO_STAGE_ARTS_CHART; + end PKG_P8PANELS_PROJECTS; / diff --git a/img/prj_info.jpg b/img/prj_info.jpg new file mode 100644 index 0000000000000000000000000000000000000000..dd39446aeefc2bb7146dd7a52ddb238a6e509414 GIT binary patch literal 136923 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%0DT($@Y}@K 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ℑsuUJj1=a2Ta2;Z~W3#U#%{AA=F^6Z?T2p&K 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 A=Kufz literal 0 HcmV?d00001 diff --git a/p8panels.config b/p8panels.config index 2f6647b..0fb505c 100644 --- a/p8panels.config +++ b/p8panels.config @@ -8,6 +8,7 @@ + @@ -59,6 +60,16 @@ icon="insights" showInPanelsList="true" preview="./img/prj_graph.jpg"/> +