智慧水务管理系统 - 精河县供水工程综合管理平台

truncate-smart.js 6.6KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181
  1. /**
  2. * Date: 2015-10-05
  3. * Author: Kasper Søfren <soefritz@gmail.com> (https://github.com/kafoso)
  4. *
  5. * A truncation feature, where the ellipsis will be placed at a section within
  6. * the URL making it still somewhat human readable.
  7. *
  8. * @param {String} url A URL.
  9. * @param {Number} truncateLen The maximum length of the truncated output URL string.
  10. * @param {String} ellipsisChars The characters to place within the url, e.g. "...".
  11. * @return {String} The truncated URL.
  12. */
  13. export function truncateSmart(url, truncateLen, ellipsisChars) {
  14. var ellipsisLengthBeforeParsing;
  15. var ellipsisLength;
  16. if (ellipsisChars == null) {
  17. ellipsisChars = '&hellip;';
  18. ellipsisLength = 3;
  19. ellipsisLengthBeforeParsing = 8;
  20. }
  21. else {
  22. ellipsisLength = ellipsisChars.length;
  23. ellipsisLengthBeforeParsing = ellipsisChars.length;
  24. }
  25. // If the URL is shorter than the truncate length, return it as is
  26. if (url.length <= truncateLen) {
  27. return url;
  28. }
  29. var availableLength = truncateLen - ellipsisLength;
  30. var urlObj = parseUrl(url);
  31. // Clean up the URL by removing any malformed query string
  32. // (e.g. "?foo=bar?ignorethis")
  33. if (urlObj.query) {
  34. var matchQuery = urlObj.query.match(/^(.*?)(?=(\?|#))(.*?)$/i);
  35. if (matchQuery) {
  36. // Malformed URL; two or more "?". Removed any content behind the 2nd.
  37. urlObj.query = urlObj.query.substr(0, matchQuery[1].length);
  38. url = buildUrl(urlObj);
  39. }
  40. }
  41. if (url.length <= truncateLen) {
  42. return url; // removing a malformed query string brought the URL under the truncateLength
  43. }
  44. // Clean up the URL by removing 'www.' from the host if it exists
  45. if (urlObj.host) {
  46. urlObj.host = urlObj.host.replace(/^www\./, '');
  47. url = buildUrl(urlObj);
  48. }
  49. if (url.length <= truncateLen) {
  50. return url; // removing 'www.' brought the URL under the truncateLength
  51. }
  52. // Process and build the truncated URL, starting with the hostname
  53. var truncatedUrl = '';
  54. if (urlObj.host) {
  55. truncatedUrl += urlObj.host;
  56. }
  57. if (truncatedUrl.length >= availableLength) {
  58. if (urlObj.host.length === truncateLen) {
  59. return (urlObj.host.substr(0, truncateLen - ellipsisLength) + ellipsisChars).substr(0, availableLength + ellipsisLengthBeforeParsing);
  60. }
  61. return buildSegment(truncatedUrl, availableLength, ellipsisChars).substr(0, availableLength + ellipsisLengthBeforeParsing);
  62. }
  63. // If we still have available chars left, add the path and query string
  64. var pathAndQuery = '';
  65. if (urlObj.path) {
  66. pathAndQuery += '/' + urlObj.path;
  67. }
  68. if (urlObj.query) {
  69. pathAndQuery += '?' + urlObj.query;
  70. }
  71. if (pathAndQuery) {
  72. if ((truncatedUrl + pathAndQuery).length >= availableLength) {
  73. if ((truncatedUrl + pathAndQuery).length == truncateLen) {
  74. return (truncatedUrl + pathAndQuery).substr(0, truncateLen);
  75. }
  76. var remainingAvailableLength = availableLength - truncatedUrl.length;
  77. return (truncatedUrl + buildSegment(pathAndQuery, remainingAvailableLength, ellipsisChars)).substr(0, availableLength + ellipsisLengthBeforeParsing);
  78. }
  79. else {
  80. truncatedUrl += pathAndQuery;
  81. }
  82. }
  83. // If we still have available chars left, add the fragment
  84. if (urlObj.fragment) {
  85. var fragment = '#' + urlObj.fragment;
  86. if ((truncatedUrl + fragment).length >= availableLength) {
  87. if ((truncatedUrl + fragment).length == truncateLen) {
  88. return (truncatedUrl + fragment).substr(0, truncateLen);
  89. }
  90. var remainingAvailableLength2 = availableLength - truncatedUrl.length;
  91. return (truncatedUrl + buildSegment(fragment, remainingAvailableLength2, ellipsisChars)).substr(0, availableLength + ellipsisLengthBeforeParsing);
  92. }
  93. else {
  94. truncatedUrl += fragment;
  95. }
  96. }
  97. // If we still have available chars left, add the scheme
  98. if (urlObj.scheme && urlObj.host) {
  99. var scheme = urlObj.scheme + '://';
  100. if ((truncatedUrl + scheme).length < availableLength) {
  101. return (scheme + truncatedUrl).substr(0, truncateLen);
  102. }
  103. }
  104. if (truncatedUrl.length <= truncateLen) {
  105. return truncatedUrl;
  106. }
  107. var end = '';
  108. if (availableLength > 0) {
  109. end = truncatedUrl.substr(-1 * Math.floor(availableLength / 2));
  110. }
  111. return (truncatedUrl.substr(0, Math.ceil(availableLength / 2)) + ellipsisChars + end).substr(0, availableLength + ellipsisLengthBeforeParsing);
  112. }
  113. /**
  114. * Parses a URL into its components: scheme, host, path, query, and fragment.
  115. */
  116. function parseUrl(url) {
  117. // Functionality inspired by PHP function of same name
  118. var urlObj = {};
  119. var urlSub = url;
  120. // Parse scheme
  121. var match = urlSub.match(/^([a-z]+):\/\//i);
  122. if (match) {
  123. urlObj.scheme = match[1];
  124. urlSub = urlSub.slice(match[0].length);
  125. }
  126. // Parse host
  127. match = urlSub.match(/^(.*?)(?=(\?|#|\/|$))/i);
  128. if (match) {
  129. urlObj.host = match[1];
  130. urlSub = urlSub.slice(match[0].length);
  131. }
  132. // Parse path
  133. match = urlSub.match(/^\/(.*?)(?=(\?|#|$))/i);
  134. if (match) {
  135. urlObj.path = match[1];
  136. urlSub = urlSub.slice(match[0].length);
  137. }
  138. // Parse query
  139. match = urlSub.match(/^\?(.*?)(?=(#|$))/i);
  140. if (match) {
  141. urlObj.query = match[1];
  142. urlSub = urlSub.slice(match[0].length);
  143. }
  144. // Parse fragment
  145. match = urlSub.match(/^#(.*?)$/i);
  146. if (match) {
  147. urlObj.fragment = match[1];
  148. //urlSub = urlSub.slice(match[0].length); -- not used. Uncomment if adding another block.
  149. }
  150. return urlObj;
  151. }
  152. function buildUrl(urlObj) {
  153. var url = '';
  154. if (urlObj.scheme && urlObj.host) {
  155. url += urlObj.scheme + '://';
  156. }
  157. if (urlObj.host) {
  158. url += urlObj.host;
  159. }
  160. if (urlObj.path) {
  161. url += '/' + urlObj.path;
  162. }
  163. if (urlObj.query) {
  164. url += '?' + urlObj.query;
  165. }
  166. if (urlObj.fragment) {
  167. url += '#' + urlObj.fragment;
  168. }
  169. return url;
  170. }
  171. function buildSegment(segment, remainingAvailableLength, ellipsisChars) {
  172. var remainingAvailableLengthHalf = remainingAvailableLength / 2;
  173. var startOffset = Math.ceil(remainingAvailableLengthHalf);
  174. var endOffset = -1 * Math.floor(remainingAvailableLengthHalf);
  175. var end = '';
  176. if (endOffset < 0) {
  177. end = segment.substr(endOffset);
  178. }
  179. return segment.substr(0, startOffset) + ellipsisChars + end;
  180. }
  181. //# sourceMappingURL=truncate-smart.js.map