代码之家  ›  专栏  ›  技术社区  ›  Gael

自动将本机dll复制到Visual Studio中引用项目的bin文件夹

  •  2
  • Gael  · 技术社区  · 7 年前

    如果我将生成操作设置为 所容纳之物 ,它们将被复制到bin文件夹,但保持文件夹结构,因此它们将不在bin文件夹中,而是在子文件夹中。因此,在运行程序时,它将无法解析dll,因为它们位于子文件夹中。

    例如,如果我在项目文件中有此代码

    <Choose>
        <When Condition=" '$(Platform)'=='x86' ">
          <ItemGroup>
            <Content Include="nativedll\somelib\x86\somelib.dll">
              <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
            </Content>
          </ItemGroup>
        </When>
        <When Condition=" '$(Platform)'=='x64' ">
          <ItemGroup>
            <Content Include="nativedll\somelib\x64\somelib.dll">
              <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
            </Content>
          </ItemGroup>
        </When>
      </Choose>
    

    dll将位于文件夹中 bin\nativedll\somelib\x86\somelib.dll 对于x86。

    所以我试着使用后期构建脚本

    <PostBuildEvent>
    
                IF "$(Platform)" == "x86" (
                xcopy /s /y "$(ProjectDir)\nativedll\somelib\x86" "$(TargetDir)"
                )
                IF "$(Platform)" == "x64" (
                xcopy /s /y "$(ProjectDir)\nativedll\somelib\x64" "$(TargetDir)"
                )
    </PostBuildEvent>
    

    但是dll会复制到项目的bin文件夹中,但不会复制到引用它的项目的bin文件夹中。

    所以我现在的解决方案是在使用这个脚本的所有项目中添加一个编译后脚本。

    在Visual Studio中有更好的方法来实现这一点吗?

    2 回复  |  直到 7 年前
        1
  •  5
  •   dajuric    7 年前

    尝试对每个必须复制的文件使用此选项(csproj文件-创建项目组):

    <ItemGroup>
       <ContentWithTargetPath Include="mySourcePath\myFile.dll">
        <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
        <TargetPath>myFile.dll</TargetPath>
     </ContentWithTargetPath >
    </ItemGroup>
    

    引用项目还应包含复制的文件。


    Copy native dependencies locally in a Visual Studio project

    Add native files from NuGet package to project output directory @kjbartel

        2
  •  0
  •   Gael    7 年前

    我给出了我在得到dajuric anwser之前使用的解决方案。 我更喜欢dajuric解决方案,因为它不涉及在其他文件夹中查找代码。

    <When Condition=" '$(Platform)'=='x86' ">
          <ItemGroup>
            <Content Include="nativedll\somelib\x86\somelib.dll">
              <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
            </Content>
          </ItemGroup>
        </When>
    //same for x64
        ...
    

    然后在使用本机dll初始化库之前,我用kernel32将该文件夹添加到dll查找文件夹列表中 SETDLL目录

            [DllImport("kernel32.dll", CharSet = CharSet.Unicode, SetLastError = true)]
            [return: MarshalAs(UnmanagedType.Bool)]
            static extern bool SetDllDirectory(string lpPathName);
    
     SetDllDirectory(@".\nativedll\somelib\x"+ (Environment.Is64BitProcess ? "64" : "32"));