我正在从EmguCV扩展ImageBox控件。控件的Image
属性可以设置为实现IImage
接口的任何内容。
以下所有实现此接口:
Image<Bgr, Byte>
Image<Ycc, Byte>
Image<Hsv, Byte>
现在我想在上述类型的对象上调用Draw
方法(无论它是什么)。
问题是当我访问Image属性时,返回类型为IImage
。 IImage没有实现Draw
方法,但上述所有方法都是如此。
我相信我可以将IImage
类型的对象转换为上面的一个(右边的),然后我可以访问Draw
方法。但我怎么知道正确的是什么?如果您有更好的方法,请同时提出建议。
修改
很抱歉,但我忘了提一条重要信息。上述每个类的Draw方法都有一个不同的参数。对于例如Draw
的{{1}}采用Image<Bgr, Byte>
类型的参数,Bgr
的{{1}}采用类型为Draw
的参数。
答案 0 :(得分:3)
添加一个继承自IImage的IDrawableImage。
public interface IDrawableImage : IImage
{
void Draw(object val);
void Draw();
}
然后您可以简单地执行以下操作:
var drawableImage = container.Image as IDrawableImage;
if (drawableImage != null)
drawableImage.Draw();
符合上述说明:
public interface IDrawableImage<T, B> : IDrawableImage where B : byte
{
void Draw<T>(T val);
}
然后如果您知道类型:
var value = new Hvr();
var drawableImage = container.Image as IDrawableImage<Hvr, Byte>;
if (drawableImage != null)
drawableImage.Draw(value);
如果你不
var value = new Hvr();
var drawableImage = container.Image as IDrawableImage;
if (drawableImage != null)
drawableImage.Draw(value);
答案 1 :(得分:1)
如果我理解正确 - Image类实现了draw方法。我不知道你将如何使用它,但你可以这样做:
private void DrawImage<T1, T2>(Image<T1, T2> image)
{
image.Draw();
}
上面的主要问题是上述方法的调用者应该指定T1和T2类型。
如果您无法控制IImage接口及其实现,那么我认为您将从两个解决方案中进行选择:指定T1和T2类型,或者使用ifs / switch以及所有可能的IImage实现。
如果您可以访问IImage接口和Image类,那么您应该添加通用IImage接口并向其添加Draw方法。
答案 2 :(得分:1)
你应该有一个添加Draw()的共享界面。
答案 3 :(得分:0)
这样的事情怎么样:
void foo( IImage image )
{
if ( image is Image<Bgr, Byte> )
{
((Image<Bgr, Byte>)(image)).Draw();
}
// handle the other types the same way.
}
答案 4 :(得分:0)
如果你确定Image&lt; T,U&gt;您将拥有(无论类型)将具有Draw方法,您可以使用反射和黑客围绕它:
我会将其作为扩展方法:
public static void Draw(this IImage image)
{
var method = image.GetType().GetMethod("Draw");
if(method != null)
{
method.Invoke(image,null);
}
}
有点黑客,但话说回来,我会说API没有正确设计。至少应该有一些Drawer类或者知道如何对图像进行操作的东西。
答案 5 :(得分:0)
您的问题缺少一条重要的信息:您想写的代码。
我们需要知道你打算如何编写调用Draw(...)
方法的代码。
答案 6 :(得分:0)
或者,您可以使用动态方法并抓住机会。