I am using a VCL TImage
component to load a picture from a file in Embarcadero C++Builder 11.3.
"pic.bmp" is a valid picture:
Image1->Picture->LoadFromFile("C:\\SomePath\\pic.bmp");
This fully works as intended.
However, "pic2.bmp" is a corrupted file:
Image1->Picture->LoadFromFile("C:\\SomePath\\pic2.bmp");
This displays a message box informing of an error and terminates the rest of the procedure.
What I really want to happen is that the error is caught and a "broken picture" is loaded and displayed in its place.
Code I have tried:
Ustr="C:\\SomePath\\pic2.bmp";
try
{
Image1->Picture->LoadFromFile(Ustr);
}
catch (const exception& e)
{
Ustr="C:\\SomePath\\ErrorPicture.png";
Image1->Picture->LoadFromFile(Ustr);
}
Image1 seems to ignore the handling and displays the error message box anyway.
I have tried:
Image1->NoErrMsg = true;
..in conjunction with the try
/catch
. On compiling for a test run, I received a compiler error:
no member named 'NoErrMsg' in 'Vcl::Extctrls::TImage'
I have also tried:
#include <SysUtils.hpp>
...
NoErrMsg = true;
But that didn't work.
I am obviously missing something and it is probably simple, but all of my Google-fu returns results on resolving images, not loading. I need to know how to handle a bad image quietly and behind the scenes, without bothering the user with a message box.
exception
(lowercase e
) usually refers to the std::exception
base class (assuming you have a using
statement somewhere that is pulling exception
into the calling namespace). However, that is a C++-specific class, whereas the RTL/VCL is written in Delphi Pascal instead, which uses the System::Sysutils::Exception
(uppercase E
) base class for its exceptions.
Remember, C++ is a case-sensitive language!
Since you are not actually catching what LoadFromFile()
is throwing, that is why you are still seeing the message box.
Try this instead:
try
{
Image1->Picture->LoadFromFile(Ustr);
}
catch (const Exception&) // <-- use Exception, not exception!
{
Ustr="C:\\SomePath\\ErrorPicture.png";
Image1->Picture->LoadFromFile(Ustr);
}
Alternatively, fully qualify the class namespace so there is no confusion:
catch (const System::Sysutils::Exception&)
Alternatively, use a catch-all instead, since you are not doing anything with the Exception
object (such as logging it, etc):
catch (...)
As for NoErrMsg
, the compiler is correct, it is not a member of the TImage
class, it is a global variable in System.hpp
instead. But even so, the VCL doesn't actually use it, which is why setting it has no effect in your case. It is used only by System::WriteErrorMessage()
, which is called only when a runtime error occurs during app startup or when calling System::Halt()
.