d6bdbb45260bed16ff2b3711993b3e0fa5c6fda1
[Mograsim.git] / net.mograsim.logic.ui / src / net / mograsim / logic / ui / serializing / CodeSnippetSupplier.java
1 package net.mograsim.logic.ui.serializing;
2
3 import java.io.IOException;
4 import java.io.InputStream;
5 import java.util.HashMap;
6 import java.util.Map;
7
8 import net.mograsim.logic.ui.serializing.snippets.Renderer;
9 import net.mograsim.logic.ui.serializing.snippets.SnippetSupplier;
10 import net.mograsim.logic.ui.serializing.snippets.outlinerenderers.DefaultOutlineRenderer;
11 import net.mograsim.logic.ui.serializing.snippets.symbolrenderers.DefaultSymbolRenderer;
12 import net.mograsim.logic.ui.util.JsonHandler;
13
14 public class CodeSnippetSupplier<S>
15 {
16         // public static members
17         public static final CodeSnippetSupplier<Renderer> symbolRendererProviderSupplier;
18         public static final CodeSnippetSupplier<Renderer> outlineRendererProviderSupplier;
19
20         static
21         {
22                 symbolRendererProviderSupplier = new CodeSnippetSupplier<>(SnippetSupplier.create(Void.class, DefaultSymbolRenderer::new));
23                 outlineRendererProviderSupplier = new CodeSnippetSupplier<>(SnippetSupplier.create(Void.class, DefaultOutlineRenderer::new));
24         }
25
26         // per-instance members
27
28         private final Map<String, String> standardSnippetIDClassNames = new HashMap<>();
29         private final Map<String, SnippetSupplier<?, S>> snippetProvidersForClassNames = new HashMap<>();
30         private final SnippetSupplier<?, S> defaultSnippetProvider;
31
32         private CodeSnippetSupplier(SnippetSupplier<?, S> defaultSnippetProvider)
33         {
34                 this.defaultSnippetProvider = defaultSnippetProvider;
35         }
36
37         public void addStandardSnippetID(String standardSnippetID, String associatedSnippetClassName)
38         {
39                 standardSnippetIDClassNames.put(standardSnippetID, associatedSnippetClassName);
40         }
41
42         public void setSnippetProvider(String id, SnippetSupplier<?, S> snippetProvider)
43         {
44                 snippetProvidersForClassNames.put(id, snippetProvider);
45         }
46
47         // TODO report errors
48         public SnippetSupplier<?, S> getSnippetProvider(String id)
49         {
50                 if (id != null)
51                 {
52                         String snippetProviderClassName;
53                         if (id.startsWith("class:"))
54                                 snippetProviderClassName = id.substring(6);
55                         else
56                                 snippetProviderClassName = standardSnippetIDClassNames.get(id);
57                         if (snippetProviderClassName != null)
58                         {
59                                 tryLoadSnippetClass(snippetProviderClassName);
60                                 SnippetSupplier<?, S> snippetProvider = snippetProvidersForClassNames.get(snippetProviderClassName);
61                                 if (snippetProvider != null)
62                                         return snippetProvider;
63                         }
64                 }
65                 System.err.println("Couldn't load snippet " + id + "; using default");
66                 return defaultSnippetProvider;
67         }
68
69         // static helpers
70
71         static
72         {
73                 try (InputStream s = IndirectGUIComponentCreator.class.getResourceAsStream("./standardSnippetIDMapping.json"))
74                 {
75                         if (s == null)
76                                 throw new IOException("Resource not found");
77                         SnippetIDClassNames tmp = JsonHandler.readJson(s, SnippetIDClassNames.class);
78                         tmp.standardOutlineRendererProviders.forEach(outlineRendererProviderSupplier::addStandardSnippetID);
79                         tmp.standardSymbolRendererProviders.forEach(symbolRendererProviderSupplier::addStandardSnippetID);
80                 }
81                 catch (Exception e)
82                 {
83                         System.err.println("Failed to initialize standard snippet ID mapping: ");
84                         e.printStackTrace();
85                 }
86         }
87
88         private static class SnippetIDClassNames
89         {
90                 public Map<String, String> standardOutlineRendererProviders;
91                 public Map<String, String> standardSymbolRendererProviders;
92         }
93
94         private static void tryLoadSnippetClass(String snippetClassName)
95         {
96                 tryInvokeStaticInitializer(snippetClassName, "Error getting snippet class: %s: %s\n");
97         }
98
99         public static void tryInvokeStaticInitializer(String className, String errorMessageFormat)
100         {
101                 try
102                 {
103                         Class.forName(className, true, CodeSnippetSupplier.class.getClassLoader());
104                 }
105                 catch (ClassNotFoundException e)
106                 {
107                         System.err.printf(errorMessageFormat, className, "ClassNotFoundException thrown: " + e.getMessage());
108                 }
109         }
110
111 }