Em julho de 2019 (versão 2.20190722) uma API de campos mais codificados foi adicionada. Ele tem como objetivo ser o mais compatível possível com versões anteriores. Isso significa que, se você tivesse criado antes de julho de 2019, ele provavelmente continuará funcionando. Antes de decidir se o campo personalizado precisa passar por upgrade, leia na seção Áreas de perigo e faça um teste minucioso do campo.
Porque não havia padronização entre os campos antes de julho de 2019. é complicado cobrir todas as mudanças que um desenvolvedor pode precisar fazer. Este documento tenta cobrir todas as alterações prováveis, mas, se ele não abordar algo em que você tem interesse, leia a seção sobre recebendo assistência para upgrade.
Áreas de perigo
Áreas perigosas são lugares conhecidos onde a API mudou, e seu campo pode ser de quebrar.
Blockly.Field.register
Os campos não são mais registrados por Blockly.Field.register();
. Há
agora um namespace fieldRegistry que gerencia o registro.
Blockly.Field.register('my_field_name', myFieldClass);
O resultado é:
Blockly.fieldRegistry.register('my_field_name', myFieldClass);
setText
A função setText
não é mais chamada pelo núcleo do Blockly. Portanto, se o setText
contém lógica. Ela precisará ser movida para
processamento de valores
o pacote de funções getText
e as funções de renderização
(dependendo do que exatamente a função setText
está fazendo).
CustomFields.UpgradeField.prototype.setText = function(newText) {
// Do validation.
if (typeof newText != 'string' || newText === this.text_) {
return;
}
// Fire event.
if (this.sourceBlock_ && Blockly.Events.isEnabled()) {
Blockly.events.fire(new Blockly.Events.BlockChange(
this.sourceBlock_, 'field', this.name, this.text_, newText
));
}
// Update text value.
this.text_ = 'prefix' + newText;
// Rerender.
this.size_.width = 0;
};
O resultado é:
CustomFields.UpgradeField.prototype.doClassValidation_ = function(newValue) {
if (typeof newValue != 'string') {
return null;
}
return newValue;
};
CustomFields.UpgradeField.prototype.getText = function() {
return 'prefix' + this.value_;
}
O Blockly gerencia automaticamente:
- Verificar se o novo valor é diferente do antigo.
- Atualizando o valor.
- Disparando eventos de alteração.
- Rerenderizando o campo.
Você precisará lidar com o seguinte:
- Validação de valor (
doClassValidation_
). - Texto do campo (
getText
). - Interface do campo
Upgrades recomendados
Os upgrades recomendados são lugares onde a API do campo foi alterada, mas se você optar por não fazer alterações, seu campo provavelmente ainda funcionará.
SÉRIE
Para mais informações sobre as propriedades EDITABLE
e SERIALIZABLE
, consulte
Propriedades editáveis e serializáveis.
CustomFields.UpgradeField.prototype.SERIALIZABLE = true;
O aviso abaixo pode ser ignorado, mas é possível resolvê-lo definindo o SERIALIZABLE
:
Detected an editable field that was not serializable. Please define
SERIALIZABLE property as true on all editable custom fields. Proceeding
with serialization.
O aviso acima significa que o Blockly acredita que você quer
campo a ser serializado (porque a propriedade EDITABLE
é verdadeira), mas
não é possível ter certeza até definir a propriedade SERIALIZABLE
. Se você escolher
deixe isso em paz, tudo funcionará corretamente e seu campo será
serializados, mas você receberá avisos do console.
size_.width
this.size_.width = 0;
O resultado é:
this.isDirty_ = true;
O aviso abaixo pode ser ignorado, mas ele pode ser resolvido definindo a isDirty_
em vez de size_.width
:
Deprecated use of setting size_.width to 0 to rerender a field. Set
field.isDirty_ to true instead.
O aviso acima significa que o Blockly detectou que você está usando um método antigo para renderizar novamente uma campo, e gostaria que você usasse o novo método.
Para mais informações sobre a propriedade isDirty_
, consulte
isDirty_.
init
A função init
foi transformada em um modelo
função para
de redução do código duplicado em subclasses.
CustomFields.UpgradeField.prototype.init = function() {
if (this.fieldGroup_) {
// Already initialized once.
return;
}
// Call superclass.
CustomFields.UpgradeField.superClass_.init.call(this);
// Create DOM elements.
this.extraDom_ = Blockly.utils.dom.createSvgElement('image',
{
'height': '10px',
'width': '10px'
});
this.extraDom_.setAttributeNS('http://www.w3.org/1999/xlink',
'xlink:href', 'image.svg');
this.extraDom_.style.cursor = 'pointer';
this.fieldGroup_.appendChild(this.extraDom_);
// Bind events.
this.mouseOverWrapper_ =
Blockly.browserEvents.bind(
this.getClickTarget_(), 'mouseover', this, this.onMouseOver_);
this.mouseOutWrapper_ =
Blockly.browserEvents.bind(
this.getClickTarget_(), 'mouseout', this, this.onMouseOut_);
// Render.
this.setValue(this.getValue());
};
O resultado é:
CustomFields.UpgradeField.prototype.initView = function() {
CustomFields.UpgradeField.superClass_.initView.call(this);
this.extraDom_ = Blockly.utils.dom.createSvgElement('image',
{
'height': '10px',
'width': '10px'
});
this.extraDom_.setAttributeNS('http://www.w3.org/1999/xlink',
'xlink:href', 'image.svg');
this.extraDom_.style.cursor = 'pointer';
this.fieldGroup_.appendChild(this.extraDom_);
};
CustomFields.UpgradeField.prototype.bindEvents_ = function() {
CustomFields.UpgradeField.superClass_.bindEvents_.call(this);
this.mouseOverWrapper_ =
Blockly.bindEvent_(
this.getClickTarget_(), 'mouseover', this, this.onMouseOver_);
this.mouseOutWrapper_ =
Blockly.bindEvent_(
this.getClickTarget_(), 'mouseout', this, this.onMouseOut_);
};
Isso significa que o bloqueio agora processa automaticamente:
- Verificando se o campo já foi inicializado.
- Criando o
fieldGroup_
. - Renderizando o campo.
- Dica de vinculação e exibição de eventos do editor.
Você precisará lidar com o seguinte:
- Adicionar outros
Elementos DOM (
initView
). - Adicionar outros
vinculações de eventos (
bindEvents_
). - Descarte de vinculações de eventos (
dispose
).
onMouseDown_
CustomFields.UpgradeField.prototype.onMouseDown_ = function(e) {
// ...
};
O resultado é:
CustomFields.UpgradeField.prototype.showEditor_ = function() {
// ...
}
Recomendamos substituir a função showEditor_
para processar dados
em vez da função onMouseDown_
, já que ela permite que a entrada transmita
pelo sistema de gestos.
Para mais informações sobre editores, consulte Editores.
setValue
A função setValue
agora é um modelo
função para
de redução do código duplicado em subclasses. Se a função setValue
tiver lógica,
considere refatorá-lo para que se ajuste aos caminhos de tratamento de valores descritos em
Processamento de valores.
text_
Recomendamos que você nunca acesse ou atualize a propriedade text_
dos seus
no campo correspondente. Em vez disso, use o método
Função getText
para acessar o texto legível pelo usuário do seu campo e a
Função setValue
para atualizar o valor armazenado do campo.
Para mais informações sobre o valor de um campo em comparação com o texto dele, consulte Anatomia de um campo.
Como receber assistência para upgrade
O que fornecer
Ao pedir ajuda, é melhor fazer perguntas específicas:
Não recomendado: "O que há de errado com este campo?"
Também não recomendado: "Ajude-me a atualizar este campo".
Recomendado: "O texto do campo não está sendo atualizado corretamente."
Também é necessário fornecer recursos às pessoas que ajudam você. Esses devem ser fáceis de usar.
Não recomendado:
- Imagens do código.
- Código incompleto.
Recomendado:
- Preencha o código do campo em formato de texto.
- Imagens de GIFs de mau comportamento de campo.
- Etapas para reproduzir o mau comportamento de campo.
- A versão do Blockly de onde você está fazendo upgrade.
Onde postar
Perguntas pós-upgrade no desenvolvedor do Blockly fórum.
Se você tiver certeza de que o problema é com o núcleo bloqueado, também publicar um problema no GitHub. Se você decidir postar um problema, preencha todos informações solicitadas.