Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations Chris Miller on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

How to insert bmp on form 2

Status
Not open for further replies.

taterday

Programmer
Jan 28, 2009
183
US
VFP 9.0. I created an image control. In the control picture.filename.bmp, displays fine. I don't know how to insert a picture on a form that changes depending on the selection. I want to change the picture depending on the screw type, to show the buyer what they are purchasing. I use a listbox to show their purchase. I want to put a picture outside the listbox to display the item picture.

I can not get the picture into a table with a general field or blob field (numbers here). I think I would prefer to have the images on a folder. Having the individual images (named the screw id) in a folder and insert them when I need them into a blank image control. When I do a getfile(screwid), I get the name, not the image.

I know this has to be possible?

Thank you guys for any help.


 
I can not get the picture into a table

It is best NOT to put the picture data into a data table at all.

Instead it is best to put the fully pathed filename into the data table and keep the picture in a directory which is accessible by your application.

Good Luck,
JRB-Bldr

 

DO whatimage WITH this.value=screw_id
gImage = GETINTERFACE(m.icimage, "iPicture")
thisform.image1.Pictureval=m.gimage

FUNCTION WHATIMAGE
LPARAMETERS TCIMAGE
DIMAGE=alltrim('&TCIMAGE')+'.bmp'
IF file('&dimage')
ICIMAGE=LOADPICTURE('&DIMAGE')
ELSE
MESSAGEBOX('IC not found')
ENDIF
RETURN ICIMAGE

This seems to be returning the picture. Is it the best way?
 
Hi Taterday,

First, you are correct in not using a General of Blob field. Instead, use a character field that holds the path and filename to the BMP.

In the InteractiveChange of your listbox, navigate to the appropriate record for the item you wish to show. Then set the Image control's picture property to the contents of the field that holds the path and filename.

That's all there is to it.

Mike


__________________________________
Mike Lewis (Edinburgh, Scotland)

Visual FoxPro articles, tips, training, consultancy
 
>LOADPICTURE('&DIMAGE')
First of all using macro substitution within a string like '&DIMAGE' is the same as the pure DIAMGE.

Then LOADIMAGE() loads the image file into a variable, you can use that with Pictureval, correct. But what always worked and still works and is much easier to use is to set image.Picture proeprty to the image filename. Pictureval is good for display of images loaded from eg SQL Server blob or image or varbinary(MAX) fields. But keep it simple, if your source is a file name, then use that.

Code:
lcFilename = screw_id+".bmp"
Thisform.image1.Picture=IIF(File(lcFilename),lcFilename,"")

Bye, Olaf.
 
Olaf, I really appreciate the code sample. It worked beautifully. Thank you guys, I was really over thinking this.

 
Taterday,

Contrary to what's been said above, there's no reason not to use a binary memo field and store the image data, except that you'll have to be constantly extracting it out and writing to temporary files, and image files are usually quite large relatively speaking. However, VFP is designed to handle large data items for you and it is not error prone. Use FILETOSTR() and a REPLACE statement to populate the table. And STRTOFILE() to write out the temp file. This is a common practice for on-the-fly constructed bitmaps, especially for those which are parsed in a custom DLL prior to being written (as the bitmap data is passed for colorization, alpha blending, whatever, to the DLL as character data).

To use, define a binary memo field, or "m NOCPTRAN" if programmatically creating the table.

For debugging purposes, it's sometimes better not to use an IIF on the assignment line, but to assign the value ahead of time on the source code line above, so as you're stepping through code you can more easily see the context simply by hovering over it. It doesn't really change anything functionally, however. Both methods work.

Code:
lcFilename              = screw_id + ".bmp"
lcFilename              = IIF(FILE(lcFileName), lcFilename, SPACE(0))
thisForm.image1.picture = lcFilename

Best regards,
Rick C. Hodgin
 
>except that you'll have to be constantly extracting it out and writing to temporary files,

There is no need for a temp file, you can use PictureVal with a blob or binary memo field (eg an image retrieved from SQL Server), without writing it to a temp file. But if you start with a bmp file there is no good reason to first load a file into a variable or a blob to display it.

Bye, Olaf.
 
OlafDoschke said:
But if you start with a bmp file there is no good reason to first load a file into a variable or a blob to display it.

Unless you're pre-processing the image content (bits) using a visual theme BEFORE writing it out to disk for use as a temporary file for the duration of the form's existence, such as taking a single source image and applying color operations, alpha operations, shadow operations, overlay operations (to watermark portions of the button set-aside for specific visual cues), and those for idle, enter, leave, left-down, right-down, images, etc.

PictureVal is great ... but it's limited to what it offers. There are more possibilities out there if you look outside the box.

Best regards
Rick C. Hodgin
 
If I or taterday wanted to do operations on an image, we would end up with that processed image in a variable perhaps. Using GDIPLUXS for example, that's easily achieved. And now, what is the limiting factor of PictureVal to display that processed image?

Actually that's leading a bit off topic, but I'm not against a broader answer, that's ok.

To recap from the start, this is what taterday did in the first place:
Code:
DIMAGE=alltrim('&TCIMAGE')+'.bmp'
IF file('&dimage')
	ICIMAGE=LOADPICTURE('&DIMAGE')
...

So besides that convoluted code, the outset is he has bmp files on hdd (as he checks for them with FILE()). Actually the images might also be within the EXE and the FILE() function would aslo find those. In the end those should be displayed with an image control. And that can be done by .Picture = lcFilename.

What's wrong with the KISS principle? ([link en.wikipedia.org/wiki/KISS_principle][/url])

Bye, Olaf.
 
Code:
DIMAGE=alltrim('&TCIMAGE')+'.bmp' IF file('&dimage') ICIMAGE=LOADPICTURE('&DIMAGE')

Yes. And now I'm carrying around a bunch of (unnecessary) BMP files that have to be named and wielded, stored some place, loaded indirectly from my table lookup which points only to the name, rather than having only a single table and related memo file which contains not only the name, but also the bitmap data. In the binary memo example, once you find the record you have the BMP file data. In the lookup-and-separate-bitmap-file example, once you find the record you have to check to see if the file actually exists, and then load it.

To me, KISS applies. One table, all bitmaps. One item to manage in the app install, diagnostics, debugging, etc. In your example, one table to find the bitmap filename, and then however many (dozens?? of) bitmaps stored as separate files someplace else.

Code:
SEEK lcBitmapFilename IN foo
IF NOT EOF('foo')
    lcBitmap = foo.cBmpData
    my_dll_generate_images(@lcBitmapFilename, @lcBitmap, LEN(lcBitmap))
    * Right now, I have images for idle, over, disabled, left-down, right-down, etc.
ELSE
    my_dll_generate_missing_images(@lcBitmapFilename)
    * Possibly generate an error
ENDIF

Take that data as a character string, pass it to a DLL, the DLL uses it as a reference, applies coloring, themes, whatever is necessary, and from the one input source bitmap data, produces several images which make an active button have a themed appearance based on mouse movements, writing out temporary files to disk which are deleted when the app exits, all using the source bitmap name as a base, and then tagging on "_idle" and "_over", etc. to the name.

It's all about what you're willing to work with. Sticking entirely with the VFP toolset, you have a way to proceed. Using some very simple DLLs to extend VFP's base abilities, and you open up a world of possibilities that simply aren't easily possible otherwise.

But again, it's all about how creative you are, what you're willing to work with, etc. Maintaining a custom DLL written in C++ or VB requires extra work and isn't for everybody.

Best regards,
Rick C. Hodgin
 
You can simply add images to the other files section, if it's about static images and then include them into the exe in the build and still use the .picture property.

Actually if you add an image control and set it's picture at design time foxpro automatically includes the image into the project and includes it in compilation into the exe. So if it's about resources, you don't need a resource DLL in foxpro and no helper DLL.

Bye, Olaf.
 
Adding them to the static files section would work, assuming they are static. I was under the impression that the reason they're in a table (or located at some location that needs to have a path in a table to reference) is that they're dynamic.

I use this technique (of capturing bitmaps and saving them to a binary memo file) as part of various algorithms, including on some systems, error trapping algorithms.

Best regards,
Rick C. Hodgin
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top