Crie um seletor de seções de relatório com o componente Transfer controlado da Arco. Explore as escalas reais de espaçamento e tamanho, as convenções de variáveis de CSS, as superfícies semânticas e a diferença entre selecionar linhas e movê-las.
Interpretação independente HTML do comportamento de Transfer no Arco e de referências verificadas do tema; exemplo nativo React fornecido separadamente. · Referência de implementação
02
Referência de design do sistema de design Arco Design
Fonte original do Arco React. As constantes Less são indicadas com @; as variáveis CSS em tempo de execução usam --. O espaçamento da prévia e o layout dos painéis são escolhas originais da aplicação, baseadas nessas escalas.
No sistema de design Arco Design, Transfer representa associação, não apenas uma lista de caixas de seleção
Escolha as seções do relatório com atenção
O Arco Transfer é útil quando um operador precisa comparar dois conjuntos: seções disponíveis e seções incluídas em um relatório. Marcar uma linha a seleciona para uma operação posterior; isso não move a seção imediatamente, a menos que o modo simples esteja ativado.
O exemplo mantém a ação explícita em duas etapas. O usuário seleciona Canais de aquisição, ativa Incluir e, em seguida, prepara um esboço. Esse esboço é uma captura separada; por isso, alterações posteriores no editor não modificam silenciosamente a versão preparada.
Sistema de design Arco Design: use a escala de tamanhos e a escala de espaçamento separadamente
O mesmo número pode representar dimensões diferentes
As constantes de tamanho do Arco avançam em incrementos de quatro pixels, enquanto a escala de espaçamento começa com 2, 4, 6, 8, 10 e 12, antes de passar a incrementos maiores. O tamanho padrão do componente corresponde a 32px. Presumir que todo sufixo de tamanho ou espaçamento representa a mesma medida levaria a controles inconsistentes.
Neste layout original, os dois painéis de transferência têm cantos com raio médio e margem de página de 24px. Caixas de seleção pequenas e divisórias entre linhas dão suporte à tarefa densa de seleção; áreas maiores da página criam separação sem substituir conteúdo útil por cartões grandes demais.
Sistema de design Arco Design: mantenha os papéis semânticos na estilização da aplicação
CSS As variáveis têm um contrato de nomenclatura próprio
O tema padrão exporta variáveis como --color-text-1 e --color-fill-2, sem o prefixo arco. Compilações personalizadas podem alterar esse prefixo; por isso, inspecione o tema compilado ao integrá-lo a uma aplicação com namespace. As variáveis da paleta principal contêm canais RGB; quem as consumir deve usar rgb(var(--primary-6)), em vez de tratá-las como uma cor hexadecimal completa.
A prévia usa o tom de azul do Arco verificado como referência para a ação principal e as linhas selecionadas. Uma seção restrita usa uma caixa de seleção desativada e um texto explicativo, em vez de vermelho, que poderia sugerir um erro que o operador pode corrigir.
Sistema de design Arco Design: dê suporte a rótulos compactos e nomes longos de seções
Uma escala prática para o texto do corpo
O tamanho padrão do texto do corpo é 14px, com multiplicador de altura de linha de 1.5715. A família publicada começa com Inter e inclui alternativas de sistema e para CJK. Esta é uma pilha CSS, não uma prova de que um arquivo de fonte Inter foi carregado.
O rótulo de uma seção do relatório pode ser mais longo que o exemplo. A versão offline quebra o texto das linhas e empilha os painéis em telas pequenas, mantendo legíveis os rótulos Incluir e Remover. Ela não reduz o componente de transferência inteiro até tornar o texto ilegível.
Sistema de design Arco Design: dois arrays controlados evitam comportamentos ambíguos
Pertencimento e seleção têm significados diferentes
targetKeys indica quais itens fazem parte do relatório. selectedKeys indica quais caixas de seleção estão ativas no momento nas duas listas. onSelectChange fornece arrays para a esquerda e para a direita; concatene-os ao controlar selectedKeys. onChange fornece o novo pertencimento, a direção e as chaves movidas.
Mantenha estável a chave de cada item de origem, mesmo quando o rótulo exibido mudar.
Combine os arrays de seleção da esquerda e da direita em onSelectChange.
Substitua targetKeys pelo novo array recebido em onChange.
Limpe a seleção temporária após uma movimentação e informe seu efeito local.
Sistema de design Arco Design: a pesquisa deve restringir a visualização sem excluir itens do conjunto
Deixe explícita a regra de correspondência
O filtro padrão da origem compara a consulta com o valor do item usando uma busca de substring que diferencia maiúsculas de minúsculas. O exemplo fornecido substitui esse comportamento por uma busca que converte o texto para minúsculas. Pesquisar uma linha selecionada que esteja oculta não deve sugerir que ela deixou de fazer parte do relatório.
Para esta lista pequena, paginação e virtualização agregam pouco valor. O Arco oferece essas opções para conjuntos maiores, mas a aplicação continua responsável pelas chaves estáveis, pelo conjunto completo de destino e pelas regras de seleção de itens em visualizações filtradas.
As listas de itens disponíveis e incluídos têm campos de pesquisa com nomes distintos.
Uma mensagem de nenhum resultado descreve a visualização filtrada, não um conjunto de dados vazio.
A preparação de um esboço usa targetKeys, não apenas as linhas visíveis no momento.
Sistema de design Arco Design: o modo escuro altera as superfícies e também o texto
Defina o seletor publicado
O Arco publica suas substituições para o modo escuro sob a tag de tema com arco-theme="dark". Na compilação padrão, a tag é body. Remover esse atributo restaura as regras normais; adicionar uma classe sem relação chamada dark não é o mesmo API.
Se adicionar uma prévia do modo escuro, ajuste em conjunto os papéis do contêiner e do texto. O exemplo offline permanece intencionalmente claro, enquanto o exemplo nativo pode usar o tema CSS já importado. Não inverta miniaturas de relatórios nem ilustrações com um filtro aplicado indiscriminadamente.
Sistema de design Arco Design: pacote, folha de estilos e limites reais
Um esboço de relatório não exporta dados do relatório
O pacote React é @arco-design/web-react e sua entrada completa de CSS é dist/css/arco.css. O exemplo importa Transfer e Button da raiz do pacote e usa estado controlado, em vez de inventar uma API para criação de relatórios.
A prévia independente reproduz o comportamento de seleção com caixas de seleção e botões nativos para funcionar offline. Ela valida a lógica de interação e a composição responsiva; não comprova que o pacote nativo foi compilado em um projeto consumidor. Um exportador de produção precisaria de um backend e de verificações de permissão, além de uma linha de exemplo desativada.
Arco Design Exemplos de componentes do sistema de design
Exemplo interativo completo e independente
Salve o documento completo como index.html e abra-o em um navegador. HTML independente do comportamento do Arco Transfer e de referências de tema verificadas; exemplo nativo de React fornecido separadamente.
html
<!doctype html><html lang="en"><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1"><title>Arco report section transfer</title><style>
*{box-sizing:border-box}body{margin:0;color:#1d2129;background:#f7f8fa;font:14px/22px Arial,sans-serif}header{padding:20px 28px;background:white;border-bottom:1px solid #e5e6eb;display:flex;justify-content:space-between}.logo{font-size:18px;font-weight:bold;letter-spacing:-.02em}.logo i{font-style:normal;color:#165dff;margin-right:8px}header small{color:#4e5969}main{max-width:1050px;padding:28px;margin:auto}h1{font-size:24px;line-height:32px;margin:0 0 8px}.lead{color:#4e5969;margin:0 0 24px}.transfer{display:grid;grid-template-columns:minmax(0,1fr) 106px minmax(0,1fr);align-items:stretch}.list{border:1px solid #e5e6eb;background:white;border-radius:4px;min-width:0}.head{padding:16px;background:#f2f3f5;display:flex;gap:8px;justify-content:space-between}.head h2{font-size:14px;margin:0}.count{font-size:12px;color:#4e5969}.search{padding:12px;border-bottom:1px solid #e5e6eb}.search label{font-size:12px;display:block;margin-bottom:4px;color:#4e5969}.search input{height:32px;width:100%;border:1px solid transparent;background:#f2f3f5;padding:4px 12px;font:inherit;border-radius:2px}input:focus,button:focus-visible{outline:2px solid #165dff;outline-offset:2px}.items{min-height:290px;padding:8px}.item{display:flex;gap:10px;padding:12px 8px;border-radius:2px;align-items:start;cursor:pointer}.item:has(input:checked){background:#e8f3ff}.item input{width:16px;height:16px;accent-color:#165dff;margin-top:3px;flex-shrink:0}.item small{display:block;color:#4e5969;font-size:12px}.item:has(input:disabled){color:#86909c;cursor:not-allowed}.ops{padding:16px 12px;display:flex;flex-direction:column;gap:12px;justify-content:center}button{font:14px/22px Arial;border:1px solid #e5e6eb;background:white;color:#1d2129;border-radius:2px;padding:5px 12px;cursor:pointer}.ops button{padding:5px 4px}.primary{background:#165dff;border-color:#165dff;color:#fff}button:disabled{background:#f2f3f5;color:#86909c;border-color:#e5e6eb;cursor:not-allowed}.footer{display:flex;justify-content:space-between;align-items:center;gap:16px;padding:20px 0}.footer p{font-size:12px;color:#4e5969;margin:0}.outline{background:white;border:1px solid #e5e6eb;border-radius:4px;padding:24px}.outline h2{font-size:16px;margin:0 0 12px}.outline ol{margin:0;padding-left:20px}.note{color:#4e5969;font-size:12px;margin-top:20px}.empty{padding:20px 8px;color:#4e5969}.selection{font-size:12px;color:#4e5969;padding:10px 16px;border-top:1px solid #e5e6eb}@media(max-width:650px){main{padding:24px 16px}.transfer{grid-template-columns:1fr}.ops{flex-direction:row;padding:12px}.ops button{padding:6px 16px}.items{min-height:160px}.footer{align-items:start;flex-direction:column}header{padding:16px}}
</style><header><span class="logo"><i>A /</i> Analytics workspace</span><small>Report studio</small></header><main><h1>Choose report sections</h1><p class="lead">Build an outline from the sections available to this workspace.</p><div class="transfer"><section class="list"><div class="head"><h2>Available sections</h2><span id="left-count" class="count"></span></div><div class="search"><label for="left-search">Find available section</label><input id="left-search" type="search" placeholder="Search by section name"></div><div class="items" id="left"></div><div class="selection" id="left-selected"></div></section><div class="ops"><button class="primary" id="include" disabled>Include →</button><button id="remove" disabled>← Remove</button></div><section class="list"><div class="head"><h2>Included in report</h2><span id="right-count" class="count"></span></div><div class="search"><label for="right-search">Find included section</label><input id="right-search" type="search" placeholder="Search included sections"></div><div class="items" id="right"></div><div class="selection" id="right-selected"></div></section></div><div class="footer"><p id="status" role="status">Select a section, then choose Include or Remove.</p><button id="prepare" class="primary">Prepare outline</button></div><section class="outline"><h2>Prepared outline</h2><div id="snapshot">No outline prepared yet.</div></section><p class="note">HTML interpretation of Arco Transfer · Original sample sections · Local outline only, no analytics data exported</p></main><script>
const data=[{key:'overview',value:'Executive overview',detail:'A concise summary of the reporting period'},{key:'traffic',value:'Acquisition channels',detail:'How people arrive at your product'},{key:'retention',value:'Retention cohorts',detail:'Returning usage by cohort'},{key:'revenue',value:'Revenue breakdown',detail:'Revenue categories and trends'},{key:'raw',value:'Raw event export',detail:'Restricted · unavailable in this specimen',disabled:true}];const $=id=>document.getElementById(id);let target=new Set(['overview']),selected=new Set();
function render(){for(const side of ['left','right']){const items=data.filter(x=>target.has(x.key)===(side==='right')),query=$(side+'-search').value.toLowerCase(),host=$(side);host.replaceChildren();$(side+'-count').textContent=items.length+' sections';const visible=items.filter(x=>x.value.toLowerCase().includes(query));if(!visible.length){const p=document.createElement('p');p.className='empty';p.textContent=query?'No matching sections.':'No sections in this column.';host.append(p)}for(const item of visible){const label=document.createElement('label');label.className='item';const input=document.createElement('input');input.type='checkbox';input.id='check-'+item.key;input.checked=selected.has(item.key);input.disabled=!!item.disabled;input.setAttribute('aria-label',item.value);input.onchange=()=>{input.checked?selected.add(item.key):selected.delete(item.key);render();$('check-'+item.key)?.focus()};const text=document.createElement('span'),small=document.createElement('small');text.textContent=item.value;small.textContent=item.detail;text.append(small);label.append(input,text);host.append(label)}$(side+'-selected').textContent=items.filter(x=>selected.has(x.key)).length+' selected'}$('include').disabled=!data.some(x=>selected.has(x.key)&&!target.has(x.key)&&!x.disabled);$('remove').disabled=!data.some(x=>selected.has(x.key)&&target.has(x.key)&&!x.disabled);$('prepare').disabled=!target.size}
function move(toTarget){const moved=data.filter(x=>selected.has(x.key)&&target.has(x.key)!==toTarget&&!x.disabled);for(const item of moved)toTarget?target.add(item.key):target.delete(item.key);selected.clear();render();$('status').textContent=moved.length+' section(s) '+(toTarget?'included in':'removed from')+' the local draft.';$(toTarget?'right-search':'left-search').focus()}
$('include').onclick=()=>move(true);$('remove').onclick=()=>move(false);for(const side of ['left','right'])$(side+'-search').oninput=render;$('prepare').onclick=()=>{const ol=document.createElement('ol');for(const item of data.filter(x=>target.has(x.key))){const li=document.createElement('li');li.textContent=item.value;ol.append(li)}$('snapshot').replaceChildren(ol);$('status').textContent='Local report outline prepared. No data exported.'};render();
</script></html>
A seção restrita do relatório não pode ser movida. As linhas selecionadas e as seções incluídas são estados separados, de acordo com a distinção explicada para o Transfer nativo.
Transferência controlada de seções do relatório
O Transfer gerencia o pertencimento aos conjuntos de origem e destino, enquanto o estado da aplicação armazena um esboço preparado separadamente. Uma linha restrita demonstra uma opção desativada sem fingir impor autorização no servidor.
jsx
// npm install @arco-design/web-react react react-dom
import React,{useState} from 'react';
import {createRoot} from 'react-dom/client';
import {Transfer,Button} from '@arco-design/web-react';
import '@arco-design/web-react/dist/css/arco.css';
const data = [
{key:'overview',value:'Executive overview'},
{key:'traffic',value:'Acquisition channels'},
{key:'retention',value:'Retention cohorts'},
{key:'revenue',value:'Revenue breakdown'},
{key:'raw',value:'Raw event export (restricted)',disabled:true}
];
function ReportBuilder(){
const [target,setTarget]=useState(['overview']);
const [selected,setSelected]=useState([]);
const [snapshot,setSnapshot]=useState([]);
const [status,setStatus]=useState('Choose sections for a local report.');
return <main style={{padding:24,maxWidth:960,margin:'auto'}}>
<h1>Report sections</h1>
<Transfer dataSource={data} targetKeys={target} selectedKeys={selected}
titleTexts={['Available sections','Included in report']}
operationTexts={['Include','Remove']}
showSearch searchPlaceholder={['Find available section','Find included section']}
filterOption={(query,item)=>item.value.toLowerCase().includes(query.toLowerCase())}
onSelectChange={(left,right)=>setSelected([...left,...right])}
onChange={(keys,direction,moved)=>{
setTarget(keys);setSelected([]);
setStatus(`${moved.length} section(s) moved to ${direction}. Draft only.`);
}} />
<p role="status">{status}</p>
<Button type="primary" disabled={!target.length} onClick={()=>{
setSnapshot([...target]);setStatus('Local report outline prepared. No data exported.');
}}>Prepare outline</Button>
<h2>Prepared outline</h2>
{snapshot.length ? <ol>{snapshot.map(key=><li key={key}>{data.find(item=>item.key===key).value}</li>)}</ol> : <p>No outline prepared yet.</p>}
</main>;
}
createRoot(document.getElementById('root')).render(<ReportBuilder />);
A seleção das caixas de seleção e o pertencimento ao relatório são arrays diferentes.
O filtro personalizado não diferencia maiúsculas de minúsculas.
Os dados de exemplo são originais; nenhum dado de análise é carregado ou exportado. A compilação nativa continua sendo uma verificação de integração separada.
04
Configuração do agente para o sistema de design Arco Design
Ponto de partida para implementação
Importe a folha de estilos completa arco.css uma única vez e monte o exemplo React em um elemento raiz. Não misture este pacote React com importações do Arco Vue.
Use o Transfer do Arco React com chaves estáveis em dataSource e targetKeys e selectedKeys controlados separadamente. Forneça um filtro que ignore diferenças entre maiúsculas e minúsculas, ações explícitas de Incluir/Remover e uma captura preparada da estrutura em árvore. Preserve a sintaxe de variáveis do Arco CSS e identifique com clareza a interpretação offline.
05
Fontes e escopo do sistema de design Arco Design
Referência independente de OpenDesign. Dados originais do relatório e pré-visualização somente local; linhas desativadas não constituem uma barreira de autorização.