Como usar TForm::getFormByName? Olá pessoal do Adianti! Estou com um problema/dúvida: Tenho uma list que tem o form de pesquisa com o nome 'form_search_horario". Nesse form, tenho duas TDBCombos, uma com o nome dos barcos e a outra com a respetiva lotação. Ao fazer a pesquisa, eu quero que só possa pesquisar ou por barco ou por lotação e não por ambos, então criei uma Action para cada uma das combos que cham...
AG
Como usar TForm::getFormByName?  
Olá pessoal do Adianti!

Estou com um problema/dúvida:

Tenho uma list que tem o form de pesquisa com o nome 'form_search_horario".

Nesse form, tenho duas TDBCombos, uma com o nome dos barcos e a outra com a respetiva lotação.

Ao fazer a pesquisa, eu quero que só possa pesquisar ou por barco ou por lotação e não por ambos, então criei uma Action para cada uma das combos que chama o método static onChange, no qual escondo/mostro uma ou outra combo, conforme a escolha da combo no form.

Acontece que ao voltar a mostrar a combo ela aparece com o valor anterior e eu quero que ela aparecça na default option (em branco) só que não estou a conseguir obter o objeto do form com a instrução TForm::getFormByName que me devolve sempre NULL.

Estou a fazer o pedido assim:

$form = TQuickForm::getFormByName($param['_form_name']);


Preciso de saber se estou a fazer algo mal ou se este método getFormByName tem outro tipo de aplicação que não é a que eu estou a pensar?

Agradeço a vossa ajuda!

Um abraço de Portugal!

Abel Gomes

Curso Dominando o Adianti Framework

O material mais completo de treinamento do Framework.
Curso em vídeo aulas + Livro completo + Códigos fontes do projeto ERPHouse.
Conteúdo Atualizado!


Dominando o Adianti Framework Quero me inscrever agora!

Comentários (9)


MC

Abel, boas.

Voce esta querendo saber o nome do form da tela atual ou o form chamador ?


Eu costumo o código abaixo para dar nome aos meus forms, assim não tem erro.

1 - Temos uma variável de ambiente __CLASS__ nela fica gravada o nome da Classe onde esta o form, assim dou o nome ao form
'form_'.__CLASS__.

2 - Ou seja você sempre terá o nome da tela atual. 'form_'.__CLASS__.

3 - Se você utilizou uma tela para chamar outra tela, através de um action, basta colocar um parâmetro conforme abaixo:

->setParameter( 'Form', 'form_'.__CLASS__. );

4 - Na tela chamada guardar o parâmetro numa variável de sessão Ex: abaixo:

<?php    public function onNew( $param )    {        $this->form->clear();                $data = $this->form->getData();        TSession::setValue( 'FormX', $param['Form'] );                $this->form->setData( $data );    }?>


5 - Para voltar a Tela chamadora ai tem varias formas, vou apenas sitar uma, final de uma função onSave:

<?php            $act_dcto = new TAction( array( TSession::getValue('FormX'), 'onEdit' ));            $act_dcto->setParameter( 'key', $object->DCTOID );                        new TMessage( 'ok', 'Registro Salvo', $act_dcto );?>



Espero ter ajudado,


AG

Oi Marco, muito obrigado pela sua resposta, que vai ajudar-me noutras situações.

Porém, a situação com que eu estava a debater-me era conseguir obter o form dentro de um método estático.

Como eu referi, é uma classe onde eu tenho um form de pesquisa (form_search_Horario) e uma lista de horários por baixo.

Como os campos BARCO e LOTAÇÃO vêm da mesma tabela e estão relacionados, não faz sentido eu pesquisar por exemplo, pelo BARCO: "Titanic" que tem lotação de 3000 lugares e também pesquisar pela LOTAÇÃO: 1500 porque, obviamente não vou obter nenhum registo.

Assim, eu queria esconder o outro campo sempre que preenchesse um deles (pesquiso BARCO e esconde LOTAÇÃO e vice-versa).

Esconder e mostrar eu consigo facilmente com

TQuickForm::hideField($param['_form_name'], $param['field']); e TQuickForm::showField($param['_form_name'], $param['field']);

O meu problema está na situação em que, se depois de eu escolher "Titanic" na combo eu pensar em pesquisar antes pela lotação "1500", quando faço o campo lotação aparecer, ele ainda vem com o último valor que tinha, antes de ter sido escondido. Parece complicado, mas não é... :-)

Eu estava pensando em pegar o objeto do form, e fazer o setDefaultValue à combo antes de ser escondida, para que quando voltasse ao ecrã estivesse em branco.

Resolvi o problema com um script antes do hideField, para onde passo os parametros nome do form e nome da combo e coloco o atributo "selected"

$('form[name='+form_name+'] select[name='+input_name+']' + " option[value='']").attr("selected","selected");

De qualquer forma, gostaria de saber, se dentro de um método estático, existe alguma maneira de obter o objeto do form e trabalhá-lo.

Mais uma vez, muito obrigado pelo seu tempo!

Abel Gomes
MC

Abel, boas

Posta ai o seu codigo ou parte dele para que possamos entender melhor a sua situação.

Abraços
AG

Oi Marco Campos, obrigado pelo teu interesse, mas como disse antes, já resolvi o problema com um script.

Mesmo assim, volto a explicar para quem estiver com o mesmo problema, o que eu queria fazer era o seguinte:

- tenho 2 campos COMBO, ambos relacionados com a mesma tabela e os quais só é lógico procurar por um deles de cada vez
- escolhendo uma opção na COMBO 1, a COMBO 2 desaparece (e vice-versa)
- limpando a escolha da COMBO 1, a COMBO 2 volta a aparecer (e vice-versa)

mas eu queria colocar ativa a opção default da combo antes de a esconder.

Só que, por ter de estar num método estático (onChange) não conseguia ir buscar o objecto form, para depois alterar o default value das combos.

A resposta do Pablo, por email, foi esta:

«Você pode limpar a combo, e logo em seguida adicionar o elemento vazio.
Este método estático somente funciona quando você passa pelo método construtor (ele registra o formulário em uma variável estática).
Em um método estático (ex: change) não passa pelo construtor, logo o formulário não é criado.»

CONCLUSÃO: tem de se alterar os componentes através de Javascript.

A parte do código que pode interessar:

<?php// no construt...        $barco = new TDBCombo('barco', 'viagens', 'Barco', 'barco', '{barco}'); // o 4º parametro é 'barco' e não 'id' porque preciso do nome do barco para a pesquisa        $lotacao = new TDBCombo('lotacao', 'viagens', 'Barco', 'lotacao', '{lotacao}');        // atribuir as ações onChange        $change_barco = new TAction(array($this, 'onChange'));        $change_barco->setParameter('field', 'lotacao');        $barco->setChangeAction($change_barco);        $change_lotacao = new TAction(array($this, 'onChange'));        $change_lotacao->setParameter('field', 'barco');        $lotacao->setChangeAction($change_lotacao);    //..... fim do construct    /** My onChange     * Turn on/off field based on choice from combo     */    public static function onChange($param)    {        $caller = $param['_field_name'];        if ($param[$caller] != ''){            TScript::create( " my_set_default_selected('{$param[_form_name]}', '{$param[field]}'); " );            TQuickForm::hideField($param['_form_name'], $param['field']);        } else {            TQuickForm::showField($param['_form_name'], $param['field']);        }    } ?>


depois no application.js...

function my_set_default_selected(form_name, input_name){
try {
$('form[name='+form_name+'] select[name='+input_name+']' + " option[value='']").attr("selected","selected");

} catch (e) {
console.log(e);
}
}

Valeu pela ajuda!

Abraço
NR

Abel, você pode usar a função estática sendData da classe TForm:
adianti.com.br/framework_files/tutor/index.php?class=FormInteraction
AG

Nataniel, muito obrigado pela sua resposta, mas no meu caso não consigo, porque estou a usar TDBCombos e não tenho índices (ou não sei como indicar quais) para enviar pelo sendData.

Daí a minha tentativa pelo getFormByName, na esperança de conseguir obter o objecto da TDBCombo e fazer setDefaultOption.

De qualquer forma, a chamada de atenção para sendData vai ser muito útil.

Um abraço e continuação de bom trabalho no fórum.

Abel
NR

Abel, teste o seguinte:
<?php$obj = new stdclass();$obj->{$param['field']} = '';        TForm::sendData($param['_form_name'],$obj);?>
AG

Funciona!!

Muito obrigado, Nataniel, você é um Ás!

Esta solução vai ajudar-me bastante noutras situações deste projeto.

Já agora, perdoando os meus poucos conhecimentos de OOP, dê-me uma justificação para funcionar desta forma e não sem as chavetas { } conforme o exemplo do Tutor que me enviou antes?

E já que estamos numa de troca de impressões entre rookie e pro, na sua opinião, é mais eficiente o script javascript ou esta solução?

MAis uma vez, muito obrigado pelo seu interesse e profissionalismo!

Abraço de Portugal.

Abel
NR

Abel, a questão das chaves é pra evitar ambiguidade. Veja o link abaixo para maiores informações:
php.net/manual/pt_BR/language.variables.variable.php

Sobre a questão de eficiência: internamente a função sendData vai gerar um javascript da mesma maneira, mas como a ideia do Adianti é facilitar o trabalho, aconselho usar as funções do framework ao invés de escrever seu próprio javascript.