-
Notifications
You must be signed in to change notification settings - Fork 6
/
Copy pathindex.js
109 lines (100 loc) · 2.9 KB
/
index.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
import React from 'react';
import ReactDOM from 'react-dom';
import("./node_modules/lalrpop-lambda/lalrpop_lambda.js").then(wasm => {
class LambdaEditor extends React.Component {
constructor(props) {
super(props);
this.state = { input: '', expression: null, error: null };
this.handleChange = this.handleChange.bind(this);
}
handleChange(event) {
let input = event.target.value;
try {
let expression = new wasm.Exp(input);
this.setState({ input, expression, error: null });
} catch(e) {
this.setState({ input, expression: null, error: e });
}
}
render() {
if (this.state.input === '') {
var display = (
<p>
<strong>Input a valid λ-expression, e.g.</strong>
<code>\x.x x</code>
</p>
);
} else if (this.state.error) {
var display = <LambdaParseError message={this.state.error} />
} else {
var display = <LambdaOutputs exp={this.state.expression} />
}
return (
<div className="lambda">
<textarea onChange={this.handleChange}
value={this.state.input}></textarea>
{display}
</div>
);
}
}
class LambdaOutputs extends React.Component {
render() {
let outputs = [
{ label: 'parse', func: 'toString' },
{ label: 'app ->', func: 'applicative' },
{ label: 'cbv ->', func: 'call_by_value' },
{ label: 'norm ->', func: 'normal' },
{ label: 'cbn ->', func: 'call_by_name' },
// TODO: Hybrid by-func and applicative.
{ label: 'spine ->', func: 'head_spine' },
// TODO: Hybrid head spine and normal.
{ label: "numeral =", func: 'toNumber' },
{ label: "bool =", func: 'toBool' },
];
return (
<table>
<tbody>
{outputs.map((o, i) => {
return (<LambdaOutput key={i}
label={o.label}
exp={this.props.exp}
func={o.func} />);
})}
</tbody>
</table>
)
}
}
class LambdaOutput extends React.Component {
render() {
if (this.props.func) {
try {
var result = (<code>
{this.props.exp[this.props.func]().toString()}
</code>);
} catch(e) {
var result = <code className='error'>{e.toString()}</code>;
}
} else {
var result = '';
}
return (
<tr>
<th>{this.props.label}</th>
<td>{result}</td>
</tr>
);
}
}
class LambdaParseError extends React.Component {
render() {
return (
<p>
<code className="error">{this.props.message}</code>
</p>
)
}
}
ReactDOM.render(<LambdaEditor />, document.getElementById('mount'));
});