utf8.js 2.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141
  1. function byteLength(string) {
  2. let length = 0
  3. for (let i = 0, n = string.length; i < n; i++) {
  4. const code = string.charCodeAt(i)
  5. if (code >= 0xd800 && code <= 0xdbff && i + 1 < n) {
  6. const code = string.charCodeAt(i + 1)
  7. if (code >= 0xdc00 && code <= 0xdfff) {
  8. length += 4
  9. i++
  10. continue
  11. }
  12. }
  13. if (code <= 0x7f) length += 1
  14. else if (code <= 0x7ff) length += 2
  15. else length += 3
  16. }
  17. return length
  18. }
  19. let toString
  20. if (typeof TextDecoder !== 'undefined') {
  21. const decoder = new TextDecoder()
  22. toString = function toString(buffer) {
  23. return decoder.decode(buffer)
  24. }
  25. } else {
  26. toString = function toString(buffer) {
  27. const len = buffer.byteLength
  28. let output = ''
  29. let i = 0
  30. while (i < len) {
  31. let byte = buffer[i]
  32. if (byte <= 0x7f) {
  33. output += String.fromCharCode(byte)
  34. i++
  35. continue
  36. }
  37. let bytesNeeded = 0
  38. let codePoint = 0
  39. if (byte <= 0xdf) {
  40. bytesNeeded = 1
  41. codePoint = byte & 0x1f
  42. } else if (byte <= 0xef) {
  43. bytesNeeded = 2
  44. codePoint = byte & 0x0f
  45. } else if (byte <= 0xf4) {
  46. bytesNeeded = 3
  47. codePoint = byte & 0x07
  48. }
  49. if (len - i - bytesNeeded > 0) {
  50. let k = 0
  51. while (k < bytesNeeded) {
  52. byte = buffer[i + k + 1]
  53. codePoint = (codePoint << 6) | (byte & 0x3f)
  54. k += 1
  55. }
  56. } else {
  57. codePoint = 0xfffd
  58. bytesNeeded = len - i
  59. }
  60. output += String.fromCodePoint(codePoint)
  61. i += bytesNeeded + 1
  62. }
  63. return output
  64. }
  65. }
  66. let write
  67. if (typeof TextEncoder !== 'undefined') {
  68. const encoder = new TextEncoder()
  69. write = function write(buffer, string) {
  70. return encoder.encodeInto(string, buffer).written
  71. }
  72. } else {
  73. write = function write(buffer, string) {
  74. const len = buffer.byteLength
  75. let i = 0
  76. let j = 0
  77. while (i < string.length) {
  78. const code = string.codePointAt(i)
  79. if (code <= 0x7f) {
  80. buffer[j++] = code
  81. i++
  82. continue
  83. }
  84. let count = 0
  85. let bits = 0
  86. if (code <= 0x7ff) {
  87. count = 6
  88. bits = 0xc0
  89. } else if (code <= 0xffff) {
  90. count = 12
  91. bits = 0xe0
  92. } else if (code <= 0x1fffff) {
  93. count = 18
  94. bits = 0xf0
  95. }
  96. buffer[j++] = bits | (code >> count)
  97. count -= 6
  98. while (count >= 0) {
  99. buffer[j++] = 0x80 | ((code >> count) & 0x3f)
  100. count -= 6
  101. }
  102. i += code >= 0x10000 ? 2 : 1
  103. }
  104. return len
  105. }
  106. }
  107. module.exports = {
  108. byteLength,
  109. toString,
  110. write
  111. }