Partilhar via


Composto Personalizado usando Atividade Nativa

O exemplo CustomCompositeNativeActivity demonstra como escrever um NativeActivity que agenda outros Activity objetos para controlar o fluxo de execução de um fluxo de trabalho. Este exemplo usa dois fluxos de controle comuns, Sequence e While, para demonstrar como fazer isso.

Detalhes da amostra

Começando com MySequence, a primeira coisa a notar é que deriva de NativeActivity. NativeActivity é o Activity objeto que expõe toda a amplitude do tempo de execução do fluxo de trabalho através do NativeActivityContext passado para o Execute método.

MySequence Expõe uma coleção pública de objetos que é preenchida pelo autor do fluxo de Activity trabalho. Antes de executar o fluxo de trabalho, o tempo de execução do fluxo de trabalho chama o CacheMetadata método em cada atividade em um fluxo de trabalho. Durante este processo, o tempo de execução estabelece relações pai-filho para escopo de dados e gerenciamento de ciclo de vida. A implementação padrão do método usa a classe de instância CacheMetadata para a atividade TypeDescriptor para adicionar qualquer propriedade pública do tipo MySequence ou ActivityIEnumerable<Activity como filhos da atividade MySequence.

Sempre que uma atividade expõe uma coleção pública de atividades infantis, é provável que essas atividades infantis compartilhem o estado. É uma boa prática para a atividade dos pais, neste caso MySequence, expor também uma coleção de variáveis através das quais as atividades da criança podem realizar isso. Tal como as atividades filho, o método CacheMetadata adiciona propriedades públicas do tipo Variable ou IEnumerable<Variable> como variáveis associadas à atividade MySequence.

Além das variáveis públicas, que são manipuladas pelos filhos de MySequence, MySequence também deve acompanhar onde está na execução dos seus filhos. Ele usa uma variável privada, currentIndex, para conseguir isso. Essa variável é registada como parte do ambiente MySequence ao adicionar uma chamada ao método AddImplementationVariable dentro do método da atividade MySequenceCacheMetadata. Os Activity objetos adicionados à MySequenceActivities coleção não podem acessar variáveis adicionadas dessa maneira.

Quando MySequence é executado pelo tempo de execução, o tempo de execução chama o método Execute, passando um NativeActivityContext. O NativeActivityContext é o proxy da atividade de volta ao tempo de execução para desreferenciar argumentos e variáveis, bem como agendar outros Activity objetos, ou ActivityDelegates. MySequence usa um InternalExecute método para encapsular a lógica de agendamento do primeiro filho e todos os filhos subsequentes em um único método. Começa por desreferenciar o currentIndex. Se for igual à contagem na coleção Activities, a sequência é concluída, a atividade retorna sem agendar nenhum trabalho e o tempo de execução move a atividade para o estado Closed. Se o currentIndex for menor que a contagem de atividades, o próximo filho é obtido da coleção Activities e MySequence chama ScheduleActivity, passando o filho a ser agendado e um CompletionCallback que aponta para o método InternalExecute. Finalmente, o currentIndex é incrementado e o controlo é transferido de volta para o tempo de execução. Desde que uma instância de MySequence tenha um objeto filho Activity agendado, o runtime considera-o no estado de execução.

Quando a atividade filho é concluída, a CompletionCallback é executada. O loop continua a partir do topo. Como Execute, a CompletionCallback recebe um NativeActivityContext, dando ao implementador acesso ao tempo de execução.

MyWhile difere de MySequence no facto de agendar um único objeto Activity repetidamente, e ao usar um Activity<TResult><bool> chamado Condition para determinar se esse agendamento deve ocorrer. Como MySequence, MyWhile usa um InternalExecute método para centralizar sua lógica de agendamento. Ele agenda o ConditionActivity<bool> com um CompletionCallback<TResult><bool> chamado OnEvaluationCompleted. Quando a execução do Condition é concluída, o seu resultado fica disponível através deste CompletionCallback em um parâmetro fortemente tipado chamado result. Se true, MyWhile chama ScheduleActivity, passando o objeto BodyActivity e InternalExecute como o CompletionCallback. Quando a execução de Body for concluída, Condition será novamente agendado em InternalExecute, reiniciando o loop. Quando o Condition retorna false, uma instância de MyWhile devolve o controle ao ambiente de execução sem agendar o Body e o ambiente de execução move-o para o estado Closed.

Para configurar, compilar e executar o exemplo

  1. Abra a solução de exemplo Composite.sln no Visual Studio.

  2. Crie e execute a solução.