# 分享 SDK

轻量级的分享 SDK。支持以下渠道

  1. 游戏内
  2. 营地
  3. QQ、微信
  4. 其他,包括系统浏览器

# 1. 如何使用

可直接引入,也可异步加载。

# 1.1. 直接引入

安装:

pnpm add share-light

main.ts 中:

import { initShare, openShareUI } from 'share-light';

initShare({
  showToast: (message) => {
    Toast.show(message);
  },
  showConfirmDialog: Dialog.confirm,
  title: 'Better Share',
  configWx,
});

openShareUI();

# 1.2. 异步加载

也可异步加载,并使用其提供的全局变量 shareLightSDK,性能更佳。

const SHARE_LIGHT_SCRIPT = 'https://image-1251917893.file.myqcloud.com/igame/npm/share-light/share-light%400.0.5.prod.js';

function init(
  func: 'initShare' | 'hideShareBtn' | 'openShareUI' | 'setupWzydShare',
  options?: ShareObject | string,
) {
  return new Promise((resolve) => {
    const innerCall = () => window.shareLightSDK?.[func]?.(options);
    if (inited && window.shareLightSDK) {
      resolve(innerCall());
      return;
    }

    loader(SHARE_LIGHT_SCRIPT, () => {
      inited = true;
      resolve(innerCall());
      return;
    });
  });
}

export function initShare(options: ShareObject) {
  return init('initShare', {
    hideShareType: getHideShareType(),
    showToast: (message) => {
      Toast.show(message);
    },
    showConfirmDialog: Dialog.confirm,

    configWx,
    // 业务如果需要,自行传入 postGetMiniProgramOpenLink,减小公共代码体积
    // 以下代码为示例
    // postGetMiniProgramOpenLink: (shareObject) => {
    //   const data = (shareObject.path || '').split('?');
    //   return postGetMiniProgramOpenLink({
    //     adcfg: {},
    //     appid: getJumpMiniProgramAppid(shareObject.gid),
    //     path: data.length > 0 ? data[0] : '',
    //     param_data: data.length > 1 ? data[1] : '',
    //     jump_type: JUMP_TYPES.CUSTOM_NO_ENCODE,
    //   });
    // },

    ...options,
  });
}

export function hideShareBtn() {
  return init('hideShareBtn');
}

export function openShareUI() {
  return init('openShareUI');
}

export function setupWzydShare(url: string) {
  return init('setupWzydShare', url);
}

# 2. 类型

export const SHARE_TYPE_MAP = {
  Wechat: 1,
  Timeline: 2,
  QQ: 3,
  QZone: 4,
} as const;

export type ShareType = typeof SHARE_TYPE_MAP[keyof typeof SHARE_TYPE_MAP];


export interface ShareObject {
  title?: string;
  desc?: string;
  icon?: string;
  link?: string;
  callback?: (_shareType?: ShareType) => {};

  path?: string | null;
  type?: string | number | null;
  miniprogram_link?: string;
  miniprogramAppId?: string;

  gid?: number;
  forceHistoryMode?: boolean;
  isWzydShare?: boolean;
  wzydShareText?: string;

  // 要隐藏的分享类型,游戏内可用,比如传入 [1],即隐藏微信好友分享
  hideShareType?: Array<ShareType>;

  tipMap?: {
    copyTextSuccess?: string;
    copyTextFail?: string;
    dialogTitle?: string;
    dialogMessage?: string;
    dialogConfirmButton?: string;
  };

  showToast?: (message: string) => any;
  showConfirmDialog?: (options: {
    title?: string;
    message?: string;
    confirmButtonText?: string;
    showCancelButton?: boolean;
  }) => any;

  postGetMiniProgramOpenLink?: (options: ShareObject) => Promise<any>;
  configWx?: (apiList: string[], openTagList?: string[]) => Promise<any>;
}

export interface ShareUIObject {
  initCommShareUI?: (callbackName: string) => void;
  initCommShareTip?: () => void;
  showCommShareUI?: () => void;
  showCommShareTip?: () => void;
  openShareUI?: () => void;
}

# 3. 内部配置

默认分享图片和提示文案等,可通过 initShare 参数覆盖。

export const DEFAULT_SHARE_ICON = 'http://ossweb-img.qq.com/images/pmd/igameapp/logo/log_igame_3.0.png';

export const DEFAULT_TIP_MAP = {
  copyTextSuccess: '复制链接成功,快去粘贴吧!',
  copyTextFail: '该浏览器不支持自动复制',
  dialogTitle: '温馨提示',
  dialogMessage: '请复制链接到微信或手机QQ内打开参与活动',
  dialogConfirmButton: '我知道了',
};

# 4. 更新日志

点此查看

# 5. 制作背景

# 5.1. 当前痛点

  1. 引入了jsapi,体积太大,文件太多,可读性、可维护性太差。本来就是非常简单的东西,加载sdk、调用全局变量即可,现在变得非常麻烦
  2. 类型缺失,使用、阅读、开发、调试困难
    • 多个全局对象 shareObjectshareUiObject 没有类型
    • 分享类别 shareType 没有类型,都是1234的魔法字符串
    • 对外的API,比如 initShare 没有类型
  3. 最关键的一点,分享根本不是首屏所需资源,不是必要路径,完全可以异步加载

当前 pmd 体积:

把分享重定向到一个伪文件,即去掉分享后的 pmd 体积:

可见分享模块的体积已经达到了 97.49KB,亟需优化。

jsapi 就有 58.34KB

# 5.2. 优化思路

  1. 去掉 jsapi
  2. 补充类型提示
  3. 封装异步加载逻辑,业务不关心

其他:

  1. ToastDialog 改为外部传入,方便切换组件库
    • Toast.show => showToast
    • Dialog.confirm => showConfirmDialog
  2. toastdialog 文案支持自定义
  3. postGetMiniProgramOpenLink 改为外部传入,可以充分自定义。传入的时候,就应该封装好参数,share 内部不关心。另外,这里真的需要这么做吗,很多业务已经改成明文 scheme 了,根本不用传了
  4. configWx 改为外部传入,适应任意业务
  5. 支持隐藏任意分享渠道,传入 hideShareType 参数即可,并把之前内部的账号判断移出 share 核心逻辑
  6. getEnvVersion 去掉,没找到需要它的地方
  7. isTestEnv,同样去掉

# 6. 效果

减少 85KB

之前:

之后:

# 7. 其他

更新为异步后,每次修改 share-light,需要:

  1. 发布 share-lightnpm
  2. build 后,将构建产物 index.prod.js 上传到 COS 上,并重命名为 share-light@version.prod.js
  3. 用上面新的 COS 链接代替 pmd-widget/share-v2 中的 script 链接
Last Updated: 2025/3/29 16:32:34