Object overlapping color problem - page 2

 

You are now a coder, so you must learn to think logically and learn to use the tools available to you.

  • Always reference the build-in documentation in the Editor and check the usage of each function, parameter, property, etc.
  • Learn to use the "Debug" option in the Compiler.
  • Learn to identify at what line number the error occurs so that you can track down the culprit.
  • Think like an investigator and test things step-by-step so as to narrow the search down.
  • Interpret the Error Code description. It tells you what the problem is. It is a "clue", so investigate your code and find the possible "suspect".

So here is my take on things:

  1. Read the documentation about the OBJ_BITMAP chart object and verify what properties it has.
    In the example given, do you see it using the properties OBJPROP_XDISTANCE or OBJPROP_YDISTANCE?
    No, it does not! Do you even understand what those properties do or what they are for?

  2. Previously, you correctly tested the results of "ObjectCreate()" before setting the properties. Yet this time, you removed that test. Please use it again:
    if( ObjectFind(0,"Box") < 0 ) // If there is no object in the chart.
    {
       if( ObjectCreate(0,"Box",OBJ_BITMAP,0,0,0) ) // now create object
       {
          // set properties
       }
    }
    else
    {
       // adjust properties if need be
    }

  3. When deleting, also test for the existence of the Chart Object:
    if( ObjectFind(0,"Box") >= 0 ) ObjectDelete(0,"Box"); // Delete Object
 
FMIC:

You are now a coder, so you must learn to think logically and learn to use the tools available to you.

  • Always reference the build-in documentation in the Editor and check the usage of each function, parameter, property, etc.
  • Learn to use the "Debug" option in the Compiler.
  • Learn to identify at what line number the error occurs so that you can track down the culprit.
  • Think like an investigator and test things step-by-step so as to narrow the search down.
  • Interpret the Error Code description. It tells you what the problem is. It is a "clue", so investigate your code and find the possible "suspect".

So here is my take on things:

  1. Read the documentation about the OBJ_BITMAP chart object and verify what properties it has.
    In the example given, do you see it using the properties OBJPROP_XDISTANCE or OBJPROP_YDISTANCE?
    No, it does not! Do you even understand what those properties do or what they are for?

  2. Previously, you correctly tested the results of "ObjectCreate()" before setting the properties. Yet this time, you removed that test. Please use it again:
  3. When deleting, also test for the existence of the Chart Object:

Hi FMIC,

Thank you very much for providing the guidance.

Sorry that I made mistake with xy distance. But added the condition as you suggested, now no error.

But object is still not showing up on the chart. I did checked the visibility scope as I already added xy offset and xy size. 

If I open the object list on the chart, nothing shows until I click on the "list all". Then it shows an object in the object list.

#resource "\\Images\\Box.bmp" 
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
input string          InpFile="\\Images\\Box.bmp"; // Bitmap file name
input bool            InpBack=false;                  // Background object


int start()
{

if(ObjectFind(0,"Box")<0) // If there is no object in the chart.
{
ObjectCreate(0,"Box",OBJ_BITMAP,0,0,0); // now create object
 { 
   ObjectSetString(0,"Box",OBJPROP_BMPFILE,0,InpFile);
   ObjectSetInteger(0,"Box",OBJPROP_XSIZE,150);
   ObjectSetInteger(0,"Box",OBJPROP_YSIZE,150);
   ObjectSet("Box",OBJPROP_COLOR,clrRed);
   ObjectSet("Box",OBJPROP_BACK,InpBack);
   ObjectSetInteger(0,"Box",OBJPROP_XOFFSET,4);
   ObjectSetInteger(0,"Box",OBJPROP_YOFFSET,4);
   ObjectSetInteger(0,"Box",OBJPROP_WIDTH,1);
   ObjectSetInteger(0,"Box",OBJPROP_STYLE,1);
   
  }
}
//else part is not required at this moment.

return(0);
}
 
  1. You did not do as I suggested and and also left out a few key things in your code:
    int start()
    {
       if(ObjectFind(0,"Box")<0) // If there is no object in the chart.
       {
          if( ObjectCreate(0,"Box",OBJ_BITMAP,0,timedate,price) ) // now create object
          { 
             // set properties
          }
       }
       //else part is not required at this moment.
       
       return(0);
    }
    
    int deinit()
    {
       if( ObjectFind(0,"Box") >= 0 ) ObjectDelete(0,"Box"); // Delete Object 
       return(0);
    }

  2. Please make an effort on your part. Don't just keep coming back here on every little step. You are a coder. Think and investigate the problem. Read the documentation.
    As you yourself have verified, the "Chart Object" is there and appears in the object list. So what is wrong?
  1. Is it it maybe in the wrong place? Is it at the correct time/date and price?
  2. Was the function used correctly? Was the property correctly set?
  3. Was the correct size used? Is it perhaps too large causing it to become invisible?
  4. etc. (Ask yourself questions and try to verify the answers).
 

I read the help section . Ok I added both price & time. Note I already added the deinit part, I just didn't shared here. I shared only the start function in my last post. Correct size is used for the picture already. Picture is 150x150. So I used same size in here.

//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
input string          InpFile="\\Images\\Box.bmp"; // Bitmap file name
input bool            InpBack=false;                  // Background object


int start()
{

double price = iOpen(Symbol(),0,2);
datetime time = iTime(Symbol(),0,2);

if(ObjectFind(0,"Box")<0) // If there is no object in the chart.
{
if(ObjectCreate(0,"Box",OBJ_BITMAP,0,time,price)) // now create object
 { 
   ObjectSetString(0,"Box",OBJPROP_BMPFILE,0,InpFile);
   ObjectSetInteger(0,"Box",OBJPROP_XSIZE,150);
   ObjectSetInteger(0,"Box",OBJPROP_YSIZE,150);
   ObjectSetInteger(0,"Box",OBJPROP_COLOR,clrRed);
   ObjectSetInteger(0,"Box",OBJPROP_BACK,InpBack);
   ObjectSetInteger(0,"Box",OBJPROP_XOFFSET,1);
   ObjectSetInteger(0,"Box",OBJPROP_YOFFSET,1);
   ObjectSetInteger(0,"Box",OBJPROP_WIDTH,1);
   ObjectSetInteger(0,"Box",OBJPROP_STYLE,0);
   ObjectSetInteger(0,"Box",OBJPROP_ZORDER,0);
   ObjectSetInteger(0,"Box",OBJPROP_SELECTABLE,true);
   
  }
 }

return(0);
}
//--------------------------------------------------------
int deinit()
{
if( ObjectFind(0,"Box") >= 0 ) ObjectDelete(0,"Box"); // Delete Object

return(0);
}

I added all parameters, Changed the coded many times to figure out it. But its still not showing any object on the chart.

I got one question do I need to move the object then it will show up as price time is changing?

Thanks. 

PS: Sorry I don't want to keep coming back here with every little step. I tried searching for other post on same topic for a sample code. But it was difficult.

https://docs.mql4.com/constants/objectconstants/enum_object/obj_bitmap

I tried using the script code from the above site. Its working successfully. But not my code for a single instance. 

 
cashcube:

I read the help section . Ok I added both price & time. Note I already added the deinit part, I just didn't shared here. I shared only the start function in my last post. Correct size is used for the picture already. Picture is 150x150. So I used same size in here.

I added all parameters, Changed the coded many times to figure out it. But its still not showing any object on the chart.

I got one question do I need to move the object then it will show up as price time is changing?

Thanks. 

Think!

  • If the image is exactly 150 x 150 but you shift its cropping offset by 1, then what do you think will happen? Do you really think that it will create an imaginary pixel at the border + 1 pixel? Do you really think that it will continue visible?
    READ THE DOCUMENTATION: Essentially, the highlighted section is saying the following: ( XSIZE + XOFFSET ) <= Image Width and ( YSIZE + YOFFSET ) <= Image Height
    For objects OBJ_BITMAP_LABEL and OBJ_BITMAP, a special mode of image display can be set programmatically. In this mode, only part of an original image (at which a rectangular visible area is applied) is displayed, while the rest of the image becomes invisible. The size of this area should be set using the properties OBJPROP_XSIZE and OBJPROP_YSIZE. The visible area can be "moved" only within the original image using the properties OBJPROP_XOFFSET and OBJPROP_YOFFSET.
  • The Object is only created ONCE on the first tick, so why are you generating the "time" and "price" for it on every tick. You only need that information when you create it (or when you need to move it).
  • If you want the OBJECT to move or track current prices, then obviously, yes you need to move it with the ObjectMove() function.
 
FMIC:

Think!

  • If the image is exactly 150 x 150 but you shift its cropping offset by 1, then what do you think will happen? Do you really think that it will create an imaginary pixel at the border + 1 pixel? Do you really think that it will continue visible?
    READ THE DOCUMENTATION: Essentially, the highlighted section is saying the following: ( XSIZE + XOFFSET ) <= Image Width and ( YSIZE + YOFFSET ) <= Image Height
    For objects OBJ_BITMAP_LABEL and OBJ_BITMAP, a special mode of image display can be set programmatically. In this mode, only part of an original image (at which a rectangular visible area is applied) is displayed, while the rest of the image becomes invisible. The size of this area should be set using the properties OBJPROP_XSIZE and OBJPROP_YSIZE. The visible area can be "moved" only within the original image using the properties OBJPROP_XOFFSET and OBJPROP_YOFFSET.
  • The Object is only created ONCE on the first tick, so why are you generating the "time" and "price" for it on every tick. You only need that information when you create it (or when you need to move it).
  • If you want the OBJECT to move or track current prices, then obviously, yes you need to move it with the ObjectMove() function.

Thank you I adjusted it. Now problem solved & its showing the picture.

I have last question, can we add 2 Time coordinate & 2 price coordinate on the bitmap image? 

One time & price coordinate get already added when we create the object, can we add more 1 price & 1 time coordinate on the same object? Just like what we can do for rectangles.

Regards

 
cashcube:

Thank you I adjusted it. Now problem solved & its showing the picture.

I have last question, can we add 2 Time coordinate & 2 price coordinate on the bitmap image? 

One time & price coordinate get already added when we create the object, can we add more 1 price & 1 time coordinate on the same object? Just like what we can do for rectangles.

What would that accomplish? Again, you fail to read the documentation! A Bitmap, is NOT a rectangle! It only has one anchor point (not 2)! You cannot "stretch" it as a pixel only occupies a pixel (no more, no less).

PS! If you want to simulate an adjustable sized rectangle, then you should have a "very large" bitmap, and use the OBJPROP_XSIZE and OBJPROP_YSIZE so as to adjust the visible part and emulate a variable sized rectangle. You can use ChartTimePriceToXY() to get the pixel x,y coordinates of a second simulated anchor point, in order to calculate the delta size of the simulated rectangle to be used for the OBJPROP_XSIZE and OBJPROP_YSIZE.

 

In general terms, you're always going to run into problems with the colours of overlapping objects getting inverted, it's the default behaviour.

Whilst it's true that you can get around this to an extent by creating a mask for the overlapping colour, it's only going to be of benefit in fringe cases - where one object sits exactly inside another.

The only "true" solution to this is to use the CCanvas class with the appropriate colour mode, and draw rectangles using the appropriate methods.

 
Hoodlum:

In general terms, you're always going to run into problems with the colours of overlapping objects getting inverted, it's the default behaviour.

Whilst it's true that you can get around this to an extent by creating a mask for the overlapping colour, it's only going to be of benefit in fringe cases - where one object sits exactly inside another.

The only "true" solution to this is to use the CCanvas class with the appropriate colour mode, and draw rectangles using the appropriate methods.

@Hoodlum. With the level of coding skill that the OP has demonstrated (with this and several other threads of his) and the great difficulty he has had with the most basic of concepts, I do believe that OOP programming and the use of the CCanvas, is WAY BEYOND his reach and understanding at the moment.
 
FMIC:
@Hoodlum. With the level of coding skill that the OP has demonstrated (with this and several other threads of his) and the great difficulty he has had with the most basic of concepts, I do believe that OOP programming and the use of the CCanvas, is WAY BEYOND his reach and understanding at the moment.

It is true that I am junior coder that's why I had to look for support. I was working with Bitmap 1st time. But I will try learning CCanvas if it works to solve this problem.

Thank u for your generous support!

Reason: