SheetForge Web
O SheetForge distribui um aplicativo web companheiro em web.sheetforge.workers.dev. Ele traz autoria, validação e reflexão de planilha para o navegador — sem Unity, sem instalação.
O mesmo core, não uma reimplementação
O aplicativo web compila as mesmas fontes exatas do core em C# — as mesmas que o harness de testes headless de .NET roda — para um assembly browser-wasm do .NET. Não existe uma segunda cópia do parser ou do validador, então os dois nunca podem divergir: uma regra corrigida uma vez é corrigida nos dois lugares.
Duas coisas seguem diretamente desse design.
- As suas DLLs de plugin compiladas carregam sem modificação, e elas acendem os mesmos slots aqui que no editor (abaixo).
- As regras de sintaxe de planilha deste site valem de forma idêntica no navegador. Marcadores, o sistema de tipos,
@overlap,@style,@enum,@loce integridade de referência se comportam todos da mesma forma, porque é o mesmo código respondendo. Isso inclui a paridade deIntId@Tab,LocRef@Tab— veja Sintaxe da Planilha.
Um plugin, doze slots, dois hosts
Um plugin não tem um "subconjunto web". A montagem — instanciação, ordenação, isolamento e o portão de compatibilidade — é uma única função Core pura que os dois hosts chamam. Apenas a descoberta difere: a Unity indexa os tipos do projeto, enquanto o navegador varre o assembly que você enviou.
Então os doze slots que um plugin pode preencher são os mesmos nos dois lados:
| Slot | No navegador |
|---|---|
| Enums · parsers de célula · tipos wrapper | Células fazem parsing, validam e fazem round-trip através da sua própria notação |
| Validadores de domínio | As suas regras aparecem em Problems ao lado das do core |
| Contribuidores de aresta | Vínculos enterrados na sua notação são desenhados no canvas e contados no índice de referências |
| Marcadores estruturais | As suas linhas @marker são aceitas e validadas |
| Templates de planilha | Os seus templates aparecem em Create sheet |
| Ampliadores de canvas | Nós virtuais, arestas extras, dicas de camada e de exibição |
| Registros de código | Chaves que vivem no código param de ser desenhadas como referências quebradas |
| Predefinições de cor | Mapeadas para as variáveis CSS do app |
| UI declarativa do Studio | As suas ações, painéis, selos de coluna e hints de editor de célula, renderizados em React |
| Strings de UI | Os seus rótulos seguem o idioma do usuário através da mesma sobreposição que o t() consulta |
| Observadores de pipeline | Notificados ao final de um ciclo de importação, exatamente como no editor |
As superfícies declarativas são o motivo pelo qual as extensões de autoria de um plugin sequer existem aqui. Um contrato que devolvesse um elemento UIToolkit nunca poderia carregar em um navegador, então o invólucro é descrito como dado — um id, uma chave de rótulo, um posicionamento, um tom — e cada host o desenha com os seus próprios widgets.
Onde um pacote precisa de algo que o vocabulário não consegue dizer, ele registra um painel rico exclusivo do editor sob o mesmo id. O editor desenha esse, o navegador desenha o descrito, e a extensão nunca simplesmente falta.
Duas regras valem no momento da renderização. Texto vindo de um plugin é escapado, e uma ação cuja situação mudou desde que foi desenhada responde com um no-op honesto, em vez de agir sobre um id desatualizado.
Um assembly de plugin também pode declarar para qual geração do formato de plugin ele foi construído. Se ela cair fora do que este host lê, o assembly inteiro é recusado com um motivo legível, em vez de carregado pela metade. É o mesmo portão, lendo a mesma declaração, no caminho do market, no caminho de sideload e em um arquivo local. Veja Autoria de Plugins.
O que permanece na Unity
A mesma honestidade cobre a localização: uma planilha de localização é totalmente autorada e validada aqui, mas sincronizar as StringTables do Unity Localization é tarefa do editor — o navegador não tem um projeto Unity no qual gravar tabelas.
Codegen e bake continuam sendo uma responsabilidade exclusiva da Unity. O navegador não consegue emitir arquivos .cs nem gravar ScriptableObjects, e não finge que consegue. O mesmo vale para qualquer coisa que precise do próprio projeto: o seletor de asset, o arrastar e soltar da janela Project e os registros do Addressables que eles preparam existem somente no editor; o <Type> de AssetRef@Group<Type> é analisado e mostrado no navegador, mas resolvido — e verificado quanto ao tipo — apenas onde os tipos do projeto estão carregados; e as miniaturas, visualizações ampliadas e reprodução de áudio de asset do editor não têm equivalente na web, porque o navegador não tem assets de projeto para ler — uma célula de asset na grade web é o seu texto de endereço.
A saída web é a planilha refletida — a origem validada e com round-trip — não assets cozidos (bake). Você faz a autoria e valida no navegador, depois roda uma importação na Unity quando quer classes fortemente tipadas e SOs cozidos (bake). A planilha é a única fonte da verdade de qualquer forma, então as duas superfícies se encontram na planilha.
O que o aplicativo web faz
Tudo faz round-trip através de um único contrato de fronteira JSON para o core WebAssembly, então a UI do navegador nunca rederiva uma regra que o core já possui.
| Área | O que você ganha |
|---|---|
| Sessão de autoria | Importação, projeção, e um painel Problems alimentado pelo mesmo validador de importação — diagnósticos de pre-flight, não uma checagem separada. A importação aceita arquivos TSV e CSV e workbooks .xlsx — toda planilha de um workbook chega como a sua própria aba, lida pelo mesmo leitor que o editor usa (compilado para WebAssembly), e quando algo precisou ser interpretado — o valor em cache de uma fórmula, uma data como texto yyyy-MM-dd, formatação não lida — o diálogo de importação diz isso em uma nota "Como esta pasta de trabalho foi lida". |
| Edição de tabela | Widgets de célula por tipo, undo, fixação de coluna, ordenação, busca, agrupamento e cor por @style — mais o mesmo conjunto de recursos de coluna de planilha eletrônica que o editor tem: arraste a alça do cabeçalho para definir a largura de uma coluna (clique duas vezes para ajustar; salvo por planilha neste navegador), oculte e mostre colunas com as letras e uma marca de fronteira mantidas honestas, filtros de valor por coluna que se combinam com a busca, e limpar-dados-da-coluna como um único passo de undo. + Row prepara uma linha de uma vez com uma chave sugerida — colunas de id inteiro pré-preenchidas —, pronta para renomear na célula de chave, e uma planilha sem coluna-chave o desabilita com o motivo. Células de enum e de boolean opcional abrem o mesmo seletor pesquisável que células de referência usam — e apenas uma janela de seletor fica aberta por vez: abrir outra fecha a última, e clicar em outro lugar ou Esc a fecha. Números de linha e letras de coluna selecionam (Ctrl alterna, Shift abrange), o cabeçalho e o corpo destacam a seleção, a célula selecionada desenha um contorno que segue o teclado, e uma seleção se arrasta para uma nova posição com uma linha de inserção — uma seleção não adjacente chega reunida no ponto de soltura, na ordem em que foi selecionada, como um único passo de undo — enquanto os menus de clique-direito aplicam largura, ajuste, ocultar, mover, excluir e limpar-dados a toda coluna selecionada (movimentos e exclusão a toda linha selecionada), com os itens de alvo único ficando à parte em sua própria seção. Planilhas de definição de enum têm o mesmo eixo de largura de coluna que planilhas de dados — arrastar, clique duas vezes para ajustar, largura exata, autoajuste, ocultar. Acima de 200 linhas, a grade renderiza apenas a janela visível (mais overscan), com espaçadores sustentando a altura real de rolagem — o mesmo limite que a tabela do editor usa, então os dois parecem iguais em uma planilha grande. |
| Valores visuais | Células Color, AnimationCurve e Gradient mostram uma prévia que preenche a célula — uma amostra de cor, uma polilinha de curva, uma barra de gradiente — e abrem um editor completo em um popover: um editor de cor com um quadrado HSV, sliders de matiz e alfa e um campo hexadecimal (o input de cor nativo do navegador não tem alfa, então ele não é usado); um editor de curva com uma grade com zoom, chaves e alças de tangente arrastáveis, modos de tangente (Free, Auto, Linear, Constant, ClampedAuto — clique com o botão direito em uma chave ou use o select), toggles de quebrada e ponderada, campos numéricos, wrap de antes/depois e as predefinições Linear / Entrada e saída suave / Constante; um editor de gradiente com chaves de cor e de alfa arrastáveis (até 8 de cada), um select de modo e um select de espaço de cor. Toda alteração faz o round-trip através do core WebAssembly — parsing, recálculo de tangente e amostragem são C#, não JavaScript — e o texto gravado é a mesma forma canônica que o editor escreve, byte a byte. As alterações são gravadas no momento em que você as faz, exatamente como os campos nativos do editor: a célula, o canvas e o Problems acompanham enquanto o editor está aberto, uma sessão de edição se funde em um único passo de undo não importa quantas alterações ela faça, e reabrir o editor inicia um novo passo. Não existe um Apply — o único botão é Close (Esc também fecha, e no editor de cor o Esc também restaura o valor de antes da sessão); reverter é Ctrl+Z. Abrir e fechar sem alterar nada não prepara nada. Uma coluna opcional mostra — quando vazia e oferece Limpar (padrão) em um menu de botão direito; um List<> dos três é uma lista de chips cujos gestos de adicionar / remover / reordenar / editar são cada um um passo de undo. A faixa de prévia fica dentro da altura padrão de linha, como na tabela do editor. As linhas de valor do canvas usam os mesmos componentes. |
| Edição de estrutura | Adicionar / remover / mover colunas, o formulário de coluna de quatro campos ✎, renomeação de aba (trocas mútuas e ciclos incluídos; abas xlsx são bloqueadas), criação/exclusão de planilha, e um dropdown de configurações ativas — cada um preparado como um passo de undo. Planilhas de definição de enum são autoradas da mesma forma — defina um novo enum, renomeie (com toda @type referente reescrita no mesmo lote), exclua, reordene colunas, edite o tipo subjacente e a descrição — sob as mesmas regras do editor, porque é o mesmo código decidindo. |
| Busca entre planilhas | A entrada All da barra lateral busca os ids e valores de campo de toda planilha por correspondência parcial, listando planilha · chave · campo · valor, 50 linhas por página — a mesma correspondência, ordenação e tamanho de página do editor. Ela lê os valores que a sessão mostra agora mesmo, edições preparadas incluídas, então um valor que você acabou de alterar é encontrado na hora. Dê duplo clique em um resultado — ou selecione-o e pressione Enter — e aquela planilha abre com a célula correspondente selecionada; como a busca lê a própria sessão, todo resultado pode ser aberto. |
| Localização | Planilhas de localização são planilhas comuns aqui — autoria, validação e cobertura por idioma incluídas. A célula LocRef de uma planilha de dados mostra em linha o texto no idioma de origem da entrada e abre o mesmo seletor de chave que as outras referências têm; digitar em uma célula vazia cunha a chave, seu texto de origem e a referência como um único passo de undo, exatamente como o editor faz. A lente de idiomas alterna quais colunas de idioma ficam visíveis (somente exibição), e a pasta de trabalho de tradução exporta os idiomas escolhidos para xlsx e reimporta o arquivo devolvido como uma mesclagem somente das colunas de idioma. Sincronizar as StringTables do Unity Localization continua sendo tarefa do editor. |
| Canvas de registros | Os materiais e consumidores de um registro são cards que você conecta arrastando fios — o canvas reutiliza o mesmo código puro de layout, fiação e cadeia de edição que o editor, então a matemática de pixel vive em C#, não em uma biblioteca de grafo em JS. Os cards mostram a mesma projeção que a tabela: uma coluna preparada neste lote já aparece no card marcada como pendente, uma renomeação preparada mostra o novo nome sobre o valor original, e uma exclusão preparada remove a linha aqui também. |
| Saída | Download em TSV / CSV por planilha, um download de workbook .xlsx carregando toda planilha escolhida em um único arquivo (um nome de planilha que as regras do workbook não conseguem guardar é ajustado e relatado, nunca renomeado silenciosamente), e leitura/gravação de Planilhas do Google, com os dropdowns de validação de dados da planilha atualizados automaticamente depois de cada push (veja abaixo). |
Feito idêntico, não apenas parecido
A UI web combina com o Data Studio do editor de propósito, até a lógica compartilhada.
- Respostas compartilhadas. Os predicados de cabeçalho (
pending/edited), o modal de diff, e a ordem de composição da projeção são C# compartilhado, então as duas superfícies dão a mesma resposta para a mesma pergunta. - Frases compartilhadas. Onde a web espelha uma tela do Studio, ela usa as próprias chaves de string do Studio, e os valores são gerados a partir das tabelas de idioma do editor em tempo de build, em vez de redigitados. Adicionar uma frase que as duas superfícies mostram é uma chave em
Lang*.cs; a divergência é estruturalmente impossível, e não apenas desencorajada. Duas coisas são deliberadamente mantidas separadas, e uma proteção em tempo de build impõe a fronteira:- strings que são genuinamente exclusivas da web permanecem no catálogo web;
- diagnósticos e relatórios são renderizados pelo core WebAssembly, não reformulados na UI.
- Aparência compartilhada. O grafo e a planilha são mostrados juntos em um painel dividido redimensionável que espelha o comportamento de clamp do canvas do editor, e toda cor vem do conjunto de tokens
.aw-rootdo editor como a única fonte da verdade — sem paleta fixa. - Kit de componentes compartilhado. A UI é construída sobre um kit
awinterno cujos nomes de classe, tokens e posicionamento de pop-up correspondem um a um ao USS do editor e ao mockup HTML canônico. Um único mockup agora alimenta duas portas — o app web e o editor UIToolkit — em vez da web divergir por conta própria.web/Docs/ui-parity.mdregistra como a web segue o studio quando ele muda. - Editores de célula compartilhados. Qual widget uma célula recebe é decidido pelo hint de editor de célula do core — primeiro o registro de um pacote, depois a tabela embutida (
BuiltinCellEditorHints) — então um tipo de plugin que declara o arquétipoColorPicker,CurveEditorouGradientEditorabre aqui os mesmos editores que abre na Unity, e os dois hosts não podem escolher widgets diferentes para o mesmo nome de tipo. - Paridade de canvas. Arrastar e soltar alcançou paridade completa com o editor: pan com arrastar do botão do meio ou Alt-arrastar, menus em cascata de espaço vazio, inspectors de fio e nó, esmaecimento do fio selecionado, e exclusão de terminus com uma caixa de confirmação. O intervalo de zoom é o do editor (25–200%), e as métricas de card vêm do core, em vez de uma segunda cópia em JavaScript.
- Lista de tipos compartilhada. O dropdown de
@typeoferece o que o registry de parser de fato conhece, agrupado exatamente como o editor os agrupa: os escalares embutidos (Color,AnimationCurveeGradientincluídos), chavesRecordId/IntId, referênciasRecordId@TabeIntId@Tab,Enum<…>,AssetRef@Group, e qualquer tipo ou wrapper que um plugin carregado registrou. Um plugin que registra um novo tipo, portanto, aparece no navegador sem nenhuma mudança na web. (Antes de o core WebAssembly terminar de inicializar, a primeiríssima pintura recorre aos quatro escalares embutidos.)
Quando usar qual
- Use o navegador para autoria rápida, validação e edições de planilha de qualquer lugar, e para colegas de equipe que não abrem a Unity.
- Use a Unity quando você precisar de classes C# geradas e ScriptableObjects cozidos (bake) — as etapas de importação, codegen e bake.
Os dois gravam na mesma planilha, então uma mudança feita em um é captada pelo outro na próxima leitura.
Páginas relacionadas
- Sintaxe da Planilha — as regras que o core do navegador impõe, inalteradas
- Planilhas de Localização — planilhas de texto do jogo, no navegador e no editor
- Mercado de Plugins Web — instalando e fazendo sideload de plugins no navegador
- Acesso Web às Planilhas Google — lendo e gravando planilhas a partir do site publicado
- Data Studio — a superfície de autoria no editor que o app web espelha