|
|
|
| на форме есть выкидной список, в нем источник строк (select id, ФИО from сотрудники), при этом первый столбец ширины 0, т.е. в списке видны только фамилии.
вопрос:
можно ли сделать так чтобы при вводе букв производился автоматический отбор из всего списка фамилий начинающихся на эти буквы и этот укороченный список предлагался открытием пользователю?
Me![ПолеВыборСотрудника].DropDown можно открыть список, а вот как быть с уменьшением числа записей? надо налету менять RecordSource? или есть другие варианты решения? | |
|
| |
|
|
|
|
Очередной перл. | |
|
| |
|
18 Кб. |
|
| Можно нга лету менять рекордсоурс списка. Вот пример - уже был на этом форуме ( или другом ) . От туда можно подчерпнуть решение. | |
|
| |
|
|
|
| спасибо пойду погляжу пример :) | |
|
| |
|
|
|
| сделал так
Private Sub ПолеВыбораСотрудника_Change()
Dim strWhere, strSQL1, strSQL2 As String
If Len([ПолеВыбораСотрудника].Text) <> 0 Or Not IsNull([ПолеВыбораСотрудника].Text) Then
strSQL1 = "SELECT id, ФИО FROM Usys_sotr"
strSQL2 = " ORDER BY Usys_sotr.ФИО;"
strWhere = " WHERE Left(ФИО," & Len([ПолеВыбораСотрудника].Text) & ") = '" & [ПолеВыбораСотрудника].Text & "'"
Me![ПолеВыбораСотрудника].RowSource = strSQL1 & strWhere & strSQL2
Me![ПолеВыбораСотрудника].Dropdown
End If
End Sub
работает но как то криво не пойму почему???
завел двух сотрудников например петров и петрухин...
набираю до "петр" в списке показывает только одного петрова. набираю "петру" вываливается один петрухин...
а если начинать стирать символы, список начинает показывать обоих ...
помогите разобраться в чем дело:( | |
|
| |
|
|
|
| Так ведь вы хотите выбрать по частичному, а не полному совпадению Вместе с тем в запросе вы задаете условие на полное совпадение. Задайте вместо равенства - Like [Forms]![Имя_вашей_формы]![ПолеВыбораСотрудника].Text & "*".
А кривая работа получается потому, что аксовский комбобокс сам отбирает значения на частичное совпадение при вводе в него букв. | |
|
| |
|
|
|
| Like вроде я тоже пробовал уже.
все равно спасибо за подсказку! | |
|
| |
|
|
|
| Но зачем вам эта морока?
Если ваш "выкидной список" (правильные термины "Поле со списком" или Combobox ) отсортирован по фамилиям, то при вводе каждого символа Акс сам перемешает указатель на 1-ю подходящую строку в открытом (DropDown) списе и ниже вы видите все остальные варианты. | |
|
| |
|
|
|
| в открытом методом DropDown я вижу все скажем 16 записей, что не очень удобно для глаза пользователя (хотя конечно первая строка подходящая там выделена, как вы и говорите), вот и возникла идея, нельзя ли сделать так, набрал "пет" из всег осписка сотрудников произвелся отбор.. и выкинуло для пользователя только начинающихся с "пет"... | |
|
| |
|
|
|
| А кривая работа получается потому, что аксовский комбобокс сам отбирает значения на частичное совпадение при вводе в него букв. |
Поставить свойство в настройках "автоподстановка" в "Нет". | |
|
| |
|
|
|
|
Поставить свойство в настройках "автоподстановка" в "Нет".
|
Да Вы правы! Так работает спасибо:)
осталось только отслеживать теперь RecordSource и после апдейта вертать его в зад:) а то список остается из одной двух фамилий:) собственно в зависимости от того что ввели:) | |
|
| |
|
|
|
| сделал так
Private Sub ПолеВыбораСотрудника_Change()
Dim strWhere, strSQL1, strSQL2 As String
If Len([ПолеВыбораСотрудника].Text) <> 0 Or Not IsNull([ПолеВыбораСотрудника].Text) Then
strSQL1 = "SELECT id, ФИО FROM Usys_sotr"
strSQL2 = " ORDER BY Usys_sotr.ФИО;"
strWhere = " WHERE ФИО Like '" & Me![ПолеВыбораСотрудника].Text & "*' "
Me![ПолеВыбораСотрудника].RowSource = strSQL1 & strWhere & strSQL2
Me![ПолеВыбораСотрудника].Dropdown
End If
End Sub
Private Sub ПолеВыбораСотрудника_LostFocus()
'возврат RecordSource к исходному значению
Me![ПолеВыбораСотрудника].RowSource = "SELECT id, ФИО FROM Usys_sotr ORDER BY Usys_sotr.ФИО;"
Me![ПолеВыбораСотрудника].Requery
End Sub
вроде все работает нормально, осталлся такой только момент. Ввожу первые буквы фамилии, в списке происходит отбор, список открывается. А далее если выбор осуществить клавишами вверх-вниз и потом нажатием ввод то все нормально.
а если выбор осуществить мышкой из предложенных фамилий, то лишний раз срабатывает DropDown. Приходится давить мышкой куда нибудь чтобы сбросить фокус...
Это конечно уже не глюк, но можно ли как нибудь избежать этого? Ведь если выбор с клавиш то список нормально закрывается. | |
|
| |
|
|
|
|
если выбор осуществить мышкой из предложенных фамилий, то лишний раз срабатывает DropDown
|
А енто потому, что при клике мышом у вас осуществляется лишний раз событие Change(). отседова и лишний дроп-даун.
Вааще-то если вы уж так хотите выбирать по вводимиы данным - то , ИМХО, лучше использовать сочетание текстового поля, кнопки и списка. В текстовое поле вводится искомый параметр и по нажатию кнопки список делается видимиы и формируется его рекордсоурс. Если в текстовое поле не введено ничего - в список по нажатию на кнопку выводятся все записи. Таким образом будет работать коррктнее. А то всякие LоstFocusы() - это извращение. | |
|
| |
|
|
|
| может вы и правы!
кстати лишний дроп-даун можно проскакивать на автомате используя SetFocus, то есть принудительно переставив его в какое нибудь другое поле, тогда все обновится и закроется список, но вот пока не могу понять куда его примостить, бывает возникает ошибка... | |
|
| |
|
|
|
|
Задействовать логическую переменную, на получение фокуса=True, на после обновления=False.
Осуществлять действия после проверки значения переменной.
+
Описать все это отдельным классом.
При открытии формы объявлять столько переменных класса, сколько комбобоксов в форме, передавать ссылку на комбобокс в класс. А если с событиями, то вообще супер получится. | |
|
| |
|
|
|
| все вроде заработало! только кроме логической переменной еще потребовалось на после обновления добавить передачу фокуса!
кто захочет гемороя вот полный код
Private Sub ПолеВыбораСотрудника_AfterUpdate()
'поиск записи, соответствующей этому элементу управления.
If Not IsNull(Me![ПолеВыбораСотрудника]) Then
With Me.RecordsetClone
.FindFirst "id = " & Me![ПолеВыбораСотрудника]
If Not .NoMatch Then Me.Bookmark = .Bookmark
End With
Else
If MsgBox("Не выбрана фамилия сотрудника. Выбор осуществить невозможно", vbInformation, "Внимание") = vbOK Then
End If
ПолеВыбораСотрудника.Value = id
End If
'подсчет значений
With Me.RecordsetClone
If Not .BOF Or Not .EOF Then .MoveLast
RecCount.Caption = .RecordCount
End With
bolvar = False
'передача фокуса в поле ФИО на форме
If Not IsNull([ПолеВыбораСотрудника]) Then Me.полеФ.SetFocus
End Sub
Private Sub ПолеВыбораСотрудника_Change()
If bolvar Then
Dim strWhere, strSQL1, strSQL2 As String
'Me![ПолеВыбораСотрудника].RowSource = ""
If Len([ПолеВыбораСотрудника].Text) <> 0 Or Not IsNull([ПолеВыбораСотрудника].Text) Then
strSQL1 = "SELECT id, ФИО FROM Usys_sotr"
strSQL2 = " ORDER BY Usys_sotr.ФИО;"
strWhere = " WHERE ФИО Like '" & Me![ПолеВыбораСотрудника].Text & "*' "
'" WHERE Left(ФИО," & Len([ПолеВыбораСотрудника].Text) & ") = '" & [ПолеВыбораСотрудника].Text & "'"
Me![ПолеВыбораСотрудника].RowSource = strSQL1 & strWhere & strSQL2
Me![ПолеВыбораСотрудника].Dropdown
End If
End If
End Sub
Private Sub ПолеВыбораСотрудника_GotFocus()
bolvar = True
End Sub
Private Sub ПолеВыбораСотрудника_LostFocus()
'возврат RecordSource к исходному значению
Me![ПолеВыбораСотрудника].RowSource = "SELECT id, ФИО FROM Usys_sotr ORDER BY Usys_sotr.ФИО;"
Me![ПолеВыбораСотрудника].Requery
End Sub | |
|
| |
|
|
|
|
|
А может Вас устроит такой вариант
http://hiprog.com/index.php?option=com_content&task=view&id=251661615&Itemid=35
|
нет это не подходит форма по другому устроена, этот вариант я первым делом посмотрел:) он же на главной странице:)
Описать все это отдельным классом.
При открытии формы объявлять столько переменных класса, сколько комбобоксов в форме, передавать ссылку на комбобокс в класс. А если с событиями, то вообще супер получится.
|
| |
|
| |
|
|
|
|
Описать все это отдельным классом.
При открытии формы объявлять столько переменных класса, сколько комбобоксов в форме, передавать ссылку на комбобокс в класс. А если с событиями, то вообще супер получится.
|
а вот в этом совсем не силен, хотя о че речь идет представляю... было бы правда прикольно, но сам сделать не смогу:( | |
|
| |
|
|
|
| Чтобы лишний раз не срабатывал DropDown, можно Me![ПолеВыбораСотрудника].Dropdown убрать из события Change и повесить на KeyUp | |
|
| |
|
|
|
|
Чтобы лишний раз не срабатывал DropDown, можно Me![ПолеВыбораСотрудника].Dropdown убрать из события Change и повесить на KeyUp
| так событие дроп-даун отрабатывает так что список моргает при выпадении и пользователь не успевает нажать ничего и ничего не выбрать.
А вообще, обращаюсь всем тем кто помог написать указанный выше код.. выявил новую свою недоработку, которую пока не знаю как решить:)
теперь при наборе букв, список выкидывается и видны отобранные фамилии, выбор можно осуществить мышкой и тогда все работает хорошо.
а вот клавишей вниз дальше второй записи данный код не позволяет спуститься. При нажатии ее происходит выбор второй в списке записи, после чего сразу происходит отбор ее одно и все пользователь уже не видит всех тех что ему показали в первый раз, а хотелось бы чтобы не только мышка работала а можно было по предложенному списку пройтись и курсорными клавишами.. можно как нибудь это реализовать??? может в коде недоработка? | |
|
| |
|
|
|
| Так и будет происходить. При нажатии клавиши срабатывает событие change() вашего комбобокса и меняет источник записей. В нем( источнике записей ) содержится только одна запись, которую вы и выбрали. | |
|
| |
|
17 Кб. |
|
| а вот клавишей вниз дальше второй записи данный код не позволяет спуститься |
Глянь атач | |
|
| |
|
|
|
| ООО спасибо!!! на первый взгляд именно то что хотелосьбы, посмотрел Ваш аттач вродевсе рабтает! попробую прикрутить к своей форме | |
|
| |
|
|
|
| есть тут тоже недоделка:( если осуществлять выбор мышкой, то фокус остается в поле со списком и соответственно не обновляется рекорд-соурс... | |
|
| |
|
|
|
| Господа эксперты ну подскажите что делать!?
вот к какому коду сейчсас пришел...
Private Sub ПолеВыбораСотрудника_AfterUpdate()
'возврат RecordSource к исходному значению
Me![ПолеВыбораСотрудника].RowSource = "SELECT id, ФИО FROM Usys_sotr ORDER BY Usys_sotr.ФИО;"
Me![ПолеВыбораСотрудника].Requery
'сброс существующего фильтра при его наличии
If Me.FilterOn Then
Me.Filter = ""
Me.FilterOn = False
ПолеФильтр = ""
ПолеФильтр.BackColor = 16777215
End If
'поиск записи, соответствующей этому элементу управления.
If Not IsNull(Me![ПолеВыбораСотрудника]) Then
With Me.RecordsetClone
.FindFirst "id = " & Me![ПолеВыбораСотрудника]
If Not .NoMatch Then Me.Bookmark = .Bookmark
End With
Else
If MsgBox("Не выбрана фамилия сотрудника. Выбор осуществить невозможно", vbInformation, "Внимание") = vbOK Then
End If
ПолеВыбораСотрудника.Value = id
End If
'подсчет значений
With Me.RecordsetClone
If Not .BOF Or Not .EOF Then .MoveLast
RecCount.Caption = .RecordCount
End With
End Sub
Private Sub ПолеВыбораСотрудника_Change()
If var_long = 40 Then Exit Sub
If var_long = 38 Then Exit Sub
Dim strWhere, strSQL1, strSQL2 As String
If Len([ПолеВыбораСотрудника].Text) <> 0 Or Not IsNull([ПолеВыбораСотрудника].Text) Then
strSQL1 = "SELECT id, ФИО FROM Usys_sotr"
strSQL2 = " ORDER BY Usys_sotr.ФИО;"
strWhere = " WHERE ФИО Like '" & Me![ПолеВыбораСотрудника].Text & "*' "
Me![ПолеВыбораСотрудника].RowSource = strSQL1 & strWhere & strSQL2
End If
End Sub
Private Sub ПолеВыбораСотрудника_KeyDown(KeyCode As Integer, Shift As Integer)
var_long = KeyCode
End Sub
Private Sub ПолеВыбораСотрудника_KeyUp(KeyCode As Integer, Shift As Integer)
Me![ПолеВыбораСотрудника].Dropdown
End Sub
Private Sub ПолеВыбораСотрудника_LostFocus()
'возврат RecordSource к исходному значению
Me![ПолеВыбораСотрудника].RowSource = "SELECT id, ФИО FROM Usys_sotr ORDER BY Usys_sotr.ФИО;"
Me![ПолеВыбораСотрудника].Requery
End Sub
есть две проблемы:
1. после выбора мышкой не обновляется источник строк так как фокус не уходит из поля со списком. (если самому тыкнуть куда нибудь на форме, то есть сбросить фокус со списка. источник строк обновляется и все ок)
2. этот кусок кода
'поиск записи, соответствующей этому элементу управления.
If Not IsNull(Me![ПолеВыбораСотрудника]) Then
With Me.RecordsetClone
.FindFirst "id = " & Me![ПолеВыбораСотрудника]
If Not .NoMatch Then Me.Bookmark = .Bookmark
End With
Else
If MsgBox("Не выбрана фамилия сотрудника. Выбор осуществить невозможно", vbInformation, "Внимание") = vbOK Then
End If
ПолеВыбораСотрудника.Value = id
End If
вызывает дополнительное выпадение списка почему-то.. не понимаю почему:( то есть если этот кусок закоментить список будет отрабатывать нормально (за исключением пункта 1), но тогда не обновляются в соответсвии с выбором данные на форме самой...
|
| |
|
| |
|
|
|
| может надо объединить афтер апдейт с изменением??? и весь код разместить в обработчике "изменение"??? | |
|
| |
|
|
|
| все заработало! СПАСИБО ВСЕМ КТО ПОМОГ! | |
|
| |
|
|
|
| если осуществлять выбор мышкой, то фокус остается в поле со списком и соответственно не обновляется рекорд-соурс | Покажи как поборол, плиз | |
|
| |
|
|
|
| Вот весь код, использовать булевую переменную и соотвественно if с ней тебе наверно ненадо, просто у меня в афтер апдейт там дополнительное событие Change возникало... тебе надо добавить наверно только обновление на получение фокуса и отловить нажатие мыши и проверять его в Change.
Private Sub ПолеВыбораСотрудника_AfterUpdate()
'возврат RecordSource к исходному значению
Me![ПолеВыбораСотрудника].RowSource = "SELECT id, ФИО FROM Usys_sotr ORDER BY Usys_sotr.ФИО;"
Me![ПолеВыбораСотрудника].Requery
'поиск записи, соответствующей этому элементу управления.
If Not IsNull(Me![ПолеВыбораСотрудника]) Then
With Me.RecordsetClone
.FindFirst "id = " & Me![ПолеВыбораСотрудника]
If Not .NoMatch Then Me.Bookmark = .Bookmark
End With
Else 'подстановка текущего значения в случае отсутствия ФИО, соответствующего введеному тексту
Me![ПолеВыбораСотрудника] = id
End If
'подсчет значений
With Me.RecordsetClone
If Not .BOF Or Not .EOF Then .MoveLast
RecCount.Caption = .RecordCount
End With
End Sub
Private Sub ПолеВыбораСотрудника_Change()
Dim strWhere, strSQL1, strSQL2 As String
If var_long = 40 Then Exit Sub
If var_long = 38 Then Exit Sub
'осуществление динамического отбора записей по введеным символам
If (Not bolvar) Or (var_long <> -1) Then
If Len([ПолеВыбораСотрудника].Text) <> 0 Or Not IsNull([ПолеВыбораСотрудника].Text) Then
strSQL1 = "SELECT id, ФИО FROM Usys_sotr"
strSQL2 = " ORDER BY Usys_sotr.ФИО;"
strWhere = " WHERE ФИО Like '" & Me![ПолеВыбораСотрудника].Text & "*' "
Me![ПолеВыбораСотрудника].RowSource = strSQL1 & strWhere & strSQL2
Me![ПолеВыбораСотрудника].Dropdown
End If
End If
bolvar = False
End Sub
Private Sub ПолеВыбораСотрудника_GotFocus()
Me![ПолеВыбораСотрудника].RowSource = "SELECT id, ФИО FROM Usys_sotr ORDER BY Usys_sotr.ФИО;"
Me![ПолеВыбораСотрудника].Requery
End Sub
Private Sub ПолеВыбораСотрудника_KeyDown(KeyCode As Integer, Shift As Integer)
var_long = KeyCode
End Sub
Private Sub ПолеВыбораСотрудника_LostFocus()
Me![ПолеВыбораСотрудника].RowSource = "SELECT id, ФИО FROM Usys_sotr ORDER BY Usys_sotr.ФИО;"
Me![ПолеВыбораСотрудника].Requery
End Sub
Private Sub ПолеВыбораСотрудника_MouseDown(Button As Integer, Shift As Integer, X As Single, Y As Single)
bolvar = True
var_long = -1
End Sub | |
|
| |