3636function _model_macro (mod, name, expr, isconnector)
3737 exprs = Expr (:block )
3838 dict = Dict {Symbol, Any} (
39+ :constants => Dict {Symbol, Dict} (),
3940 :kwargs => Dict {Symbol, Dict} (),
4041 :structural_parameters => Dict {Symbol, Dict} ()
4142 )
@@ -347,6 +348,8 @@ function parse_model!(exprs, comps, ext, eqs, icon, vs, ps, sps,
347348 parse_structural_parameters! (exprs, sps, dict, mod, body, kwargs)
348349 elseif mname == Symbol (" @equations" )
349350 parse_equations! (exprs, eqs, dict, body)
351+ elseif mname == Symbol (" @constants" )
352+ parse_constants! (exprs, dict, body, mod)
350353 elseif mname == Symbol (" @icon" )
351354 isassigned (icon) && error (" This model has more than one icon." )
352355 parse_icon! (body, dict, icon, mod)
@@ -355,13 +358,53 @@ function parse_model!(exprs, comps, ext, eqs, icon, vs, ps, sps,
355358 end
356359end
357360
361+ function parse_constants! (exprs, dict, body, mod)
362+ Base. remove_linenums! (body)
363+ for arg in body. args
364+ MLStyle. @match arg begin
365+ Expr (:(= ), Expr (:(:: ), a, type), Expr (:tuple , b, metadata)) || Expr (:(= ), Expr (:(:: ), a, type), b) => begin
366+ type = getfield (mod, type)
367+ b = _type_check! (get_var (mod, b), a, type, :constants )
368+ constant = first (@constants $ a:: type = b)
369+ push! (exprs, :($ a = $ constant))
370+ dict[:constants ][a] = Dict (:value => b, :type => type)
371+ if @isdefined metadata
372+ for data in metadata. args
373+ dict[:constants ][a][data. args[1 ]] = data. args[2 ]
374+ end
375+ end
376+ end
377+ Expr (:(= ), a, Expr (:tuple , b, metadata)) => begin
378+ constant = first (@constants $ a = b)
379+ push! (exprs, :($ a = $ constant))
380+ dict[:constants ][a] = Dict {Symbol, Any} (:value => get_var (mod, b))
381+ for data in metadata. args
382+ dict[:constants ][a][data. args[1 ]] = data. args[2 ]
383+ end
384+ end
385+ Expr (:(= ), a, b) => begin
386+ constant = first (@constants $ a = b)
387+ push! (exprs, :($ a = $ constant))
388+ dict[:constants ][a] = Dict (:value => get_var (mod, b))
389+ end
390+ _ => error (""" Malformed constant definition `$arg `. Please use the following syntax:
391+ ```
392+ @constants begin
393+ var = value, [description = "This is an example constant."]
394+ end
395+ ```
396+ """ )
397+ end
398+ end
399+ end
400+
358401function parse_structural_parameters! (exprs, sps, dict, mod, body, kwargs)
359402 Base. remove_linenums! (body)
360403 for arg in body. args
361404 MLStyle. @match arg begin
362405 Expr (:(= ), Expr (:(:: ), a, type), b) => begin
363- type = Core . eval (mod, type)
364- b = _type_check! (Core . eval (mod, b), a, type, :structural_parameters )
406+ type = getfield (mod, type)
407+ b = _type_check! (get_var (mod, b), a, type, :structural_parameters )
365408 push! (sps, a)
366409 push! (kwargs, Expr (:kw , Expr (:(:: ), a, type), b))
367410 dict[:structural_parameters ][a] = dict[:kwargs ][a] = Dict (
@@ -922,16 +965,15 @@ function parse_conditional_model_statements(comps, dict, eqs, exprs, kwargs, mod
922965 end ))
923966end
924967
925- function _type_check! (val, a, type, varclass )
968+ function _type_check! (val, a, type, class )
926969 if val isa type
927970 return val
928971 else
929972 try
930973 return convert (type, val)
931- catch
932- (e)
974+ catch e
933975 throw (TypeError (Symbol (" `@mtkmodel`" ),
934- " `$varclass `, while assigning to `$a `" , type, typeof (val)))
976+ " `$class `, while assigning to `$a `" , type, typeof (val)))
935977 end
936978 end
937979end
0 commit comments