DrawImage doesn't work AT ALL [NOW IT DOES]

Started by NsMn, Sat 16/01/2010 14:58:55

Previous topic - Next topic

NsMn

This time, I have another problem with DrawingSurfaces, but this time, I know exactly which function's the problem.

Code: ags

function AddText(const string Text,  int color){
  String TextAdd=Text;
  TextSprite=DynamicSprite.CreateFromExistingSprite(btnTexts.Graphic, true);
  TextSurface=TextSprite.GetDrawingSurface();
  TextSurface.Clear(COLOR_TRANSPARENT);
  int Y=(0 - GetTextHeight(Text, eFontFont0, 150));
  TextSurface.DrawImage(1, Y, btnTexts.Graphic, true, 150, 175);
  
  TextSurface.DrawingColor=color;
  TextSurface.DrawStringWrapped(0, 175-GetTextHeight(TextAdd.Copy(), eFontFont0, 150), 150, eFontFont0, eAlignLeft, TextAdd.Copy());
  TextSurface.Release();
  btnTexts.NormalGraphic=TextSprite.Graphic;
}


The TextSurface.DrawImage, which is supposed to draw the Button's graphic a few pixels further up, doesn't do anything. The Clear function's not the problem, neither are the coordinates. I am really desperate here.

monkey0506

#1
One problem that stands out to me here is that you're creating a DrawingSurface that is exactly the size of the button but then you're drawing the button's graphic onto that surface at a negative Y co-ordinate. This would actually crop the image...were you aware of that?

Oh and also, you're using the transparency parameter of DrawImage wrong. It's not a boolean, it's an integer. So you're drawing it at 1% transparency. :D

I wanted to ask you, is there a reason you're using a "const string" parameter only to turn around and store it in a String? Unless you're inter-operating with old-style strings then this is unnecessary. You can just use String as the parameter type. And there's no reason you should have to pass TextAdd.Copy to those functions, just using TextAdd should be sufficient.

NsMn

OHH. Holy sh*t. Thanks, that thing with the transparency is really what the error was.

monkey0506

Heh. I don't have the full parameter lists of all the functions memorized just yet, but I thought something looked off there. :=

Glad to hear that got it sorted out. Oh and I edited my last post with some words about const string vs. String. Basically unless you need to use old-style strings there's no need for using const string at all. :P

NsMn

Okay... maybe I was a bit hasty.

Of COURSE that couldn't have been the matter, since 1% Transparency is nearly completely visible. There also can't be a problem with the sprite being cropped because of the negative coords, since I did that in another script which worked fine.

monkey0506

#5
Right I was thinking that through backwards too. ::)

...hmm...let me see what I can figure out. But it will crop the sprite the way that you're doing that (possibly even cropping it out of existence).

Edit: I just used the following and it worked completely as expected. The original button image is being cropped, the new text is added to the bottom of the button. Presumably this is actually the effect you were going for though? Making the button look somewhat like a listbox?

Code: ags
DynamicSprite *sprite;

void AddText(String text, int color) {
  DynamicSprite *tempSprite = DynamicSprite.CreateFromExistingSprite(btnTexts.Graphic, true);
  if (sprite != null) {
    btnTexts.NormalGraphic = tempSprite.Graphic;
    sprite.Delete();
  }
  sprite = DynamicSprite.CreateFromExistingSprite(btnTexts.Graphic, true);
  DrawingSurface *surface = sprite.GetDrawingSurface();
  surface.Clear(COLOR_TRANSPARENT);
  int Y = (0 - GetTextHeight(text, Game.NormalFont, btnTexts.Width));
  surface.DrawImage(0, Y, btnTexts.Graphic, 0, btnTexts.Width, btnTexts.Height);
  surface.DrawingColor = color;
  surface.DrawStringWrapped(0, btnTexts.Height - GetTextHeight(text, Game.NormalFont, btnTexts.Width), btnTexts.Width, Game.NormalFont, eAlignLeft, text);
  surface.Release();
  btnTexts.NormalGraphic = sprite.Graphic;
  tempSprite.Delete();
}


Also something else you were doing is that by drawing the image at (1, Y) each time you were also shifting the existing image to the right by 1 pixel every time you called the function.

It seems to me that the only reason this would not be working "AT ALL" would be because the height of your text is larger than (or equal to) the height of the button and so your Y co-ordinate is drawing the old image completely out of the range of the surface.

Edit: I updated the function because it was deleting a sprite in-use. It now creates an additional temporary sprite to prevent this happening.

NsMn

As I've said, I tried 0, 1 and some more positive coordinates, but it didn't help.

monkey0506

When you say it's not doing anything, what precisely is happening? In my tests I found that if I called the function more than once then it was deleting a sprite in-use which prevented it from working more than once, but it would still work at least one time.

I updated my code to use a temporary sprite and it is now working 100% as expected. It is not shifting the location of the button. It is shifting the old image up, adding text at the bottom, and cropping the top portion off. All exactly as expected.

NsMn

#8
The command itself does absolutely nothing. It just doesn't draw anything. Maybe I'll try and let it draw a black box or something like that.

Edit: THAT is weird. Now it works, and exactly how it should with the Sprite with the text. But, what the hell? Mabye I can find some workaround... but probably not.

Edit 2: Okay, there is no workaround... it's still strange that it worked before though.
Also, I guess I'm pretty much screwed unless I go back to just boringly print the text again in one colour every time. Sigh.

monkey0506

I'm still not clear what you're wanting it to do to be honest.

Based on the code you've given what will happen is you have your image:

-----------
|@@@@|
|@@@@|
|@@@@|
-----------

You then create a dynamic sprite from the image and a drawing surface from the sprite. Next you clear out the surface:

-----------
|           |
|           |
|           |
-----------

You draw the original image onto the surface shifted up by the height of the text:

-----------
|@@@@|
|@@@@|
|            |
-----------

And finally you add the text to the image:

-----------
|@@@@|
|@@@@|
|the text|
-----------

The top portion of the image (equal to the height of the given text) is getting cropped off every time you call this function.

Unless you have corrected it, you are also deleting a sprite in memory when you use:

Code: ags
TextSprite=DynamicSprite.CreateFromExistingSprite(btnTexts.Graphic, true);


The first time you call this btnTexts.Graphic is set to whatever value was given in the editor. The next (and every subsequent) time you call it btnTexts.Graphic will be set to TextSprite.Graphic which gets deleted as soon as you re-assign TextSprite. This will break your code (meaning that you can only ever call the function once). If you look at my code snippet above, I show how to correct this by creating a temporary sprite.

The code is working exactly as it should be. If you're still experiencing problems, why not put a Display in there:

Code: ags
// ...
int Y=...
Display("Y: %d, surface height: %d", Y, btnTexts.Height);


See what's going on there.

NsMn

Thanks a lot monkey. Yes, it seems to have been deleted - so I made a buffer, and it worked.
And yes, that's exactly waht I wanted to achieve.

monkey0506

Yay! That means it's solved? :D For real this time? :=

NsMn

Yes! Solved and fixed for eternities.... if the apocalypse isn't coming before th 25th.

SMF spam blocked by CleanTalk