无法从Access 2007中的用户定义函数中提取值

时间:2011-05-12 14:05:05

标签: vba ms-access-2007 access-vba

我创建了这个函数Ge​​tSubName,我需要从下拉框中返回保存的名称。它做得很好,因为我使用的对话框显示它正确设置变量。问题是,当下面的SQL在查询中运行时,我得到错误:“表达式中的未定义函数'GetSubName'。”我是VBA的新手,所以任何帮助都会非常感激。

以下是代码:

Option Compare Database
Option Explicit
Private stSubName As String

Private Sub Command2_Click()
On Error GoTo Err_Command2_Click
Dim stDocName As String
Dim stSubName As String

SubcontractorCombo.SetFocus
stSubName = SubcontractorCombo.SelText
'Confirm that stSubName variable is holding correct value'
MsgBox "Name of Subcontractor Selected is " & stSubName

SetSubName stSubName
GetSubName

DoCmd.Close

stDocName = "Summary Asphalt Production for Subcontractor"
DoCmd.OpenQuery stDocName

Exit_Command2_Click:
Exit Sub

Err_Command2_Click:
MsgBox Err.Description
Resume Exit_Command2_Click

End Sub

Public Sub SetSubName(Value As String)
'Set the module variable to be the value passed in from externally'
stSubName = Value
End Sub

Public Function GetSubName() As String
'Returns the value of the module variable'
GetSubName = stSubName
'MsgBox "GetSubName Variable is " & stSubName'

End Function

这是我在Access 2007内部的SQL:

SELECT DISTINCTROW Subs.Subcontractor, Counties.County, Projects.ContractID,
Sum(Project_Items.USTons) AS SumOfUSTons, Projects.PlanQuantity,
Max(Project_Items.EstDate) AS MaxOfEstDate, Project_Items.Sub
FROM Counties INNER JOIN (Subs INNER JOIN (Projects INNER JOIN Project_Items ON  
Projects.ContractID = Project_Items.ProjectID) ON Subs.VendID = Project_Items.Sub) ON 
Counties.ID = Project_Items.County
WHERE (((Projects.Completed)<>True) AND ((Subs.Subcontractor)=GetSubName()))
GROUP BY Subs.Subcontractor, Counties.County, Projects.ContractID,   
Projects.PlanQuantity, Project_Items.Sub;

3 个答案:

答案 0 :(得分:2)

无法识别功能的原因是您尚未完全指定名称。需要使用表单名称

指定表单模块中的公共函数
  Forms!MyForm.GetSubName()

但这是错误的做法,你的代码太复杂了。您可以直接在查询中访问组合框的值:

  Forms!MyForm!SubcontractorCombo

现在,你正在使用.SelText的事实告诉我,你做的事情非常棘手,或者你的组合框设置错误。组合框可以具有找到的字段和显示值,这样员工列表可以显示员工LastName / FirstName,而组合框实际上具有EmployeeID作为其绑定字段。

如果您的组合框有一个隐藏的绑定字段,但您想要显示的值,则不需要使用.SelText - 只需使用组合框的相应.Column():

  Forms!MyForm!SubcontractorCombo.Column(1)

(列数从零开始,因此隐藏列将为第0列,假设它是隐藏的第一列)

此外,还有一个问题是,如果用户选择组合框中文本的PART,则表示您的匹配不完整,所以您根本不想使用.SelText。

因此,SQL的WHERE子句最终会成为这个(假设我已经正确地诊断了所有内容):

  WHERE Projects.Completed<>True 
     AND Subs.Subcontractor=Forms!MyForm!SubcontractorCombo.Column(1)

...您可能会丢失所有标记的代码:

Option Compare Database
Option Explicit
<strike>Private stSubName As String</strike>

Private Sub Command2_Click()
On Error GoTo Err_Command2_Click
  Dim stDocName As String
  Dim stSubName As String

  SubcontractorCombo.SetFocus
  <strike>stSubName = SubcontractorCombo.SelText</strike>
  'Confirm that stSubName variable is holding correct value'
  <strike>MsgBox "Name of Subcontractor Selected is " & stSubName</strike>

  <strike>SetSubName stSubName</strike>
  <strike>GetSubName</strike>

  DoCmd.Close

  stDocName = "Summary Asphalt Production for Subcontractor"
  DoCmd.OpenQuery stDocName

Exit_Command2_Click:
  Exit Sub

Err_Command2_Click:
  MsgBox Err.Description
  Resume Exit_Command2_Click

End Sub

<strike>Public Sub SetSubName(Value As String)
  'Set the module variable to be the value passed in from externally'
  stSubName = Value
End Sub</strike>

<strike>Public Function GetSubName() As String
  'Returns the value of the module variable'
  GetSubName = stSubName
  'MsgBox "GetSubName Variable is " & stSubName'    
End Function</strike>

答案 1 :(得分:0)

替代方法会有效吗?

使用一个字段创建一个表( SubNameTable ): SubName

添加一条记录。

然后将您的Sub更改为:

Public Sub SetSubName(Value As String)
  CurrentDb.Execute ("Update SubNameTable Set SubName = '" & Value & "'")
End Sub

现在您可以删除函数和模块变量。

然后,改变你的SQL:

SELECT 
  *BlahBlahBlahFields*
FROM 
     *BlahBlahBlahTables* 
              INNER JOIN Subs 
                 INNER JOIN SubNameTable ON Subs.SubContractor = SubNameTable.SubName
WHERE (((Projects.Completed)<>True) 
GROUP BY 
          Subs.Subcontractor, 
          Counties.County, 
          Projects.ContractID,   
          Projects.PlanQuantity, 
          Project_Items.Sub

答案 2 :(得分:0)

并不是说这是最好的解决方案,而是应该解决尝试在表单中引用函数的未来问题。您可以在查询中使用参数并将其值设置为组合框。

您应该将公共功能放在模块中。我称之为 Module2

Option Compare Database
Option Explicit


Private stSubName As String

Public Sub SetSubName(Value As String)
'Set the module variable to be the value passed in from externally'
stSubName = Value
End Sub

Public Function GetSubName() As String
'Returns the value of the module variable'
GetSubName = stSubName
'MsgBox "GetSubName Variable is " & stSubName'

End Function

您的表单将引用模块中的功能:

Option Compare Database
Option Explicit
Private stSubName As String

Private Sub Command2_Click()
On Error GoTo Err_Command2_Click
Dim stDocName As String
Dim stSubName As String

SubcontractorCombo.SetFocus
stSubName = SubcontractorCombo.SelText
'Confirm that stSubName variable is holding correct value'
MsgBox "Name of Subcontractor Selected is " & stSubName

Module2.SetSubName stSubName
Module2.GetSubName

DoCmd.Close

stDocName = "Summary Asphalt Production for Subcontractor"
DoCmd.OpenQuery stDocName

Exit_Command2_Click:
Exit Sub
Err_Command2_Click:
MsgBox Err.Description
Resume Exit_Command2_Click
End Sub

查询将能够在模块中找到公共功能。