2

Linea Pro(Apple Stores、Lowesで使用されているバーコードスキャナー)SDKへのバインディングを作成しようとしています。David Sandorのバインディングを参照として使用していますが、SDKは2011年1月から数回更新されています。

Linea Proデバイスでサウンドを再生するために使用される playSound呼び出しを除いて、ほとんどすべてが機能しています。

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に真剣に精通していないので、助けていただければ幸いです。

4

2 に答える 2

1

NSArrayObjective-C コードが を使用しない限り、を使用することはできませんNSArray。つまり、ジェネレーターにより、一部の ObjC 構造を .NET 型 (たとえば ) にマップNSStringできstringますが、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);

これは、内部バインディングを呼び出すパブリック ヘルパー メソッドを使用して行うのが最適です。メソッドの定義に属性を追加することでPlaySoundメソッドを作成できます。したがって、次のようになります。internal[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ですが、それは近いはずです。

于 2012-09-15T23:52:39.680 に答える
1

私は同じ問題を抱えていました。ただし、上記の poupou によって提供されたヘルプは、私を正しい軌道に乗せるのに十分でした。私の linea pro デバイスは、要求するとビープ音を 2 回鳴らすようになったので、テスト済みのコードを実行してフォローアップする必要があると考えました。スタイルの混乱を許してください、これは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;

    }
于 2013-03-14T23:41:06.700 に答える