Package sun.awt.motif

Source Code of sun.awt.motif.X11RemoteOffScreenImage

/*
* This file is modified by Ivan Maidanski <ivmai@ivmaisoft.com>
* Project name: JCGO-SUNAWT (http://www.ivmaisoft.com/jcgo/)
*/

/*
* @(#)X11RemoteOffScreenImage.java     1.15 03/01/23
*
* Copyright 2003 Sun Microsystems, Inc. All rights reserved.
* SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
*/

package sun.awt.motif;

import java.awt.Component;
import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.GraphicsConfiguration;
import java.awt.image.BufferedImage;
import java.awt.image.ColorModel;
import java.awt.image.DataBuffer;
import java.awt.image.DirectColorModel;
import java.awt.image.PixelInterleavedSampleModel;
import java.awt.image.SampleModel;
import java.awt.image.SinglePixelPackedSampleModel;
import java.awt.image.WritableRaster;
import sun.awt.X11SurfaceData;
import sun.awt.X11SurfaceData.X11PixmapSurfaceData;
import sun.awt.image.AcceleratedOffScreenImage;
import sun.awt.image.BufImgSurfaceData;
import sun.awt.image.DataBufferNative;
import sun.awt.image.WritableRasterNative;
import sun.java2d.SunGraphics2D;
import sun.java2d.SurfaceData;
import sun.java2d.loops.CompositeType;
import sun.java2d.pipe.DrawImage;

/**
* This class extends the functionality of X11OffScreenImage by
* forcing the use of a pixmap-based surfaceData object.  In
* X11OffScreenImage, the default surfaceData object is the default
* one used by BufferedImage, setup by a call to the superclass
* constructor.  Acceleration is achieved by caching a version of
* the data in a pixmap and copying from that pixmap when appropriate.
* <P>
* This is sufficient for accelerating sprite-type images, which are
* rendered to infrequently but copied from often.  Back buffers
* do not benefit from this acceleration since the cached copy
* would never be used.  This is deemed sufficient for local X
* usage; users performing complex Java2D operations (e.g.,
* anti-aliasing, compositing, text, or anything that requires
* read-modify-write operations) would see a degradation in performance
* were we to force all operations to go through the pixmap-based
* image.
* <P>
* In the RemoteX case, however, performance is so abysmal in the
* case of double-buffering (with the back buffer living in the
* Java heap), that the advantage of speeding up the basic
* applications (i.e., those using 1.1 API or simple Swing operations,
* and thus avoiding complex Java2D read-modify-write operations)
* is judged to outweigh the possible performance loss in some
* applications from having the back buffer located in a pixmap.
* <P>
* The decision to instantiate this class (versus X11OffScreenImage)
* is based on whether we are running remotely and whether the
* user has enabled/disabled a property related to this issue:
* -Dsun.java2d.remote
*/
public class X11RemoteOffScreenImage extends X11OffScreenImage {

    int bufImageTypeSw;     // Cache for later BI creation
                            // in getSnapshot()
    SurfaceData bisd;       // intermediate BufImgSD for use in
                            // copyBackupToAccelerated

    private static native void initIDs();

    static {
        initIDs();
    }

    public X11RemoteOffScreenImage(Component c, ColorModel cm, WritableRaster raster,
                                   boolean isRasterPremultiplied)
    {
        super(c, cm, raster, isRasterPremultiplied, false);
        bufImageTypeSw = getType();
        if (!accelerationEnabled) {
            return;
        }
        GraphicsConfiguration gc =
            X11SurfaceData.getGC(c == null ? null : (MComponentPeer)c.getPeer());
        initAcceleratedBackground(gc, getWidth(), getHeight());
        if (surfaceDataHw != null) {
            setCurrentSurfaceData(surfaceDataHw);
            // this is the trick: we treat surfaceDataHw as the default
            // software sd in X11OffScreenImage, this way we can use
            // all of the functionality of X11OSI.
            // REMIND: rename surfaceDataHw and surfaceDataSw to
            // something more appropriate, i.e. sdDefault and sdCached
            surfaceDataSw = surfaceDataHw;
            initContents();
            createNativeRaster();
        }
    }

    private native void
        setSurfaceDataNative(SurfaceData sData);
    private native void
        setRasterNative(WritableRaster raster);

    private void setCurrentSurfaceData(SurfaceData sd) {
        if (sd != surfaceData) {
            surfaceData = sd;           // OffScreenImage copy
            setSurfaceDataNative(sd);   // BufferedImage copy
        }
    }

    public void initContents() {
        Graphics2D g2 = createGraphics();
        g2.clearRect(0, 0, getWidth(), getHeight());
        g2.dispose();
    }

    /**
     * Need to override this method as we don't need to check for
     * the number of copies done from this image
     */
    public SurfaceData getSourceSurfaceData(SurfaceData destSD,
                                            CompositeType comp,
                                            Color bgColor) {
        if (accelerationEnabled             &&
            (destSD != surfaceDataHw)       &&
            destSurfaceAccelerated(destSD))
        {
            // First, we validate the pixmap sd if necessary and then return
            // the appropriate surfaceData object.

            validate(destSD.getDeviceConfiguration());
            if (surfaceDataHw != null) {
                return surfaceDataHw;
            }
        }
        return surfaceDataSw;
    }

    private void createNativeRaster() {
        ColorModel cm = getColorModel();
        SampleModel smHw = null;
        int dataType = 0;
        int scanStride = getWidth();

        switch (cm.getPixelSize()) {
        case 8:
        case 12:
            // 8-bits uses PixelInterleavedSampleModel
            if (cm.getPixelSize() == 8) {
                dataType = DataBuffer.TYPE_BYTE;
            } else {
                dataType = DataBuffer.TYPE_USHORT;
            }

            int[] bandOffsets = new int[1];
            bandOffsets[0] = 0;
            smHw = new PixelInterleavedSampleModel(dataType, getWidth(),
                                                   getHeight(),
                                                   1, scanStride,
                                                   bandOffsets);
            break;

            // all others use SinglePixelPackedSampleModel
        case 15:
        case 16:
            dataType = DataBuffer.TYPE_USHORT;
            int[] bitMasks = new int[3];
            DirectColorModel dcm = (DirectColorModel)cm;
            bitMasks[0] = dcm.getRedMask();
            bitMasks[1] = dcm.getGreenMask();
            bitMasks[2] = dcm.getBlueMask();
            smHw = new SinglePixelPackedSampleModel(dataType, getWidth(),
                                                    getHeight(), scanStride,
                                                    bitMasks);
            break;

        case 24:
        case 32:
            dataType = DataBuffer.TYPE_INT;
            bitMasks = new int[3];
            dcm = (DirectColorModel)cm;
            bitMasks[0] = dcm.getRedMask();
            bitMasks[1] = dcm.getGreenMask();
            bitMasks[2] = dcm.getBlueMask();
            smHw = new SinglePixelPackedSampleModel(dataType, getWidth(),
                                                    getHeight(), scanStride,
                                                    bitMasks);
            break;

        default:
            throw new InternalError("Unsupported depth " + cm.getPixelSize());
        }
        DataBuffer dbn = new DataBufferNative(surfaceDataHw, dataType,
                                              getWidth(), getHeight());
        // set the native raster as a default raster of BI
        setRasterNative(WritableRasterNative.createNativeRaster(smHw, dbn));
    }

    /**
     * Returns a BufferedImage representation of this image.
     * In this default method, it just returns this object.
     * Platform-dependent implementations may choose to return
     * something different.  For example, X11RemoteOffScreenImage
     * might want to return a BufferedImage that points to data current
     * with its pixmap version of the image.
     */
    public BufferedImage getSnapshot() {
        BufferedImage bImg;

        if (bufImageTypeSw > 0) {
            bImg = new BufferedImage(getWidth(), getHeight(),
                    bufImageTypeSw);
        } else {
            ColorModel colormodel = getColorModel();
            WritableRaster writableraster =
             colormodel.createCompatibleWritableRaster(getWidth(),
             getHeight());
            bImg = new BufferedImage(colormodel, writableraster,
                    colormodel.isAlphaPremultiplied(), null);
        }

        Graphics2D g = bImg.createGraphics();
        g.drawImage(this, 0, 0, null);
        g.dispose();
        return bImg;
    }

    protected void copyBackupToAccelerated() {
        if (surfaceDataSw != null && surfaceDataHw != null &&
            surfaceDataSw != surfaceDataHw) {
            java.awt.Font defaultFont =
                new java.awt.Font("Dialog", java.awt.Font.PLAIN, 12);

            // we can't render directly from hw sd to hw sd
            // as we might end up in XCopyArea with pixmaps from different
            // screens. So we use a temp BI SD as a bypass:
            // OSI.surfaceDataSw -> bisd -> AccOSI.surfaceDataHw
            if (bisd == null) {
                BufferedImage bi;

                if (bufImageTypeSw > 0) {
                    bi = new BufferedImage(getWidth(), getHeight(),
                          bufImageTypeSw);
                } else {
                    ColorModel colormodel = getColorModel();
                    WritableRaster writableraster =
                     colormodel.createCompatibleWritableRaster(getWidth(),
                     getHeight());
                    bi = new BufferedImage(colormodel, writableraster,
                          colormodel.isAlphaPremultiplied(), null);
                }

                bisd = BufImgSurfaceData.createData(bi);
            }

            SunGraphics2D swG2d =
                new SunGraphics2D(bisd, java.awt.Color.black,
                                  java.awt.Color.white, defaultFont);

            DrawImage.renderSurfaceData(swG2d, surfaceDataSw,
                                        (java.awt.Color)null,
                                        0, 0, 0, 0, getWidth(), getHeight());
            swG2d.dispose();
            SunGraphics2D hwG2D =
                new SunGraphics2D(surfaceDataHw, java.awt.Color.black,
                                  java.awt.Color.white, defaultFont);
            DrawImage.renderSurfaceData(hwG2D, bisd,
                                        (java.awt.Color)null,
                                        0, 0, 0, 0, getWidth(), getHeight());
            hwG2D.dispose();
        }
    }
}
TOP

Related Classes of sun.awt.motif.X11RemoteOffScreenImage

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.