Solved

graphics drawimage -- requires refresh

Posted on 2003-11-17
11
554 Views
Last Modified: 2012-08-14
I've asked a previous question about this, although previously the image wasn't displaying at all.  (http://www.experts-exchange.com/Programming/Programming_Languages/Java/Q_20799877.html)

Now, the jsp page calls the servlet and the page loads with the image, only the text is on top of a black box (the desired width/height of the image), not the background image...It requires a page refresh (F5) to display the background image as expected.

The servlet utilizes MediaTracker prior to drawing and graphics.drawImage() returns true....yet a black screen.

Is there something missing in the servlet or something I need to add to the jsp to display the image on load?

Here's the code again:

      res.setContentType("image/jpeg");

      ServletOutputStream out = res.getOutputStream();
      BufferedOutputStream bout = new BufferedOutputStream(out);

     int imageWidth = 597;
     int imageHeight = 769;
     
     BufferedImage image = new BufferedImage ( imageWidth,
            imageHeight, BufferedImage.TYPE_INT_RGB );
     Graphics g = image.getGraphics ();

     Image imageS = null;
     Toolkit toolkit = Toolkit.getDefaultToolkit ();

     try {
         imageS = toolkit.getImage(stationaryFilename);
     }
     catch (Exception e) {System.err.println("Exception: " + e.getMessage ()); }

    try {
      MediaTracker imageTracker = new MediaTracker (new Frame ());
      imageTracker.addImage (imageS, 0);
      imageTracker.waitForID (0);
    }
    catch(Exception e) {}

     g.drawImage (imageS, 0, 0, null);
     g.drawString("Hello World", 0, 0);

      JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(bout);
      JPEGEncodeParam param = encoder.getDefaultJPEGEncodeParam(image);
      param.setQuality(50f, true);
      encoder.encode(image, param);
     
      bout.close();
      out.close();
0
Comment
Question by:sapientconceptions
11 Comments
 
LVL 86

Expert Comment

by:CEHJ
ID: 9766606
Try setting the content length as well
0
 
LVL 92

Expert Comment

by:objects
ID: 9767037
Check for errors from MediaTracker.
Try also using MediaTracker to wait for 'image'.
0
 

Author Comment

by:sapientconceptions
ID: 9769069
Thanks objects, but that didn't help at all.

CEHJ, can you offer example code for setting the content length of the jpeg?
0
Free Tool: Path Explorer

An intuitive utility to help find the CSS path to UI elements on a webpage. These paths are used frequently in a variety of front-end development and QA automation tasks.

One of a set of tools we're offering as a way of saying thank you for being a part of the community.

 
LVL 92

Expert Comment

by:objects
ID: 9769100
Are you always using the same image, or different images?
0
 

Author Comment

by:sapientconceptions
ID: 9771014
There are 3 images...they are always the same, but are user defined.

If you're interested, you can see the preview here: http://66.111.11.8/index2.jsp -- the third page or so is the preview page.  You will see how it displays and the behavior.
0
 
LVL 92

Expert Comment

by:objects
ID: 9774420
So it works sometimes, and not others?

I tried it and it worked fine.
 Can u posy your latest code so we're all looking at the same code.
0
 

Author Comment

by:sapientconceptions
ID: 9775910
Thank you for your help.  Yes, it works at times and sporadically you may get a black screen.  At first I thought it may have been the server, but the production machine behaves the same.  (Even if after you get to the preview page and it displays fine, if you back up to the stationary page and select a new piece, it sometimes 'goes black')

Here is the code I have currently (additional things were added recently just for experimentation purposes):

    public void doGet(HttpServletRequest req, HttpServletResponse res)
      throws IOException, ServletException
    {
      res.setContentType("image/jpeg");
      
      String stationaryFilename = stationary.getPreviewFilename ();

         //I know you said i didn't need this line, but didn't work with just String.
      URL imageURL = getClass().getResource(stationaryFilename);

      String urlString = imageURL.toString();
      ServletOutputStream out = res.getOutputStream ();

      int imageWidth = 0;
      int imageHeight = 0;
      
      if(urlString.indexOf("preview_workshop") != -1)
          {
            imageWidth = 597;
            imageHeight = 769;
          }
      else if(urlString.indexOf("preview_santa") != -1)
          {
            imageWidth = 598;
            imageHeight = 771;
          }
      else if(urlString.indexOf("preview_scroll") != -1)
          {
            imageWidth = 597;
            imageHeight = 762;
          }

      BufferedImage image = new BufferedImage (imageWidth, imageHeight, BufferedImage.TYPE_INT_RGB);
      Graphics g = image.createGraphics ();

      Image imageS = null;
      Toolkit toolkit = Toolkit.getDefaultToolkit ();

      try {
          imageS = toolkit.getImage(imageURL);
      }
      catch (Exception e) {System.err.println("Exception: " + e.getMessage ()); }

      ImageObserver observer = new ImageObserver ()
                                     {
                                       public boolean imageUpdate (Image img, int flags,
                                                                   int x, int y, int w, int h)
                                       {
                                         return (flags & (ALLBITS | ABORT)) == 0;
                                       }
                                     };

      MediaTracker imageTracker = new MediaTracker (new Frame ());
      
      try
        {
            imageTracker.addImage (image, 0);
            imageTracker.addImage (imageS, 1);
                imageTracker.waitForAll();

            if(imageTracker.isErrorAny ())
              System.err.println("imageTracker error...");

            if(imageTracker.checkAll())  //always returns true
              System.err.println("All images have finished loading");
        }
        catch (Exception e)
        { System.err.println("error with MediaTracker: "  +e.getMessage ()); }

      boolean imageDrawn = g.drawImage (imageS, 0, 0, imageWidth, imageHeight, observer);
      
      InputStream is = getClass().getResourceAsStream("LCALLIG.TTF");
      Font font = null;
        
      try{
          font = Font.createFont (Font.TRUETYPE_FONT, is);
      }
      catch(FontFormatException ffe) {System.err.println(ffe.getMessage()); }

      g.setFont(font.deriveFont(11f));
      g.setColor(Color.red);
      
      //Code for added text removed...

        g.dispose ();
      JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(out);
      encoder.encode(image);

      out.close ();
    }
0
 
LVL 92

Expert Comment

by:objects
ID: 9776056
strange, if you use the following  do you get a red rectangle instead of a black one?


g.drawImage (imageS, 0, 0, Color.red, null);
try
{
  imageTracker.addImage (image, 0);
  imageTracker.waitForAll();

  if(imageTracker.isErrorAny ())
      System.err.println("imageTracker error...");

  if(imageTracker.checkAll())  //always returns true
      System.err.println("All images have finished loading");
}
catch (Exception e)
{ System.err.println("error with MediaTracker: "  +e.getMessage ()); }
0
 

Author Comment

by:sapientconceptions
ID: 9776564
No, that didn't work, just resulted in empty image symbol.

But thatnks anyway for all your help, but after being redirected by someone to the ImageIO class, I've fixed the problem and reduced the code to:

      URL imageURL = getClass().getResource(stationaryFilename);
      String urlString = imageURL.toString();
      ServletOutputStream out = res.getOutputStream ();

      BufferedImage image = ImageIO.read(imageURL);
      Graphics g = image.createGraphics ();

        //removed the addition of text...

      ImageIO.write(image, "jpg", out);
      out.close ();

For anyone else that may run into this problem later...it seems the behavior of the black rectangle appearing sometimes (especially for the first time) is typical with one specific problem....using the image object before it got loaded into memory.  With headless environements you can not use frames or windows, so you cannot use MediaTracker either (it just gets HeadlessException thrown without waiting for anything)...instead use the javax.imageio package to load images.

Thanks again for you help, and I hope this helps others.
0
 
LVL 1

Accepted Solution

by:
DarthMod earned 0 total points
ID: 11688313
Submitted to PAQ with points refunded (50)

DarthMod
Community Support Moderator
0

Featured Post

Free Tool: Site Down Detector

Helpful to verify reports of your own downtime, or to double check a downed website you are trying to access.

One of a set of tools we are providing to everyone as a way of saying thank you for being a part of the community.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
more than one jdk and one jre 1 50
Java string replace 11 53
add projects t working set in maven 2 16
Bot application - advice 3 37
For customizing the look of your lightweight component and making it look opaque like it was made of plastic.  This tip assumes your component to be of rectangular shape and completely opaque.   (CODE)
For customizing the look of your lightweight component and making it look lucid like it was made of glass. Or: how to make your component more Apple-ish ;) This tip assumes your component to be of rectangular shape and completely opaque. (COD…
Viewers will learn about the regular for loop in Java and how to use it. Definition: Break the for loop down into 3 parts: Syntax when using for loops: Example using a for loop:
This video teaches viewers about errors in exception handling.

792 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question