Simple example: I draw a horizontal, 1000px line in Illustrator (tried in CS5 & CS6) and put a text on it. I drag the starting point of the text on the path to 250px.
When I export to SVG, I would expect Illustrator to set the 'startOffset'-Attribute of the textPath tag to 25%. Instead, it's somewhere around 32% (a third??).
When I drag the text to 500px, however, 'startOffset' is set to 50% as expected.
At 750px, the attribute will be 67%.
The problem is that, viewing the SVG in Firefox, the text is displayed at a different position as it seems to apply the percentage in a linear way. So 32% really means 320px and not 250px the way Illustrator seems to calculate it...
Am I missing something here? Or does anybody know a way to recalculate the percentage so it's displayed correctly in SVG?
Thx for any help
Ok, so i figured out how to calculate the right percentages:
Apparently, Illustrator calculates the percentage depending on the number of path segments. If the path is made of two segments (i.e. 3 vertices), and a path text is applied and positioned at the second vertex (the 'middle'), this will result in a startOffset of 50% in the SVG-File, regardless of the size of each path segment. The first segment can be 1000px long and the second one only 4px (total path length of 1004px): Placing the text at the second vertex will always result in 50%.
SVG/Browsers on the other side calculate the percentage depending on the total path length. So, referring to the example above, the text will not be placed at a length of 1000px (which is 50% if you look at the number of segments and thus the end of the first segment) but at 502px which is 50% of the total path length.
In order to convert the 'illustrator percentage' to the 'browser percentage', you could do something like this (not optimized):
// Get the current percentage
var oldPercent = parseFloat(textPathNode.getAttribute('startOffset').split('%')[0])/100;
// Get the path
var parentPath = document.getElementById(textPathNode.getAttribute('xlink:href').split('#')[1])
// Get the path segments
var parentPath.getAttribute('d').match(/[MmLlHhCc][\d\,\.\-\s]+/g);
// Calculate the percentage for one segment
var percentPerSegment = 1/segments.length;
// Find out on which segment the textPath lies
var offsetIsOnSegmentNo = Math.floor(oldPercent/percentPerSegment);
// Calculate the length of that segment
var virtualPath = document.createElementNS('http://www.w3.org/2000/svg', 'path');
virtualPath.setAttribute('d', 'M0,0'+segments[offsetIsOnSegmentNo]);
var segLength = virtualPath.getTotalLength();
// Calculate the total path length of the previous segments
var prevSegLength=0;
var prevD = '';
for(var i=0; i<offsetIsOnSegmentNo; i++)
prevD += segments[s];
var virtualPrevPath = document.createElementNS('http://www.w3.org/2000/svg', 'path');
virtualPrevPath.setAttribute('d', 'M0,0'+prevD);
var prevPathLength = virtualPrevPath.getTotalLength();
// Calculate the actual path length for the old percentage
var totalLength = prevPathLength + segLength*(oldPercent-(percentPerSegment*offsetIsOnSegmentNo))/(percentPerSegment);
// Calculate the correct percentage
var newPercentage = totalLength / parentPath.getTotalLength();
textPathNode.setAttribute('startOffset', newPercentage*100+'%');