|  | /* | 
|  | * Copyright (C) 2013 The Android Open Source Project | 
|  | * | 
|  | * Licensed under the Apache License, Version 2.0 (the "License"); | 
|  | * you may not use this file except in compliance with the License. | 
|  | * You may obtain a copy of the License at | 
|  | * | 
|  | *      http://www.apache.org/licenses/LICENSE-2.0 | 
|  | * | 
|  | * Unless required by applicable law or agreed to in writing, software | 
|  | * distributed under the License is distributed on an "AS IS" BASIS, | 
|  | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | 
|  | * See the License for the specific language governing permissions and | 
|  | * limitations under the License. | 
|  | */ | 
|  |  | 
|  | package android.print; | 
|  |  | 
|  | import android.compat.annotation.UnsupportedAppUsage; | 
|  | import android.os.Bundle; | 
|  | import android.os.CancellationSignal; | 
|  | import android.os.ParcelFileDescriptor; | 
|  |  | 
|  | /** | 
|  | * Base class that provides the content of a document to be printed. | 
|  | * | 
|  | * <h3>Lifecycle</h3> | 
|  | * <p> | 
|  | * <ul> | 
|  | * <li> | 
|  | * Initially, you will receive a call to {@link #onStart()}. This callback | 
|  | * can be used to allocate resources. | 
|  | * </li> | 
|  | * <li> | 
|  | * Next, you will get one or more calls to {@link #onLayout(PrintAttributes, | 
|  | * PrintAttributes, CancellationSignal, LayoutResultCallback, Bundle)} to | 
|  | * inform you that the print attributes (page size, density, etc) changed | 
|  | * giving you an opportunity to layout the content to match the new constraints. | 
|  | * </li> | 
|  | * <li> | 
|  | * After every call to {@link #onLayout(PrintAttributes, PrintAttributes, | 
|  | * CancellationSignal, LayoutResultCallback, Bundle)}, you <strong>may</strong> get | 
|  | * a call to {@link #onWrite(PageRange[], ParcelFileDescriptor, CancellationSignal, | 
|  | * WriteResultCallback)} asking you to write a PDF file with the content for | 
|  | * specific pages. | 
|  | * </li> | 
|  | * <li> | 
|  | * Finally, you will receive a call to {@link #onFinish()}. You can use this | 
|  | * callback to release resources allocated in {@link #onStart()}. | 
|  | * </li> | 
|  | * </ul> | 
|  | * <p> | 
|  | * The {@link #onStart()} callback is always the first call you will receive and | 
|  | * is useful for doing one time setup or resource allocation before printing. You | 
|  | * will not receive a subsequent call here. | 
|  | * </p> | 
|  | * <p> | 
|  | * The {@link #onLayout(PrintAttributes, PrintAttributes, CancellationSignal, | 
|  | * LayoutResultCallback, Bundle)} callback requires that you layout the content | 
|  | * based on the current {@link PrintAttributes}. The execution of this method is | 
|  | * not considered completed until you invoke one of the methods on the passed in | 
|  | * callback instance. Hence, you will not receive a subsequent call to any other | 
|  | * method of this class until the execution of this method is complete by invoking | 
|  | * one of the callback methods. | 
|  | * </p> | 
|  | * <p> | 
|  | * The {@link #onWrite(PageRange[], ParcelFileDescriptor, CancellationSignal, | 
|  | * WriteResultCallback)} requires that you render and write the content of some | 
|  | * pages to the provided destination. The execution of this method is not | 
|  | * considered complete until you invoke one of the methods on the passed in | 
|  | * callback instance. Hence, you will not receive a subsequent call to any other | 
|  | * method of this class until the execution of this method is complete by invoking | 
|  | * one of the callback methods. You will never receive a sequence of one or more | 
|  | * calls to this method without a previous call to {@link #onLayout(PrintAttributes, | 
|  | * PrintAttributes, CancellationSignal, LayoutResultCallback, Bundle)}. | 
|  | * </p> | 
|  | * <p> | 
|  | * The {@link #onFinish()} callback is always the last call you will receive and | 
|  | * is useful for doing one time cleanup or resource deallocation after printing. | 
|  | * You will not receive a subsequent call here. | 
|  | * </p> | 
|  | * </p> | 
|  | * <h3>Implementation</h3> | 
|  | * <p> | 
|  | * The APIs defined in this class are designed to enable doing part or all | 
|  | * of the work on an arbitrary thread. For example, if the printed content | 
|  | * does not depend on the UI state, i.e. on what is shown on the screen, then | 
|  | * you can offload the entire work on a dedicated thread, thus making your | 
|  | * application interactive while the print work is being performed. Note that | 
|  | * while your activity is covered by the system print UI and a user cannot | 
|  | * interact with it, doing the printing work on the main application thread | 
|  | * may affect the performance of your other application components as they | 
|  | * are also executed on that thread. | 
|  | * </p> | 
|  | * <p> | 
|  | * You can also do work on different threads, for example if you print UI | 
|  | * content, you can handle {@link #onStart()} and {@link #onLayout(PrintAttributes, | 
|  | * PrintAttributes, CancellationSignal, LayoutResultCallback, Bundle)} on | 
|  | * the UI thread (assuming onStart initializes resources needed for layout). | 
|  | * This will ensure that the UI does not change while you are laying out the | 
|  | * printed content. Then you can handle {@link #onWrite(PageRange[], ParcelFileDescriptor, | 
|  | * CancellationSignal, WriteResultCallback)} and {@link #onFinish()} on another | 
|  | * thread. This will ensure that the main thread is busy for a minimal amount of | 
|  | * time. Also this assumes that you will generate the printed content in | 
|  | * {@link #onLayout(PrintAttributes, PrintAttributes, CancellationSignal, | 
|  | * LayoutResultCallback, Bundle)} which is not mandatory. If you use multiple | 
|  | * threads, you are responsible for proper synchronization. | 
|  | * </p> | 
|  | */ | 
|  | public abstract class PrintDocumentAdapter { | 
|  |  | 
|  | /** | 
|  | * Extra: mapped to a boolean value that is <code>true</code> if | 
|  | * the current layout is for a print preview, <code>false</code> otherwise. | 
|  | * This extra is provided in the {@link Bundle} argument of the {@link | 
|  | * #onLayout(PrintAttributes, PrintAttributes, CancellationSignal, | 
|  | * LayoutResultCallback, Bundle)} callback. | 
|  | * | 
|  | * @see #onLayout(PrintAttributes, PrintAttributes, CancellationSignal, | 
|  | * LayoutResultCallback, Bundle) | 
|  | */ | 
|  | public static final String EXTRA_PRINT_PREVIEW = "EXTRA_PRINT_PREVIEW"; | 
|  |  | 
|  | /** | 
|  | * Called when printing starts. You can use this callback to allocate | 
|  | * resources. This method is invoked on the main thread. | 
|  | */ | 
|  | public void onStart() { | 
|  | /* do nothing - stub */ | 
|  | } | 
|  |  | 
|  | /** | 
|  | * Called when the print attributes (page size, density, etc) changed | 
|  | * giving you a chance to layout the content such that it matches the | 
|  | * new constraints. This method is invoked on the main thread. | 
|  | * <p> | 
|  | * After you are done laying out, you <strong>must</strong> invoke: {@link | 
|  | * LayoutResultCallback#onLayoutFinished(PrintDocumentInfo, boolean)} with | 
|  | * the last argument <code>true</code> or <code>false</code> depending on | 
|  | * whether the layout changed the content or not, respectively; or {@link | 
|  | * LayoutResultCallback#onLayoutFailed(CharSequence)}, if an error occurred; | 
|  | * or {@link LayoutResultCallback#onLayoutCancelled()} if layout was | 
|  | * cancelled in a response to a cancellation request via the passed in | 
|  | * {@link CancellationSignal}. Note that you <strong>must</strong> call one of | 
|  | * the methods of the given callback for this method to be considered complete | 
|  | * which is you will not receive any calls to this adapter until the current | 
|  | * layout operation is complete by invoking a method on the callback instance. | 
|  | * The callback methods can be invoked from an arbitrary thread. | 
|  | * </p> | 
|  | * <p> | 
|  | * One of the arguments passed to this method is a {@link CancellationSignal} | 
|  | * which is used to propagate requests from the system to your application for | 
|  | * canceling the current layout operation. For example, a cancellation may be | 
|  | * requested if the user changes a print option that may affect layout while | 
|  | * you are performing a layout operation. In such a case the system will make | 
|  | * an attempt to cancel the current layout as another one will have to be performed. | 
|  | * Typically, you should register a cancellation callback in the cancellation | 
|  | * signal. The cancellation callback <strong>will not</strong> be made on the | 
|  | * main thread and can be registered as follows: | 
|  | * </p> | 
|  | * <pre> | 
|  | * cancellationSignal.setOnCancelListener(new OnCancelListener() { | 
|  | *     @Override | 
|  | *     public void onCancel() { | 
|  | *         // Cancel layout | 
|  | *     } | 
|  | * }); | 
|  | * </pre> | 
|  | * <p> | 
|  | * <strong>Note:</strong> If the content is large and a layout will be | 
|  | * performed, it is a good practice to schedule the work on a dedicated | 
|  | * thread and register an observer in the provided {@link | 
|  | * CancellationSignal} upon invocation of which you should stop the | 
|  | * layout. | 
|  | * </p> | 
|  | * | 
|  | * @param oldAttributes The old print attributes. | 
|  | * @param newAttributes The new print attributes. | 
|  | * @param cancellationSignal Signal for observing cancel layout requests. | 
|  | * @param callback Callback to inform the system for the layout result. | 
|  | * @param extras Additional information about how to layout the content. | 
|  | * | 
|  | * @see LayoutResultCallback | 
|  | * @see CancellationSignal | 
|  | * @see #EXTRA_PRINT_PREVIEW | 
|  | */ | 
|  | public abstract void onLayout(PrintAttributes oldAttributes, PrintAttributes newAttributes, | 
|  | CancellationSignal cancellationSignal, LayoutResultCallback callback, | 
|  | Bundle extras); | 
|  |  | 
|  | /** | 
|  | * Called when specific pages of the content should be written in the | 
|  | * form of a PDF file to the given file descriptor. This method is invoked | 
|  | * on the main thread. | 
|  | *<p> | 
|  | * After you are done writing, you should close the file descriptor and | 
|  | * invoke {@link WriteResultCallback#onWriteFinished(PageRange[])}, if writing | 
|  | * completed successfully; or {@link WriteResultCallback#onWriteFailed( | 
|  | * CharSequence)}, if an error occurred; or {@link WriteResultCallback#onWriteCancelled()}, | 
|  | * if writing was cancelled in a response to a cancellation request via the passed | 
|  | * in {@link CancellationSignal}. Note that you <strong>must</strong> call one of | 
|  | * the methods of the given callback for this method to be considered complete which | 
|  | * is you will not receive any calls to this adapter until the current write | 
|  | * operation is complete by invoking a method on the callback instance. The callback | 
|  | * methods can be invoked from an arbitrary thread. | 
|  | * </p> | 
|  | * <p> | 
|  | * One of the arguments passed to this method is a {@link CancellationSignal} | 
|  | * which is used to propagate requests from the system to your application for | 
|  | * canceling the current write operation. For example, a cancellation may be | 
|  | * requested if the user changes a print option that may affect layout while | 
|  | * you are performing a write operation. In such a case the system will make | 
|  | * an attempt to cancel the current write as a layout will have to be performed | 
|  | * which then may be followed by a write. Typically, you should register a | 
|  | * cancellation callback in the cancellation signal. The cancellation callback | 
|  | * <strong>will not</strong> be made on the main thread and can be registered | 
|  | * as follows: | 
|  | * </p> | 
|  | * <pre> | 
|  | * cancellationSignal.setOnCancelListener(new OnCancelListener() { | 
|  | *     @Override | 
|  | *     public void onCancel() { | 
|  | *         // Cancel write | 
|  | *     } | 
|  | * }); | 
|  | * </pre> | 
|  | * <p> | 
|  | * <strong>Note:</strong> If the printed content is large, it is a good | 
|  | * practice to schedule writing it on a dedicated thread and register an | 
|  | * observer in the provided {@link CancellationSignal} upon invocation of | 
|  | * which you should stop writing. | 
|  | * </p> | 
|  | * | 
|  | * @param pages The pages whose content to print - non-overlapping in ascending order. | 
|  | * @param destination The destination file descriptor to which to write. | 
|  | * @param cancellationSignal Signal for observing cancel writing requests. | 
|  | * @param callback Callback to inform the system for the write result. | 
|  | * | 
|  | * @see WriteResultCallback | 
|  | * @see CancellationSignal | 
|  | */ | 
|  | public abstract void onWrite(PageRange[] pages, ParcelFileDescriptor destination, | 
|  | CancellationSignal cancellationSignal, WriteResultCallback callback); | 
|  |  | 
|  | /** | 
|  | * Called when printing finishes. You can use this callback to release | 
|  | * resources acquired in {@link #onStart()}. This method is invoked on | 
|  | * the main thread. | 
|  | */ | 
|  | public void onFinish() { | 
|  | /* do nothing - stub */ | 
|  | } | 
|  |  | 
|  | /** | 
|  | * Base class for implementing a callback for the result of {@link | 
|  | * PrintDocumentAdapter#onWrite(PageRange[], ParcelFileDescriptor, CancellationSignal, | 
|  | * WriteResultCallback)}. | 
|  | */ | 
|  | public static abstract class WriteResultCallback { | 
|  |  | 
|  | /** | 
|  | * @hide | 
|  | */ | 
|  | @UnsupportedAppUsage | 
|  | public WriteResultCallback() { | 
|  | /* do nothing - hide constructor */ | 
|  | } | 
|  |  | 
|  | /** | 
|  | * Notifies that all the data was written. | 
|  | * | 
|  | * @param pages The pages that were written. Cannot be <code>null</code> | 
|  | *        or empty. <br /> | 
|  | *        Returning {@link PageRange#ALL_PAGES} indicates that all pages that were | 
|  | *        requested as the {@code pages} parameter in {@link #onWrite} were written. | 
|  | */ | 
|  | public void onWriteFinished(PageRange[] pages) { | 
|  | /* do nothing - stub */ | 
|  | } | 
|  |  | 
|  | /** | 
|  | * Notifies that an error occurred while writing the data. | 
|  | * | 
|  | * @param error The <strong>localized</strong> error message. | 
|  | * shown to the user. May be <code>null</code> if error is unknown. | 
|  | */ | 
|  | public void onWriteFailed(CharSequence error) { | 
|  | /* do nothing - stub */ | 
|  | } | 
|  |  | 
|  | /** | 
|  | * Notifies that write was cancelled as a result of a cancellation request. | 
|  | */ | 
|  | public void onWriteCancelled() { | 
|  | /* do nothing - stub */ | 
|  | } | 
|  | } | 
|  |  | 
|  | /** | 
|  | * Base class for implementing a callback for the result of {@link | 
|  | * PrintDocumentAdapter#onLayout(PrintAttributes, PrintAttributes, | 
|  | * CancellationSignal, LayoutResultCallback, Bundle)}. | 
|  | */ | 
|  | public static abstract class LayoutResultCallback { | 
|  |  | 
|  | /** | 
|  | * @hide | 
|  | */ | 
|  | @UnsupportedAppUsage | 
|  | public LayoutResultCallback() { | 
|  | /* do nothing - hide constructor */ | 
|  | } | 
|  |  | 
|  | /** | 
|  | * Notifies that the layout finished and whether the content changed. | 
|  | * | 
|  | * @param info An info object describing the document. Cannot be <code>null</code>. | 
|  | * @param changed Whether the layout changed. | 
|  | * | 
|  | * @see PrintDocumentInfo | 
|  | */ | 
|  | public void onLayoutFinished(PrintDocumentInfo info, boolean changed) { | 
|  | /* do nothing - stub */ | 
|  | } | 
|  |  | 
|  | /** | 
|  | * Notifies that an error occurred while laying out the document. | 
|  | * | 
|  | * @param error The <strong>localized</strong> error message. | 
|  | * shown to the user. May be <code>null</code> if error is unknown. | 
|  | */ | 
|  | public void onLayoutFailed(CharSequence error) { | 
|  | /* do nothing - stub */ | 
|  | } | 
|  |  | 
|  | /** | 
|  | * Notifies that layout was cancelled as a result of a cancellation request. | 
|  | */ | 
|  | public void onLayoutCancelled() { | 
|  | /* do nothing - stub */ | 
|  | } | 
|  | } | 
|  | } |