GITのすばらしいVFRPDFビューアからのObjCコードを持っています。CGPDFDictionaryGetString
PDF注釈から文字列へのポインタを取得するために使用しています。次に、バイトポインタ変換を使用して最終的な文字列を取得します。Monotouchには、文字列を返すCGPDFDictionary.GetString()
唯一.GetName()
のメソッドがありますが、これは正しいメソッドである必要があると思いましたが、機能しません。配列、辞書、浮動小数点数、整数を問題なく取得できます。文字列だけが機能していないようです。
以下の小さなコード例を参照してください。
CGPDFStringRef uriString = NULL;
// This returns TRUE in the ObjC version and uriString is a valid pointer to a string.
if (CGPDFDictionaryGetString(actionDictionary, "URI", &uriString) == true)
{
// Do some pointer magic - how to do this in MT? Do I have to at all?
const char *uri = (const char *)CGPDFStringGetBytePtr(uriString);
// *uri now contains a URL, I can see it in the debugger.
}
私はそれをそのように翻訳しました:
string sUri = null;
// This returns FALSE. Hence my sUri is NULL. Seems like GetName() is not the analogy to CGPDFDictionaryGetString.
if(oActionDic.GetName("URI", out sUri))
{
// I never get here.
}
編集: Monoソースを見ると、マスターブランチでこれを見ることができます: // TODO:GetString->CGPDFStringを返します
ブランチ4.2に切り替えると、そこにあるように見えます。そこで、そこからコードをコピーしましたが、2つの問題があります。
- 「unsafe」キーワードについてエラーが発生します。「安全でない」コマンドラインオプションを追加するように指示されます。それは何ですか、それを追加するのは良い考えですか?どこ?
- とにかく実行されているようですが、CGPDFStringを取得するとアプリがハングします。
[DllImport(Constants.CoreGraphicsLibrary)] public extern static IntPtr CGPDFStringGetLength(IntPtr pdfStr);
[DllImport (Constants.CoreGraphicsLibrary)]
public extern static IntPtr CGPDFStringGetBytePtr (IntPtr pdfStr);
public static string PdfStringToString (IntPtr pdfString)
{
if (pdfString == IntPtr.Zero)
return null;
int n = (int)CGPDFStringGetLength (pdfString);
unsafe
{
return new String ((char *)CGPDFStringGetBytePtr (pdfString), 0, n);
}
}
[DllImport (Constants.CoreGraphicsLibrary)]
extern static bool CGPDFDictionaryGetString (IntPtr handle, string key, out IntPtr result);
public static bool GetStringFromPdfDictionary (CGPDFDictionary oPdfDic, string key, out string result)
{
if (key == null)
throw new ArgumentNullException ("key");
IntPtr res;
if (CGPDFDictionaryGetString (oPdfDic.Handle, key, out res))
{
result = PdfStringToString (res);
return true;
}
result = null;
return false;
}