<commit_before>var moduleDefinitions = {
	osc: {
		wave: {
			type: 'list',
			values: ['sin','cos','pulse','saw','tri','fami','konami'],
			initial: 'sin',
		},
		freq: {
			type: 'integer',
			min: 0,
			max: 2600,
			step: 1,
			initial: 500,
		}
	},
	noise: {
		mul: {
			type: 'integer',
			initial: 1,
		},
		add: {
			type: 'integer',
			initial: 0,
		},
	},
};

var Page = React.createClass({
	getInitialState: function() {
		return {
			modules: [{
				name: 'osc',
				properties: {wave:'sin', freq:500}
			}],
			sequence: null,
		};
	},

	isPlaying: function() {
		return (this.state.sequence != null);
	},

	addNewModule: function(m) {
		var modules = this.state.modules
		m.myT = T(m.name, m.properties)
		modules.push(m)
		var sequence = this.state.sequence
		if (this.isPlaying()) {
			sequence.append(m.myT)
		}

		this.setState({
			modules: modules,
			sequence: sequence,
		})
	},

	oscChanged: function(i, values) {
		var modules = this.state.modules;
		modules[i] = values;
		this.setState({modules: modules});
	},

	togglePlay: function() {
		if (this.state.sequence == null) {
			this.play();
		}
		else {
			this.pause();
		}
	},

	play: function() {
		if (this.state.sequence != null) {
			//pause first so we're not playing multiple sequences
			this.state.sequence.pause();
		}
		var sequence = null;
		this.state.modules.forEach(function (m) {
			m.myT = T(m.name, m.properties);
			if (sequence == null) {
				sequence = m.myT;
			} else {
				sequence = sequence.append(m.myT);
			}
		});
		this.setState({sequence: sequence});
		sequence.play();
		console.log('playing');
	},

	pause: function() {
		if (this.state.sequence != null) {
			this.state.sequence.pause();
			this.state.sequence = null
		}
	},

	render: function() {
		return (
			<div>
				<div className="header-row">
					<h1>Snap-In Synth</h1>
				</div>
				<div className="button-row">
					<ModuleSelector addNewModule={this.addNewModule} />
					<PlayButton playFn={this.togglePlay} />
				</div>
				<div className="module-row">
					{this.state.modules.map(function(s, i) {
						return <Module key={i} mod={s} id={i} changed={this.oscChanged} />;
					}.bind(this))}
				</div>
			</div>
		);
	}
});

var Module = React.createClass({
	changed: function() {
		var wave = $(this.getDOMNode()).find('select').val();
		var freq = $(this.getDOMNode()).find('input').val();

		this.props.mod.properties.wave = wave;
		this.props.mod.properties.freq = parseInt(freq);
		if (this.props.mod.myT != null) {
			this.props.mod.myT.set(this.props.mod.properties)
		}

		this.props.changed(this.props.id, this.props.mod);
	},
	render: function() {

		var controls = [];
		for (prop in moduleDefinitions[this.props.mod.name]) {
			var def = moduleDefinitions[this.props.mod.name][prop];
			if (def['type'] == 'list') {
				controls.push(
					<select onChange={this.changed} value={this.props.mod.properties[prop]}>
						{def.values.map(function(s, i) {
							return <option value={s}>{s}</option>
						})}
					</select>
				);
			} else if (def['type'] == 'integer') {
				controls.push(<input type='range' min={def.min} max={def.max} step={def.step} onChange={this.changed} />)
			}
		}

		return (
			<div className='module'>
				<h2>{this.props.mod.name}</h2>
				{controls}
			</div>
		);
	}
});

var ModuleSelector = React.createClass({<commit_msg>update change function for dynamic properties<commit_after>var moduleDefinitions = {
	osc: {
		wave: {
			type: 'list',
			values: ['sin','cos','pulse','saw','tri','fami','konami'],
			initial: 'sin',
		},
		freq: {
			type: 'integer',
			min: 0,
			max: 2600,
			step: 1,
			initial: 500,
		}
	},
	noise: {
		mul: {
			type: 'integer',
			initial: 1,
		},
		add: {
			type: 'integer',
			initial: 0,
		},
	},
};

var Page = React.createClass({
	getInitialState: function() {
		return {
			modules: [{
				name: 'osc',
				properties: {wave:'sin', freq:500}
			}],
			sequence: null,
		};
	},

	isPlaying: function() {
		return (this.state.sequence != null);
	},

	addNewModule: function(m) {
		var modules = this.state.modules
		m.myT = T(m.name, m.properties)
		modules.push(m)
		var sequence = this.state.sequence
		if (this.isPlaying()) {
			sequence.append(m.myT)
		}

		this.setState({
			modules: modules,
			sequence: sequence,
		})
	},

	oscChanged: function(i, values) {
		var modules = this.state.modules;
		modules[i] = values;
		this.setState({modules: modules});
	},

	togglePlay: function() {
		if (this.state.sequence == null) {
			this.play();
		}
		else {
			this.pause();
		}
	},

	play: function() {
		if (this.state.sequence != null) {
			//pause first so we're not playing multiple sequences
			this.state.sequence.pause();
		}
		var sequence = null;
		this.state.modules.forEach(function (m) {
			m.myT = T(m.name, m.properties);
			if (sequence == null) {
				sequence = m.myT;
			} else {
				sequence = sequence.append(m.myT);
			}
		});
		this.setState({sequence: sequence});
		sequence.play();
		console.log('playing');
	},

	pause: function() {
		if (this.state.sequence != null) {
			this.state.sequence.pause();
			this.state.sequence = null
		}
	},

	render: function() {
		return (
			<div>
				<div className="header-row">
					<h1>Snap-In Synth</h1>
				</div>
				<div className="button-row">
					<ModuleSelector addNewModule={this.addNewModule} />
					<PlayButton playFn={this.togglePlay} />
				</div>
				<div className="module-row">
					{this.state.modules.map(function(s, i) {
						return <Module key={i} mod={s} id={i} changed={this.oscChanged} />;
					}.bind(this))}
				</div>
			</div>
		);
	}
});

var Module = React.createClass({
	changed: function() {
		// for each prop
		for (tPropName in this.props.mod.properties) {
			var tPropValue = $(this.getDOMNode()).find('.' + tPropName).val()
			//TODO: add variable parsing
			switch(moduleDefinitions[this.props.mod.name][tPropName].type) {
				case 'integer':
					console.dir(tPropValue);
					tPropValue = parseInt(tPropValue);
				default:
					tPropValue = tPropValue
					break;
			}

			this.props.mod.properties[tPropName] = tPropValue;
		}

		if (this.props.mod.myT != null) {
			this.props.mod.myT.set(this.props.mod.properties);
		}

		this.props.changed(this.props.id, this.props.mod);
	},
	render: function() {
		var controls = [];
		for (prop in moduleDefinitions[this.props.mod.name]) {
			var def = moduleDefinitions[this.props.mod.name][prop];
			if (def['type'] == 'list') {
				controls.push(
					<select className={prop} onChange={this.changed} value={this.props.mod.properties[prop]}>
						{def.values.map(function(s, i) {
							return <option value={s}>{s}</option>
						})}
					</select>
				);
			} else if (def['type'] == 'integer') {
				controls.push(<input className={prop} type='range' min={def.min} max={def.max} step={def.step} onChange={this.changed} />)
			}
		}

		return (
			<div className='module'>
				<h2>{this.props.mod.name}</h2>
				{controls}
			</div>
		);
	}
});

var ModuleSelector = React.createClass({
{'fraction_non_alphanumeric': 0.18808911739502998, 'fraction_numerical': 0.005141388174807198, 'mean_word_length': 3.059710144927536, 'pattern_counts': {'":': 0, '<': 47, '<?xml version=': 0, '>': 47, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2071066', 'n_tokens_mistral': 3042, 'n_tokens_neox': 2514, 'n_words': 471}