No h:selectManyMenu deveria retornar uma lista com os valores vindos do banco de dados, mas o que aparece é apenas um valor tipo beans.CadastradorBean@1e48948
O trecho do código da página xhtml é esse:
<h:selectManyMenu id="cadastradorSelect">
<f:selectItems value="#{cadastradorC.lista}" />
</h:selectManyMenu><h:message for="cadastradorSelect" /
Trecho da Classe do CadastradorControlador:
...
private List lista;
public List getLista() throws Exception {
CadastradorDAO dao = new CadastradorDAO();
this.lista = dao.getTodosCadastradores();
return this.lista;
}
...
O trecho da Classe CadastradorDao, que é usado pelo CadastradorControlador:
public List getTodosCadastradores() throws Exception {
...
try {
connection = this.conn;
ps = connection.prepareStatement("SELECT nome FROM cadastradores");
rs = ps.executeQuery();
List<CadastradorBean> lista = new ArrayList<CadastradorBean>();
while(rs.next()) {
String nome = rs.getString(1);
lista.add(new CadastradorBean(nome));
}
return lista;
}
...
Na Classe CadastradorBean, há vários construtores, sendo que o que é utilizado pelo CadastradorDao (nesse caso) é esse:
...
private String id;
private String nome;
private String senha;
public CadastradorBean(String nome) {
this.nome = nome;
}
...
Meu arquivo facex-config.xml:
<managed-bean>
<managed-bean-name>cadastrador</managed-bean-name>
<managed-bean-class>beans.CadastradorBean</managed-bean-class>
<managed-bean-scope>session</managed-bean-scope>
</managed-bean>
<managed-bean>
<managed-bean-name>cadastradorC</managed-bean-name>
<managed-bean-class>controladores.CadastradorControlador</managed-bean-class>
<managed-bean-scope>session</managed-bean-scope>
</managed-bean>
Alguém consegue ver onde estou errando? Qualquer ajuda seria bem vinda, estou começando ainda com o JSF…
Desde já, obrigado!
Esse é o retorno do método toString padrão. Para arrumar isso vc tem algumas opções:
Sobrescreve o método toString na classe CadastradorBean para exibir um nome mais simples:
class CadastradorBean {
public String toString() {
return this.nome; // Por exemplo
}
}
Ou altera o f:selectItems informando o atributo da descrição do select:
<f:selectItems value="#{cadastradorC.lista}" var="c" itemLabel="#{c.nome}" />
Thanks in advance, lsjunior.
Vou testar aqui, qualquer coisa aviso!
Funcionou, obrigado!
Mudei para SelectOneMenu para dar o resultado que eu queria.
Ficou assim:
<h:selectOneMenu id="cadastradorSelect">
<f:selectItems value="#{cadastradorC.lista}" var="c" itemLabel="#{c.nome}" />
</h:selectOneMenu><h:message for="cadastradorSelect" />
Valeu lsjunior, pela paciência!
Tem que ver como vc fez, pelo bean ou pelo f:selectItems.
Para capturar o valor selecionado pelo usuário, é aqui que deve estar a captura?
<h:selectOneMenu id="cadastradorSelect" value="#{beanQueVaiGuardarCadastrador.nome}">
Valeu!
Sim, só fica atendo para o tipo.
Se vc tem um bean tipo esse:
class Pessoa {
Integer id;
String nome;
}
E faz isso:
<h:selectOneMenu id="pessoa" value="#{cadastroBean.pessoa}">
<f:selectItems value="#{pessoaBean.pessoas}" var="p" itemLabel="#{p.nome}" />
</h:selectOneMenu>
O CadastroBean deve ser assim:
class CadastroBean {
void setPessoa(Pessoa pessoa)...
}
Mas se faz isso:
<h:selectOneMenu id="pessoa" value="#{cadastroBean.pessoaId}">
<f:selectItems value="#{pessoaBean.pessoas}" var="p" itemValue="#{p.id}" itemLabel="#{p.nome}" /><!-- O valor é o ID -->
</h:selectOneMenu>
O CadastroBean deve ser assim:
class CadastroBean {
void setPessoaId(Integer pessoaId)...
}
lsjunior, obrigado. Você comentou uma futura dúvida minha.
Existe um tabela no BD para o Cadastrador, e outra para o Cliente. Porém, na tabela Cliente, existe uma chave estrangeira que aponta para o ID do Cadastrador. Não existe Cliente sem um Cadastrador associado a ele.
Então, no formulário do cadastro do Cliente, é obrigatório escolher um Cadastrador. Daí minha necessidade de exibir todos os Cadastradores nesse SELECT. Entretanto, estou exibindo os NOMES, e através do DAO/CONTROLADOR/ETC teria que buscar o ID correspondente aquele NOME do Cadastrador.
Com Scriptlets/JSP (HTML puro) era mais “fácil”, por assim dizer, pois no SELECT do HTML simples, eu exibia os nomes para o usuário, porém, o valor do SELECT era o ID relativo ao nome.
Como estou usando JSF/PrimeFaces, ainda vou verificar como aplico essa “técnica”.
Imagino que seja o que você colocou no código:
<f:selectItems value="#{pessoaBean.pessoas}" var="p" itemValue="#{p.id}" itemLabel="#{p.nome}" /><!-- O valor é o ID -->
É por aí… Vou testar…
Obrigado pela paciência!
Na verdade postei para vc ver que pode definir diretamente como Bean, no caso Pessoa, ou como um tipo nativo. O problema de colocar como Bean é que vc deve criar um Converter para o JSF saber o que fazer quando pegar o valor da tela e voltar para o Java.
Continuando:
<h:selectOneMenu id="pessoa" value="#{cadastroBean.pessoa}" converter="pessoaConverter"> <!-- Adicionamos o converter -->
<f:selectItems value="#{pessoaBean.pessoas}" var="p" itemLabel="#{p.nome}" />
</h:selectOneMenu>
[code]@FacesConverter(value = “pessoaConverter”)
public class PessoaConverter implements Converter {
@Override
public Object getAsObject(FacesContext context, UIComponent component, String value) {
Pessoa pessoa = new Pessoa();
pessoa.setId(Integer.valueOf(value)); // Ou pega do banco
return pessoa;
}
@Override
public String getAsString(FacesContext context, UIComponent component, Object value) {
Pessoa pessoa = (Pessoa) value;
return pessoa.getId().toString();
}
}[/code]
Eu acho dessa forma um saco de fazer, prefiro setar as propriedades em tipos ‘nativos’ e recuperar apenas os necessários. No seu caso tanto para ver o valor atual no select como para setar no bean vc não precisa da Pessoa em si, apenas do identificador.