Isso é muito útil e acho que seria melhor se fosse nativo da biblioteca:
{{#switch state}}
{{#case "page1" "page2"}}toolbar{{/case}}
{{#case "page1" break=true}}page1{{/case}}
{{#case "page2" break=true}}page2{{/case}}
{{#case "page3" break=true}}page3{{/case}}
{{#default}}page0{{/default}}
{{/switch}}
Isso é algo que pode ser alcançado (de uma maneira hacky) usando ajudantes padrão. Queremos manter os helpers integrados relativamente leves, em vez de permitir que terceiros implementem os helpers de que precisam, da maneira que melhor lhes convier, usando a API do helper.
Esta página é atualmente o terceiro resultado de pesquisa do Google para "Handlebars switch helper". Para o benefício das pessoas que chegam aqui de um mecanismo de pesquisa, aqui está uma implementação de Chris Montrois que oferece suporte a cláusulas de valor único case
, como {{#case "page1"}}
:
Handlebars.registerHelper("switch", function(value, options) {
this._switch_value_ = value;
var html = options.fn(this); // Process the body of the switch block
delete this._switch_value_;
return html;
});
Handlebars.registerHelper("case", function(value, options) {
if (value == this._switch_value_) {
return options.fn(this);
}
});
Aqui está um case
helper aprimorado que oferece suporte a cláusulas com um número variável de valores, como {{#case "page1" "page2"}}
:
Handlebars.registerHelper("case", function() {
// Convert "arguments" to a real array - stackoverflow.com/a/4775938
var args = Array.prototype.slice.call(arguments);
var options = args.pop();
var caseValues = args;
if (caseValues.indexOf(this._switch_value_) === -1) {
return '';
} else {
return options.fn(this);
}
});
Muito bom, curto e doce. Eu já encontrei muitos mais longos no passado.
Algumas coisas a serem adicionadas podem ser {{#default}} {{/default}}
e {{#case "value" break=true}}
.
@stevenvachon Conforme solicitado;)
module.exports = {
switch: function(value, options) {
this._switch_value_ = value;
this._switch_break_ = false;
var html = options.fn(this);
delete this._switch_break_;
delete this._switch_value_;
return html;
},
case: function(value, options) {
var args = Array.prototype.slice.call(arguments);
var options = args.pop();
var caseValues = args;
if (this._switch_break_ || caseValues.indexOf(this._switch_value_) === -1) {
return '';
} else {
if (options.hash.break === true) {
this._switch_break_ = true;
}
return options.fn(this);
}
},
default: function(options) {
if (!this._switch_break_) {
return options.fn(this);
}
}
};
@ Billy- Onde devemos incluir isso?
@jimkoul Essas são funções auxiliares, portanto, dependem de sua configuração.
Minha configuração (com Gulp + gulp-hb) suporta a especificação de um padrão glob para arquivos js que exportam funções auxiliares, como acima, assim fica assim:
// ...
.pipe(handlebars({
helpers: 'handlebars/helpers/*.js'
})
// ...
Se você ainda não tiver certeza, faça uma pequena pesquisa sobre como as funções auxiliares funcionam com o guidão e como implementá-las com qualquer implementação de guidão que você esteja usando.
Seria bom se pudéssemos passar a variável pelo nome do switch e não precisarmos escrever um {{assign}}
completo
Além disso, também estou recebendo uma mensagem indefinida, embora a variável esteja mudando corretamente quando o caso é encontrado.
Isso é o que eu tenho como ajudante
"use strict";
Handlebars.registerHelper("switch", function(value, options) {
this._switch_value_ = value;
this._switch_break_ = false;
var html = options.fn(this);
delete this._switch_break_;
delete this._switch_value_;
return html;
});
Handlebars.registerHelper("case", function(value, options) {
var args = Array.prototype.slice.call(arguments);
var options = args.pop();
var caseValues = args;
if (this._switch_break_ || caseValues.indexOf(this._switch_value_) === -1) {
return '';
} else {
if (options.hash.break === true) {
this._switch_break_ = true;
}
return options.fn(this);
}
});
Handlebars.registerHelper("default", function(options) {
if (!this._switch_break_) {
return options.fn(this);
}
});
Isto é o que tenho em meu arquivo hbs:
{{#assign "testParam"}}foo{{/assign}}
{{#switch testParam}}
{{#case "boo"}}{{#assign "testParam"}}case1 has been met{{/assign}}{{/case}}
{{#case "foo" break=true}}{{#assign "testParam"}}case2 has been met{{/assign}}{{/case}}
{{#case "tried" break=true}}{{#assign "testParam"}}case3 has been met{{/assign}}{{/case}}
{{#case "bwahahaha" break=true}}{{#assign "testParam"}}case4 has been met{{/assign}}{{/case}}
{{#default break=true}}{{#assign "testParam"}}nothing matched{{/assign}}{{/default}}
{{/switch}}
{{#ttpartial "testSwitch.content"}}
{{testParam}}
{{/ttpartial}}
ou algum motivo acima faz com que o padrão sempre tenha precedência, mesmo quando um dos casos acima for atendido.
Aqui está o que eu uso:
Handlebars.registerHelper('switch', function(name, value, options) {
this['_switch_value_' + name] = value;
this['_switch_break_' + name] = false;
var html = options.fn(this);
delete this['_switch_break_' + name];
delete this['_switch_value_' + name];
return html;
});
Handlebars.registerHelper('case', function(name, value, options) {
var args = Array.prototype.slice.call(arguments);
var options = args.pop();
var caseValues = args;
if ( this['_switch_break_' + name] || caseValues.indexOf(this['_switch_value_' + name]) === -1) {
return '';
} else {
this['_switch_break_' + name] = true;
return options.fn(this);
}
});
Handlebars.registerHelper('default', function(name, options) {
if ( !this['_switch_break_' + name] ) {
return options.fn(this);
}
});
Os switches são nomeados, portanto, é possível ramificá-los (imbricação? Não tenho certeza sobre a palavra ...)
Além disso, a pausa é sempre feita quando uma condição é atendida
ie:
{{#switch "1" "aaa"}}
{{#case "1" "aaa"}}
{{#switch "2" "bbb"}}
{{#case "2" "bbb"}}ok{{/case}}
{{/switch}}
{{/case}}
{{#default "1"}}nok{{/default}}
{{/switch}}
Tenho certeza de que não estou entendendo como isso funciona, então peço desculpas pela minha confusão, mas ... É possível que o switch funcione dentro de each
? Tenho experimentado, mas continuo recebendo erros.
Aqui está o que eu tenho:
{{#each columns}}
{{#switch this}}
{{#case 'foo'}}
{{/case}}
{{#case 'bar'}}
{{/case}}
{{/switch}}
{{/each}}
Mas estou entendendo:
Uncaught TypeError: Cannot create property '_switch_value_' on string 'name'
Parece-me que this
deve ser algo diferente do que é esperado, mas eu realmente não sei.
Parece que consegui fazê-lo funcionar alterando o switch
seguinte forma:
Handlebars.registerHelper({
switch: function(value, options) {
return options.fn({
_switch_value_: value,
_switch_break_: false
});
},
//...
});
Mas acho que estou perdendo algo para outros casos. Dito isso, eu sempre poderia anexar esses valores a options
e acho que funcionaria.
@ Billy- @ a-le?
@infinityplusone, infelizmente, não uso o guidão adequadamente há anos, então imagino que a implementação do helper pode ter mudado muito desde que escrevi isso, provavelmente por isso não estava funcionando como o esperado. Eu não tenho certeza, lamento desapontar.
@infinityplusone Se você usar minha versão, terá que "nomear" o switch.
Então, com seu exemplo:
{{#each columns}}
{{#switch "myswitch" this}}
{{#case "myswitch" 'foo'}}
{{/case}}
{{#case "myswitch" 'bar'}}
{{/case}}
{{/switch}}
{{/each}}
para bloco de switch aninhado
Handlebars.__switch_stack__ = [];
Handlebars.registerHelper( "switch", function( value, options ) {
Handlebars.__switch_stack__.push({
switch_match : false,
switch_value : value
});
var html = options.fn( this );
Handlebars.__switch_stack__.pop();
return html;
} );
Handlebars.registerHelper( "case", function( value, options ) {
var args = Array.from( arguments );
var options = args.pop();
var caseValues = args;
var stack = Handlebars.__switch_stack__[Handlebars.__switch_stack__.length - 1];
if ( stack.switch_match || caseValues.indexOf( stack.switch_value ) === -1 ) {
return '';
} else {
stack.switch_match = true;
return options.fn( this );
}
} );
Handlebars.registerHelper( "default", function( options ) {
var stack = Handlebars.__switch_stack__[Handlebars.__switch_stack__.length - 1];
if ( !stack.switch_match ) {
return options.fn( this );
}
} );
{{#switch state}}
{{#case "page1" "page2"}}page 1 or 2{{/case}}
{{#case "page3"}}page3{{/case}}
{{#case "page4"}}page4{{/case}}
{{#case "page5"}}
{{#switch s}}
{{#case "3"}}s = 3{{/case}}
{{#case "2"}}s = 2{{/case}}
{{#case "1"}}s = 1{{/case}}
{{#default}}unknown{{/default}}
{{/switch}}
{{/case}}
{{#default}}page0{{/default}}
{{/switch}}
var data = {
state : 'page5',
s : '1'
};
var html = template( data );
Que tal agora?
apenas se você deseja converter a chave em valor.
`` `` javascript
module.exports = function (input, cases, values) {
const caseArray = cases.split (',')
const valueArray = values.split (',')
const index = caseArray.indexOf (input)
return valueArray [index]
};
Guiador
{{mudar "S" "S, N, D", "SIM, NÃO, EXCLUÍDO"}}
`` ``
Comentários muito úteis
Esta página é atualmente o terceiro resultado de pesquisa do Google para "Handlebars switch helper". Para o benefício das pessoas que chegam aqui de um mecanismo de pesquisa, aqui está uma implementação de Chris Montrois que oferece suporte a cláusulas de valor único
case
, como{{#case "page1"}}
:Aqui está um
case
helper aprimorado que oferece suporte a cláusulas com um número variável de valores, como{{#case "page1" "page2"}}
: