Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

Каким образом передавать в Property больше 1 значения?

266
27 февраля 2004 года
mhaturov
901 / / 23.10.2003
Задача у меня возникла следующая:
Пишу свой грид (все известные мне гриды (TrueDbGrid, MSFlexGrid, ListViev и т.д.) не удовлетворяют различным требованиям, предъявляемым мною для решения одной задачки). Описал столбец для него. Столбцы выкладываю на другой контрол, который и будет являться гридом.
Мне необходимо задавать стили отображения для столбцов, такие как ширина, размеры шрифтов, стиль, ответственный за то, что будет отображаться в столбце (каждый столбец может отображать разные элементы управления) и т.п.
Я уже писал подобный грид (только он был несколько ограниченным). В него стиль для столбца передавался через Public Sub. Т.е., например:
 
Код:
Public Sub ColStyle(ByVal ColIndex as long, Style as long)

Т.е. передаётся, как видите, индекс столбца и стиль его отображения.
Данная структура очень удобна и проста в реализации, но в случае, если я передаю стиль столбца через Property, я могу при разработке проекта, выложив контрол на форму, задать в свойствах контрола все стили для всех столбцов и наглядно посмотреть, что получается. Если использую процедуру (Sub), то этого уже добиться нельзя. Кирме того, если работать через Propery, то гораздо легче из кода обрабатывать (получать и передавать) различные значения для контрола. Например, если есть структура:
 
Код:
Public Property Let ColumnStyle(ByVal Style As Long)
 Тыры-пыры
End Property

Public Property Get ColumnStyle() As Long
 ColumnStyle = Column.Style
 Тыры-пыры
End Property

то я могу из кода обращаться к ней:
 
Код:
МойКонтрол.ColumnStyle = A
 B = МойКонтрол.ColumnStyle

А если есть структура:
 
Код:
Public Sub SetColumnStyle(ByVal ColIndex As Long, Style As Long)
 Тыры-пыры
End Property

Public Function RetColumnStyle(ByVal ColIndex As Long) As Long
 Тыры-пыры
 RetColumnStyle = Column(ColIndex).Style
End Property

то я при обращении из кода должен использовать:
 
Код:
МойКонтрол.SetColumnStyle A, B
 C = МойКонтрол.RetColumnStyle(A)

что не так удобно, так как нужно помнить имена процедур (понимаете, когда много свойств, даже если процедуры обозваны понятно, всё равно возникает "запарка")
Можно, конечно, реализовать отдельную настройку столбцов, как это сделано у всех гридов, но это - дополнительный довесок и время, которое поджимает. К тому же это не снимает вторую проблему (с именованием).
Поэтому мне желательно это дело реаливывать через Property, но Property "по умолчанию" позволяет передавать и возвращать только 1 свойство. И структура:
 
Код:
Public Property Let ColumnStyle(ByVal ColIndex as long, Style As Long)
 Тыры-пыры
End Property

Public Property Get ColumnStyle(ByVal ColIndex as long) As Long
 ColumnStyle = Column(ColIndex).Style
 Тыры-пыры
End Property

"не прокатывает".
Кто-нибудь знает, возможно ли вообще, и, если возможно, то как, это обойти?
258
27 февраля 2004 года
SergeySV
1.5K / / 19.03.2003
Насколько мне известно - никак.
Ведь свойство токо выглядит как функция, но ее вызов же идет в коде, так:
Dim a as MyClass
Set a = New MyClass

a.Text = "dfsfs"

т.е. ты пишешь Объект.Свойство и дальше равно "=", а после "=" не может следовать несколько значений .

Кроме как описаных тобой методы (написать не свойство Text, а метод - SetText(,)) я больше не вижу. Тем более я не представляю все равно как станд. инспектор свойств сможет отобразить такое свойство - тут все равно понадобится Построитель, например как для Color'а.

Что мне приходит в голову.
Можно забить твои свойства прям в класс по типу:
Col1 As Long
Style1 As Long
Col2 As Long
Style2 As Long
Col3 As Long
Style3 As Long
......
и т.д.

Сотв. нарожать стоко же Property Get/Let, а тебе в классе придется следить за ними и заполнять эти переменные, чтобы они всегда соотвествовали реальному положению дел. Недостатки - выглядеть код будет прикольно :)

Вариант 2: Нельзя передать больше одной переменной в Property, но можно передать структуру, массив. Тогда тебе придется сначала в коде создавать массив/структуру и потом уже его присваивать свойству:

a.Text = myType/myArray
319
27 февраля 2004 года
xelos
577 / / 27.02.2003
По определению Property - только одно свойство. Единственный выход, что вижу - делать несколько независимых свойств. Но по мне, лучше все-таки функцию определить, а не свойства.
266
27 февраля 2004 года
mhaturov
901 / / 23.10.2003
Цитата:
Originally posted by xelos
По определению Property - только одно свойство. Единственный выход, что вижу - делать несколько независимых свойств. Но по мне, лучше все-таки функцию определить, а не свойства.


Ладно, что уж поделать...:{
Тем более, что я уже начал через процедуры и функции енто делать...
А, кстати, немного не понял насчёт массива... Можно поподробнее? Приблизительный код, например?:P

258
27 февраля 2004 года
SergeySV
1.5K / / 19.03.2003
Хм.. признаю свою ошибку, оказывается все не так уже плохо, можно написать и так:
Код:
Dim s As String

Public Property Let ds(a1 As String, a2 As String, s1 As String)
  If a1 = "sd" And a2 = "dsf" Then
    s = s1
  End If
End Property

Public Property Get ds(a1 As String, a2 As String) As String
  ds = s
End Property


Т.е. как значение для свойства будет браться последний аргумент в Let, т.е. именно он то и будет стоять после "=". А вот остальные (a1 и a2) будут играть роль вспомогательных и они должны быть идентичными что у Let, то и у Get - иначе не откомпиллируется.

Т.е. вид будет такой:
 
Код:
Dim a As Class1
 
 Set a = New Class1
 a.ds("sdf", "sfsd") = "fddsf"
258
27 февраля 2004 года
SergeySV
1.5K / / 19.03.2003
Да, чуть не забыл, можно же еще эти параметры как Optional объявлять:

Public Property Let ds(Optional a1 As String = "111", Optional a2 As String = "222", s1 As String)

и тогда мона писать как хочется:

Set a = New Class1



a.ds("sfs","ssd") = "sdfsd"
или так
a.ds = "sdfsd" - что уже очень приятно

Ну и также кроме обычных переменных мона еще и массивы сувать:
..... Let ds(ParamArray a1() As String,.....
266
27 февраля 2004 года
mhaturov
901 / / 23.10.2003
Цитата:
Originally posted by SergeySV
Да, чуть не забыл, можно же еще эти параметры как Optional объявлять:

Public Property Let ds(Optional a1 As String = "111", Optional a2 As String = "222", s1 As String)

и тогда мона писать как хочется:

Set a = New Class1



a.ds("sfs","ssd") = "sdfsd"
или так
a.ds = "sdfsd" - что уже очень приятно

Ну и также кроме обычных переменных мона еще и массивы сувать:
..... Let ds(ParamArray a1() As String,.....


Простите за просто идиотский вопрос (возможно, меня от упорного труда вновь клинит), но как узнать размерность массива? Хотя бы его верхнюю границу?P(

258
29 февраля 2004 года
SergeySV
1.5K / / 19.03.2003
Цитата:
Originally posted by mhaturov

Простите за просто идиотский вопрос (возможно, меня от упорного труда вновь клинит), но как узнать размерность массива? Хотя бы его верхнюю границу?P(



Dim mas(1 To 10) as String

верхн. UBound(mas)
нижн. LBound(mas)

2.2K
01 марта 2004 года
USA-Lesh
50 / / 02.04.2003
Делай свойство типа Variant и передавай туда что пожелаешь, хоть массив, хоть свой тип данных.
266
02 марта 2004 года
mhaturov
901 / / 23.10.2003
Цитата:
Originally posted by USA-Lesh
Делай свойство типа Variant и передавай туда что пожелаешь, хоть массив, хоть свой тип данных.


Большое спасибо!
Но у меня проблема поинтереснее. Так как мне нужно передавать массив для заполнения комбобокса, то я передаю в него 2-х мерный массив. А вот как определить его размерность?

266
02 марта 2004 года
mhaturov
901 / / 23.10.2003
Цитата:
Originally posted by mhaturov

Большое спасибо!
Но у меня проблема поинтереснее. Так как мне нужно передавать массив для заполнения комбобокса, то я передаю в него 2-х мерный массив. А вот как определить его размерность?


И ещё один вопрос. Можно ли создавать коллекцию массивов в массиве. Тоесть, очень заманчиво заполнять грид целиком из массива. В основном проекте формировать массив, а потом передавать его гриду, а тот уж пусть сам себя из массива заполняет. Но так как в гриде есть комбобоксы, то их данные прийдётся, в свою очередь, хранить в массивах. Поэтому получится ли "запихнуть" массив в массив?

258
02 марта 2004 года
SergeySV
1.5K / / 19.03.2003
Цитата:
Originally posted by mhaturov

Большое спасибо!
Но у меня проблема поинтереснее. Так как мне нужно передавать массив для заполнения комбобокса, то я передаю в него 2-х мерный массив. А вот как определить его размерность?



Наскоко мне известно встроенной функции для определения размерности массива нет, поэтому как вариант я накатал следующую функцию:

Код:
Public Function RazmMassive(mas As Variant) As Long
  Dim i As Long, k As Long

 On Error GoTo Er_
  RazmMassive = 0
   
  Do
    i = i + 1
    k = UBound(mas, i)
  Loop Until i = 1000
     
Ex_:
  Exit Function
 
Er_:
  If Err.Number = 9 Then ' Error - Subscript out of range
    RazmMassive = i - 1
  Else
    MsgBox Err.Description
  End If
  Resume Ex_
 
End Function


Принцип очень простой, мы просто пытаемся определить верхн. границу каждой размерности по очереди, пока не получим ошибку №9 - Subscript out of range

P.S. функция обламается, если в опциях компилляции отказатся от установленного по умолч. опции - проверка индекса на выход из массива
2.2K
04 марта 2004 года
USA-Lesh
50 / / 02.04.2003
Sub Sample()
Dim a() As Variant
Dim k As Variant

ReDim a(3)
k = a
ReDim a(2)
k(0) = a
k(1) = a
k(2) = a
k(3) = a

End Sub

Перед выходом посмотри значение к. Обращание к элементам типа к(1)(3)(4. В любой элемент можно запихать сколько угодно вложенных массивов и контроль наличия массива легко определить.
266
04 марта 2004 года
mhaturov
901 / / 23.10.2003
Цитата:
Originally posted by USA-Lesh
Sub Sample()
Dim a() As Variant
Dim k As Variant

ReDim a(3)
k = a
ReDim a(2)
k(0) = a
k(1) = a
k(2) = a
k(3) = a

End Sub

Перед выходом посмотри значение к. Обращание к элементам типа к(1)(3)(4. В любой элемент можно запихать сколько угодно вложенных массивов и контроль наличия массива легко определить.


О, огромное спасибо!
Обязательно постараюсь в ближайшее время вклюсить это в код грида (правда, теперь уже в следующую версию, к сохалению - эту уже сегодня буду подключать к проекту)

Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог