Accurate Price Axis Text Positioning On Chart

 

Hello,

I am trying to come up with a robust solution to position text objects above/below price. Obviously, I have my price bar's high and low values but, I want to be able to have a high and low "offset" so that a user defined value can be provided in the inputs so that the text is adjusted to something more to the user's taste. I propose something like the following:-

   double price=_getAdjustedPriceLevel(_lastBar.High(),_lastBar.Low(),_config.LabelOffsetHigh,_config.LabelOffsetLow);

   _primaryText=new CChartObjectText();
   _createdPrimaryText=_primaryText.Create(0,StringConcatenate("__Label__",m_instance,"__"),0,_time2,price);

The _getAdjustedPriceLevel method needs implementing but, it would "know" whether to return a price based on high or low. I can pass the bar's high/low values and high/low offsets that are specified in the input parameters (and assigned to a config object).

I would like the label offsets to be some kind of arbitrary value so, say, 20 or 30 (not specifically "pip" related) so that the user has reasonably granular control over the padding between the bar's high/low and the text. I just don't know what would be the best approach (code/calculation) to transform such a number into a pip value to add/subtract from the bar's high/low. If the user specified an offset of 25 and it wasn't quite enough, they could specify, say, 30 with a reasonable expectation that this would pad out the text sufficiently based on the current distance between the bar's high/low and the text, currently using 25. I hope I'm being clear enough.

Any advice/recommendation would be greatly appreciated.

Many thanks,--G

 
Geester:

I am trying to come up with a robust solution to position text objects above/below price. Obviously, I have my price bar's high and low values but, I want to be able to have a high and low "offset" so that a user defined value can be provided in the inputs so that the text is adjusted to something more to the user's taste. I propose something like the following:-

The _getAdjustedPriceLevel method needs implementing but, it would "know" whether to return a price based on high or low. I can pass the bar's high/low values and high/low offsets that are specified in the input parameters (and assigned to a config object).

I would like the label offsets to be some kind of arbitrary value so, say, 20 or 30 (not specifically "pip" related) so that the user has reasonably granular control over the padding between the bar's high/low and the text. I just don't know what would be the best approach (code/calculation) to transform such a number into a pip value to add/subtract from the bar's high/low. If the user specified an offset of 25 and it wasn't quite enough, they could specify, say, 30 with a reasonable expectation that this would pad out the text sufficiently based on the current distance between the bar's high/low and the text, currently using 25. I hope I'm being clear enough.

Perhaps the price range displayed within the chart can play a part too. If for example, I define the user's input of 25 to mean "25 points in a 500 points chart" (this ratio can be fixed), then when the chart displays 1000 points price range, I'll have to double 25 to be 50 points before displaying the text. This way, the same input of 25 by the user will be dynamically adjusted to suit different charts, and the apparent padding will remain quite constant and comfortable.

 
Seng Joo Thio:

Perhaps the price range displayed within the chart can play a part too. If for example, I define the user's input of 25 to mean "25 points in a 500 points chart" (this ratio can be fixed), then when the chart displays 1000 points price range, I'll have to double 25 to be 50 points before displaying the text. This way, the same input of 25 by the user will be dynamically adjusted to suit different charts, and the apparent padding will remain quite constant and comfortable.

Thank you for your comments. Do you have a code sample showing how you apply this to the high or low of the price bar?

 
Geester:

Thank you for your comments. Do you have a code sample showing how you apply this to the high or low of the price bar?

Ok, here's a script sample - you can drag and drop to any bar on your chart and see what happens... can zoom in/out to change the min/max prices of the chart, then drag and drop the script again to see what happens...

//+------------------------------------------------------------------+
//| Script program start function                                    |
//+------------------------------------------------------------------+
void OnStart()
{
   const int desiredGapPoints = 500;
   int desiredGap = 25; // Predecide that this is the optimum gap in points, for a chart with max-min=500 points.
   long cID = ChartID();
   
   datetime t = ChartTimeOnDropped();
   int b = iBarShift(_Symbol,_Period,t);
   double chartPriceRange = ChartGetDouble(cID,CHART_PRICE_MAX)-
                            ChartGetDouble(cID,CHART_PRICE_MIN);
   double adjustedGap = (chartPriceRange/(desiredGapPoints*_Point))*desiredGap*_Point;
   
   // Update position of previously created "Text"s
   for (int i=0; i<ObjectsTotal(OBJ_TEXT); i++)
   {
      string name = ObjectName(cID,i,-1,OBJ_TEXT);
      datetime oldT = datetime(ObjectGetInteger(cID,name,OBJPROP_TIME1));
      int currB = iBarShift(_Symbol,_Period,oldT);
      ObjectSetDouble(cID,name,OBJPROP_PRICE1,iHigh(_Symbol,_Period,currB)+adjustedGap);
   }

   // Create new "Text"
   ObjectCreate(cID,"Text"+IntegerToString(b),OBJ_TEXT,0,t,iHigh(_Symbol,_Period,b)+adjustedGap);
}
 
Seng Joo Thio:

Ok, here's a script sample - you can drag and drop to any bar on your chart and see what happens... can zoom in/out to change the min/max prices of the chart, then drag and drop the script again to see what happens...

Thank you so much for sharing this code with me! It works very well indeed and I appreciate you taking the time to help! I have definitely learned from this and it provides an excellent basis for me to do what I want to do :) Regards and thanks again! --G 

Reason: