【问题标题】:Monotouch Binding to Linea Pro SDKMonotouch 绑定到 Linea Pro SDK
【发布时间】:2012-09-15 21:34:05
【问题描述】:

我正在尝试创建与 Linea Pro(这是他们在 Apple Stores, Lowes 中使用的条形码扫描仪)SDK 的绑定。我使用 David Sandor's 绑定作为参考,但 SDK 自 2011 年 1 月以来已经更新了几次。

除了 playSound 调用外,我几乎所有的东西都在工作,它用于在 Linea Pro 设备上播放声音。

SDK 中的 .h 文件调用如下:

-(BOOL)playSound:(int)volume beepData:(int *)data length:(int)length error:(NSError **)error;

我尝试使用 int[]、NSArray 和 IntPtr 到 int[],但似乎没有任何效果。

我的绑定的最后一次不成功的迭代看起来像:

[Export ("playSound:beepData:length:")]
void PlaySound (int volume, NSArray data, int length);

现在,这根本行不通。另请注意,我也不知道如何处理 error:(NSError **)error 部分。

我对 C 缺乏一定的了解,因此非常感谢任何帮助。

【问题讨论】:

    标签: c# ios binding xamarin.ios linea-pro


    【解决方案1】:

    除非 Objective-C 代码使用 NSArray,否则您不能使用 NSArray,即生成器允许我们将一些 ObjC 构造映射到 .NET 类型(例如,NSStringstring),但它不允许你重新定义 ObjC 类型。

    -(BOOL)playSound:(int)volume beepData:(int *)data length:(int)length error:(NSError **)error;
    

    应该是这样的:

    [Export ("playSound:beepData:length:error:")]
    bool PlaySound (int volume, IntPtr data, int length, out NSError error);
    

    您需要将data 编组为IntPtr

    IntPtr data = Marshal.AllocHGlobal (length);
    Marshal.WriteInt32 (data1, 0);
    

    然后释放它。

    Marshal.FreeHGlobal (data);
    

    最好使用调用 internal 绑定的公共辅助方法来完成。您可以通过在其定义中添加[Internal] 属性来创建PlaySound 方法internal。于是就变成了:

    [Export ("playSound:beepData:length:error:")][Internal]
    bool PlaySound (int volume, IntPtr data, int length, out NSError error);
    

    并且您在绑定中包含以下代码(例如 API.cs):

    bool PlaySound (int volume, int[] data)
    {
        // I assume length is byte-based (check the docs)
        int length = data.Length * 4; 
        IntPtr p = Marshal.AllocHGlobal (length);
        int j = 0;
        for (int i=0; i < length; i+=4)
            Marshal.WriteInt32 (p [j++], i);
        NSError error;
        bool result = PlaySound (volume, p, length, out error);
        // free memory before throwing the exception (if any)
        Marshal.FreeHGlobal (data);
        if (error != null)
           throw new Exception (error.LocalizedDescription);
        return result;
    }
    

    注意:完全没有尝试过 :-) 我没有硬件、SDK 或文档。 YMMV,但应该很接近。

    【讨论】:

    • 你是一个绅士和一个学者。我明天早上试试这个。谢谢!
    • 这是不行的。 Mono 对 Marshal.WriteInt32 (p [j++], i) 犹豫不决,所以我将其更改为 Marshal.WriteInt32 (p, i, data[j++]),仍然没有。还尝试使用 GCHandle.Alloc 获取 IntPtr,没有。我在 xcode 中尝试过,int sound[]={2730,150,0,30,2730,2730}; int size = sizeof(sound); [linea playSound:100 beepData:sound length:size error:nil];,这很有效。当调试器点击实际的 PlaySound 行时,应用程序输出显示 -[Linea playSound:beepData:length:error]: unrecognized selector sent to instance 0xa2e6b40,但没有引发真正的错误。
    • 我不知道你的原始数据格式是什么。查看其他Marshal 方法(如Copy)来复制您的数据。您也可以尝试将其绑定为(int*) 并在您的辅助方法中使用unsafe fixed。但是没有硬件和上下文我们所能做的就是猜测;-)
    • @jeffrapp 导出应该是:[Export ("playSound:beepData:length:error:")]。这将防止无法识别的选择器问题。请注意末尾的“:”,这是必需的。
    【解决方案2】:

    我也遇到了同样的问题。然而,上面 poupou 提供的帮助足以让我走上正轨。我的 linea pro 设备现在在我要求它时会发出双哔声,所以我认为我应该跟进工作测试代码。原谅任何风格混乱,这是我在 stackoverflow 上的第一篇文章......

    这是我使用的导出定义。和上面建议的一样,只是想验证它是否有效。

        [Export ("playSound:beepData:length:error:")]
        bool PlaySound (int volume, IntPtr data, int length, out NSError error);
    

    从那里开始,我只需要学习足够多的 c# 就可以搞定编组。 (我也是 c# 的新手)如您所见,这只是上面发布的内容的一个修补。非常感谢您为我指明了正确的方向!

        public void Beep()
        {
            int[] sound = {2730, 150, 0, 30, 2730, 150};
            PlaySound(100, sound);
        }
    
        public bool PlaySound(int volume, int[] data)
        {
    
            // length is byte-based
            int length = data.Length*4;
            IntPtr p = Marshal.AllocHGlobal(length);
    
            for (int i = 0; i < data.Length; i ++)
            {
                Marshal.WriteInt32(p, i*4, data[i]);
            }
    
            NSError error;
            bool result = dtDevice.PlaySound(volume, p, length, out error);
    
            // free memory before throwing the exception (if any)
            Marshal.FreeHGlobal(p);
    
            if (error != null)
                throw new Exception(error.LocalizedDescription);
    
            return result;
    
        }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多