UNPKG

minigame-std

Version:

Mini Game Standard Development Library.

114 lines (93 loc) 2.88 kB
/** * @fileoverview Encode/Decode between Uint8Array and base64 encoded string. * * Forked from @std/encoding/base64 and https://github.com/cross-org/base64 */ import { bufferSource2U8a } from '../utils/mod.ts'; /** * A string containing standard base64 characters */ const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'; /** * Standard base64 characters */ const base64abc = chars.split(''); /** * Lookup table for standard base64 characters */ const lookup = ((): Uint8Array => { const lookupTemp = new Uint8Array(256); // base64abc.length * 4 for (let i = 0; i < base64abc.length; i++) { lookupTemp[base64abc[i].charCodeAt(0)] = i; } return lookupTemp; })(); /** * Converts BufferSource into a base64 encoded string. * * @param data - The data to encode. * @returns The base64 encoded string. */ export function base64FromBuffer(data: BufferSource): string { let result = ''; const u8a = bufferSource2U8a(data); const len = u8a.length; let i: number; for (i = 2; i < len; i += 3) { result += base64abc[(u8a[i - 2]) >> 2]; result += base64abc[ (((u8a[i - 2]) & 0x03) << 4) | ((u8a[i - 1]) >> 4) ]; result += base64abc[ (((u8a[i - 1]) & 0x0f) << 2) | ((u8a[i]) >> 6) ]; result += base64abc[(u8a[i]) & 0x3f]; } if (i === len + 1) { // 1 octet yet to write result += base64abc[(u8a[i - 2]) >> 2]; result += base64abc[((u8a[i - 2]) & 0x03) << 4]; result += '=='; } if (i === len) { // 2 octets yet to write result += base64abc[(u8a[i - 2]) >> 2]; result += base64abc[ (((u8a[i - 2]) & 0x03) << 4) | ((u8a[i - 1]) >> 4) ]; result += base64abc[((u8a[i - 1]) & 0x0f) << 2]; result += '='; } return result; } /** * Converts a base64 encoded string to an Uint8Array * * @param data - Base64 encoded string * @returns The decoded data as an Uint8Array. */ export function base64ToBuffer(data: string): Uint8Array { const len = data.length; let bufferLength = len * 0.75; if (data[len - 1] === '=') { bufferLength--; if (data[len - 2] === '=') { bufferLength--; } } const u8a = new Uint8Array(bufferLength); let pos = 0; for (let i = 0; i < len; i += 4) { const encoded1 = lookup[data.charCodeAt(i)]; const encoded2 = lookup[data.charCodeAt(i + 1)]; const encoded3 = lookup[data.charCodeAt(i + 2)]; const encoded4 = lookup[data.charCodeAt(i + 3)]; u8a[pos++] = (encoded1 << 2) | (encoded2 >> 4); u8a[pos++] = ((encoded2 & 15) << 4) | (encoded3 >> 2); u8a[pos++] = ((encoded3 & 3) << 6) | (encoded4 & 63); } return u8a; }