]> gerrit.simantics Code Review - simantics/platform.git/blob
e369050e906e0f5dd422e150d47c6cffdc90c2ad
[simantics/platform.git] /
1 package org.simantics.structural2.scl;\r
2 \r
3 import java.util.Collections;\r
4 import java.util.Map;\r
5 \r
6 import org.simantics.databoard.Bindings;\r
7 import org.simantics.db.ReadGraph;\r
8 import org.simantics.db.Resource;\r
9 import org.simantics.db.common.procedure.adapter.TransientCacheListener;\r
10 import org.simantics.db.common.request.ResourceRead2;\r
11 import org.simantics.db.exception.DatabaseException;\r
12 import org.simantics.db.layer0.scl.AbstractExpressionCompilationContext;\r
13 import org.simantics.db.layer0.scl.AbstractExpressionCompilationRequest;\r
14 import org.simantics.db.layer0.util.RuntimeEnvironmentRequest;\r
15 import org.simantics.db.layer0.variable.Variable;\r
16 import org.simantics.layer0.Layer0;\r
17 import org.simantics.scl.compiler.elaboration.expressions.EApply;\r
18 import org.simantics.scl.compiler.elaboration.expressions.EConstant;\r
19 import org.simantics.scl.compiler.elaboration.expressions.EVariable;\r
20 import org.simantics.scl.compiler.elaboration.expressions.Expression;\r
21 import org.simantics.scl.compiler.elaboration.modules.SCLValue;\r
22 import org.simantics.scl.compiler.environment.Environment;\r
23 import org.simantics.scl.compiler.environment.Environments;\r
24 import org.simantics.scl.compiler.runtime.RuntimeEnvironment;\r
25 import org.simantics.scl.compiler.top.SCLExpressionCompilationException;\r
26 import org.simantics.scl.compiler.types.Type;\r
27 import org.simantics.structural2.scl.AbstractCompileStructuralValueRequest.CompilationContext;\r
28 \r
29 /**\r
30  * Compiles an SCL expression that is attached to a literal\r
31  * whose parent is a component that is a part of a component type.\r
32  * \r
33  * @author Antti Villberg\r
34  */\r
35 abstract public class AbstractCompileStructuralValueRequest extends AbstractExpressionCompilationRequest<CompilationContext, Variable> {\r
36     \r
37     protected final Resource relation;\r
38     \r
39     public static class CompilationContext extends AbstractExpressionCompilationContext {\r
40         public final Map<String, ComponentTypeProperty> propertyMap;\r
41         \r
42         public CompilationContext(RuntimeEnvironment runtimeEnvironment,\r
43                 Map<String, ComponentTypeProperty> propertyMap) {\r
44             super(runtimeEnvironment);\r
45             this.propertyMap = propertyMap;\r
46         }\r
47     }\r
48     \r
49     public AbstractCompileStructuralValueRequest(Resource relation) {\r
50         this.relation = relation;\r
51     }\r
52 \r
53     @Override\r
54     abstract protected String getExpressionText(ReadGraph graph) throws DatabaseException;\r
55     abstract protected Resource getIndexRoot(ReadGraph graph) throws DatabaseException;\r
56     abstract protected Resource getComponentType(ReadGraph graph) throws DatabaseException;\r
57     \r
58     @Override\r
59     protected Type getExpectedType(ReadGraph graph, CompilationContext context)\r
60             throws DatabaseException {\r
61         Layer0 L0 = Layer0.getInstance(graph);\r
62         String valueType = graph.getPossibleRelatedValue(relation, L0.RequiresValueType, Bindings.STRING);\r
63         if(valueType != null) {\r
64             try {\r
65                 return Environments.getType(context.runtimeEnvironment.getEnvironment(), valueType);\r
66             } catch (SCLExpressionCompilationException e) {\r
67                 e.printStackTrace();\r
68             }\r
69         }\r
70         return super.getExpectedType(graph, context);\r
71     }\r
72     \r
73     \r
74 \r
75     @Override\r
76     protected CompilationContext getCompilationContext(ReadGraph graph)\r
77             throws DatabaseException {\r
78         Resource indexRoot = getIndexRoot(graph);\r
79         Resource componentType = getComponentType(graph);\r
80         if(componentType == null) {\r
81             RuntimeEnvironment runtimeEnvironment = graph.syncRequest(new RuntimeEnvironmentRequest(indexRoot));\r
82             return new CompilationContext(runtimeEnvironment, Collections.<String,ComponentTypeProperty>emptyMap());\r
83         } else {\r
84                 return graph.syncRequest(new ResourceRead2<CompilationContext>(componentType, indexRoot) {\r
85                     @Override\r
86                     public CompilationContext perform(ReadGraph graph)\r
87                             throws DatabaseException {\r
88                         RuntimeEnvironment runtimeEnvironment = graph.syncRequest(new RuntimeEnvironmentRequest(resource2));\r
89                         Map<String, ComponentTypeProperty> propertyMap =\r
90                                 graph.syncRequest(new ReadComponentTypeInterfaceRequest(resource, runtimeEnvironment.getEnvironment()),\r
91                                         TransientCacheListener.<Map<String, ComponentTypeProperty>>instance());\r
92                         return new CompilationContext(runtimeEnvironment, propertyMap);\r
93                     }\r
94                 });\r
95         }\r
96     }\r
97 \r
98     @Override\r
99     protected Type getContextVariableType() {\r
100         return VARIABLE; \r
101     }\r
102 \r
103     protected static Expression accessInputVariable(Environment environment,\r
104             org.simantics.scl.compiler.elaboration.expressions.Variable contextVariable) {\r
105         SCLValue variableParentFunction = environment.getValue(VARIABLE_PARENT);\r
106         return new EApply(new EConstant(variableParentFunction),\r
107                 new EApply(new EConstant(variableParentFunction),\r
108                         new EVariable(contextVariable)));\r
109     }\r
110     \r
111     @Override\r
112     protected Expression getVariableAccessExpression(\r
113             ReadGraph graph,\r
114             CompilationContext context,\r
115             org.simantics.scl.compiler.elaboration.expressions.Variable contextVariable,\r
116             String name) throws DatabaseException {\r
117         ComponentTypeProperty property = context.propertyMap.get(name);\r
118         if(property != null) {\r
119             Environment environment = context.runtimeEnvironment.getEnvironment();\r
120             return getPropertyFlexible(environment,\r
121                     accessInputVariable(environment, contextVariable),\r
122                     name,\r
123                     property.type);\r
124         }\r
125         else if(name.equals("input")) {\r
126             Environment environment = context.runtimeEnvironment.getEnvironment();\r
127             return accessInputVariable(environment, contextVariable);\r
128         }\r
129         else if(name.equals("self"))\r
130             return new EVariable(contextVariable);\r
131         else\r
132             return null;\r
133     }\r
134     \r
135 }\r