Announcement

Collapse
No announcement yet.

Partner 728x90

Collapse

Problem with WPF units and DPI

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

    Problem with WPF units and DPI

    Hi!

    I'm trying to positionate a StackPanel on Chart (within drawing tool source code). On one PC it worked perfect but on other screen it's positionated wrong, so I suppose it's WPF units or somethin like that.

    The best code it worked it's the next:

    Code:
    buttonPanel = new StackPanel
    {
         Orientation = Orientation.Vertical
    };
    
    Point puntoFinLinea = EndAnchor.GetPoint(chartControl, chartPanel, chartScale);
    
    double margenIzquierdoX = puntoFinLinea.X + 10;
    double margenSuperiorY = puntoFinLinea.Y;
    double altoGridBotones = listaBotones.Count * alturaBotones;
    int totalWidth = chartPanel.W + chartPanel.X;
    int totalHeight = chartPanel.Y + chartPanel.H;​
    
    margenIzquierdoX += -chartPanel.ActualWidth + 60;
    margenSuperiorY = chartPanel.ActualHeight/2;[/B]​
    
    buttonPanel.Margin = new Thickness(margenIzquierdoX, margenSuperiorY, 0, 0);[/B]
    I see if margenIzquierdoX​ is 0, the StackPanel is drawn at the middle of screen. If I want it more to the left margenIzquierdoX has to be a negative number so I don't know if that makes sense.

    I tried something like ChartingExtensions.ConvertToHorizontalPixels(punto FinLinea.X, chartControl.PresentationSource) with worst results.

    #2
    Hello franjcy,

    Thank you for your post.

    What is this stack panel / your script trying to accomplish? If possible, can you provide a more complete example of your code?

    Are you trying to make a panel that can be drawn on the chart?

    Please note that Drawing objects work based on ChartPanel positioning, and not WPF positioning.



    Therefore, anything added to the WPF control will cause a different outcome, such as adding a control to the ChartControl or to the UserControlCollection - the x/y coordinates from the drawing objects, OnRender, or MouseEvents would not make sense in that context because the ChartPanel has more objects in it which the anchor/rendering in the drawing tool use.

    I look forward to your response.

    Comment


      #3
      Originally posted by NinjaTrader_Gaby View Post
      Hello franjcy,

      Thank you for your post.

      What is this stack panel / your script trying to accomplish? If possible, can you provide a more complete example of your code?

      Are you trying to make a panel that can be drawn on the chart?

      Please note that Drawing objects work based on ChartPanel positioning, and not WPF positioning.



      Therefore, anything added to the WPF control will cause a different outcome, such as adding a control to the ChartControl or to the UserControlCollection - the x/y coordinates from the drawing objects, OnRender, or MouseEvents would not make sense in that context because the ChartPanel has more objects in it which the anchor/rendering in the drawing tool use.

      I look forward to your response.

      I'm putting a panel with clickable Buttons inside a Drawing Tool. I have managed to solve the problem of using UserControlCollection because inside drawing tool can't be accesed.

      Now i'm drawing that panel inside OnMouseDown but it seems depending of screen its well drawn or not. I just found one way to positionate that StackPanel and its with Margin.

      Comment


        #4
        Hello franjcy,

        Thank you for your response.

        Are you able to provide a more complete example of your code to get an idea of what the code is doing?

        Comment


          #5
          Originally posted by NinjaTrader_Gaby View Post
          Hello franjcy,

          Thank you for your response.

          Are you able to provide a more complete example of your code to get an idea of what the code is doing?

          I just create a Panel with Buttons positionated next to EndAnchor point that when i click one, it executes some code. All it's working but StackPanel position isn't..



          INSIDE OnMouseDown():

          Code:
          if (!isButtonAdded && chartControl != null)
          {
          CreateButtons();
          
          if (listaBotones != null && listaBotones.Count > 0)
          {
          chartControl.Dispatcher.InvokeAsync(() =>
          {
          try
          {
          var chartWindow = System.Windows.Window.GetWindow(chartControl);
          var mainGrid = chartWindow.Content as Grid;
          
          if (mainGrid != null)
          {
          // Creamos un StackPanel para contener los botones.
          buttonPanel = new StackPanel
          {
          Orientation = Orientation.Vertical,
          HorizontalAlignment = HorizontalAlignment.Left,
          VerticalAlignment = VerticalAlignment.Top
          };
          
          // Limpiamos cualquier botón previo para evitar duplicados y conflictos de posición.
          foreach (var button in listaBotones)
          {
          if (mainGrid.Children.Contains(button))
          {
          mainGrid.Children.Remove(button);
          }
          }
          
          // Añadimos los botones al StackPanel.
          for (int i = 0; i < listaBotones.Count; i++)
          {
          buttonPanel.Children.Add(listaBotones[i]);
          }
          Point puntoFinLinea = EndAnchor.GetPoint(chartControl, chartPanel, chartScale);
          
          double margenIzquierdoX = puntoFinLinea.X + 10;
          double margenSuperiorY = puntoFinLinea.Y;
          double altoGridBotones = listaBotones.Count * alturaBotones;
          int totalWidth = chartPanel.W + chartPanel.X;
          int totalHeight = chartPanel.Y + chartPanel.H;
          
          if (margenIzquierdoX + anchuraBotones > totalWidth)
          {
          margenIzquierdoX -= anchuraBotones + 20;
          }
          if (margenSuperiorY + altoGridBotones > totalHeight)
          {
          margenSuperiorY -= altoGridBotones - 10;
          }
          
          buttonPanel.Margin = new Thickness(margenIzquierdoX, margenSuperiorY, 0, 0);
          
          // Añadimos el StackPanel al Grid principal si no está ya presente.
          if (!mainGrid.Children.Contains(buttonPanel))
          {
          mainGrid.Children.Add(buttonPanel);
          }
          
          isButtonAdded = true;
          }
          else
          {
          Print("No se pudo obtener el Grid del chart window.");
          }
          }
          catch (Exception ex)
          {
          Print("Error al modificar la ventana del gráfico: " + ex.Message);
          }
          });
          }
          }

          Comment


            #6
            Hello franjcy,

            Thank you for your response.

            From this code, it looks like you are adding a StackPanel into the content of the ChartControl over the existing control which is a problem. When you add more than one item to a grid, it will go to the middle of the grid over the first control.

            By default, a StackPanel constricts to the content - so it will not expand to fit the grid and will most likely go in the center. The parent grid's content settings will apply to the control since it is a child.

            Another issue is that the x and y from Drawing objects anchors are relevant to the rendering based on the ChartPanel the drawing object is applied to, this would not be the same as the x and y a mouse event produces in a WPF control.

            What is the end goal for your StackPanel? Is this supposed to be a side panel, or be positioned relative to a bar? If you are trying to create a side panel, we have an existing sample script demonstrating creating a side panel using WPF modifications (CustomSidePanelExample_NT8):

            Comment


              #7
              Originally posted by NinjaTrader_Gaby View Post
              Hello franjcy,

              Thank you for your response.

              From this code, it looks like you are adding a StackPanel into the content of the ChartControl over the existing control which is a problem. When you add more than one item to a grid, it will go to the middle of the grid over the first control.

              By default, a StackPanel constricts to the content - so it will not expand to fit the grid and will most likely go in the center. The parent grid's content settings will apply to the control since it is a child.

              Another issue is that the x and y from Drawing objects anchors are relevant to the rendering based on the ChartPanel the drawing object is applied to, this would not be the same as the x and y a mouse event produces in a WPF control.

              What is the end goal for your StackPanel? Is this supposed to be a side panel, or be positioned relative to a bar? If you are trying to create a side panel, we have an existing sample script demonstrating creating a side panel using WPF modifications (CustomSidePanelExample_NT8):

              https://forum.ninjatrader.com/forum/...ions#post96376
              The goal of the StackPanels is when I finished drawing with tool, a 'popup' panel with buttons appears next to end of line drawn.

              Finally, I get something it works using this code (I'll leave it in case it's useful to someone.)

              Code:
              Point puntoFinLinea = EndAnchor.GetPoint(chartControl, chartPanel, chartScale);
              
              
              PresentationSource source = PresentationSource.FromVisual(chartControl);
              double dpiX = 96.0, dpiY = 96.0;
              if (source != null)
              {
              dpiX = 96.0 * source.CompositionTarget.TransformToDevice.M11;
              dpiY = 96.0 * source.CompositionTarget.TransformToDevice.M22;
              }
              
              
              double margenIzquierdoX = puntoFinLinea.X * (96.0 / dpiX);
              double margenSuperiorY = puntoFinLinea.Y * (96.0 / dpiY);
              
              margenIzquierdoX -= chartPanel.ActualWidth - margenIzquierdoX - anchuraBotones + 20;
              
              if (margenIzquierdoX + anchuraBotones + 20 > chartPanel.ActualWidth)
              {
              margenIzquierdoX = chartPanel.ActualWidth - anchuraBotones * 2;
              }
              if (margenSuperiorY + alturaBotones * listaBotones.Count > chartPanel.ActualHeight)
              {
              margenSuperiorY = chartPanel.ActualHeight - alturaBotones * listaBotones.Count - 20;
              }
              ​
              buttonPanel.Margin = new Thickness(margenIzquierdoX, margenSuperiorY, 0, 0);


              Comment

              Latest Posts

              Collapse

              Topics Statistics Last Post
              Started by Geovanny Suaza, 02-11-2026, 06:32 PM
              0 responses
              628 views
              0 likes
              Last Post Geovanny Suaza  
              Started by Geovanny Suaza, 02-11-2026, 05:51 PM
              0 responses
              359 views
              1 like
              Last Post Geovanny Suaza  
              Started by Mindset, 02-09-2026, 11:44 AM
              0 responses
              105 views
              0 likes
              Last Post Mindset
              by Mindset
               
              Started by Geovanny Suaza, 02-02-2026, 12:30 PM
              0 responses
              562 views
              1 like
              Last Post Geovanny Suaza  
              Started by RFrosty, 01-28-2026, 06:49 PM
              0 responses
              568 views
              1 like
              Last Post RFrosty
              by RFrosty
               
              Working...
              X