Skip to content

Встраивание в лаунчер: use-методы

Расширение «подключается» к лаунчеру через готовые точки расширения. В коде это делается функциями с префиксом use…, импортируемыми из @rynt/sdk/extension. У каждой точки свой контракт: что передать в register(key, value, order?).

Ниже — что можно расширить и зачем, без теории про внутреннее хранилище.

Таблица: use-метод → что даёт

ФункцияНазначение
useExtensionPageRegistry()Новый экран приложения (маршрут + Vue-компонент + заголовок).
useExtensionNavRegistry()Пункт главного меню (ссылка, подпись, иконка, опционально бейдж).
useExtensionSidebarRegistry()Боковая колонка: слот strip или footer + компонент.
useExtensionShellRegistry()Оверлей поверх интерфейса (модальные слои, глобальные панели).
useExtensionUserStripRegistry()Зона действий рядом с профилем пользователя.
useLoaderRegistry()Подключение лоадера Minecraft (свой тип установки/запуска).
useModProviderRegistry()Подключение источника модов для маркетплейса.
useAccountProviderRegistry()Свой провайдер входа (ключ = provider.id).
useInviteHandlerRegistry()Обработка инвайта по типу (ключ = invite.type).
useBuildCardActionsRegistry() и др.Визуальные слоты в карточках, деталках, экранах — см. справочник core.*.

Вызов someRegistry().register('уникальный-ключ', значение, порядок?) внутри defineRyntExtension((ctx) => { … }) привязывает запись к вашему расширению автоматически.

Полный перечень (~60 core.* реестров), props и примеры — Справочник core.*.

Страница и меню (как в Hello World)

Тот же сценарий можно записать через use-методы — результат тот же:

ts
import { markRaw } from 'vue';
import {
  defineRyntExtension,
  resolvedNavigationPath,
  useExtensionPageRegistry,
  useExtensionNavRegistry,
} from '@rynt/sdk/extension';

import HelloPage from './HelloPage.vue';

const EXTENSION_ID = '@acme/hello-world';

export default defineRyntExtension(() => {
  const routePath = resolvedNavigationPath(EXTENSION_ID, 'hello');

  useExtensionPageRegistry().register(
    'hello',
    {
      path: 'hello',
      title: 'Hello',
      component: markRaw(HelloPage),
      resolvedRoutePath: routePath,
    },
    100,
  );

  useExtensionNavRegistry().register(
    'hello',
    {
      link: routePath,
      label: 'Hello',
      icon: 'home',
    },
    100,
  );
});

ctx.registerRegistryEntry({ registryId: 'core.page', … }) и useExtensionPageRegistry().register(…) — два равноправных стиля; выберите один и придерживайтесь его в проекте.

Боковая колонка и shell

Сайдбар — компонент в полосе слева или в подвале боковой зоны:

ts
import { markRaw } from 'vue';
import {
  defineRyntExtension,
  useExtensionSidebarRegistry,
} from '@rynt/sdk/extension';

import MyStrip from './MyStrip.vue';

export default defineRyntExtension(() => {
  useExtensionSidebarRegistry().register('my-strip', {
    placement: 'strip',
    component: markRaw(MyStrip),
  });
});

Shell — для оверлеев на весь экран (например глобальный звонок или статус):

ts
useExtensionShellRegistry().register('my-overlay', markRaw(MyOverlay));

Лоадеры и маркетплейс модов

  • useLoaderRegistry() — регистрация экземпляра лоадера с полем id и реализацией контракта лоадера из SDK.
  • useModProviderRegistry() — регистрация провайдера каталога модов (поиск, установка и т.д. по контракту SDK).

Точные поля объектов смотрите в типах @rynt/sdk (экспорты extension и minecraft-loader, где применимо).

Аккаунты и инвайты (паттерн A)

Провайдер входа:

ts
import { defineRyntExtension, useAccountProviderRegistry } from '@rynt/sdk/extension';

export default defineRyntExtension(() => {
  useAccountProviderRegistry().register('my-provider', myAuthProvider);
});

Инвайт по типу (subtitle, кнопка, свой onAccept):

ts
import { defineRyntExtension, useInviteHandlerRegistry } from '@rynt/sdk/extension';

export default defineRyntExtension(() => {
  useInviteHandlerRegistry().register('my_campaign', {
    subtitle: () => 'Специальное приглашение',
    primaryActionLabel: () => 'Открыть',
    onAccept: async (invite, ctx) => {
      await ctx.acceptInvite(invite.id);
      await ctx.routerPush('/my-page');
    },
  });
});

Дальше