1
- use crate :: { delta_q:: DeltaQ , EvaluationContext } ;
1
+ use crate :: { delta_q:: DeltaQ , EvaluationContext , CDF } ;
2
2
use std:: { rc:: Rc , sync:: Arc } ;
3
3
use web_sys:: HtmlInputElement ;
4
4
use yew:: prelude:: * ;
@@ -37,7 +37,7 @@ pub fn delta_q_component(props: &Props) -> Html {
37
37
html ! { <NameComponent name={ ( & * * name) . to_owned( ) } rec={ * rec} { on_change} /> }
38
38
}
39
39
DeltaQ :: CDF ( cdf) => {
40
- html ! { <div class= { classes! ( " cdf" ) } > { format! ( "{}" , cdf ) } </div > }
40
+ html ! { <CdfComponent cdf= { cdf. clone ( ) } { on_change } / > }
41
41
}
42
42
DeltaQ :: Seq ( first, second) => {
43
43
html ! ( <Seq first={ ( * * first) . clone( ) } second={ ( * * second) . clone( ) } { on_change} />)
@@ -148,6 +148,56 @@ pub fn name_component(props: &NameProps) -> Html {
148
148
}
149
149
}
150
150
151
+ #[ derive( Properties , Clone , PartialEq ) ]
152
+ pub struct CdfProps {
153
+ pub cdf : CDF ,
154
+ pub on_change : Callback < ( String , Option < DeltaQ > ) > ,
155
+ }
156
+
157
+ #[ function_component( CdfComponent ) ]
158
+ pub fn cdf_component ( props : & CdfProps ) -> Html {
159
+ let cdf = props. cdf . clone ( ) ;
160
+ let on_change = props. on_change . clone ( ) ;
161
+ let popup = use_state ( || false ) ;
162
+ let ctx = use_context :: < DeltaQContext > ( ) . unwrap ( ) ;
163
+
164
+ let abstract_name = use_state ( || "" . to_string ( ) ) ;
165
+ let abstract_input = Callback :: from ( cloned ! ( abstract_name;
166
+ move |e: InputEvent | abstract_name. set( e. target_unchecked_into:: <HtmlInputElement >( ) . value( ) ) ) ) ;
167
+ let abstract_submit = Callback :: from ( cloned ! ( abstract_name, on_change, ctx, cdf;
168
+ move |e: SubmitEvent | {
169
+ e. prevent_default( ) ;
170
+ on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: name( & abstract_name) ) ) ) ;
171
+ on_change. emit( ( ( * abstract_name) . clone( ) , Some ( DeltaQ :: CDF ( cdf. clone( ) ) ) ) ) ;
172
+ }
173
+ ) ) ;
174
+
175
+ html ! {
176
+ <div class={ classes!( "cdf" , "anchor" ) } onclick={ cloned!( popup; move |_| if !* popup { popup. set( true ) } ) } >
177
+ { format!( "{}" , props. cdf) }
178
+ if * popup {
179
+ <div class={ classes!( "popup" ) } >
180
+ <button onclick={ cloned!( popup; move |_| popup. set( false ) ) } >{ "abort" } </button>
181
+ <button onclick={ cloned!( on_change, cdf, ctx;
182
+ move |_| on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: seq( DeltaQ :: CDF ( cdf. clone( ) ) , DeltaQ :: BlackBox ) ) ) ) ) } >{ "append" } </button>
183
+ <button onclick={ cloned!( on_change, cdf, ctx;
184
+ move |_| on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: choice( DeltaQ :: CDF ( cdf. clone( ) ) , 1.0 , DeltaQ :: BlackBox , 1.0 ) ) ) ) ) } >{ "make choice" } </button>
185
+ <button onclick={ cloned!( on_change, cdf, ctx;
186
+ move |_| on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: for_all( DeltaQ :: CDF ( cdf. clone( ) ) , DeltaQ :: BlackBox ) ) ) ) ) } >{ "make forAll" } </button>
187
+ <button onclick={ cloned!( on_change, cdf, ctx;
188
+ move |_| on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: for_some( DeltaQ :: CDF ( cdf. clone( ) ) , DeltaQ :: BlackBox ) ) ) ) ) } >{ "make forSome" } </button>
189
+ <button onclick={ cloned!( on_change, ctx;
190
+ move |_| on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: BlackBox ) ) ) ) } >{ "black box" } </button>
191
+ <form onsubmit={ abstract_submit} >
192
+ <input type ="submit" value="abstract" />
193
+ <input type ="text" value={ ( * abstract_name) . clone( ) } oninput={ abstract_input} />
194
+ </form>
195
+ </div>
196
+ }
197
+ </div>
198
+ }
199
+ }
200
+
151
201
#[ derive( Properties , Clone , PartialEq ) ]
152
202
pub struct SeqProps {
153
203
pub first : DeltaQ ,
@@ -213,6 +263,8 @@ pub fn seq(props: &SeqProps) -> Html {
213
263
move |_| on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: for_some( DeltaQ :: seq( first. clone( ) , second. clone( ) ) , DeltaQ :: BlackBox ) ) ) ) ) } > { "make forSome" } </button>
214
264
<button onclick={ cloned!( on_change, first, second, popup, ctx;
215
265
move |_| { popup. set( false ) ; on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: seq( second. clone( ) , first. clone( ) ) ) ) ) } ) } >{ "switch" } </button>
266
+ <button onclick={ cloned!( on_change, first, second, ctx;
267
+ move |_| on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: seq( first. clone( ) , second. clone( ) ) ) ) ) ) } >{ "append" } </button>
216
268
<button onclick={ cloned!( popup, on_change, first, ctx;
217
269
move |_| { popup. set( false ) ; on_change. emit( ( ctx. name. clone( ) , Some ( first. clone( ) ) ) ) } ) } >{ "keep left" } </button>
218
270
<button onclick={ cloned!( popup, on_change, second, ctx;
@@ -257,7 +309,8 @@ impl BranchKind {
257
309
258
310
#[ function_component( BranchKindComponent ) ]
259
311
pub fn branch_kind_component ( props : & BranchProps ) -> Html {
260
- let kind = match & props. kind {
312
+ let kind = props. kind ;
313
+ let kind_html = match kind {
261
314
BranchKind :: Choice ( first_weight, second_weight) => html ! {
262
315
<div class={ classes!( "column" , "center" ) } >
263
316
<div>{ first_weight} </div>
@@ -293,19 +346,17 @@ pub fn branch_kind_component(props: &BranchProps) -> Html {
293
346
let abstract_name = use_state ( || "" . to_string ( ) ) ;
294
347
let abstract_input = Callback :: from ( cloned ! ( abstract_name;
295
348
move |e: InputEvent | abstract_name. set( e. target_unchecked_into:: <HtmlInputElement >( ) . value( ) ) ) ) ;
296
- let abstract_submit = Callback :: from (
297
- cloned ! ( abstract_name, on_change, ctx, bottom, bottom_frac, top, top_frac;
298
- move |e: SubmitEvent | {
299
- e. prevent_default( ) ;
300
- on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: name( & abstract_name) ) ) ) ;
301
- on_change. emit( ( ( * abstract_name) . clone( ) , Some ( DeltaQ :: choice( top. clone( ) , * top_frac, bottom. clone( ) , * bottom_frac) ) ) ) ;
302
- }
303
- ) ,
304
- ) ;
349
+ let abstract_submit = Callback :: from ( cloned ! ( abstract_name, on_change, ctx, bottom, top;
350
+ move |e: SubmitEvent | {
351
+ e. prevent_default( ) ;
352
+ on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: name( & abstract_name) ) ) ) ;
353
+ on_change. emit( ( ( * abstract_name) . clone( ) , Some ( mk_branch( kind, top. clone( ) , bottom. clone( ) ) ) ) ) ;
354
+ }
355
+ ) ) ;
305
356
306
357
html ! (
307
358
<div class={ classes!( "row" , "center" , "branchKind" , "anchor" ) } onclick={ cloned!( popup; move |_| if !* popup { popup. set( true ) } ) } >
308
- { kind }
359
+ { kind_html }
309
360
if * popup {
310
361
<div class={ classes!( "popup" ) } >
311
362
<button onclick={ cloned!( popup; move |_| popup. set( false ) ) } >{ "abort" } </button>
@@ -324,8 +375,10 @@ pub fn branch_kind_component(props: &BranchProps) -> Html {
324
375
} ) } >{ "make forSome" } </button>
325
376
<button onclick={ cloned!( popup, on_change, top, bottom, ctx; move |_| {
326
377
popup. set( false ) ;
327
- on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: choice ( bottom. clone( ) , * bottom_frac , top. clone( ) , * top_frac ) ) ) )
378
+ on_change. emit( ( ctx. name. clone( ) , Some ( mk_branch ( kind , bottom. clone( ) , top. clone( ) ) ) ) )
328
379
} ) } >{ "switch" } </button>
380
+ <button onclick={ cloned!( popup, on_change, top, bottom, ctx;
381
+ move |_| { popup. set( false ) ; on_change. emit( ( ctx. name. clone( ) , Some ( DeltaQ :: seq( mk_branch( kind, top. clone( ) , bottom. clone( ) ) , DeltaQ :: BlackBox ) ) ) ) } ) } >{ "append" } </button>
329
382
<button onclick={ cloned!( popup, on_change, top, ctx;
330
383
move |_| { popup. set( false ) ; on_change. emit( ( ctx. name. clone( ) , Some ( top. clone( ) ) ) ) } ) } >{ "keep top" } </button>
331
384
<button onclick={ cloned!( popup, on_change, bottom, ctx;
@@ -341,6 +394,14 @@ pub fn branch_kind_component(props: &BranchProps) -> Html {
341
394
</div>)
342
395
}
343
396
397
+ fn mk_branch ( kind : BranchKind , top : DeltaQ , bottom : DeltaQ ) -> DeltaQ {
398
+ match kind {
399
+ BranchKind :: Choice ( l, r) => DeltaQ :: Choice ( Arc :: new ( top) , l, Arc :: new ( bottom) , r) ,
400
+ BranchKind :: ForAll => DeltaQ :: ForAll ( Arc :: new ( top) , Arc :: new ( bottom) ) ,
401
+ BranchKind :: ForSome => DeltaQ :: ForSome ( Arc :: new ( top) , Arc :: new ( bottom) ) ,
402
+ }
403
+ }
404
+
344
405
/// A component that renders a branch of a DeltaQ tree.
345
406
///
346
407
/// The HTML representation consists of two DIV, with the left showing the branch kind and the right showing the branch content.
@@ -352,20 +413,15 @@ fn branch(props: &BranchProps) -> Html {
352
413
let top = props. top . clone ( ) ;
353
414
let bottom = props. bottom . clone ( ) ;
354
415
let kind = props. kind ;
355
- let constructor: Arc < dyn Fn ( Arc < DeltaQ > , Arc < DeltaQ > ) -> DeltaQ > = match kind {
356
- BranchKind :: Choice ( l, r) => Arc :: new ( move |dql, dqr| DeltaQ :: Choice ( dql, l, dqr, r) ) ,
357
- BranchKind :: ForAll => Arc :: new ( DeltaQ :: ForAll ) ,
358
- BranchKind :: ForSome => Arc :: new ( DeltaQ :: ForSome ) ,
359
- } ;
360
416
let ctx = use_context :: < DeltaQContext > ( ) . unwrap ( ) ;
361
417
362
- let on_top_change = Callback :: from ( cloned ! ( bottom, on_change, constructor , ctx;
418
+ let on_top_change = Callback :: from ( cloned ! ( bottom, on_change, ctx;
363
419
move |( name, delta_q) | {
364
420
// if the name matches our context, edit the DeltaQ; otherwise just bubble up
365
421
if name != ctx. name {
366
422
on_change. emit( ( name, delta_q) ) ;
367
423
} else if let Some ( delta_q) = delta_q {
368
- on_change. emit( ( name, Some ( constructor ( Arc :: new ( delta_q) , Arc :: new ( bottom. clone( ) ) ) ) ) ) ;
424
+ on_change. emit( ( name, Some ( mk_branch ( kind , delta_q, bottom. clone( ) ) ) ) ) ;
369
425
}
370
426
}
371
427
) ) ;
@@ -376,7 +432,7 @@ fn branch(props: &BranchProps) -> Html {
376
432
if name != ctx. name {
377
433
on_change. emit( ( name, delta_q) ) ;
378
434
} else if let Some ( delta_q) = delta_q {
379
- on_change. emit( ( name, Some ( constructor ( Arc :: new ( top. clone( ) ) , Arc :: new ( delta_q) ) ) ) ) ;
435
+ on_change. emit( ( name, Some ( mk_branch ( kind , top. clone( ) , delta_q) ) ) ) ;
380
436
}
381
437
}
382
438
) ) ;
0 commit comments