Прошу дать простой пример / объяснить

Clarion, Clarion 7

Модератор: Дед Пахом

Правила форума
При написании вопроса или обсуждении проблемы, не забывайте указывать версию Clarion который Вы используете.
А так же пользуйтесь спец. тегами при вставке исходников!!!
KoMap
Новичок
Сообщения: 21
Зарегистрирован: 13 Апрель 2006, 5:23
Откуда: Томск

Прошу дать простой пример / объяснить

Сообщение KoMap »

Объясните, пожайлуста, а лучше дайте пример: Как сделать зависимость видимости поля от другого поля. Т.е. есть база в ней два поля, первое видно всегда, второе видно в зависимоти от значения первого. Хочется написать это действо в одном месте, а не вдвух (при открытии и при смене значения первого поля)
Аватара пользователя
Admin
Администратор
Сообщения: 3960
Зарегистрирован: 05 Июль 2005, 15:59
Откуда: Хабаровск
Благодарил (а): 25 раз
Поблагодарили: 22 раза
Контактная информация:

Сообщение Admin »

Если сделать в одном месте то очень часто данный кусок кода будет срабатывать. Делай локальную процедуру и вызывай ее в этих двух местах. Это если тебе не нравится повторять код.
Аватара пользователя
Олег
Ветеран движения
Сообщения: 122
Зарегистрирован: 16 Июль 2005, 2:35
Откуда: Москва
Контактная информация:

Сообщение Олег »

Не совсем согласен с Admin-ом!
Hide/UnHide или Disable/Enable контрола(контролов) требуют не много процессорного времени. А лишние физические перерисовки окна легко убираются стандартными операторами Клариона типа System{PROP:LazyDisplay} = True/False.
У меня в рутинке RefreshWindow в сложных формах мои шаблоны иногда столько подобного кода генерят! И ничего - даже на слабеньких компах никаких "тормозов" и артефактов! Вообщем, имхо, данные операторы - не повод беспокоиться о производительности. Тем более в таблицах или формах, где основным "тормозом" всегда является оператор!

To КоМар: Код, в принципе, довольно простой:

Код: Выделить всё

IF FILE:Field1 = True
   UNHIDE(?FILE:Field2)
ELSE
   HIDE(?FILE:Field2)
END
?FILE:Field2 - экранная метка второго поля файла. Если это форма, сгенеренная стандартными шаблонами, то, обычно, экранная метка поля совпадает с именем поля (с добавлением "?", естественно).
Что-бы посоветовать - куда, именно, вставлять этот код, необходимо уточнить - шаблонная процедура или ручной код? Если шаблонная - какой набор шаблонов (ABC/Legacy/ШВС) и какой, конкретно, шаблон (бровз/форма/обычное окно)?
Самое универсальное место - в начале ACCEPT-цикла. Но в случае ручного кода необходимо установить у окна аттрибуты IMM и AUTO. Тогда любой "чих" в окне будет приводить к проходу через ACCEPT-цикл с принудительной перерисовкой всех контролов.
Если шаблонная процедура из Legacy или ШВС, то лучше всего вставить этот код в точку вставки в рутинке RefreshWindow. Если первое поле находится в этом-же окне и доступно для редактирования, то необходимо в свойствах экранного контрола для этого поля установить флажок типа "Обновить окно при завершении ввода" (устанавливается автоматом при создании нового Entry-контрола). Тогда, после каждого изменения первого поля будет производится вызов рутинки RefreshWindow, в которой и будет отрабатывать твой код отображения второго поля.
Если используешь сразу много операторов по отображению контролов в окне, то рекомендую заключать их в "кавычки":

Код: Выделить всё

SYSTEM{PROP:LazyDisplay} = True
... ! Твой код
SYSTEM{PROP:LazyDisplay} = False
Это уберет промежуточные перерисовки окна.

Удачи!
Аватара пользователя
Admin
Администратор
Сообщения: 3960
Зарегистрирован: 05 Июль 2005, 15:59
Откуда: Хабаровск
Благодарил (а): 25 раз
Поблагодарили: 22 раза
Контактная информация:

Сообщение Admin »

Не совсем согласен с Admin-ом!
Я и не спорю про тормоза. Просто мне к примеру не очень нравится что код будет больше чем нужно раз, исполняться ...
KoMap
Новичок
Сообщения: 21
Зарегистрирован: 13 Апрель 2006, 5:23
Откуда: Томск

Сообщение KoMap »

C6.3, ABC, Form
На мой взгляд (в конкретном случае): производительность тоже очень не принципиальна - лучше минимум кода !
Вставил в ThisWindow.TakeAccepted PROCEDURE, подправил галочки в атрибутах окна и в результате срабатывает только на обновлении первого поля, а при открытии - нет.
Делать три вставки (2-а вызова процедуры + сама проца) или, Олег, я чего-то проглядел в Ваших обяснениях?
KoMap
Новичок
Сообщения: 21
Зарегистрирован: 13 Апрель 2006, 5:23
Откуда: Томск

Сообщение KoMap »

В фоксе есть такое дело - макроподстановка, т.е. можно написать так
a = 'b * 10 + 5'
b = 10
С = &a
и в результате получить С равное 105

можно ли в кларионе сделать подобное?, а то придется либо жестко прописывать вариантность (грубо), либо писать свои функции разбора "макро"строки с последующим преобразованием (долго)

для примера кусок вариантности реальной задачи:
1. C = '20'& Sub(T_RD:N[31],1,12)
2. C = Format(DeFormat(T_RD:N[4],@d5),@d12) & Sub(T_RD:N[5],1,2) & Sub(T_RD:N[5],4,2) &'00'
Последний раз редактировалось KoMap 02 Июль 2006, 11:02, всего редактировалось 1 раз.
Аватара пользователя
Дед Пахом
Старичок
Сообщения: 3134
Зарегистрирован: 07 Июль 2005, 16:51
Откуда: Москва, Россия
Благодарил (а): 10 раз
Поблагодарили: 28 раз
Контактная информация:

Сообщение Дед Пахом »

ThisWindow.TakeAccepted срабатывает (название говорит само за себя), когда для какого-то контрола произошло событие Event:Accepted, поэтому при открытии окна оно и не должно происходить. Сунь свой код знаешь куда? ;^) В ThisWindow.Refresh(), например. Она, кажется, как раз на каждый чих вызывается. Или по OpenWindow-событию пошли POST(Event:Accepted,?File:Field1), тогда ThisWindow.TakeAccepted сработает сразу.
С уважением, ДП
KoMap
Новичок
Сообщения: 21
Зарегистрирован: 13 Апрель 2006, 5:23
Откуда: Томск

Сообщение KoMap »

Дед Пахом писал(а):Сунь свой код в ThisWindow.Refresh()
В АВС не могу найти данное место
Аватара пользователя
Дед Пахом
Старичок
Сообщения: 3134
Зарегистрирован: 07 Июль 2005, 16:51
Откуда: Москва, Россия
Благодарил (а): 10 раз
Поблагодарили: 28 раз
Контактная информация:

Сообщение Дед Пахом »

функция EVALUATE() вычисляет выражения:
BIND('a',b)
BIND('b',b)
b=10
c=EVALUATE('b*10+a')

можно использовать и встроенные функции
c=EVALUATE('sin(pi)')
С уважением, ДП
Аватара пользователя
Дед Пахом
Старичок
Сообщения: 3134
Зарегистрирован: 07 Июль 2005, 16:51
Откуда: Москва, Россия
Благодарил (а): 10 раз
Поблагодарили: 28 раз
Контактная информация:

Сообщение Дед Пахом »

Прямо чат какой-то!
Не Refresh(), а Reset(), ошибся...
С уважением, ДП
KoMap
Новичок
Сообщения: 21
Зарегистрирован: 13 Апрель 2006, 5:23
Откуда: Томск

Сообщение KoMap »

Дед Пахом писал(а):Reset()
Срабатывает только при открытии, при изменении нет.
Хотелось бы получить вставку в одном месте, а не в трех
Последний раз редактировалось KoMap 02 Июль 2006, 13:11, всего редактировалось 1 раз.
KoMap
Новичок
Сообщения: 21
Зарегистрирован: 13 Апрель 2006, 5:23
Откуда: Томск

Сообщение KoMap »

Вопрос в продолжение EVALUATE()

В фоксе можно писать так:
a = 0
b = Iif(a>0,5,10)

В кларионе есть подобная возможность или же надо думать нас счет функций ??

Для примера:
Есть строка (ch), ее надо модифицировать (убрав первый символ) если она начинается на "8", длина строки меньше 6 и второй символ не равен "1", пока на кларе код такой:
j=Len(ch)-1
If ch[1]='8' And j<6 And ch[2]<>'1' Then ch=ch[2:j].

в фоксе это было бы так:
ch=Iif(Left(ch,1)='8' And Len(ch)<7 And SubStr(ch,2,1)<>'1', SubStr(ch,2), ch)

т.е. задача - получить простейшую функцию в одну строку, которую можно было бы впихнуть в таблицу с последующим получением результата через EVALUATE()
Аватара пользователя
Дед Пахом
Старичок
Сообщения: 3134
Зарегистрирован: 07 Июль 2005, 16:51
Откуда: Москва, Россия
Благодарил (а): 10 раз
Поблагодарили: 28 раз
Контактная информация:

Сообщение Дед Пахом »

ну и в чём проблема? делай bind всем переменным выражения и запихивай всё в evaluate() (апострофы и знаки < надо дублировать). Не забудь unbind() по выходе.
По поводу Accepted() - меньше 2-х точек вставки всё равно вряд ли получится - открытие окна и изменение значения поля (полей).
С уважением, ДП
Аватара пользователя
Дед Пахом
Старичок
Сообщения: 3134
Зарегистрирован: 07 Июль 2005, 16:51
Откуда: Москва, Россия
Благодарил (а): 10 раз
Поблагодарили: 28 раз
Контактная информация:

Сообщение Дед Пахом »

или ещё так (я про evaluate):
map
myfunc(long,string),string
end

code
.... Init()
bind('myfunc',myfunc)
bind('a',a)
bind('b',b)
...
ch=evaluate('myfunc(a,b)')
... Kill()
unbind('b')
unbind('a')
unbind('myfunc')
С уважением, ДП
Аватара пользователя
Олег
Ветеран движения
Сообщения: 122
Зарегистрирован: 16 Июль 2005, 2:35
Откуда: Москва
Контактная информация:

Сообщение Олег »

KoMap писал(а):
Дед Пахом писал(а):Reset()
Срабатывает только при открытии, при изменении нет.
Хотелось бы получить вставку в одном месте, а не в трех
Я с ABC-шаблонами не работаю, поэтому точно подсказать не могу. Но что-то я сомневаюсь, что в ABC меньше функционал, чем в Legacy! А там делается именно так, как я и писал - весь необходимый код вставляется в одно место, в рутинку RefreshWindow. Правда, сам шаблон генерит ее вызов при открытии окна и для каждого случая, когда необходима перерисовка. Если в ABC подобного механизма нет, то, вероятно, лучшим вариантом будет написание своего дополнительного метода для класса WindowManager и вставка его вызова как в метод Init после открытия окна, так и в метод TakeAccepted.
Ответить