Перейти к группе записей

А каким образом можно было бы переходить не только к одной записи по ID, а к группе записей?
Например, из контактов "Перейти к невыполненным задачам по контакту"

Особенно интересно это было бы делать из "Итогов". Потому что одно дело - это видеть обобщенную информацию, а другое - это сразу ее расскрывать.

Нравится

15 комментариев

Здравствуйте!

Для реализации данной функциональности Вам необходимо выполнить некоторые изменения в скрипте.

1. scr_BaseGridArea
a. Изменить функцию GotoReference:

function GotoReference(ActionMenuItem) {
                var SelectedIDsArray = GetGridSelectedIDsArray();
                GotoWorkspaceByActionMenuItem(ActionMenuItem, dlData.Dataset, SelectedIDsArray);
}   

// плюс создать функцию:

function GetGridSelectedIDsArray() {
                if (!Assigned(grdData) && !Assigned(BaseGridArea.Grid)) {
                               return null;
                } else {
                               if (!Assigned(BaseGridArea.Grid)) {
                                               BaseGridArea.Grid = grdData;
                               }
                }
                if (BaseGridArea.Grid.SelectedIDs.Count == 0) {
                               return null;
                }
                var SelectedIDsArray = new Array();
                for (var i = 0; i < BaseGridArea.Grid.SelectedIDs.Count; i++) {
                               SelectedIDsArray.push(BaseGridArea.Grid.SelectedIDs.Items(i));
                }
                return SelectedIDsArray;
}

2. scr_WindowUtils
a. Изменить функцию GotoWorkspaceByActionMenuItem (добавить еще один параметр SelectedIDsArray):

function GotoWorkspaceByActionMenuItem(ActionMenuItem, Dataset, SelectedIDsArray) {
               var ReferenceInfo = ActionMenuItem.Tag.split(',');
               var WorkspaceWindowUSI = ReferenceInfo[0];
               var DataFieldName = ReferenceInfo[1];
               GotoWorkspaceByReferenceInfo(Dataset, DataFieldName,
                               WorkspaceWindowUSI, SelectedIDsArray);
}

b. Изменить функцию GotoWorkspaceByReferenceInfo

function GotoWorkspaceByReferenceInfo(Dataset, DataFieldName,
                               WorkspaceWindowUSI, SelectedIDsArray) {
                if (IsDatasetEmpty(Dataset)){
                               var Message = "Запись не выделена";
                               ShowInformationDialog(Message);
                               return;
                }
                var DataFieldValue;
                if (!Assigned(SelectedIDsArray)) {
                               DataFieldValue = GetFieldValueFromDisabledField(Dataset, DataFieldName);
                               if (!IsEmptyGUID(DataFieldValue)) {
                                               GotoWorkspace(WorkspaceWindowUSI, DataFieldValue);
                                               return;
                               }
                } else {
                               DataFieldValuesArray = new Array();
                               var FieldValue;
                               Dataset.DisableEvents();
                               try {
                                               for (var i = 0; i < SelectedIDsArray.length; i++) {
                                                               Dataset.Locate('ID', SelectedIDsArray[i]);
                                                               FieldValue = GetFieldValueFromDisabledField(Dataset, DataFieldName);
                                                               if (IsEmptyValue(FieldValue)) {
                                                                              continue;
                                                               }
                                                               var IsValueExists = false;
                                                               for (var j = 0; j < DataFieldValuesArray.length; j++) {
                                                                              if (DataFieldValuesArray[j] == FieldValue) {
                                                                                              IsValueExists = true;
                                                                                              break;
                                                                              }
                                                               }
                                                               if (!IsValueExists) {
                                                                              DataFieldValuesArray.push(FieldValue);
                                                               }              
                                               }
                               } finally {              
                                               Dataset.EnableEvents();
                               }              
                               if (DataFieldValuesArray.length > 0) {
                                               GotoWorkspace(WorkspaceWindowUSI, DataFieldValuesArray);
                                               return;
                               }
                }              
                var DataField = Dataset.DataFields(DataFieldName);
                var Message = FormatStr("Поле %1 пусто или Вы не имеете прав для чтения",
                               DataField.Caption);
                ShowInformationDialog(Message);
}

3. scr_Main
a. Изменить функцию FilterByID

function FilterByID(WorkspaceWindow, IDDataFieldValue) {
               var FBControl = WorkspaceWindow.ComponentsByName('fbcFilters');
               var Dataset = FBControl.DatasetLink.Dataset;
               FBControl.FiltersBuilder.ClearFilter();
               var IDDataField = Dataset.DataFields.ItemsByName('ID');
               var FirstIDValue;
               if (typeof(IDDataFieldValue) == 'object') {
                               FirstIDValue = IDDataFieldValue[0];
                               for (var i = 0; i < IDDataFieldValue.length; i++) {
                                              var FBItem = FBControl.FiltersBuilder.RootItems.CreateItemByDataField(
                                                              IDDataField);
                                              FBItem.Value = IDDataFieldValue[i];
                                              FBItem.Operator = totEqual;
                                              FBItem.LogicalOperator = lotOr;
                                              FBControl.FiltersBuilder.RootItems.Add(FBItem);
                               }
               } else {
                               FirstIDValue = IDDataFieldValue;
                               var FBItem = FBControl.FiltersBuilder.RootItems.CreateItemByDataField(
                                              IDDataField);
                               FBItem.Value = IDDataFieldValue;
                               FBItem.Operator = totEqual;
                               FBControl.FiltersBuilder.RootItems.Add(FBItem);
               }
               EnableDatasetFilters(Dataset, false);
               FBControl.ApplyFilter();
               FBControl.Refresh();
               SetAttribute(WorkspaceWindow, IsInSingleRowModeAttrName, true);
               RefreshDataset(Dataset);
               Dataset.Locate('ID', FirstIDValue);
               SetAttribute(WorkspaceWindow, IsInSingleRowModeAttrName, false);
}

Terrasoft Support Team

Спасибо!

Эффект интересный, но немного не тот, о котором я спрашивал.
В принципе, то, что я спрашивал - это небольшая автоматизация выбора динамического/статического фильтров и быстрого поиска.

То есть, можно открыть "Задачи", выбрать фильтр "невыполненные задачи" и задать быстрый фильтр по нужному контакту. И это я хотел бы реализовать в виде простого перехода из раздела "Итоги"

Добрый день!
При создании подобного перехода из раздела "Итоги" могут возникнуть сложности в реализации, так как само создание меню для перехода "тянет" за собой сразу несколько доработок. Попробую по порядку:

  1. Раздел итоги создается динамически, в процессе работы приложения в зависимости от настроек. Таким образом, могут формироваться любые реестры, даже в которых не присутствует поле "Контакт". Значит, меню формировать нужно не для всех реестров, а для определенных. Соответственно, нужно хранить где-то признак формировать меню или нет. Вероятнее всего, делать надо в настройке итогов.
  2. Для формирования реестра служит окно wnd_UserReportView. В скрипте этого окна нужно сделать динамическую генерацию самого меню и его пунктов, а так же динамически связать функцию перехода с событием нажатия пункта меню.
  3. Реализовать саму функцию перехода.

Вот такой общий алгоритм реализации поставленной задачи.

Здравствуйте,

А возможно ли сделать переход от Контрагента в раздел Котакты, где записи отфильтрованы по Контрагенту, из контекстного меню которого делается переход?

делала что-то похожее, не очень хороший способ, может, кто-то лучше предложит

var MainWindow = Connector.Attributes('MainWindow');
	MainWindow.ScriptControl.Run('ShowGroupWorkspace', '', 'wnd_DocumentsWorkspace',
		null, true, new Array('AccountID', 'DocumentTypeID', 'IsTemplate'), 
		new Array(AccountID, WaterAnalisDocumentTypeID, false));

для этого пришлось добавить в функцию ShowGroupWorkspace() еще два входящих параметра и в конце добавить условие

function ShowGroupWorkspace(GroupCode, WorkspaceUSI, IDDataFieldValue,
		AddHistory, FilterParamNames, FilterParamValues) {
	if (!GetIsWorkspaceAllowed(WorkspaceUSI)) {
		ShowWarningDialog("Текущий пользователь не имеет достаточно прав для просмотра данных");
		SlipGoBack();
		return;
	}
	if (!CheckX15ExcludedWorkspaces(WorkspaceUSI)) {
		return;
	}
	if ((WorkspaceUSI == 'wnd_OLAPWorkspace') && 
		(!GetIsOLAPControlIstalled())) {
		ShowWarningDialog("OLAP компонент не установлен в системе");
		var GroupActionMenuItem = GetCheckedActionMenuItem(amWorkspace);
		var ActionMenuItem = GetActionMenuItemByTag(GroupActionMenuItem,
			Main.PriorOldActionMenuItemTag);
		Main.OldActionMenuItemTag = Main.PriorOldActionMenuItemTag;
		ShowGroupWorkspace(GroupActionMenuItem.Tag, ActionMenuItem.Tag, null,
			true);
		return;
	}
	Main.WorkspaceUSI = WorkspaceUSI;
	var GroupItemValue = GetNewValue();
	var WorkspaceItemValue = GetNewValue();
	GetWorkspaceActionMenuItem(GroupCode, WorkspaceUSI,
		GroupItemValue, WorkspaceItemValue);
	var GroupActionMenuItem = GroupItemValue.Value;
	Main.GroupCode = GroupCode;
	var WorkspaceActionMenuItem = WorkspaceItemValue.Value;
	if ((!Assigned(GroupActionMenuItem)) ||
		(!Assigned(WorkspaceActionMenuItem))) {
		throw FormatStr("Модуль%1 не найден", WorkspaceUSI);
	}
	WorkspaceActionMenuItem.IsChecked = true;
	var WorkspaceWindow = GetWorkspaceByUSI(WorkspaceUSI);
	if ((!Assigned(wndWorkspace.Window)) ||
		(!wndWorkspace.Window.Equal(WorkspaceWindow))) {
		wndWorkspace.Window = WorkspaceWindow;
		if (WorkspaceUSI == 'wnd_DashboardView') {
			wndWorkspace.Window.Prepare();
		}
		if (AddHistory && !Main.DoNotUpdateHistory) {
			AddWorkspacesHistory(GroupActionMenuItem.Tag,
				WorkspaceActionMenuItem.Tag);
		}
	}
	<strong>if (IDDataFieldValue != null) {
		System.BeginProcessing();
		try {
			FilterWorkspace(WorkspaceWindow, IDDataFieldValue)
		}
		finally {
			System.EndProcessing();
		}
	} else
	if (Assigned(FilterParamNames)&&Assigned(FilterParamValues)) {
		FilterWorkspaceByParamSet(WorkspaceWindow, FilterParamNames, FilterParamValues);
	}
}</strong>

в случае, если поле, по которому накладывается фильтр, не ID, вызывается функция FilterWorkspaceByParamSet()

function FilterWorkspaceByParamSet(WorkspaceWindow, ParamNames, ParamValues) {
	var FBControl = WorkspaceWindow.ComponentsByName('fbcFilters');
	var Dataset = FBControl.DatasetLink.Dataset;
	FBControl.FiltersBuilder.ClearFilter();
	for (var i = 0; i < ParamNames.length; i++) {
		var IDDataField = Dataset.DataFields.ItemsByName(ParamNames[i]);
		var FBItem = FBControl.FiltersBuilder.RootItems.CreateItemByDataField(
			IDDataField);
		if (typeof(FBItem.Value) == 'boolean') {
			FBItem.Value = ParamValues[i];
		} else 
		if (typeof(FBItem.Value) == 'object') {
			FBItem.Value.Add(ParamValues[i]);
			FBItem.Operator = totEqual;
		}
		FBControl.FiltersBuilder.RootItems.Add(FBItem);
	}
	EnableDatasetFilters(Dataset, false);
	FBControl.ApplyFilter();
	FBControl.Refresh();
	SetAttribute(WorkspaceWindow, IsInSingleRowModeAttrName, true);
	RefreshDataset(Dataset);
	SetAttribute(WorkspaceWindow, IsInSingleRowModeAttrName, false);
}

только, кажется, я предполагала фильтрацию по IDшникам и булевским полям

фильтровали документы по контрагенту?

в данном примере документы по контагенту + по типу документа + по логическому полю "Шаблон", чтобы перейти к контактам, отфильтрованным по контрагенту, в обработчике события нажатия пункта контекстного меню нужно вызвать ShowGroupWorkspace() с такими параметрами:

var MainWindow = Connector.Attributes('MainWindow');
        MainWindow.ScriptControl.Run('ShowGroupWorkspace', '', 'wnd_ContactsWorkspace',
                null, true, new Array('AccountID'),
                new Array(AccountID));
var MainWindow = Connector.Attributes('MainWindow');
        MainWindow.ScriptControl.Run('ShowGroupWorkspace', '', 'wnd_DocumentsWorkspace',
                null, true, new Array('AccountID', 'DocumentTypeID', 'IsTemplate'),
                new Array(AccountID, WaterAnalisDocumentTypeID, false));

а эту часть кода где необходимо написать?

ой, уже на все ответили))
спасибо!!!

а сам пункт меню находится в подпункте "Перейти к"? Если да, то как это реализовано? Насколько мне известно, этот список формируется автоматически, руками ничего не добавить(

список формируется автоматически, но он добавляет к пункту контекстного меню amiGoto подпункты, которые определяет из датасета, поэтому, если Вы добавите вручную подпункт, он не исчезнет, просто после него появятся новые
также можно создавать новый подпункт динамически

function amGridOnPrepare(ActionMenu, Control) {
	Initialize(ActionMenu.ParentWindow);
	scr_BaseGridArea.amGridOnPrepare(ActionMenu, Control);
 
	if (!Assigned(Self.ComponentsByName('amiTest'))){
		var ActionMenuItem = Self.CreateComponent('ActionMenuItem', 'amiTest');
		ActionMenuItem.Caption = FormatStr("'%1'", 'Caption');
		ActionMenuItem.Tag = 'wnd_AccountsWorkspace' + ',' + 'Contacts';
		amiGoto.AddItem(ActionMenuItem);
		SetObjectEventDispatcher(amiGoto.ParentWindow, ActionMenuItem,
			ActionMenuItem.Name, 'OnExecute', 'amiTestOnExecute');
	}
}
 
function amiTestOnExecute() {
	Log.Write(1, 'test');
}

Спасибо Вам, Ольга, огромное!
не представляю, сколько пришлось бы с этим промучиться, если бы не Вы :)

я тоже, наверное, немало времени тогда потратила
всегда пожалуйста :)

Здравствуйте! А каким образом можно осуществить подобный переход не из основного реестра, а из деталей? Я поступил так:

в скрипте scr_BaseTreeArea создал функции, аналогичные предложенным Вами для scr_BaseGridArea, по идее обработчик должен уже анализировать, является ли выделенная область массивом, но этого не происходит. все остальные скрипты уже были ранее приведены к требуемому виду, и переход по группе записей из основного реестра - работает.

Хочется перейти из детали.

Здравствуйте.

scr_BaseTreeArea - это скрипт базового древовидного окна. Его менять нужно только если у Вас в деталь используется древовидный реестр.
По поводу перехода к множеству записей из детали, функционал остается тем же самым, только нужно переписать данную функцию:

function GetGridSelectedIDsArray() {
                if (!Assigned(grdData) && !Assigned(BaseGridArea.Grid)) {
                               return null;
                } else {
                               if (!Assigned(BaseGridArea.Grid)) {
                                               BaseGridArea.Grid = grdData;
                               }
                }
                if (BaseGridArea.Grid.SelectedIDs.Count == 0) {
                               return null;
                }
                var SelectedIDsArray = new Array();
                for (var i = 0; i < BaseGridArea.Grid.SelectedIDs.Count; i++) {
                               SelectedIDsArray.push(BaseGridArea.Grid.SelectedIDs.Items(i));
                }
                return SelectedIDsArray;
}

Установите отладчик, и посмотрите заполняется ли массив выделенными на детали записями?

Показать все комментарии