jdk/src/windows/classes/sun/java2d/d3d/D3DContext.java
author duke
Sat, 01 Dec 2007 00:00:00 +0000
changeset 2 90ce3da70b43
child 887 0aab8d3fa11a
permissions -rw-r--r--
Initial load
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     1
/*
90ce3da70b43 Initial load
duke
parents:
diff changeset
     2
 * Copyright 2005-2006 Sun Microsystems, Inc.  All Rights Reserved.
90ce3da70b43 Initial load
duke
parents:
diff changeset
     3
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
90ce3da70b43 Initial load
duke
parents:
diff changeset
     4
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
     5
 * This code is free software; you can redistribute it and/or modify it
90ce3da70b43 Initial load
duke
parents:
diff changeset
     6
 * under the terms of the GNU General Public License version 2 only, as
90ce3da70b43 Initial load
duke
parents:
diff changeset
     7
 * published by the Free Software Foundation.  Sun designates this
90ce3da70b43 Initial load
duke
parents:
diff changeset
     8
 * particular file as subject to the "Classpath" exception as provided
90ce3da70b43 Initial load
duke
parents:
diff changeset
     9
 * by Sun in the LICENSE file that accompanied this code.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    10
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    11
 * This code is distributed in the hope that it will be useful, but WITHOUT
90ce3da70b43 Initial load
duke
parents:
diff changeset
    12
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
90ce3da70b43 Initial load
duke
parents:
diff changeset
    13
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
90ce3da70b43 Initial load
duke
parents:
diff changeset
    14
 * version 2 for more details (a copy is included in the LICENSE file that
90ce3da70b43 Initial load
duke
parents:
diff changeset
    15
 * accompanied this code).
90ce3da70b43 Initial load
duke
parents:
diff changeset
    16
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    17
 * You should have received a copy of the GNU General Public License version
90ce3da70b43 Initial load
duke
parents:
diff changeset
    18
 * 2 along with this work; if not, write to the Free Software Foundation,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    19
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    20
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    21
 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    22
 * CA 95054 USA or visit www.sun.com if you need additional information or
90ce3da70b43 Initial load
duke
parents:
diff changeset
    23
 * have any questions.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    24
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    25
90ce3da70b43 Initial load
duke
parents:
diff changeset
    26
package sun.java2d.d3d;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    27
90ce3da70b43 Initial load
duke
parents:
diff changeset
    28
import java.awt.AlphaComposite;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    29
import java.awt.Composite;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    30
import java.awt.GraphicsEnvironment;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    31
import java.awt.geom.AffineTransform;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    32
import sun.awt.Win32GraphicsDevice;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    33
import sun.java2d.InvalidPipeException;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    34
import sun.java2d.SurfaceData;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    35
import sun.java2d.pipe.Region;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    36
import sun.java2d.windows.WindowsFlags;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    37
90ce3da70b43 Initial load
duke
parents:
diff changeset
    38
public class D3DContext {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    39
90ce3da70b43 Initial load
duke
parents:
diff changeset
    40
    public static final int NO_CONTEXT_FLAGS = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    41
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    42
     * Used in D3DBlitLoops: if the source surface is opaque
90ce3da70b43 Initial load
duke
parents:
diff changeset
    43
     * alpha blending can be turned off on the native level
90ce3da70b43 Initial load
duke
parents:
diff changeset
    44
     * (if there's no ea), thus improving performance.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    45
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    46
    public static final int SRC_IS_OPAQUE    = 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    47
90ce3da70b43 Initial load
duke
parents:
diff changeset
    48
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    49
     * This is a list of capabilities supported by the device this
90ce3da70b43 Initial load
duke
parents:
diff changeset
    50
     * context is associated with.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    51
     * @see getDeviceCaps
90ce3da70b43 Initial load
duke
parents:
diff changeset
    52
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    53
    public static final int J2D_D3D_FAILURE                = (0 << 0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    54
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    55
     * Device supports depth buffer for d3d render targets
90ce3da70b43 Initial load
duke
parents:
diff changeset
    56
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    57
    public static final int J2D_D3D_DEPTH_SURFACE_OK       = (1 << 0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    58
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    59
     * Device supports creation of plain d3d surfaces
90ce3da70b43 Initial load
duke
parents:
diff changeset
    60
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    61
    public static final int J2D_D3D_PLAIN_SURFACE_OK       = (1 << 1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    62
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    63
     * Device supports creation of opaque textures
90ce3da70b43 Initial load
duke
parents:
diff changeset
    64
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    65
    public static final int J2D_D3D_OP_TEXTURE_SURFACE_OK  = (1 << 2);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    66
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    67
     * Device supports creation of bitmask textures
90ce3da70b43 Initial load
duke
parents:
diff changeset
    68
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    69
    public static final int J2D_D3D_BM_TEXTURE_SURFACE_OK  = (1 << 3);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    70
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    71
     * Device supports creation of translucent textures
90ce3da70b43 Initial load
duke
parents:
diff changeset
    72
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    73
    public static final int J2D_D3D_TR_TEXTURE_SURFACE_OK  = (1 << 4);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    74
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    75
     * Device supports creation of opaque render-to-textures
90ce3da70b43 Initial load
duke
parents:
diff changeset
    76
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    77
    public static final int J2D_D3D_OP_RTT_SURFACE_OK      = (1 << 5);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    78
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    79
     * Device can render lines correctly (no pixelization issues)
90ce3da70b43 Initial load
duke
parents:
diff changeset
    80
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    81
    public static final int J2D_D3D_LINES_OK               = (1 << 6);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    82
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    83
     * Device supports texture mapping (no pixelization issues)
90ce3da70b43 Initial load
duke
parents:
diff changeset
    84
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    85
    public static final int J2D_D3D_TEXTURE_BLIT_OK        = (1 << 7);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    86
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    87
     * Device supports texture mapping with transforms (no pixelization issues)
90ce3da70b43 Initial load
duke
parents:
diff changeset
    88
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    89
    public static final int J2D_D3D_TEXTURE_TRANSFORM_OK   = (1 << 8);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    90
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    91
     * Device can render clipped lines correctly.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    92
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    93
    public static final int J2D_D3D_LINE_CLIPPING_OK       = (1 << 9);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    94
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    95
     * Device has all hw capabilities the d3d pipeline requires
90ce3da70b43 Initial load
duke
parents:
diff changeset
    96
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    97
    public static final int J2D_D3D_DEVICE_OK              = (1 <<10);
90ce3da70b43 Initial load
duke
parents:
diff changeset
    98
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
    99
     * Device supports all necessary texture formats required by d3d pipeline
90ce3da70b43 Initial load
duke
parents:
diff changeset
   100
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   101
    public static final int J2D_D3D_PIXEL_FORMATS_OK       = (1 <<11);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   102
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   103
     * Device supports geometry transformations
90ce3da70b43 Initial load
duke
parents:
diff changeset
   104
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   105
    public static final int J2D_D3D_SET_TRANSFORM_OK       = (1 <<12);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   106
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   107
     * The device is not from a list of known bad devices
90ce3da70b43 Initial load
duke
parents:
diff changeset
   108
     * (see D3DRuntimeTest.cpp)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   109
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   110
    public static final int J2D_D3D_HW_OK                  = (1 <<13);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   111
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   112
     * Direct3D pipeline is enabled on this device
90ce3da70b43 Initial load
duke
parents:
diff changeset
   113
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   114
    public static final int J2D_D3D_ENABLED_OK             = (1 <<14);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   115
90ce3da70b43 Initial load
duke
parents:
diff changeset
   116
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   117
     * The lock object used to synchronize access to the native windowing
90ce3da70b43 Initial load
duke
parents:
diff changeset
   118
     * system layer.  Note that rendering methods should always synchronize on
90ce3da70b43 Initial load
duke
parents:
diff changeset
   119
     * D3DContext.LOCK before calling the D3DContext.getContext() method,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   120
     * or any other method that invokes native D3d commands.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   121
     * REMIND: in D3D case we should really be synchronizing on per-device
90ce3da70b43 Initial load
duke
parents:
diff changeset
   122
     * basis.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   123
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   124
    static Object LOCK;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   125
90ce3da70b43 Initial load
duke
parents:
diff changeset
   126
    private Win32GraphicsDevice  gd;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   127
    private boolean         valid;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   128
90ce3da70b43 Initial load
duke
parents:
diff changeset
   129
    protected long          nativeContext;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   130
    private SurfaceData     validatedDstData;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   131
    private Region          validatedClip;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   132
    private Composite       validatedComp;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   133
    private int             validatedPixel;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   134
    private int             validatedFlags;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   135
    private boolean         xformInUse;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   136
    // validated transform's data
90ce3da70b43 Initial load
duke
parents:
diff changeset
   137
    private double vScaleX, vScaleY, vShearX, vShearY, vTransX, vTransY;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   138
90ce3da70b43 Initial load
duke
parents:
diff changeset
   139
    private int             deviceCaps;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   140
90ce3da70b43 Initial load
duke
parents:
diff changeset
   141
    private native void setRenderTarget(long pCtx, long pDst);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   142
    private native void setClip(long pCtx, long pDst, Region clip, boolean isRect,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   143
                                int x1, int y1, int x2, int y2);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   144
    private native void resetClip(long pCtx, long pDst);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   145
    private native void resetComposite(long pCtx);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   146
    private native void setAlphaComposite(long pCtx, int rule,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   147
                                          float extraAlpha, int flags);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   148
    private native void setTransform(long pCtx, long pDst,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   149
                                     AffineTransform xform,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   150
                                     double m00, double m10, double m01,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   151
                                     double m11, double m02, double m12);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   152
    private native void resetTransform(long pCtx, long pDst);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   153
    private native void setColor(long pCtx, int pixel, int flags);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   154
    private native long initNativeContext(int screen);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   155
    private native int getNativeDeviceCaps(long pCtx);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   156
90ce3da70b43 Initial load
duke
parents:
diff changeset
   157
    static {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   158
        if (!GraphicsEnvironment.isHeadless()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   159
            LOCK = D3DContext.class;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   160
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   161
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   162
90ce3da70b43 Initial load
duke
parents:
diff changeset
   163
    public D3DContext(Win32GraphicsDevice gd) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   164
        this.gd = gd;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   165
        reinitNativeContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   166
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   167
90ce3da70b43 Initial load
duke
parents:
diff changeset
   168
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   169
     * Reinitializes the context by retrieving a pointer to the native
90ce3da70b43 Initial load
duke
parents:
diff changeset
   170
     * D3DContext object, and resetting the device caps.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   171
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   172
    void reinitNativeContext() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   173
        nativeContext = initNativeContext(gd.getScreen());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   174
        deviceCaps = nativeContext != 0L ?
90ce3da70b43 Initial load
duke
parents:
diff changeset
   175
            getNativeDeviceCaps(nativeContext) : J2D_D3D_FAILURE;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   176
        valid = ((deviceCaps & J2D_D3D_ENABLED_OK) != 0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   177
        if (WindowsFlags.isD3DVerbose()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   178
            if (valid) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   179
                System.out.println("Direct3D pipeline enabled on screen " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   180
                                   gd.getScreen());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   181
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   182
                System.out.println("Could not enable Direct3D pipeline on " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   183
                                   "screen " + gd.getScreen() +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   184
                                   ". Device Caps: " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   185
                                   Integer.toHexString(deviceCaps));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   186
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   187
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   188
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   189
90ce3da70b43 Initial load
duke
parents:
diff changeset
   190
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   191
     * Invalidates this context by resetting its status: the validated
90ce3da70b43 Initial load
duke
parents:
diff changeset
   192
     * destination surface, and a pointer to the native context.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   193
     * This method is called in the following cases:
90ce3da70b43 Initial load
duke
parents:
diff changeset
   194
     *  - if a surface loss situation is detected at the native level
90ce3da70b43 Initial load
duke
parents:
diff changeset
   195
     *    during any of the validation methods (setClip, setRenderTarget etc)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   196
     *    and an InvalidPipeException is thrown.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   197
     *    This situation happens when there was a surface loss, but
90ce3da70b43 Initial load
duke
parents:
diff changeset
   198
     *    there were no display change event (like in case of command prompt
90ce3da70b43 Initial load
duke
parents:
diff changeset
   199
     *    going fullscreen).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   200
     *  - as part of surface restoration when a surface is the current
90ce3da70b43 Initial load
duke
parents:
diff changeset
   201
     *    target surface for this context. Since surface restoration
90ce3da70b43 Initial load
duke
parents:
diff changeset
   202
     *    resets the depth buffer contents, we need to make sure the clip
90ce3da70b43 Initial load
duke
parents:
diff changeset
   203
     *    is reset, and since the target surface is reset, we'll set a new
90ce3da70b43 Initial load
duke
parents:
diff changeset
   204
     *    clip the next time we attempt to render to the target surface.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   205
     *  - when a display change occurs, the native D3DContext object is
90ce3da70b43 Initial load
duke
parents:
diff changeset
   206
     *    released and recreated as part of primary surface recreation.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   207
     *    At the time of the release, the java D3DContext object need to be
90ce3da70b43 Initial load
duke
parents:
diff changeset
   208
     *    invalidated because a new D3D device is created and the target
90ce3da70b43 Initial load
duke
parents:
diff changeset
   209
     *    surface will need to be reset.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   210
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   211
     *  Invalidation of the context causes its revalidation the next time
90ce3da70b43 Initial load
duke
parents:
diff changeset
   212
     *  someone tries to get the D3DContext for rendering or creating a new
90ce3da70b43 Initial load
duke
parents:
diff changeset
   213
     *  surface.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   214
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   215
     *  @see #reinitNativeContext
90ce3da70b43 Initial load
duke
parents:
diff changeset
   216
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   217
    private void invalidateContext() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   218
        valid = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   219
        nativeContext = 0L;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   220
        validatedDstData = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   221
        // We don't set deviceCaps to J2D_D3D_FAILURE here because
90ce3da70b43 Initial load
duke
parents:
diff changeset
   222
        // it will prevent from creating d3d surfaces, which means that
90ce3da70b43 Initial load
duke
parents:
diff changeset
   223
        // we'll never get a chance to continue using d3d after a single
90ce3da70b43 Initial load
duke
parents:
diff changeset
   224
        // invalidation event (for example, a display change).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   225
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   226
90ce3da70b43 Initial load
duke
parents:
diff changeset
   227
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   228
     * Fetches the D3DContext associated with the current
90ce3da70b43 Initial load
duke
parents:
diff changeset
   229
     * thread/GraphicsConfig pair, validates the context using the given
90ce3da70b43 Initial load
duke
parents:
diff changeset
   230
     * parameters, then returns the handle to the native context object.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   231
     * Most rendering operations will call this method first in order to
90ce3da70b43 Initial load
duke
parents:
diff changeset
   232
     * prepare the native D3d layer before issuing rendering commands.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   233
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   234
    static long getContext(SurfaceData srcData,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   235
                           SurfaceData dstData,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   236
                            Region clip, Composite comp,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   237
                           AffineTransform xform,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   238
                           int pixel, int flags)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   239
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   240
        if (dstData instanceof D3DSurfaceData == false) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   241
            throw new InvalidPipeException("Incorrect destination surface");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   242
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   243
90ce3da70b43 Initial load
duke
parents:
diff changeset
   244
        D3DContext d3dc = ((D3DSurfaceData)dstData).getContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   245
        try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   246
            d3dc.validate(srcData, dstData, clip, comp, xform, pixel, flags);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   247
        } catch (InvalidPipeException e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   248
            d3dc.invalidateContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   249
            // note that we do not propagate the exception. Once the context
90ce3da70b43 Initial load
duke
parents:
diff changeset
   250
            // is invalidated, any d3d rendering operations are noops, and
90ce3da70b43 Initial load
duke
parents:
diff changeset
   251
            // we are waiting for the primary surface restoration, which
90ce3da70b43 Initial load
duke
parents:
diff changeset
   252
            // happens when VolatileImage is validated. At this point
90ce3da70b43 Initial load
duke
parents:
diff changeset
   253
            // the native D3DContext will be reinitialized, and the next
90ce3da70b43 Initial load
duke
parents:
diff changeset
   254
            // time around validation of the context will succeed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   255
            // Throwing the exception here will do no good, since the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   256
            // destination surface (which is associated with a VolatileImage
90ce3da70b43 Initial load
duke
parents:
diff changeset
   257
            // or a BufferStrategy) will not be restored until VI.validate()
90ce3da70b43 Initial load
duke
parents:
diff changeset
   258
            // is called by the rendering thread.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   259
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   260
        return d3dc.getNativeContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   261
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   262
90ce3da70b43 Initial load
duke
parents:
diff changeset
   263
    public int getDeviceCaps() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   264
        return deviceCaps;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   265
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   266
90ce3da70b43 Initial load
duke
parents:
diff changeset
   267
    boolean isRTTSupported() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   268
        return ((deviceCaps & J2D_D3D_OP_RTT_SURFACE_OK) != 0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   269
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   270
90ce3da70b43 Initial load
duke
parents:
diff changeset
   271
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   272
     * Returns a handle to the native D3DContext structure associated with
90ce3da70b43 Initial load
duke
parents:
diff changeset
   273
     * this object.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   274
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   275
    long getNativeContext() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   276
        return nativeContext;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   277
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   278
90ce3da70b43 Initial load
duke
parents:
diff changeset
   279
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   280
     * Validates the given parameters against the current state for this
90ce3da70b43 Initial load
duke
parents:
diff changeset
   281
     * context.  If this context is not current, it will be made current
90ce3da70b43 Initial load
duke
parents:
diff changeset
   282
     * for the given source and destination surfaces, and the viewport will
90ce3da70b43 Initial load
duke
parents:
diff changeset
   283
     * be updated.  Then each part of the context state (clip, composite,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   284
     * etc.) is checked against the previous value.  If the value has changed
90ce3da70b43 Initial load
duke
parents:
diff changeset
   285
     * since the last call to validate(), it will be updated accordingly.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   286
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   287
    private void validate(SurfaceData srcData, SurfaceData dstData,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   288
                          Region clip, Composite comp, AffineTransform xform,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   289
                          int pixel, int flags)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   290
    {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   291
        boolean updateClip = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   292
90ce3da70b43 Initial load
duke
parents:
diff changeset
   293
        if ((srcData != null && !srcData.isValid()) || !dstData.isValid() ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   294
            dstData.getNativeOps() == 0L || dstData.isSurfaceLost())
90ce3da70b43 Initial load
duke
parents:
diff changeset
   295
        {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   296
            throw new InvalidPipeException("Invalid surface");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   297
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   298
90ce3da70b43 Initial load
duke
parents:
diff changeset
   299
        if (!valid) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   300
            // attempt to reinitialize the context. If the device has been
90ce3da70b43 Initial load
duke
parents:
diff changeset
   301
            // reset, the following calls to setRenderTarget/setClip will
90ce3da70b43 Initial load
duke
parents:
diff changeset
   302
            // succeed and not throw InvalidPipeException.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   303
            reinitNativeContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   304
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   305
90ce3da70b43 Initial load
duke
parents:
diff changeset
   306
        if (dstData != validatedDstData) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   307
            // invalidate pixel and clip (so they will be updated below)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   308
            validatedPixel = ~pixel;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   309
            updateClip = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   310
90ce3da70b43 Initial load
duke
parents:
diff changeset
   311
            // update the viewport
90ce3da70b43 Initial load
duke
parents:
diff changeset
   312
            long pDst = dstData.getNativeOps();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   313
            setRenderTarget(nativeContext, pDst);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   314
90ce3da70b43 Initial load
duke
parents:
diff changeset
   315
            // keep the reference to the old data until we set the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   316
            // new one on the native level, preventing it from being disposed
90ce3da70b43 Initial load
duke
parents:
diff changeset
   317
            SurfaceData tmpData = dstData;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   318
            validatedDstData = dstData;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   319
            tmpData = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   320
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   321
        // it's better to use dstData instead of validatedDstData because
90ce3da70b43 Initial load
duke
parents:
diff changeset
   322
        // the latter may be set to null via invalidateContext at any moment.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   323
        long pDest = dstData.getNativeOps();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   324
90ce3da70b43 Initial load
duke
parents:
diff changeset
   325
        // validate clip
90ce3da70b43 Initial load
duke
parents:
diff changeset
   326
        if ((clip != validatedClip) || updateClip) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   327
            if (clip != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   328
                /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   329
                 * It's cheaper to make this check than set clip every time.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   330
                 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   331
                 * Set the new clip only if:
90ce3da70b43 Initial load
duke
parents:
diff changeset
   332
                 *  - we were asked to do it (updateClip == true)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   333
                 *  - no clip was set before
90ce3da70b43 Initial load
duke
parents:
diff changeset
   334
                 *  - if both the old and the new clip are shapes
90ce3da70b43 Initial load
duke
parents:
diff changeset
   335
                 *  - if they're both rectangular but don't represent
90ce3da70b43 Initial load
duke
parents:
diff changeset
   336
                 *    the same rectangle
90ce3da70b43 Initial load
duke
parents:
diff changeset
   337
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   338
                if (updateClip ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   339
                    validatedClip == null ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   340
                    !(validatedClip.isRectangular() && clip.isRectangular()) ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   341
                    ((clip.getLoX() != validatedClip.getLoX() ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   342
                      clip.getLoY() != validatedClip.getLoY() ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   343
                      clip.getHiX() != validatedClip.getHiX() ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   344
                      clip.getHiY() != validatedClip.getHiY())))
90ce3da70b43 Initial load
duke
parents:
diff changeset
   345
                {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   346
                    setClip(nativeContext, pDest,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   347
                            clip, clip.isRectangular(),
90ce3da70b43 Initial load
duke
parents:
diff changeset
   348
                            clip.getLoX(), clip.getLoY(),
90ce3da70b43 Initial load
duke
parents:
diff changeset
   349
                            clip.getHiX(), clip.getHiY());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   350
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   351
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   352
                resetClip(nativeContext, pDest);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   353
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   354
            validatedClip = clip;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   355
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   356
90ce3da70b43 Initial load
duke
parents:
diff changeset
   357
        if ((comp != validatedComp) || (flags != validatedFlags)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   358
            // invalidate pixel
90ce3da70b43 Initial load
duke
parents:
diff changeset
   359
            validatedPixel = ~pixel;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   360
            validatedComp = comp;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   361
            if (comp != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   362
                AlphaComposite ac = (AlphaComposite)comp;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   363
                setAlphaComposite(nativeContext, ac.getRule(),
90ce3da70b43 Initial load
duke
parents:
diff changeset
   364
                                  ac.getAlpha(), flags);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   365
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   366
                resetComposite(nativeContext);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   367
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   368
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   369
90ce3da70b43 Initial load
duke
parents:
diff changeset
   370
        // validate transform
90ce3da70b43 Initial load
duke
parents:
diff changeset
   371
        if (xform == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   372
            if (xformInUse) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   373
                resetTransform(nativeContext, pDest);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   374
                xformInUse = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   375
                vScaleX = vScaleY = 1.0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   376
                vShearX = vShearY = vTransX = vTransY = 0.0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   377
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   378
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   379
            double nScaleX = xform.getScaleX();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   380
            double nScaleY = xform.getScaleY();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   381
            double nShearX = xform.getShearX();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   382
            double nShearY = xform.getShearY();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   383
            double nTransX = xform.getTranslateX();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   384
            double nTransY = xform.getTranslateY();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   385
90ce3da70b43 Initial load
duke
parents:
diff changeset
   386
            if (nTransX != vTransX || nTransY != vTransY ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   387
                nScaleX != vScaleX || nScaleY != vScaleY ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   388
                nShearX != vShearX || nShearY != vShearY)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   389
            {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   390
                setTransform(nativeContext, pDest,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   391
                             xform,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   392
                             nScaleX, nShearY, nShearX, nScaleY,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   393
                             nTransX, nTransY);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   394
                vScaleX = nScaleX;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   395
                vScaleY = nScaleY;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   396
                vShearX = nShearX;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   397
                vShearY = nShearY;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   398
                vTransX = nTransY;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   399
                vTransY = nTransY;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   400
                xformInUse = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   401
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   402
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   403
90ce3da70b43 Initial load
duke
parents:
diff changeset
   404
        // validate pixel
90ce3da70b43 Initial load
duke
parents:
diff changeset
   405
        if (pixel != validatedPixel) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   406
            validatedPixel = pixel;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   407
            setColor(nativeContext, pixel, flags);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   408
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   409
90ce3da70b43 Initial load
duke
parents:
diff changeset
   410
        // save flags for later comparison
90ce3da70b43 Initial load
duke
parents:
diff changeset
   411
        validatedFlags = flags;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   412
90ce3da70b43 Initial load
duke
parents:
diff changeset
   413
        // mark dstData dirty
90ce3da70b43 Initial load
duke
parents:
diff changeset
   414
        dstData.markDirty();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   415
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   416
}