问题: 如何在通用Windows平台(UWP)应用程序中创建COM对象?
动机: 我想从WPF切换到UWP.由于我的工作量要求只能通过COM访问第三方库(据我所知),我需要从UWP进行COM调用.
语境:
背景
在Visual Studio 2013(Visual Studio 2015中的"经典桌面"项目)中,我使用了C#代码
// Conceptual:
DotNetInterface comObjectInstance =
(DotNetInterface)Microsoft.VisualBasic.Interaction.CreateObject(
"this string specified the COM object type"
);
// Example: Open Excel via COM:
Excel.Application oApp = (Excel.Application)Interaction.CreateObject("Excel.Application");
Run Code Online (Sandbox Code Playgroud)
Visual Studio项目需要Microsoft.VisualBasic使用Interaction.CreateObject()和COM对象的类型库的引用.
我想在Windows 10 Education上的Visual Studio 2015 Enterprise生成的通用Windows平台(UWP)应用程序中使用此C#代码.我能够添加对COM对象的类型库的引用,但无法引用,Microsoft.VisualBasic因为它没有出现在Visual Studio的Reference Manager中.
思考,尝试过的解决方案,猜测等
我添加了对"UWP的Windows桌面扩展"的引用,希望它可以启用对正常.NET功能的调用,但还没有弄清楚如何使用它.
我认为即使UWP应用程序从根本上不能进行COM调用,我们至少可以构造一个调用正常.NET程序的包装器(即使通过网络端口),这反过来又可以运行COM调用.由于即使在最糟糕的情况下显然也可以解决这个问题,我觉得微软提供的COM对象应该是(并且可能是)提供的解决方案.但我想自从UWP这么新以来,在线文档很稀疏,现在很难找到.
更新#1
发现了MSDN文章,Win32和COM for Windows Runtime应用程序和通用Windows平台(UWP)应用程序,声称WinRT应用程序(包括UWP应用程序)只能使用COM对象的子集.MSDN建议使用受支持的COM API元素或从不受支持的COM API迁移到功能替换.
我找到一种方法对我的第三方库进行COM调用后,通过谷歌搜索运行时错误找到了这篇文章.错误:
mscorlib.ni.dll中出现"System.Runtime.InteropServices.COMException"类型的异常,但未在用户代码中处理
附加信息:由于以下错误,使用CoCreateInstanceFromApp创建具有CLSID {[edit:GUID已删除]}的COM组件实例失败:80040154未注册类(HRESULT异常:0x80040154(REGDB_E_CLASSNOTREG)).请确保您的COM对象位于允许的CoCreateInstanceFromApp列表中.
我仍然不确定是否有一种内置方式来访问我的第三方库的COM API.如果没有,这可能意味着我将不得不使用网络端口或其他东西制作我自己的包装器,这似乎是错误的.
更新: 此问题已经过修改,以使其更加清晰.下面的答案似乎反映出这种方法效果很好.希望这个问题可以帮助那些需要添加get或者添加set现有财产的人.
今天遇到一个问题,我需要get用a get和覆盖基类的-only属性set.目前的共识似乎是这是不可能的,但我认为我找到了一种方法.
一般的想法是创建一个new属性而不是直接override使用旧属性,然后我们通过调用新方法创建一个override旧get方法的桥接方法.
这是一些无法修改的任意预先存在的类型结构的代码.
public abstract class A
{
public abstract int X { get; }
}
public class B : A
{
public override int X { get { return 0; } }
}
Run Code Online (Sandbox Code Playgroud)
我们想编写这段代码,但不会编译.
public class C : B // won't compile: X can't have a 'set' method
{
private int _x;
public override int X …Run Code Online (Sandbox Code Playgroud) 我怎样才能创建一个透明地转发连接到新IP地址/端口的程序?
例如,如果客户端发起TCP连接的IP地址为111.111.111.111,TCP端口为111,则可以将程序配置为转发该数据包和IP /端口222.222.222.222:222.
透明地,我的意思是:
我想用.NET,C#和Windows来做这件事.但我不想创建一个简单的TCP代理,因为各种各样但未指明的原因.如果无法做到这一点,那么在没有可能的解决方案的情况下,这可能是一个可接受的答案.
在 Win7 x64 上的 Visual Studio 2012 Ult 中使用 .NET 4.5 中的 C#。
我试图让服务器通过该System.Net.Sockets.Socket.SendFile(string filename)方法传输文件,让客户端接收它。客户端将接收到的字节附加到它创建的文件的末尾,以在其一侧重建发送的文件。这一切都有效——至少对于基本的文本文件。
当我尝试发送 *.exe 文件时,收到的 *.exe 不起作用。在 Notepad++ 中打开源 *.exe 和客户端副本,看起来文件是正确的,只是一些看起来很奇怪的字符不正确。我的问题是我该如何解决这个问题?
由于服务器代码实际上只是发送文件Socket.SendFile(string filename)而没有其他可用的相关选项,我假设客户端是问题所在。
在客户端:
private void ListenAndReport(Socket socket)
{
EndPoint remoteEndPoint = socket.RemoteEndPoint;
ReceiveObject obj = new ReceiveObject(socket);
socket.BeginReceive(obj.buffer, 0, packetSize, SocketFlags.None, new AsyncCallback(ReceiveFromListen), obj);
}
private void ReceiveFromListen(IAsyncResult ar)
{
ReceiveObject obj = (ReceiveObject)ar.AsyncState; //ReceiveObject just holds a byte[packetSize] buffer and a Socket
string received = Encoding.UTF8.GetString(obj.buffer);
WriteToFile(received);
obj.socket.EndReceive(ar); //!!! necessary? Doesn't …Run Code Online (Sandbox Code Playgroud)