30.09.2009, 15:39 | #1 |
Участник
|
Позиционирование в гриде
Доброго времени суток, уважаемые гуру аксапты!
Не могли бы вы мне помочь в следующем: имеется форма с тремя датасорсами: RContractTable, ObjectTable, PointAccountTable. На форме грид, свойство datasourse=RContractTable. Необходимо было добавить возможность удаления строки/строк из грида, для последующего вывода в отчет только нужных строчек. Удаление организовал по кнопке; ее метод кликед: X++: void clicked() { QueryBuildDatasource pointTable; query q; queryBuildRange qbr; RContractTable RContract; ObjectTable object; PointAccountTable pointAccount; int c; ; for (RContract = RContractTable_ds.getFirst(true) ? RContractTable_ds.getFirst(true) : RContractTable_ds.cursor(); RContract; RContract = RContractTable_ds.getNext()) { c++; } qbr=pointTable.findRange(FieldNum(ICLPointAccountTable,PointAccountId)); if (qbr) { for (RContract = RContractTable_ds.getFirst(true) ? RContractTable_ds.getFirst(true) : RContractTable_ds.cursor(); RContract; RContract = RContractTable_ds.getNext()) { object = RContract.joinChild(); pointAccount = object.joinChild(); qbr.value(qbr.value()+',!'+pointAccount.PointAccountId); } } else { if (c==1) { qbr=pointTable.addRange(FieldNum(ICLPointAccountTable,PointAccountId)); qbr.value('!'+ICLPointAccountTable.PointAccountId); } else { qbr=pointTable.addRange(FieldNum(ICLPointAccountTable,PointAccountId)); for (RContract = RContractTable_ds.getFirst(true) ? RContractTable_ds.getFirst(true) : RContractTable_ds.cursor(); RContract; RContract = RContractTable_ds.getNext()) { object = RContract.joinChild(); pointAccount = object.joinChild(); qbr.value(qbr.value()+',!'+pointAccount.PointAccountId); } } } RContractTable_ds.research(); } Работает, как и нужно. Но после research курсор уходит на первую запись в гриде. На форуме читал похожие темы, но то, что мне нужно не нашел..ведь мне нужно запоминать не позицию выделенной строки, а позицию следующей за ней, поскольку выделенная удаляется. Не направите ли на путь истинный? п.с. если было такое на форуме, очень извиняюсь..
__________________
..в каждой программе есть хотя бы одна ошибка.. Последний раз редактировалось Dron AKA andy; 30.09.2009 в 17:53. |
|
30.09.2009, 16:00 | #2 |
Участник
|
Вы выбрали неправильное решение для поставленной задачи. Добавьте в грид галочку и отмечайте те строчки без которых нужно выводить на печать.
|
|
30.09.2009, 16:16 | #3 |
MCTS
|
Попробуйте вслед за циклом, внутри которого удаляются строки прописать:
RContractTable_ds.next(); Должны на следующую строчку перескочить
__________________
В глухомани, в лесу Несмотря на красу Дни проводит Лиса Патрикевна. Я никак не пойму Отчего, почему Не пускают куму На деревню |
|
30.09.2009, 16:19 | #4 |
Участник
|
Цитата:
Вы выбрали неправильное решение для поставленной задачи. Добавьте в грид галочку и отмечайте те строчки без которых нужно выводить на печать.
неужели нет решения?
__________________
..в каждой программе есть хотя бы одна ошибка.. |
|
30.09.2009, 16:22 | #5 |
Участник
|
Цитата:
2. Для копирования в excel пускай сделает потом фильтр по галочке и копирует себе на здоровье. |
|
|
За это сообщение автора поблагодарили: Alexanderrrr (1). |
30.09.2009, 16:24 | #6 |
Участник
|
Позиционирование на нужную запись - это методы X_ds.findRecord() или X_ds.findValue(). Определяете запись, на которой хотите оказаться и после X_ds.research() выполняете поиск нужной записи одним из этих методов.
Как определить нужную запись? 100% гарантии надежности определения нет. Один из вариантов - это определить последнюю запись выделенного диапазона, перейти к ней, затем выполнить X_ds.next(). Теоретически, должны бы попасть на одну из записей вне диапазона. Но это без гарантий. Последний раз редактировалось Владимир Максимов; 30.09.2009 в 16:28. |
|
|
За это сообщение автора поблагодарили: Alexanderrrr (1). |
30.09.2009, 16:31 | #7 |
Участник
|
Цитата:
Не пользуйтесь этими методами на больших таблицах. |
|
30.09.2009, 17:02 | #8 |
Ищущий знания...
|
а можно и вовсе сделать через временную таблицу.
пускай пользователь удаляет в ней что хочет, а потом копирует в Excel
__________________
"Страх перед возможностью ошибки не должен отвращать нас от поисков истины." (с) С Уважением, Елизаров Артем |
|
30.09.2009, 17:25 | #9 |
Участник
|
где-то на форуме было исследование как лучше хранить галочки - во временных таблицах, в map, в контейнере или еще как. не могу найти
|
|
30.09.2009, 17:34 | #10 |
Участник
|
Alexanderrrr когда сообщение пишите на панели есть кнопочка Х++.
Код будет смотрется лучше. Сейчас он выглядит ужасно. После X++: c++; X++: if (c >= 2) break; А две или 10 вам уже без разницы. Вот так же красивее. X++: void clicked() { QueryBuildDatasource pointTable; query q; queryBuildRange qbr; RContractTable RContract; ObjectTable object; PointAccountTable pointAccount; int c; ; for (RContract = RContractTable_ds.getFirst(true) ? RContractTable_ds.getFirst(true) : RContractTable_ds.cursor(); RContract; RContract = RContractTable_ds.getNext()) { c++; } qbr=pointTable.findRange(FieldNum(ICLPointAccountTable,PointAccountId)); if (qbr) { for (RContract = RContractTable_ds.getFirst(true) ? RContractTable_ds.getFirst(true) : RContractTable_ds.cursor(); RContract; RContract = RContractTable_ds.getNext()) { object = RContract.joinChild(); pointAccount = object.joinChild(); qbr.value(qbr.value()+',!'+pointAccount.PointAccountId); } } else { if (c==1) { qbr=pointTable.addRange(FieldNum(ICLPointAccountTable,PointAccountId)); qbr.value('!'+ICLPointAccountTable.PointAccountId); } else { qbr=pointTable.addRange(FieldNum(ICLPointAccountTable,PointAccountId)); for (RContract = RContractTable_ds.getFirst(true) ? RContractTable_ds.getFirst(true) : RContractTable_ds.cursor(); RContract; RContract = RContractTable_ds.getNext()) { object = RContract.joinChild(); pointAccount = object.joinChild(); qbr.value(qbr.value()+',!'+pointAccount.PointAccountId); } } } RContractTable_ds.research(); } Но я с ним был согласен. Потом, смотреть как выглядит код когда уже всё готово, стало привычкой.
__________________
Энергия молодых и неравнодушных способна изменить мир к лучшему. |
|
|
За это сообщение автора поблагодарили: Alexanderrrr (1). |
30.09.2009, 17:36 | #11 |
Участник
|
Цитата:
|
|
|
За это сообщение автора поблагодарили: mazzy (1). |
30.09.2009, 17:38 | #12 |
Axapta
|
Цитата:
|
|
|
За это сообщение автора поблагодарили: mazzy (1). |
30.09.2009, 17:55 | #13 |
Участник
|
Lucky13, oip, то, что надо. а я на "маркировке" зациклился...
Цитата:
Предположим вы сделали как у вас просят. Предположим пользователь решил, что строчку в отчет выводить не надо и удалил строчку. Предположим что где-то в середине процесса пользователь вдруг вспомнил "Ой, а я зря удалил, печатать все ж таки надо". Как в вашей постановке пользователь сможет вернуть и напечатать строку, которую раньше удалил из грида? Ответ: никак, только закрыть форму и начать отмечать строки заново Поэтому в Аксапте используется маркировка галочками для больших таблиц а для маленьких списков - пара listview. |
|
|
За это сообщение автора поблагодарили: Alexanderrrr (1). |
01.10.2009, 08:15 | #14 |
Участник
|
В дополнение ко всему, переименуйте переменную "с" на "х". И все у вас будет!
__________________
// no comments |
|
01.10.2009, 08:43 | #15 |
Участник
|
Цитата:
Но это мне кажется не принципиальным.
__________________
Энергия молодых и неравнодушных способна изменить мир к лучшему. |
|
01.10.2009, 13:40 | #16 |
Участник
|
Насоветовали тут))
да, согласен..с постановкой задачи у нас проблемы часто. да и код написан с недочетами, согласен. Думаю с галочками будет гораздо проще и проблем меньше Спасибо всем за помощь!
__________________
..в каждой программе есть хотя бы одна ошибка.. |
|
01.10.2009, 14:07 | #17 |
Moderator
|
немного офф-топика по ходу...
Цитата:
Я знаю, что есть ограничение EDT Range, которое равно 250 символам и которое срабатывает, если у QueryRun вызывается prompt(), т.е. стандартная форма запроса показывается пользователю. И далее, если пользователь нажмет на OK, но какой-либо критерий (уже неважно, введенный вручную или поданый из кода) будет длинее 250 символов, то возникнет ошибка. Но, вроде, в коде топикстартера prompt'а нет и в этом случае можно многие тысячи символов поместить в QueryBuildRange и они корректно обработаются. Даже не знаю точно, сколько много. Разве не так? |
|
01.10.2009, 14:24 | #18 |
Участник
|
Я имел ввиду вот это. Т.е. записать в range можно строку какой угодно длины, а вот насколько корректно она потом преобразуется в запрос... Хотя на новых версиях AX не проверял, может и все хорошо уже.
|
|
01.10.2009, 14:58 | #19 |
Участник
|
В Ax 3.0 sp5 kr2 у меня на запрос ругался sql сервер (MS SQL 2005 sp2)
Ругался не на размер where, а на уровень вложености (видно по ссылке _scorp_ в сообщении Владимира Максимова кучу открывающих скобок) Получалось, что обрабатывалось 477 ограничений, а на 478-м прилетала ошибка от sql. Причем, этот запрос, перенесенный в Management Studio, в нем вызывал ту же самую ошибку, а при удалении одного из условий корректно возвращал 477 записей. Так что это ограничение самого MS SQL (по крайней мере, 2005-го). Ну и способа, которым Ax формирует запрос. Что касается просто ограничения на размер запроса в WHERE, то такого самого по себе нет. Есть общее ограничение на размер selecta'а Цитата:
Length of a string containing SQL statements (batch size)
65,536 * Network packet size 65,536 * Network packet size batch size The default packet size is 4 kilobytes (KB), and is controlled by the network packet size configuration option
__________________
Axapta v.3.0 sp5 kr2 |
|
02.10.2009, 17:17 | #20 |
Участник
|
небольшой offtop
Цитата:
X++: void clicked() { int c; ; ... for (RContract = RContractTable_ds.getFirst(true) ? RContractTable_ds.getFirst(true) : RContractTable_ds.cursor(); RContract; RContract = RContractTable_ds.getNext()) { c++; } ... }
__________________
Dynamics AX 4.0 SP2 |
|
|
За это сообщение автора поблагодарили: miklenew (3), Alexanderrrr (1). |