How do I print a WebView using KitKat 4.4 print API via reflection?

前端 未结 2 1047
遥遥无期
遥遥无期 2021-01-15 00:35

I need to support printing on KitKat devices but my target SDK is 13 (changing is not an option).

Specifically I need to print a webview.

This is the API for

相关标签:
2条回答
  • 2021-01-15 00:35

    It's an old one but printing is kind of usefull so this could be good to work correctly. (Without reflection ;))

    A better way to work with devices version. No try-catch needed, just need to add some messages before the return or you just hide the button/menu/... depending on the same condition.

    @TargetApi(Build.VERSION_CODES.KITKAT)
        private void createWebPrintJob(WebView webView) {
            if (Build.VERSION.SDK_INT < Build.VERSION_CODES.KITKAT) 
                return;
    
            // Get a PrintManager instance
            PrintManager printManager = (PrintManager) getSystemService(Context.PRINT_SERVICE);
    
            // Get a print adapter instance
            PrintDocumentAdapter printAdapter = webView.createPrintDocumentAdapter();
    
            // Create a print job with name and adapter instance
            String jobName = getString(R.string.app_name) + " Document";
            printManager.print(jobName, printAdapter,
                    new PrintAttributes.Builder().build());
    
        }
    

    The printJob will be execute only with SDK 19 and above

    0 讨论(0)
  • 2021-01-15 00:38

    Here is my solution:

    public void print(WebView webView) {
        //PrintManager
        String PRINT_SERVICE = (String) Context.class.getDeclaredField("PRINT_SERVICE").get(null);
        Object printManager = mActivity.getSystemService(PRINT_SERVICE);
    
        //PrintDocumentAdapter
        Class<?> printDocumentAdapterClass = Class.forName("android.print.PrintDocumentAdapter");
        Method createPrintDocumentAdapterMethod = webview.getClass().getMethod("createPrintDocumentAdapter");
        Object printAdapter = createPrintDocumentAdapterMethod.invoke(webview);
    
        //PrintAttributes
        Class<?> printAttributesBuilderClass = Class.forName("android.print.PrintAttributes$Builder");
        Constructor<?> ctor = printAttributesBuilderClass.getConstructor();
        Object printAttributes = ctor.newInstance(new Object[] {});
        Method buildMethod = printAttributes.getClass().getMethod("build");
        Object printAttributesBuild = buildMethod.invoke(printAttributes);
    
        //PrintJob
        String jobName = "My Document";
        Method printMethod = printManager.getClass().getMethod("print", String.class, printDocumentAdapterClass, printAttributesBuild.getClass());
        Object printJob = printMethod.invoke(printManager, jobName, printAdapter, printAttributesBuild);
    
        // Save the job object for later status checking
        mPrintJobs.add(printJob);
    }
    

    Just make sure this is called on the main thread. Also note: You need to use a try catch. Devices which are not running 4.4+ will crash if you don't.

    0 讨论(0)
提交回复
热议问题