using System; using System.IO; using System.Runtime.InteropServices; using CC = System.Runtime.InteropServices.CallingConvention; namespace MuPdfSharp { static partial class NativeMethods { #region Object creation [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_null")] internal static extern IntPtr NewNull(ContextHandle ctx, DocumentHandle doc); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_bool")] internal static extern IntPtr NewBoolean(ContextHandle ctx, DocumentHandle doc, int boolean); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_int")] internal static extern IntPtr NewInteger(ContextHandle ctx, DocumentHandle doc, int value); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_real")] internal static extern IntPtr NewFloat(ContextHandle ctx, DocumentHandle doc, float value); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_string", BestFitMapping = false)] internal static extern IntPtr NewString(ContextHandle ctx, DocumentHandle doc, [MarshalAs(UnmanagedType.LPStr)] string value, int len); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_name", BestFitMapping = false)] internal static extern IntPtr NewName(ContextHandle ctx, DocumentHandle doc, [MarshalAs(UnmanagedType.LPStr)] string name); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_array")] internal static extern IntPtr NewArray(ContextHandle ctx, DocumentHandle doc, int initCap); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_dict")] internal static extern IntPtr NewDictionary(ContextHandle ctx, DocumentHandle doc, int initCap); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_indirect")] internal static extern IntPtr NewIndirectReference(ContextHandle ctx, DocumentHandle doc, int num, int gen); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_rect")] internal static extern IntPtr NewRect(ContextHandle ctx, DocumentHandle doc, Rectangle rect); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_new_matrix")] internal static extern IntPtr NewMatrix(ContextHandle ctx, DocumentHandle doc, Matrix matrix); #endregion #region Document level object and operation [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_authenticate_password", BestFitMapping = false)] internal static extern bool AuthenticatePassword(ContextHandle ctx, DocumentHandle doc, [MarshalAs(UnmanagedType.LPStr)] string password); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_trailer")] internal static extern IntPtr GetTrailer(ContextHandle ctx, DocumentHandle doc); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_count_pages")] internal static extern int CountPages(ContextHandle ctx, DocumentHandle doc); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_flush_warnings")] internal static extern void FlushWarnings(ContextHandle ctx); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_open_document", CharSet = CharSet.Unicode)] internal static extern DocumentHandle OpenPdfDocument(ContextHandle ctx, string fileName); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "pdf_needs_password")] internal static extern bool NeedsPdfPassword(ContextHandle ctx, DocumentHandle doc); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_aa_level")] internal static extern int GetAntiAliasLevel(ContextHandle ctx); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_set_aa_level")] internal static extern void SetAntiAliasLevel(ContextHandle ctx, int level); #endregion #region Fonts internal static readonly FzLoadSystemFont LoadSystemFont = RequestSystemFont; internal static readonly FzLoadSystemCjkFont LoadSystemCjkFont = RequestSystemCjkFont; internal static readonly FzLoadSystemFallbackFont LoadSystemFallbackFont = RequestSystemFallbackFont; [UnmanagedFunctionPointer(CC.Cdecl)] internal delegate IntPtr FzLoadSystemFont(IntPtr ctx, string name, int bold, int italic, int needExactMetrics); [UnmanagedFunctionPointer(CC.Cdecl)] internal delegate IntPtr FzLoadSystemCjkFont(IntPtr ctx, string name, int registry, int serifDesired); [UnmanagedFunctionPointer(CC.Cdecl)] internal delegate IntPtr FzLoadSystemFallbackFont(IntPtr ctx, int script, int language, int serif, int bold, int italic); /// 打开系统内置汉字库功能,支持老的未正确嵌入汉字库的 PDF。 [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_install_load_system_font_funcs")] internal static extern void LoadSystemFontFuncs(ContextHandle ctx, FzLoadSystemFont fz_load_system_font_fn, FzLoadSystemCjkFont fz_load_system_cjk_font_fn, FzLoadSystemFallbackFont fz_load_system_fallback_font_fn ); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_new_font_from_file", CharSet = CharSet.Ansi)] internal static extern IntPtr LoadFontFromFile(IntPtr ctx, [MarshalAs(UnmanagedType.LPStr)] string name, [MarshalAs(UnmanagedType.LPStr)] string path, int index, int useGlyphBox); static IntPtr RequestSystemFont(IntPtr ctx, [MarshalAs(UnmanagedType.LPWStr)] string name, int bold, int italic, int needExactMetrics) { System.Diagnostics.Debug.WriteLine("Requesting system font: " + name); var f = TryLoadCompatibleFont(name); if (f != null) { return LoadFontFromFile(ctx, null, f, 0, 0); //unsafe { // MuFontFlags* flags = (MuFontFlags*)GetFontFlags(p); // var n = GetFontName(ctx, p); // var f = p.MarshalAs(); //} } //var p = LoadFontFromFile(ctx, name, @"C:\Windows\Fonts\simsun.ttc", 1, 1); return IntPtr.Zero; } static IntPtr RequestSystemCjkFont(IntPtr ctx, string name, int registry, int serifDesired) { System.Diagnostics.Debug.WriteLine("Requesting system CJK font: " + name); var ff = TryLoadCompatibleFont(name); // todo: load fallback font return ff != null ? LoadFontFromFile(ctx, name, ff, 0, 1) : IntPtr.Zero; } private static string TryLoadCompatibleFont(string name) { var ff = Path.GetDirectoryName(Environment.GetFolderPath(Environment.SpecialFolder.System)) + "\\Fonts\\"; ff = name.StartsWith("SimKai", StringComparison.OrdinalIgnoreCase) || name.StartsWith("楷体_GB2312", StringComparison.OrdinalIgnoreCase) || name.StartsWith("Kaiti_GB2312", StringComparison.OrdinalIgnoreCase) ? ff + "simkai.ttf" : name.StartsWith("SimSun", StringComparison.OrdinalIgnoreCase) || name.StartsWith("宋体", StringComparison.OrdinalIgnoreCase) || name.StartsWith("STSong", StringComparison.OrdinalIgnoreCase) ? ff + "simsun.ttc" : name.StartsWith("SimHei", StringComparison.OrdinalIgnoreCase) || name.StartsWith("黑体", StringComparison.OrdinalIgnoreCase) ? ff + "simhei.ttf" : name.StartsWith("SimLi", StringComparison.OrdinalIgnoreCase) || name.StartsWith("隶书", StringComparison.OrdinalIgnoreCase) ? ff + "simli.ttf" : name.StartsWith("SimFang", StringComparison.OrdinalIgnoreCase) || name.StartsWith("仿宋_GB2312", StringComparison.OrdinalIgnoreCase) || name.StartsWith("Fangsong_GB2312", StringComparison.OrdinalIgnoreCase) ? ff + "simfang.ttf" : name.StartsWith("SimYou", StringComparison.OrdinalIgnoreCase) || name.StartsWith("幼圆", StringComparison.OrdinalIgnoreCase) ? ff + "simyou.ttf" : null; return ff; } static IntPtr RequestSystemFallbackFont(IntPtr ctx, int script, int language, int serif, int bold, int italic) { System.Diagnostics.Debug.WriteLine("Requesting fallback font: " + script); return IntPtr.Zero; } [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_font_ft_face")] internal static extern IntPtr GetFontFace(ContextHandle ctx, IntPtr font); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_font_flags")] internal static extern MuFontFlags GetFontFlags(IntPtr font); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_font_name")] internal static unsafe extern sbyte* GetFontName(ContextHandle ctx, IntPtr font); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_font_bbox")] internal static extern BBox GetFontBBox(ContextHandle ctx, IntPtr font); #endregion #region Stream and file [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_buffer_storage")] internal static extern int BufferStorage(ContextHandle ctx, IntPtr buffer, ref IntPtr data); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_open_faxd")] internal static extern IntPtr DecodeCcittFax(ContextHandle ctx, StreamHandle stmChain, int k, int endOfLine, int encodedByteAlign, int columns, int rows, int endOfBlock, int blackIs1); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_drop_buffer")] internal static extern void DropBuffer(ContextHandle ctx, IntPtr buffer); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_tell")] internal static extern int GetPosition(ContextHandle ctx, StreamHandle stm); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_keep_stream")] internal static extern IntPtr Keep(ContextHandle ctx, StreamHandle stm); /// 打开文本流。 /// MuPDF 上下文指针。 /// 要打开的文件名。 /// 指向 fz_stream 的指针 [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_open_file_w", CharSet = CharSet.Unicode)] internal static extern IntPtr OpenFile(ContextHandle ctx, string fileName); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_open_memory")] internal static extern IntPtr OpenMemory(ContextHandle ctx, byte[] data, int len); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_open_memory")] internal static extern IntPtr OpenMemory(ContextHandle ctx, IntPtr data, int len); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_read")] internal static extern int Read(ContextHandle ctx, StreamHandle stm, byte[] buffer, int len); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_read_all")] internal static extern IntPtr ReadAll(ContextHandle ctx, StreamHandle stm, int initial); [DllImport(DLL, CallingConvention = CC.Cdecl, EntryPoint = "fz_seek")] internal static extern void Seek(ContextHandle ctx, StreamHandle stm, int offset, int whence); #endregion } }