static enum nz_pull_rc impulse_pull(struct nz_port * port) { struct nz_node * node = port->port_node; nz_obj_p input0 = NZ_NODE_PULL(node, 0); struct state * state = (struct state *) node->node_state; *(double*)port->port_value = 0.0; switch(state->status) { case STATUS_NEW: *(double*)port->port_value = 1.0; state->status = STATUS_WAIT_LOW; break; case STATUS_WAIT_HIGH: if (input0 != NULL && *(double*)input0) { *(double*)port->port_value = 1.0; state->status = STATUS_WAIT_LOW; } break; case STATUS_WAIT_LOW: if (input0 == NULL || !*(double*)input0) { state->status = STATUS_WAIT_HIGH; } break; } return NZ_PULL_RC_OBJECT; }
static enum nz_pull_rc sequencer_pull(struct nz_port * port) { struct nz_node * node = port->port_node; nz_obj_p inp_time = NZ_NODE_PULL(node, 0); nz_obj_p inp_stream = NZ_NODE_PULL(node, 1); if (inp_time == NULL || inp_stream == NULL) { return NZ_PULL_RC_NULL; } int t = (int) NZ_CAST(double, inp_time); size_t stream_idx = t % nz_vector_get_size(inp_stream); nz_obj_p* sequence = NZ_CAST(nz_obj_p*, inp_stream); nz_obj_p out = nz_obj_swap(&port->port_value, sequence[stream_idx]); return (out == NULL) ? NZ_PULL_RC_NULL : NZ_PULL_RC_OBJECT; }
static enum nz_pull_rc recorder_pull(struct nz_port * port) { struct nz_node * node = port->port_node; struct nz_obj * inp_len = NZ_NODE_PULL(node, 1); if (inp_len == NULL) return NZ_PULL_RC_NULL; size_t length = NZ_CAST(long, inp_len); size_t t = 0; free(port->port_value); port->port_value = nz_obj_create(nz_sample_type); // Resize sample size & fail if there's a problem size_t new_length = nz_vector_set_size(port->port_value, length); if (new_length != length) return NZ_PULL_RC_ERROR; double * samples = NZ_CAST(double *, port->port_value); int count = 0; while (t < length) { struct nz_obj * inp_chunk = NZ_NODE_PULL(node, 0); if (inp_chunk == NULL) { // We don't want to loop forever, if `inp_chunk` continues to be NULL // TODO: how should this be handled? fprintf(stderr, "Recorder pulled a null chunk; could loop forever; returning error.\n"); return NZ_PULL_RC_ERROR; //assert(0); continue; } double * chunk = &NZ_CAST(double, inp_chunk); if (t + nz_chunk_size < length) { memcpy(&samples[t], chunk, sizeof(double) * nz_chunk_size); t += nz_chunk_size; } else { while(t < length) samples[t++] = *chunk++; } } return NZ_PULL_RC_OBJECT; }
static enum nz_pull_rc fungen_pull(struct nz_port * port) { struct nz_node * node = port->port_node; nz_obj_p input0 = NZ_NODE_PULL(node, 0); if (input0 == NULL) { return NZ_PULL_RC_NULL; } *(double*)port->port_value = f(*(double*)input0); return NZ_PULL_RC_OBJECT; }