/*
 * 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.content.pm.PackageManager;
import android.content.pm.PackageManager.NameNotFoundException;
import android.content.res.Resources.NotFoundException;
import android.os.Parcel;
import android.os.Parcelable;
import android.text.TextUtils;
import android.util.ArrayMap;
import android.util.Log;

import com.android.internal.R;

import java.util.Map;

/**
 * This class represents the attributes of a print job. These attributes
 * describe how the printed content should be laid out. For example, the
 * print attributes may state that the content should be laid out on a
 * letter size with 300 DPI (dots per inch) resolution, have a margin of
 * 10 mills (thousand of an inch) on all sides, and be black and white.
 */
public final class PrintAttributes implements Parcelable {
    /** Color mode: Monochrome color scheme, for example one color is used. */
    public static final int COLOR_MODE_MONOCHROME = 1 << 0;
    /** Color mode: Color color scheme, for example many colors are used. */
    public static final int COLOR_MODE_COLOR = 1 << 1;

    private static final int VALID_COLOR_MODES =
            COLOR_MODE_MONOCHROME | COLOR_MODE_COLOR;

    /** Duplex mode: No duplexing. */
    public static final int DUPLEX_MODE_NONE = 1 << 0;
    /** Duplex mode: Pages are turned sideways along the long edge - like a book. */
    public static final int DUPLEX_MODE_LONG_EDGE = 1 << 1;
    /** Duplex mode: Pages are turned upwards along the short edge - like a notpad. */
    public static final int DUPLEX_MODE_SHORT_EDGE = 1 << 2;

    private static final int VALID_DUPLEX_MODES =
            DUPLEX_MODE_NONE | DUPLEX_MODE_LONG_EDGE | DUPLEX_MODE_SHORT_EDGE;

    private MediaSize mMediaSize;
    private Resolution mResolution;
    private Margins mMinMargins;

    private int mColorMode;
    private int mDuplexMode = DUPLEX_MODE_NONE;

    PrintAttributes() {
        /* hide constructor */
    }

    private PrintAttributes(Parcel parcel) {
        mMediaSize = (parcel.readInt() ==  1) ? MediaSize.createFromParcel(parcel) : null;
        mResolution = (parcel.readInt() ==  1) ? Resolution.createFromParcel(parcel) : null;
        mMinMargins = (parcel.readInt() ==  1) ? Margins.createFromParcel(parcel) : null;
        mColorMode = parcel.readInt();
        mDuplexMode = parcel.readInt();
    }

    /**
     * Gets the media size.
     *
     * @return The media size or <code>null</code> if not set.
     */
    public MediaSize getMediaSize() {
        return mMediaSize;
    }

    /**
     * Sets the media size.
     *
     * @param mediaSize The media size.
     *
     * @hide
     */
    public void setMediaSize(MediaSize mediaSize) {
        mMediaSize = mediaSize;
    }

    /**
     * Gets the resolution.
     *
     * @return The resolution or <code>null</code> if not set.
     */
    public Resolution getResolution() {
        return mResolution;
    }

    /**
     * Sets the resolution.
     *
     * @param resolution The resolution.
     *
     * @hide
     */
    public void setResolution(Resolution resolution) {
        mResolution = resolution;
    }

    /**
     * Gets the minimal margins. If the content does not fit
     * these margins it will be clipped.
     * <p>
     * <strong>These margins are physically imposed by the printer and they
     * are <em>not</em> rotated, i.e. they are the same for both portrait and
     * landscape. For example, a printer may not be able to print in a stripe
     * on both left and right sides of the page.
     * </strong>
     * </p>
     *
     * @return The margins or <code>null</code> if not set.
     */
    public Margins getMinMargins() {
        return mMinMargins;
    }

    /**
     * Sets the minimal margins. If the content does not fit
     * these margins it will be clipped.
     * <p>
     * <strong>These margins are physically imposed by the printer and they
     * are <em>not</em> rotated, i.e. they are the same for both portrait and
     * landscape. For example, a printer may not be able to print in a stripe
     * on both left and right sides of the page.
     * </strong>
     * </p>
     *
     * @param margins The margins.
     *
     * @hide
     */
    public void setMinMargins(Margins margins) {
        mMinMargins = margins;
    }

    /**
     * Gets the color mode.
     *
     * @return The color mode or zero if not set.
     *
     * @see #COLOR_MODE_COLOR
     * @see #COLOR_MODE_MONOCHROME
     */
    public int getColorMode() {
        return mColorMode;
    }

    /**
     * Sets the color mode.
     *
     * @param colorMode The color mode.
     *
     * @see #COLOR_MODE_MONOCHROME
     * @see #COLOR_MODE_COLOR
     *
     * @hide
     */
    public void setColorMode(int colorMode) {
        enforceValidColorMode(colorMode);
        mColorMode = colorMode;
    }

    /**
     * Gets whether this print attributes are in portrait orientation,
     * which is the media size is in portrait and all orientation dependent
     * attributes such as resolution and margins are properly adjusted.
     *
     * @return Whether this print attributes are in portrait.
     *
     * @hide
     */
    public boolean isPortrait() {
        return mMediaSize.isPortrait();
    }

    /**
     * Gets the duplex mode.
     *
     * @return The duplex mode.
     *
     * @see #DUPLEX_MODE_NONE
     * @see #DUPLEX_MODE_LONG_EDGE
     * @see #DUPLEX_MODE_SHORT_EDGE
     */
    public int getDuplexMode() {
        return mDuplexMode;
    }

    /**
     * Sets the duplex mode.
     *
     * @param duplexMode The duplex mode.
     *
     * @see #DUPLEX_MODE_NONE
     * @see #DUPLEX_MODE_LONG_EDGE
     * @see #DUPLEX_MODE_SHORT_EDGE
     *
     * @hide
     */
    public void setDuplexMode(int duplexMode) {
        enforceValidDuplexMode(duplexMode);
        mDuplexMode = duplexMode;
    }

    /**
     * Gets a new print attributes instance which is in portrait orientation,
     * which is the media size is in portrait and all orientation dependent
     * attributes such as resolution and margins are properly adjusted.
     *
     * @return New instance in portrait orientation if this one is in
     * landscape, otherwise this instance.
     *
     * @hide
     */
    public PrintAttributes asPortrait() {
        if (isPortrait()) {
            return this;
        }

        PrintAttributes attributes = new PrintAttributes();

        // Rotate the media size.
        attributes.setMediaSize(getMediaSize().asPortrait());

        // Rotate the resolution.
        Resolution oldResolution = getResolution();
        Resolution newResolution = new Resolution(
                oldResolution.getId(),
                oldResolution.getLabel(),
                oldResolution.getVerticalDpi(),
                oldResolution.getHorizontalDpi());
        attributes.setResolution(newResolution);

        // Do not rotate the physical margins.
        attributes.setMinMargins(getMinMargins());

        attributes.setColorMode(getColorMode());
        attributes.setDuplexMode(getDuplexMode());

        return attributes;
    }

    /**
     * Gets a new print attributes instance which is in landscape orientation,
     * which is the media size is in landscape and all orientation dependent
     * attributes such as resolution and margins are properly adjusted.
     *
     * @return New instance in landscape orientation if this one is in
     * portrait, otherwise this instance.
     *
     * @hide
     */
    public PrintAttributes asLandscape() {
        if (!isPortrait()) {
            return this;
        }

        PrintAttributes attributes = new PrintAttributes();

        // Rotate the media size.
        attributes.setMediaSize(getMediaSize().asLandscape());

        // Rotate the resolution.
        Resolution oldResolution = getResolution();
        Resolution newResolution = new Resolution(
                oldResolution.getId(),
                oldResolution.getLabel(),
                oldResolution.getVerticalDpi(),
                oldResolution.getHorizontalDpi());
        attributes.setResolution(newResolution);

        // Do not rotate the physical margins.
        attributes.setMinMargins(getMinMargins());

        attributes.setColorMode(getColorMode());
        attributes.setDuplexMode(getDuplexMode());

        return attributes;
    }

    @Override
    public void writeToParcel(Parcel parcel, int flags) {
        if (mMediaSize != null) {
            parcel.writeInt(1);
            mMediaSize.writeToParcel(parcel);
        } else {
            parcel.writeInt(0);
        }
        if (mResolution != null) {
            parcel.writeInt(1);
            mResolution.writeToParcel(parcel);
        } else {
            parcel.writeInt(0);
        }
        if (mMinMargins != null) {
            parcel.writeInt(1);
            mMinMargins.writeToParcel(parcel);
        } else {
            parcel.writeInt(0);
        }
        parcel.writeInt(mColorMode);
        parcel.writeInt(mDuplexMode);
    }

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public int hashCode() {
        final int prime = 31;
        int result = 1;
        result = prime * result + mColorMode;
        result = prime * result + mDuplexMode;
        result = prime * result + ((mMinMargins == null) ? 0 : mMinMargins.hashCode());
        result = prime * result + ((mMediaSize == null) ? 0 : mMediaSize.hashCode());
        result = prime * result + ((mResolution == null) ? 0 : mResolution.hashCode());
        return result;
    }

    @Override
    public boolean equals(Object obj) {
        if (this == obj) {
            return true;
        }
        if (obj == null) {
            return false;
        }
        if (getClass() != obj.getClass()) {
            return false;
        }
        PrintAttributes other = (PrintAttributes) obj;
        if (mColorMode != other.mColorMode) {
            return false;
        }
        if (mDuplexMode != other.mDuplexMode) {
            return false;
        }
        if (mMinMargins == null) {
            if (other.mMinMargins != null) {
                return false;
            }
        } else if (!mMinMargins.equals(other.mMinMargins)) {
            return false;
        }
        if (mMediaSize == null) {
            if (other.mMediaSize != null) {
                return false;
            }
        } else if (!mMediaSize.equals(other.mMediaSize)) {
            return false;
        }
        if (mResolution == null) {
            if (other.mResolution != null) {
                return false;
            }
        } else if (!mResolution.equals(other.mResolution)) {
            return false;
        }
        return true;
    }

    @Override
    public String toString() {
        StringBuilder builder = new StringBuilder();
        builder.append("PrintAttributes{");
        builder.append("mediaSize: ").append(mMediaSize);
        if (mMediaSize != null) {
            builder.append(", orientation: ").append(mMediaSize.isPortrait()
                    ? "portrait" : "landscape");
        } else {
            builder.append(", orientation: ").append("null");
        }
        builder.append(", resolution: ").append(mResolution);
        builder.append(", minMargins: ").append(mMinMargins);
        builder.append(", colorMode: ").append(colorModeToString(mColorMode));
        builder.append(", duplexMode: ").append(duplexModeToString(mDuplexMode));
        builder.append("}");
        return builder.toString();
    }

    /** @hide */
    public void clear() {
        mMediaSize = null;
        mResolution = null;
        mMinMargins = null;
        mColorMode = 0;
        mDuplexMode = DUPLEX_MODE_NONE;
    }

    /**
     * @hide
     */
    public void copyFrom(PrintAttributes other) {
        mMediaSize = other.mMediaSize;
        mResolution = other.mResolution;
        mMinMargins = other.mMinMargins;
        mColorMode = other.mColorMode;
        mDuplexMode = other.mDuplexMode;
    }

    /**
     * This class specifies a supported media size. Media size is the
     * dimension of the media on which the content is printed. For
     * example, the {@link #NA_LETTER} media size designates a page
     * with size 8.5" x 11".
     */
    public static final class MediaSize {
        private static final String LOG_TAG = "MediaSize";

        private static final Map<String, MediaSize> sIdToMediaSizeMap =
                new ArrayMap<String, MediaSize>();

        /**
         * Unknown media size in portrait mode.
         * <p>
         * <strong>Note: </strong>This is for specifying orientation without media
         * size. You should not use the dimensions reported by this instance.
         * </p>
         */
        public static final MediaSize UNKNOWN_PORTRAIT =
                new MediaSize("UNKNOWN_PORTRAIT", "android",
                        R.string.mediasize_unknown_portrait, 1, Integer.MAX_VALUE);

        /**
         * Unknown media size in landscape mode.
         * <p>
         * <strong>Note: </strong>This is for specifying orientation without media
         * size. You should not use the dimensions reported by this instance.
         * </p>
         */
        public static final MediaSize UNKNOWN_LANDSCAPE =
                new MediaSize("UNKNOWN_LANDSCAPE", "android",
                        R.string.mediasize_unknown_landscape, Integer.MAX_VALUE, 1);

        // ISO sizes

        /** ISO A0 media size: 841mm x 1189mm (33.11" x 46.81") */
        public static final MediaSize ISO_A0 =
                new MediaSize("ISO_A0", "android", R.string.mediasize_iso_a0, 33110, 46810);
        /** ISO A1 media size: 594mm x 841mm (23.39" x 33.11") */
        public static final MediaSize ISO_A1 =
                new MediaSize("ISO_A1", "android", R.string.mediasize_iso_a1, 23390, 33110);
        /** ISO A2 media size: 420mm x 594mm (16.54" x 23.39") */
        public static final MediaSize ISO_A2 =
                new MediaSize("ISO_A2", "android", R.string.mediasize_iso_a2, 16540, 23390);
        /** ISO A3 media size: 297mm x 420mm (11.69" x 16.54") */
        public static final MediaSize ISO_A3 =
                new MediaSize("ISO_A3", "android", R.string.mediasize_iso_a3, 11690, 16540);
        /** ISO A4 media size: 210mm x 297mm (8.27" x 11.69") */
        public static final MediaSize ISO_A4 =
                new MediaSize("ISO_A4", "android", R.string.mediasize_iso_a4, 8270, 11690);
        /** ISO A5 media size: 148mm x 210mm (5.83" x 8.27") */
        public static final MediaSize ISO_A5 =
                new MediaSize("ISO_A5", "android", R.string.mediasize_iso_a5, 5830, 8270);
        /** ISO A6 media size: 105mm x 148mm (4.13" x 5.83") */
        public static final MediaSize ISO_A6 =
                new MediaSize("ISO_A6", "android", R.string.mediasize_iso_a6, 4130, 5830);
        /** ISO A7 media size: 74mm x 105mm (2.91" x 4.13") */
        public static final MediaSize ISO_A7 =
                new MediaSize("ISO_A7", "android", R.string.mediasize_iso_a7, 2910, 4130);
        /** ISO A8 media size: 52mm x 74mm (2.05" x 2.91") */
        public static final MediaSize ISO_A8 =
                new MediaSize("ISO_A8", "android", R.string.mediasize_iso_a8, 2050, 2910);
        /** ISO A9 media size: 37mm x 52mm (1.46" x 2.05") */
        public static final MediaSize ISO_A9 =
                new MediaSize("ISO_A9", "android", R.string.mediasize_iso_a9, 1460, 2050);
        /** ISO A10 media size: 26mm x 37mm (1.02" x 1.46") */
        public static final MediaSize ISO_A10 =
                new MediaSize("ISO_A10", "android", R.string.mediasize_iso_a10, 1020, 1460);

        /** ISO B0 media size: 1000mm x 1414mm (39.37" x 55.67") */
        public static final MediaSize ISO_B0 =
                new MediaSize("ISO_B0", "android", R.string.mediasize_iso_b0, 39370, 55670);
        /** ISO B1 media size: 707mm x 1000mm (27.83" x 39.37") */
        public static final MediaSize ISO_B1 =
                new MediaSize("ISO_B1", "android", R.string.mediasize_iso_b1, 27830, 39370);
        /** ISO B2 media size: 500mm x 707mm (19.69" x 27.83") */
        public static final MediaSize ISO_B2 =
                new MediaSize("ISO_B2", "android", R.string.mediasize_iso_b2, 19690, 27830);
        /** ISO B3 media size: 353mm x 500mm (13.90" x 19.69") */
        public static final MediaSize ISO_B3 =
                new MediaSize("ISO_B3", "android", R.string.mediasize_iso_b3, 13900, 19690);
        /** ISO B4 media size: 250mm x 353mm (9.84" x 13.90") */
        public static final MediaSize ISO_B4 =
                new MediaSize("ISO_B4", "android", R.string.mediasize_iso_b4, 9840, 13900);
        /** ISO B5 media size: 176mm x 250mm (6.93" x 9.84") */
        public static final MediaSize ISO_B5 =
                new MediaSize("ISO_B5", "android", R.string.mediasize_iso_b5, 6930, 9840);
        /** ISO B6 media size: 125mm x 176mm (4.92" x 6.93") */
        public static final MediaSize ISO_B6 =
                new MediaSize("ISO_B6", "android", R.string.mediasize_iso_b6, 4920, 6930);
        /** ISO B7 media size: 88mm x 125mm (3.46" x 4.92") */
        public static final MediaSize ISO_B7 =
                new MediaSize("ISO_B7", "android", R.string.mediasize_iso_b7, 3460, 4920);
        /** ISO B8 media size: 62mm x 88mm (2.44" x 3.46") */
        public static final MediaSize ISO_B8 =
                new MediaSize("ISO_B8", "android", R.string.mediasize_iso_b8, 2440, 3460);
        /** ISO B9 media size: 44mm x 62mm (1.73" x 2.44") */
        public static final MediaSize ISO_B9 =
                new MediaSize("ISO_B9", "android", R.string.mediasize_iso_b9, 1730, 2440);
        /** ISO B10 media size: 31mm x 44mm (1.22" x 1.73") */
        public static final MediaSize ISO_B10 =
                new MediaSize("ISO_B10", "android", R.string.mediasize_iso_b10, 1220, 1730);

        /** ISO C0 media size: 917mm x 1297mm (36.10" x 51.06") */
        public static final MediaSize ISO_C0 =
                new MediaSize("ISO_C0", "android", R.string.mediasize_iso_c0, 36100, 51060);
        /** ISO C1 media size: 648mm x 917mm (25.51" x 36.10") */
        public static final MediaSize ISO_C1 =
                new MediaSize("ISO_C1", "android", R.string.mediasize_iso_c1, 25510, 36100);
        /** ISO C2 media size: 458mm x 648mm (18.03" x 25.51") */
        public static final MediaSize ISO_C2 =
                new MediaSize("ISO_C2", "android", R.string.mediasize_iso_c2, 18030, 25510);
        /** ISO C3 media size: 324mm x 458mm (12.76" x 18.03") */
        public static final MediaSize ISO_C3 =
                new MediaSize("ISO_C3", "android", R.string.mediasize_iso_c3, 12760, 18030);
        /** ISO C4 media size: 229mm x 324mm (9.02" x 12.76") */
        public static final MediaSize ISO_C4 =
                new MediaSize("ISO_C4", "android", R.string.mediasize_iso_c4, 9020, 12760);
        /** ISO C5 media size: 162mm x 229mm (6.38" x 9.02") */
        public static final MediaSize ISO_C5 =
                new MediaSize("ISO_C5", "android", R.string.mediasize_iso_c5, 6380, 9020);
        /** ISO C6 media size: 114mm x 162mm (4.49" x 6.38") */
        public static final MediaSize ISO_C6 =
                new MediaSize("ISO_C6", "android", R.string.mediasize_iso_c6, 4490, 6380);
        /** ISO C7 media size: 81mm x 114mm (3.19" x 4.49") */
        public static final MediaSize ISO_C7 =
                new MediaSize("ISO_C7", "android", R.string.mediasize_iso_c7, 3190, 4490);
        /** ISO C8 media size: 57mm x 81mm (2.24" x 3.19") */
        public static final MediaSize ISO_C8 =
                new MediaSize("ISO_C8", "android", R.string.mediasize_iso_c8, 2240, 3190);
        /** ISO C9 media size: 40mm x 57mm (1.57" x 2.24") */
        public static final MediaSize ISO_C9 =
                new MediaSize("ISO_C9", "android", R.string.mediasize_iso_c9, 1570, 2240);
        /** ISO C10 media size: 28mm x 40mm (1.10" x 1.57") */
        public static final MediaSize ISO_C10 =
                new MediaSize("ISO_C10", "android", R.string.mediasize_iso_c10, 1100, 1570);

        // North America

        /** North America Letter media size: 8.5" x 11" (279mm x 216mm) */
        public static final MediaSize NA_LETTER =
                new MediaSize("NA_LETTER", "android", R.string.mediasize_na_letter, 8500, 11000);
        /** North America Government-Letter media size: 8.0" x 10.5" (203mm x 267mm) */
        public static final MediaSize NA_GOVT_LETTER =
                new MediaSize("NA_GOVT_LETTER", "android",
                        R.string.mediasize_na_gvrnmt_letter, 8000, 10500);
        /** North America Legal media size: 8.5" x 14" (216mm x 356mm) */
        public static final MediaSize NA_LEGAL =
                new MediaSize("NA_LEGAL", "android", R.string.mediasize_na_legal, 8500, 14000);
        /** North America Junior Legal media size: 8.0" x 5.0" (203mm × 127mm) */
        public static final MediaSize NA_JUNIOR_LEGAL =
                new MediaSize("NA_JUNIOR_LEGAL", "android",
                        R.string.mediasize_na_junior_legal, 8000, 5000);
        /** North America Ledger media size: 17" x 11" (432mm × 279mm) */
        public static final MediaSize NA_LEDGER =
                new MediaSize("NA_LEDGER", "android", R.string.mediasize_na_ledger, 17000, 11000);
        /** North America Tabloid media size: 11" x 17" (279mm × 432mm) */
        public static final MediaSize NA_TABLOID =
                new MediaSize("NA_TABLOID", "android",
                        R.string.mediasize_na_tabloid, 11000, 17000);
        /** North America Index Card 3x5 media size: 3" x 5" (76mm x 127mm) */
        public static final MediaSize NA_INDEX_3X5 =
                new MediaSize("NA_INDEX_3X5", "android",
                        R.string.mediasize_na_index_3x5, 3000, 5000);
        /** North America Index Card 4x6 media size: 4" x 6" (102mm x 152mm) */
        public static final MediaSize NA_INDEX_4X6 =
                new MediaSize("NA_INDEX_4X6", "android",
                        R.string.mediasize_na_index_4x6, 4000, 6000);
        /** North America Index Card 5x8 media size: 5" x 8" (127mm x 203mm) */
        public static final MediaSize NA_INDEX_5X8 =
                new MediaSize("NA_INDEX_5X8", "android",
                        R.string.mediasize_na_index_5x8, 5000, 8000);
        /** North America Monarch media size: 7.25" x 10.5" (184mm x 267mm) */
        public static final MediaSize NA_MONARCH =
                new MediaSize("NA_MONARCH", "android",
                        R.string.mediasize_na_monarch, 7250, 10500);
        /** North America Quarto media size: 8" x 10" (203mm x 254mm) */
        public static final MediaSize NA_QUARTO =
                new MediaSize("NA_QUARTO", "android",
                        R.string.mediasize_na_quarto, 8000, 10000);
        /** North America Foolscap media size: 8" x 13" (203mm x 330mm) */
        public static final MediaSize NA_FOOLSCAP =
                new MediaSize("NA_FOOLSCAP", "android",
                        R.string.mediasize_na_foolscap, 8000, 13000);

        // Chinese

        /** Chinese ROC 8K media size: 270mm x 390mm (10.629" x 15.3543") */
        public static final MediaSize ROC_8K =
                new MediaSize("ROC_8K", "android",
                        R.string.mediasize_chinese_roc_8k, 10629, 15354);
        /** Chinese ROC 16K media size: 195mm x 270mm (7.677" x 10.629") */
        public static final MediaSize ROC_16K =
                new MediaSize("ROC_16K", "android",
                        R.string.mediasize_chinese_roc_16k, 7677, 10629);

        /** Chinese PRC 1 media size: 102mm x 165mm (4.015" x 6.496") */
        public static final MediaSize PRC_1 =
                new MediaSize("PRC_1", "android",
                        R.string.mediasize_chinese_prc_1, 4015, 6496);
        /** Chinese PRC 2 media size: 102mm x 176mm (4.015" x 6.929") */
        public static final MediaSize PRC_2 =
                new MediaSize("PRC_2", "android",
                        R.string.mediasize_chinese_prc_2, 4015, 6929);
        /** Chinese PRC 3 media size: 125mm x 176mm (4.921" x 6.929") */
        public static final MediaSize PRC_3 =
                new MediaSize("PRC_3", "android",
                        R.string.mediasize_chinese_prc_3, 4921, 6929);
        /** Chinese PRC 4 media size: 110mm x 208mm (4.330" x 8.189") */
        public static final MediaSize PRC_4 =
                new MediaSize("PRC_4", "android",
                        R.string.mediasize_chinese_prc_4, 4330, 8189);
        /** Chinese PRC 5 media size: 110mm x 220mm (4.330" x 8.661") */
        public static final MediaSize PRC_5 =
                new MediaSize("PRC_5", "android",
                        R.string.mediasize_chinese_prc_5, 4330, 8661);
        /** Chinese PRC 6 media size: 120mm x 320mm (4.724" x 12.599") */
        public static final MediaSize PRC_6 =
                new MediaSize("PRC_6", "android",
                        R.string.mediasize_chinese_prc_6, 4724, 12599);
        /** Chinese PRC 7 media size: 160mm x 230mm (6.299" x 9.055") */
        public static final MediaSize PRC_7 =
                new MediaSize("PRC_7", "android",
                        R.string.mediasize_chinese_prc_7, 6299, 9055);
        /** Chinese PRC 8 media size: 120mm x 309mm (4.724" x 12.165") */
        public static final MediaSize PRC_8 =
                new MediaSize("PRC_8", "android",
                        R.string.mediasize_chinese_prc_8, 4724, 12165);
        /** Chinese PRC 9 media size: 229mm x 324mm (9.016" x 12.756") */
        public static final MediaSize PRC_9 =
                new MediaSize("PRC_9", "android",
                        R.string.mediasize_chinese_prc_9, 9016, 12756);
        /** Chinese PRC 10 media size: 324mm x 458mm (12.756" x 18.032") */
        public static final MediaSize PRC_10 =
                new MediaSize("PRC_10", "android",
                        R.string.mediasize_chinese_prc_10, 12756, 18032);

        /** Chinese PRC 16k media size: 146mm x 215mm (5.749" x 8.465") */
        public static final MediaSize PRC_16K =
                new MediaSize("PRC_16K", "android",
                        R.string.mediasize_chinese_prc_16k, 5749, 8465);
        /** Chinese Pa Kai media size: 267mm x 389mm (10.512" x 15.315") */
        public static final MediaSize OM_PA_KAI =
                new MediaSize("OM_PA_KAI", "android",
                        R.string.mediasize_chinese_om_pa_kai, 10512, 15315);
        /** Chinese Dai Pa Kai media size: 275mm x 395mm (10.827" x 15.551") */
        public static final MediaSize OM_DAI_PA_KAI =
                new MediaSize("OM_DAI_PA_KAI", "android",
                        R.string.mediasize_chinese_om_dai_pa_kai, 10827, 15551);
        /** Chinese Jurro Ku Kai media size: 198mm x 275mm (7.796" x 10.827") */
        public static final MediaSize OM_JUURO_KU_KAI =
                new MediaSize("OM_JUURO_KU_KAI", "android",
                        R.string.mediasize_chinese_om_jurro_ku_kai, 7796, 10827);

        // Japanese

        /** Japanese JIS B10 media size: 32mm x 45mm (1.259" x 1.772") */
        public static final MediaSize JIS_B10 =
                new MediaSize("JIS_B10", "android",
                        R.string.mediasize_japanese_jis_b10, 1259, 1772);
        /** Japanese JIS B9 media size: 45mm x 64mm (1.772" x 2.52") */
        public static final MediaSize JIS_B9 =
                new MediaSize("JIS_B9", "android",
                        R.string.mediasize_japanese_jis_b9, 1772, 2520);
        /** Japanese JIS B8 media size: 64mm x 91mm (2.52" x 3.583") */
        public static final MediaSize JIS_B8 =
                new MediaSize("JIS_B8", "android",
                        R.string.mediasize_japanese_jis_b8, 2520, 3583);
        /** Japanese JIS B7 media size: 91mm x 128mm (3.583" x 5.049") */
        public static final MediaSize JIS_B7 =
                new MediaSize("JIS_B7", "android",
                        R.string.mediasize_japanese_jis_b7, 3583, 5049);
        /** Japanese JIS B6 media size: 128mm x 182mm (5.049" x 7.165") */
        public static final MediaSize JIS_B6 =
                new MediaSize("JIS_B6", "android",
                        R.string.mediasize_japanese_jis_b6, 5049, 7165);
        /** Japanese JIS B5 media size: 182mm x 257mm (7.165" x 10.118") */
        public static final MediaSize JIS_B5 =
                new MediaSize("JIS_B5", "android",
                        R.string.mediasize_japanese_jis_b5, 7165, 10118);
        /** Japanese JIS B4 media size: 257mm x 364mm (10.118" x 14.331") */
        public static final MediaSize JIS_B4 =
                new MediaSize("JIS_B4", "android",
                        R.string.mediasize_japanese_jis_b4, 10118, 14331);
        /** Japanese JIS B3 media size: 364mm x 515mm (14.331" x 20.276") */
        public static final MediaSize JIS_B3 =
                new MediaSize("JIS_B3", "android",
                        R.string.mediasize_japanese_jis_b3, 14331, 20276);
        /** Japanese JIS B2 media size: 515mm x 728mm (20.276" x 28.661") */
        public static final MediaSize JIS_B2 =
                new MediaSize("JIS_B2", "android",
                        R.string.mediasize_japanese_jis_b2, 20276, 28661);
        /** Japanese JIS B1 media size: 728mm x 1030mm (28.661" x 40.551") */
        public static final MediaSize JIS_B1 =
                new MediaSize("JIS_B1", "android",
                        R.string.mediasize_japanese_jis_b1, 28661, 40551);
        /** Japanese JIS B0 media size: 1030mm x 1456mm (40.551" x 57.323") */
        public static final MediaSize JIS_B0 =
                new MediaSize("JIS_B0", "android",
                        R.string.mediasize_japanese_jis_b0, 40551, 57323);

        /** Japanese JIS Exec media size: 216mm x 330mm (8.504" x 12.992") */
        public static final MediaSize JIS_EXEC =
                new MediaSize("JIS_EXEC", "android",
                        R.string.mediasize_japanese_jis_exec, 8504, 12992);

        /** Japanese Chou4 media size: 90mm x 205mm (3.543" x 8.071") */
        public static final MediaSize JPN_CHOU4 =
                new MediaSize("JPN_CHOU4", "android",
                        R.string.mediasize_japanese_chou4, 3543, 8071);
        /** Japanese Chou3 media size: 120mm x 235mm (4.724" x 9.252") */
        public static final MediaSize JPN_CHOU3 =
                new MediaSize("JPN_CHOU3", "android",
                        R.string.mediasize_japanese_chou3, 4724, 9252);
        /** Japanese Chou2 media size: 111.1mm x 146mm (4.374" x 5.748") */
        public static final MediaSize JPN_CHOU2 =
                new MediaSize("JPN_CHOU2", "android",
                        R.string.mediasize_japanese_chou2, 4374, 5748);

        /** Japanese Hagaki media size: 100mm x 148mm (3.937" x 5.827") */
        public static final MediaSize JPN_HAGAKI =
                new MediaSize("JPN_HAGAKI", "android",
                        R.string.mediasize_japanese_hagaki, 3937, 5827);
        /** Japanese Oufuku media size: 148mm x 200mm (5.827" x 7.874") */
        public static final MediaSize JPN_OUFUKU =
                new MediaSize("JPN_OUFUKU", "android",
                        R.string.mediasize_japanese_oufuku, 5827, 7874);

        /** Japanese Kahu media size: 240mm x 322.1mm (9.449" x 12.681") */
        public static final MediaSize JPN_KAHU =
                new MediaSize("JPN_KAHU", "android",
                        R.string.mediasize_japanese_kahu, 9449, 12681);
        /** Japanese Kaku2 media size: 240mm x 332mm (9.449" x 13.071") */
        public static final MediaSize JPN_KAKU2 =
                new MediaSize("JPN_KAKU2", "android",
                        R.string.mediasize_japanese_kaku2, 9449, 13071);

        /** Japanese You4 media size: 105mm x 235mm (4.134" x 9.252") */
        public static final MediaSize JPN_YOU4 =
                new MediaSize("JPN_YOU4", "android",
                        R.string.mediasize_japanese_you4, 4134, 9252);

        private final String mId;
        /**@hide */
        public final String mLabel;
        /**@hide */
        public final String mPackageName;
        /**@hide */
        public final int mLabelResId;
        private final int mWidthMils;
        private final int mHeightMils;

        /**
         * Creates a new instance.
         *
         * @param id The unique media size id.
         * @param packageName The name of the creating package.
         * @param labelResId The resource if of a human readable label.
         * @param widthMils The width in mils (thousands of an inch).
         * @param heightMils The height in mils (thousands of an inch).
         *
         * @throws IllegalArgumentException If the id is empty or the label
         * is empty or the widthMils is less than or equal to zero or the
         * heightMils is less than or equal to zero.
         *
         * @hide
         */
        public MediaSize(String id, String packageName, int labelResId,
                int widthMils, int heightMils) {
            if (TextUtils.isEmpty(id)) {
                throw new IllegalArgumentException("id cannot be empty.");
            }
            if (TextUtils.isEmpty(packageName)) {
                throw new IllegalArgumentException("packageName cannot be empty.");
            }
            if (labelResId <= 0) {
                throw new IllegalArgumentException("labelResId must be greater than zero.");
            }
            if (widthMils <= 0) {
                throw new IllegalArgumentException("widthMils "
                        + "cannot be less than or equal to zero.");
            }
            if (heightMils <= 0) {
                throw new IllegalArgumentException("heightMils "
                       + "cannot be less than or euqual to zero.");
            }
            mPackageName = packageName;
            mId = id;
            mLabelResId = labelResId;
            mWidthMils = widthMils;
            mHeightMils = heightMils;
            mLabel = null;

            // Build this mapping only for predefined media sizes.
            sIdToMediaSizeMap.put(mId, this);
        }

        /**
         * Creates a new instance.
         *
         * @param id The unique media size id. It is unique amongst other media sizes
         *        supported by the printer.
         * @param label The <strong>localized</strong> human readable label.
         * @param widthMils The width in mils (thousands of an inch).
         * @param heightMils The height in mils (thousands of an inch).
         *
         * @throws IllegalArgumentException If the id is empty or the label is empty
         * or the widthMils is less than or equal to zero or the heightMils is less
         * than or equal to zero.
         */
        public MediaSize(String id, String label, int widthMils, int heightMils) {
            if (TextUtils.isEmpty(id)) {
                throw new IllegalArgumentException("id cannot be empty.");
            }
            if (TextUtils.isEmpty(label)) {
                throw new IllegalArgumentException("label cannot be empty.");
            }
            if (widthMils <= 0) {
                throw new IllegalArgumentException("widthMils "
                        + "cannot be less than or equal to zero.");
            }
            if (heightMils <= 0) {
                throw new IllegalArgumentException("heightMils "
                       + "cannot be less than or euqual to zero.");
            }
            mId = id;
            mLabel = label;
            mWidthMils = widthMils;
            mHeightMils = heightMils;
            mLabelResId = 0;
            mPackageName = null;
        }

        /** @hide */
        public MediaSize(String id, String label, String packageName,
                int widthMils, int heightMils, int labelResId) {
            mPackageName = packageName;
            mId = id;
            mLabelResId = labelResId;
            mWidthMils = widthMils;
            mHeightMils = heightMils;
            mLabel = label;
        }

        /**
         * Gets the unique media size id. It is unique amongst other media sizes
         * supported by the printer.
         * <p>
         * This id is defined by the client that generated the media size
         * instance and should not be interpreted by other parties.
         * </p>
         *
         * @return The unique media size id.
         */
        public String getId() {
            return mId;
        }

        /**
         * Gets the human readable media size label.
         *
         * @param packageManager The package manager for loading the label.
         * @return The human readable label.
         */
        public String getLabel(PackageManager packageManager) {
            if (!TextUtils.isEmpty(mPackageName) && mLabelResId > 0) {
                try {
                    return packageManager.getResourcesForApplication(
                            mPackageName).getString(mLabelResId);
                } catch (NotFoundException nfe) {
                    Log.w(LOG_TAG, "Could not load resouce" + mLabelResId
                            + " from package " + mPackageName);
                } catch (NameNotFoundException nnfee) {
                    Log.w(LOG_TAG, "Could not load resouce" + mLabelResId
                            + " from package " + mPackageName);
                }
            }
            return mLabel;
        }

        /**
         * Gets the media width in mils (thousands of an inch).
         *
         * @return The media width.
         */
        public int getWidthMils() {
            return mWidthMils;
        }

        /**
         * Gets the media height in mils (thousands of an inch).
         *
         * @return The media height.
         */
        public int getHeightMils() {
            return mHeightMils;
        }

        /**
         * Gets whether this media size is in portrait which is the
         * height is greater or equal to the width.
         *
         * @return True if the media size is in portrait, false if
         * it is in landscape.
         */
        public boolean isPortrait() {
            return mHeightMils >= mWidthMils;
        }

        /**
         * Returns a new media size instance in a portrait orientation,
         * which is the height is the greater dimension.
         *
         * @return New instance in landscape orientation if this one
         * is in landscape, otherwise this instance.
         */
        public MediaSize asPortrait() {
            if (isPortrait()) {
                return this;
            }
            return new MediaSize(mId, mLabel, mPackageName,
                    Math.min(mWidthMils, mHeightMils),
                    Math.max(mWidthMils, mHeightMils),
                    mLabelResId);
        }

        /**
         * Returns a new media size instance in a landscape orientation,
         * which is the height is the lesser dimension.
         *
         * @return New instance in landscape orientation if this one
         * is in portrait, otherwise this instance.
         */
        public MediaSize asLandscape() {
            if (!isPortrait()) {
                return this;
            }
            return new MediaSize(mId, mLabel, mPackageName,
                    Math.max(mWidthMils, mHeightMils),
                    Math.min(mWidthMils, mHeightMils),
                    mLabelResId);
        }

        void writeToParcel(Parcel parcel) {
            parcel.writeString(mId);
            parcel.writeString(mLabel);
            parcel.writeString(mPackageName);
            parcel.writeInt(mWidthMils);
            parcel.writeInt(mHeightMils);
            parcel.writeInt(mLabelResId);
        }

        static MediaSize createFromParcel(Parcel parcel) {
            return new MediaSize(
                    parcel.readString(),
                    parcel.readString(),
                    parcel.readString(),
                    parcel.readInt(),
                    parcel.readInt(),
                    parcel.readInt());
        }

        @Override
        public int hashCode() {
            final int prime = 31;
            int result = 1;
            result = prime * result + mWidthMils;
            result = prime * result + mHeightMils;
            return result;
        }

        @Override
        public boolean equals(Object obj) {
            if (this == obj) {
                return true;
            }
            if (obj == null) {
                return false;
            }
            if (getClass() != obj.getClass()) {
                return false;
            }
            MediaSize other = (MediaSize) obj;
            if (mWidthMils != other.mWidthMils) {
                return false;
            }
            if (mHeightMils != other.mHeightMils) {
                return false;
            }
            return true;
        }

        @Override
        public String toString() {
            StringBuilder builder = new StringBuilder();
            builder.append("MediaSize{");
            builder.append("id: ").append(mId);
            builder.append(", label: ").append(mLabel);
            builder.append(", packageName: ").append(mPackageName);
            builder.append(", heightMils: ").append(mHeightMils);
            builder.append(", widthMils: ").append(mWidthMils);
            builder.append(", labelResId: ").append(mLabelResId);
            builder.append("}");
            return builder.toString();
        }

        /**
         * Gets a standard media size given its id.
         *
         * @param id The media size id.
         * @return The media size for the given id or null.
         *
         * @hide
         */
        public static MediaSize getStandardMediaSizeById(String id) {
            return sIdToMediaSizeMap.get(id);
        }
    }

    /**
     * This class specifies a supported resolution in DPI (dots per inch).
     * Resolution defines how many points with different color can be placed
     * on one inch in horizontal or vertical direction of the target media.
     * For example, a printer with 600 DPI can produce higher quality images
     * the one with 300 DPI resolution.
     */
    public static final class Resolution {
        private final String mId;
        private final String mLabel;
        private final int mHorizontalDpi;
        private final int mVerticalDpi;

        /**
         * Creates a new instance.
         *
         * @param id The unique resolution id. It is unique amongst other resolutions
         *        supported by the printer.
         * @param label The <strong>localized</strong> human readable label.
         * @param horizontalDpi The horizontal resolution in DPI (dots per inch).
         * @param verticalDpi The vertical resolution in DPI (dots per inch).
         *
         * @throws IllegalArgumentException If the id is empty or the label is empty
         * or the horizontalDpi is less than or equal to zero or the verticalDpi is
         * less than or equal to zero.
         */
        public Resolution(String id, String label, int horizontalDpi, int verticalDpi) {
            if (TextUtils.isEmpty(id)) {
                throw new IllegalArgumentException("id cannot be empty.");
            }
            if (TextUtils.isEmpty(label)) {
                throw new IllegalArgumentException("label cannot be empty.");
            }
            if (horizontalDpi <= 0) {
                throw new IllegalArgumentException("horizontalDpi "
                        + "cannot be less than or equal to zero.");
            }
            if (verticalDpi <= 0) {
                throw new IllegalArgumentException("verticalDpi"
                       + " cannot be less than or equal to zero.");
            }
            mId = id;
            mLabel = label;
            mHorizontalDpi = horizontalDpi;
            mVerticalDpi = verticalDpi;
        }

        /**
         * Gets the unique resolution id. It is unique amongst other resolutions
         * supported by the printer.
         * <p>
         * This id is defined by the client that generated the resolution
         * instance and should not be interpreted by other parties.
         * </p>
         *
         * @return The unique resolution id.
         */
        public String getId() {
            return mId;
        }

        /**
         * Gets the resolution human readable label.
         *
         * @return The human readable label.
         */
        public String getLabel() {
            return mLabel;
        }

        /**
         * Gets the horizontal resolution in DPI (dots per inch).
         *
         * @return The horizontal resolution.
         */
        public int getHorizontalDpi() {
            return mHorizontalDpi;
        }

        /**
         * Gets the vertical resolution in DPI (dots per inch).
         *
         * @return The vertical resolution.
         */
        public int getVerticalDpi() {
            return mVerticalDpi;
        }

        void writeToParcel(Parcel parcel) {
            parcel.writeString(mId);
            parcel.writeString(mLabel);
            parcel.writeInt(mHorizontalDpi);
            parcel.writeInt(mVerticalDpi);
        }

        static Resolution createFromParcel(Parcel parcel) {
            return new Resolution(
                    parcel.readString(),
                    parcel.readString(),
                    parcel.readInt(),
                    parcel.readInt());
        }

        @Override
        public int hashCode() {
            final int prime = 31;
            int result = 1;
            result = prime * result + mHorizontalDpi;
            result = prime * result + mVerticalDpi;
            return result;
        }

        @Override
        public boolean equals(Object obj) {
            if (this == obj) {
                return true;
            }
            if (obj == null) {
                return false;
            }
            if (getClass() != obj.getClass()) {
                return false;
            }
            Resolution other = (Resolution) obj;
            if (mHorizontalDpi != other.mHorizontalDpi) {
                return false;
            }
            if (mVerticalDpi != other.mVerticalDpi) {
                return false;
            }
            return true;
        }

        @Override
        public String toString() {
            StringBuilder builder = new StringBuilder();
            builder.append("Resolution{");
            builder.append("id: ").append(mId);
            builder.append(", label: ").append(mLabel);
            builder.append(", horizontalDpi: ").append(mHorizontalDpi);
            builder.append(", verticalDpi: ").append(mVerticalDpi);
            builder.append("}");
            return builder.toString();
        }
    }

    /**
     * This class specifies content margins. Margins define the white space
     * around the content where the left margin defines the amount of white
     * space on the left of the content and so on.
     */
    public static final class Margins {
        public static final Margins NO_MARGINS = new Margins(0,  0,  0,  0);

        private final int mLeftMils;
        private final int mTopMils;
        private final int mRightMils;
        private final int mBottomMils;

        /**
         * Creates a new instance.
         *
         * @param leftMils The left margin in mils (thousands of an inch).
         * @param topMils The top margin in mils (thousands of an inch).
         * @param rightMils The right margin in mils (thousands of an inch).
         * @param bottomMils The bottom margin in mils (thousands of an inch).
         */
        public Margins(int leftMils, int topMils, int rightMils, int bottomMils) {
            mTopMils = topMils;
            mLeftMils = leftMils;
            mRightMils = rightMils;
            mBottomMils = bottomMils;
        }

        /**
         * Gets the left margin in mils (thousands of an inch).
         *
         * @return The left margin.
         */
        public int getLeftMils() {
            return mLeftMils;
        }

        /**
         * Gets the top margin in mils (thousands of an inch).
         *
         * @return The top margin.
         */
        public int getTopMils() {
            return mTopMils;
        }

        /**
         * Gets the right margin in mils (thousands of an inch).
         *
         * @return The right margin.
         */
        public int getRightMils() {
            return mRightMils;
        }

        /**
         * Gets the bottom margin in mils (thousands of an inch).
         *
         * @return The bottom margin.
         */
        public int getBottomMils() {
            return mBottomMils;
        }

        void writeToParcel(Parcel parcel) {
            parcel.writeInt(mLeftMils);
            parcel.writeInt(mTopMils);
            parcel.writeInt(mRightMils);
            parcel.writeInt(mBottomMils);
        }

        static Margins createFromParcel(Parcel parcel) {
            return new Margins(
                    parcel.readInt(),
                    parcel.readInt(),
                    parcel.readInt(),
                    parcel.readInt());
        }

        @Override
        public int hashCode() {
            final int prime = 31;
            int result = 1;
            result = prime * result + mBottomMils;
            result = prime * result + mLeftMils;
            result = prime * result + mRightMils;
            result = prime * result + mTopMils;
            return result;
        }

        @Override
        public boolean equals(Object obj) {
            if (this == obj) {
                return true;
            }
            if (obj == null) {
                return false;
            }
            if (getClass() != obj.getClass()) {
                return false;
            }
            Margins other = (Margins) obj;
            if (mBottomMils != other.mBottomMils) {
                return false;
            }
            if (mLeftMils != other.mLeftMils) {
                return false;
            }
            if (mRightMils != other.mRightMils) {
                return false;
            }
            if (mTopMils != other.mTopMils) {
                return false;
            }
            return true;
        }

        @Override
        public String toString() {
            StringBuilder builder = new StringBuilder();
            builder.append("Margins{");
            builder.append("leftMils: ").append(mLeftMils);
            builder.append(", topMils: ").append(mTopMils);
            builder.append(", rightMils: ").append(mRightMils);
            builder.append(", bottomMils: ").append(mBottomMils);
            builder.append("}");
            return builder.toString();
        }
    }

    static String colorModeToString(int colorMode) {
        switch (colorMode) {
            case COLOR_MODE_MONOCHROME: {
                return "COLOR_MODE_MONOCHROME";
            }
            case COLOR_MODE_COLOR: {
                return "COLOR_MODE_COLOR";
            }
            default: {
                return "COLOR_MODE_UNKNOWN";
            }
        }
    }

    static String duplexModeToString(int duplexMode) {
        switch (duplexMode) {
            case DUPLEX_MODE_NONE: {
                return "DUPLEX_MODE_NONE";
            }
            case DUPLEX_MODE_LONG_EDGE: {
                return "DUPLEX_MODE_LONG_EDGE";
            }
            case DUPLEX_MODE_SHORT_EDGE: {
                return "DUPLEX_MODE_SHORT_EDGE";
            }
            default: {
                return "DUPLEX_MODE_UNKNOWN";
            }
        }
    }

    static void enforceValidColorMode(int colorMode) {
        if ((colorMode & VALID_COLOR_MODES) == 0 || Integer.bitCount(colorMode) != 1) {
            throw new IllegalArgumentException("invalid color mode: " + colorMode);
        }
    }

    static void enforceValidDuplexMode(int duplexMode) {
        if ((duplexMode & VALID_DUPLEX_MODES) == 0 || Integer.bitCount(duplexMode) != 1) {
            throw new IllegalArgumentException("invalid duplex mode: " + duplexMode);
        }
    }

    /**
     * Builder for creating {@link PrintAttributes}.
     */
    public static final class Builder {
        private final PrintAttributes mAttributes = new PrintAttributes();

        /**
         * Sets the media size.
         *
         * @param mediaSize The media size.
         * @return This builder.
         */
        public Builder setMediaSize(MediaSize mediaSize) {
            mAttributes.setMediaSize(mediaSize);
            return this;
        }

        /**
         * Sets the resolution.
         *
         * @param resolution The resolution.
         * @return This builder.
         */
        public Builder setResolution(Resolution resolution) {
            mAttributes.setResolution(resolution);
            return this;
        }

        /**
         * Sets the minimal margins. If the content does not fit
         * these margins it will be clipped.
         *
         * @param margins The margins.
         * @return This builder.
         */
        public Builder setMinMargins(Margins margins) {
            mAttributes.setMinMargins(margins);
            return this;
        }

        /**
         * Sets the color mode.
         *
         * @param colorMode A valid color mode or zero.
         * @return This builder.
         *
         * @see PrintAttributes#COLOR_MODE_MONOCHROME
         * @see PrintAttributes#COLOR_MODE_COLOR
         */
        public Builder setColorMode(int colorMode) {
            mAttributes.setColorMode(colorMode);
            return this;
        }

        /**
         * Sets the duplex mode.
         *
         * @param duplexMode A valid duplex mode or zero.
         * @return This builder.
         *
         * @see PrintAttributes#DUPLEX_MODE_NONE
         * @see PrintAttributes#DUPLEX_MODE_LONG_EDGE
         * @see PrintAttributes#DUPLEX_MODE_SHORT_EDGE
         */
        public Builder setDuplexMode(int duplexMode) {
            mAttributes.setDuplexMode(duplexMode);
            return this;
        }

        /**
         * Creates a new {@link PrintAttributes} instance.
         * <p>
         * If you do not specify a duplex mode, the default
         * {@link #DUPLEX_MODE_NONE} will be used.
         * </p>
         *
         * @return The new instance.
         */
        public PrintAttributes build() {
            return mAttributes;
        }
    }

    public static final Parcelable.Creator<PrintAttributes> CREATOR =
            new Creator<PrintAttributes>() {
        @Override
        public PrintAttributes createFromParcel(Parcel parcel) {
            return new PrintAttributes(parcel);
        }

        @Override
        public PrintAttributes[] newArray(int size) {
            return new PrintAttributes[size];
        }
    };
}
