Lineage 2 на macOS и Linux без Wine - виртуализация оригинального клиента

  • Автор темы Автор темы pvolok
  • Дата начала Дата начала

pvolok

Путник
Пользователь
Сообщения
1
Розыгрыши
0
Репутация
0
Реакции
1
Баллы
16
Привет. Я из команды l2hub.info. Мы сделали внутриигровой HUD ( ).

За несколько лет работы над худом накопилось много наработок и опыта по клиенту. И мы сделали лаунчер, который запускает оригинальный, неизменённый клиент на macOS и Linux. Это не Wine, клиент исполняется в своем виртуализированном окружении. Файлы клиента и патчи ваши, серверная часть не трогается вообще, хотя своя среда исполнения дает новые возможности для античита, но это на потом.

На маке и линуксе л2 сейчас либо через Parallels, либо через CrossOver с вылетами. Оба варианта с проблемами. Наш клиент является нативным приложением и ощущается как нативное приложение.

Демо для C1 - можно скачать и запустить прямо сейчас
Приложение под macOS (Apple Silicon) прикреплено. Заходит на наш демо-сервер.


Это демонстрация технологии, а не готовый клиент: стабильность и производительность мы сейчас закрываем. Смысл демо в том, что оригинальный клиент живой и играбельный на маке. Много оптимизаций и фиксов еще не имплементированы.

IL и H5 запускали на черновую, работаем над качественной поддержкой.

Скриптинг клиента на TypeScript
Логика клиента пишется на TypeScript, а интерфейс - на клоне React, который рендерит нативный интерфейс Lineage 2 (настоящие окна и контролы движка, а не оверлей поверх игры). Можно делать свой интерфейс на TypeScript без правки .u и без пересборки клиента.

Код:
import { h, Fragment, useState, render, Tabs, Tab } from "l2react";

declare const l2: any;

function HomePanel() {
  return (
    <Fragment>
      <text>This is the l2hub.info client.</text>
      <text></text>
      <text>This window is part of the client itself,</text>
      <text>built from the script the Source tab shows.</text>
      <text></text>
      <text>Everything here is ours to change.</text>
    </Fragment>
  );
}

const AREAS: Array<[string, number, number, number]> = [
  ["Giran", 83235, 148497, -3404],
  ["Aden", 147391, 25967, -2012],
  ["Gludio", -14138, 122042, -2988],
  ["Arena", 73579, 142709, -3763],
  ["Hardin's", 105918, 109759, -3207],
  ["LOA", 131355, 114451, -3718],
];

function AreasPanel() {
  return (
    <Fragment>
      <text>Teleport, open to any player.</text>
      {AREAS.map(([name, x, y, z]) => (
        <button key={name} onClick={() => l2.teleport(x, y, z)}>
          {name}
        </button>
      ))}
    </Fragment>
  );
}

const LINES: string[] = String(l2.source || "(source unavailable)").split("\n");
const ROW_H = 19;
const ROWS = 18;
const COLS = 68;
const PAD = 8;
const PANEL_W = 480;
const SCROLL_W = 11;

function SourcePanel() {
  const [first, setFirst] = useState(0);
  const shown: string[] = [];
  for (let i = 0; i < ROWS; i++) {
    const line = LINES[first + i];
    shown.push(line === undefined ? "" : line.slice(0, COLS));
  }
  return (
    <Fragment>
      {shown.map((line, i) => (
        <text key={"l" + i} y={PAD + i * ROW_H} w={PANEL_W - 3 * PAD - SCROLL_W}>
          {line === "" ? " " : line}
        </text>
      ))}
      <scroll
        x={PANEL_W - PAD - SCROLL_W}
        y={PAD}
        h={ROWS * ROW_H}
        max={LINES.length}
        page={ROWS}
        value={first}
        onChange={(v) => setFirst(parseInt(v, 10))}
      />
    </Fragment>
  );
}

function App() {
  return (
    <Tabs>
      <Tab title="Home">
        <HomePanel />
      </Tab>
      <Tab title="Areas">
        <AreasPanel />
      </Tab>
      <Tab title="Source">
        <SourcePanel />
      </Tab>
    </Tabs>
  );
}

render(App, { title: "l2hub.info", x: 60, y: 60, w: 480, h: 400 });


Предложение для админов
Если вы хотите поддержку macOS и Linux для своего сервера, то мы готовы адаптировать наш лаунчер под ваш клиент.

Адаптация под ваш клиент + лицензия - от 1500$. Зависит от версии клиента и необходимых кастомизаций.

Discord: pvolok
 

Вложения

  • L2hub.zip
    L2hub.zip
    8,3 МБ · Просмотры: 3
Назад
Сверху Снизу