Why is the graduatedTickUnit larger, the more it is offset when rotating the sector?

When the number of major ticks is just right, the node barely sees an offset. But as the number of major ticks gets smaller, the offset becomes more and more obvious. You can see the specific code in this link: When I dynamically changed the graduatedTickUnit, why did the tick mark disappear?

  • normal
majorScaleNum = 10;
minorScaleNum = 5;
minValue = 0;
maxValue = 100;

ring_normal

  • weird
majorScaleNum = 5;
minorScaleNum = 5;
minValue = 0;
maxValue = 100;

ring_weird

Have you set the Part.rotateObjectName to refer to the Graduated Panel and the Part.rotationSpot to go.Spot.Center?

I have tried your method, but it has not been solved. And I rotate the node by the green adornment provided by SectorReshapingTool, not the orange adornment. If I hide the scale, there is no problem with the rotation.

Sorry, we missed this one. You are using an auto panel to contain the graduated panel, but there are no other elements. I find that without the auto panel, I can rotate as expected.

Really, can I see your code? I just tried but didn’t succeed. I don’t know if it was written incorrectly. And, actually, I have some other elements, like the inner circle, the text.

function makeRing() {
  return MAKE(
      go.Node,
      "Auto",
      {
        selectionObjectName: "PAD",
        resizeObjectName: "PAD",
        background: "transparent"
      },
      MAKE(
        go.Panel,
        "Graduated",
        ...
        ...
      ),
      MAKE(
        go.Shape,
        { strokeWidth: 0 },
        new go.Binding("fill", "", getChartBarColor),
        new go.Binding("geometry", "", makeInnerSector),
      ),
      MAKE(
        go.Shape,
        "Circle",
        { fill: "#fff" },
        new go.Binding("width", "", getInnerRadius),
        new go.Binding("height", "", getInnerRadius),
        new go.Binding("stroke")
      ),
      MAKE(
        go.TextBlock,
        new go.Binding("text", "", getChartPercentage),
        new go.Binding("font", "", getPercentageFont),
        new go.Binding("stroke", "percentageColor"),
        new go.Binding("isUnderline", "percentageIsUnderline"),
        new go.Binding("visible", "showPercentage")
      )
  )
}

ring_final

@jhardy
Do you have time to help me see this question?

We are just getting back from the US holiday, we’ll look into this today.

Ok, so the problem is that the graduated panel’s center point isn’t actually at the center of the node when the ticks are laid out in certain ways. To fix this, you can override RotatingTool.computeRotationPoint to get the center of the “PAD” circle. The function would look something like this:

function(obj) {
  var part = obj.part;
  var pad = part.findObject("PAD");
  if (pad) {
    return pad.getDocumentPoint(go.Spot.Center);  // rotate about center of "PAD" object
  }
  return go.RotatingTool.prototype.computeRotationPoint.call(this, obj);
}

First of all, thank you very much for your answers. I tried your method, but it didn’t work. In fact, I did not use the RotatingTool, but the SectorReshapingTool to change the angle.

Ok, I’m having trouble recreating your setup to reproduce this since you have so many customizations. Could you post your full code here or send it to us at GoJS at our domain, nwoods.com?

Actually, I may have figured it out. I believe the problem is as I described earlier where as the ticks/labels rotate, the center of the node varies.

I think you should use a node template like this to solve the problem:

$(go.Node, "Spot",
  { selectionObjectName: "PAD" },
  $(go.Shape, "Circle",  // invisible outer circle containing everything
    { fill: null, stroke: null },
    // this binding should make the desiredSize surround the entire graduated panel, including ticks/text
    new go.Binding("desiredSize", ...),
  ),
  $(go.Panel, "Graduated",
    { alignmentFocusName: "PAD" },  // align the center of the PAD object to the outer circle
    ...
  ),
  $(go.Shape, ...) // inner red sector
  $(go.Shape, "Circle",  // inner white circle
    ...
  ),
  $(go.TextBlock, ...)
);

The main difference is that this uses a Spot panel with a main shape that surrounds the whole graduated panel so that when rotating, the node doesn’t need to move anything around. Notice that the graduated panel uses an alignmentFocusName to ensure the circle is what gets aligned to the center of the surrounding main shape.

I have written a demo, added two templates, one(red ring) is my previous method, the other(green ring) is the method you said, however, the offset still exists.

Demo link is here: vue-gojs-ring-demo

By the way, there is still a problem. This green adonment is also offset when the scale is displayed. I want it to be on the edge of the outer circle, just like when the scale is not displayed.

  1. You didn’t inflate the width/height to account for ticks as I advised. Using these bindings, it worked. You may be able to be smarter about how to inflate it instead of just a set amount.
new go.Binding("width", "width", function(w) { return w + 60; }),
new go.Binding("height", "width", function(w) { return w + 60; })
  1. The SectorReshapingTool sets the Adornment.adornedObject to part.locationObject. You haven’t set the location object of your node, so it uses the whole node. You can either modify the tool to adorn the “PAD” shape, or modify the node template by setting the locationObjectName to the “PAD” shape.

Thank you again for your help.