Method: LatexUtils(Shell)

1: /*
2: * #%~
3: * org.overture.ide.plugins.latex
4: * %%
5: * Copyright (C) 2008 - 2014 Overture
6: * %%
7: * This program is free software: you can redistribute it and/or modify
8: * it under the terms of the GNU General Public License as
9: * published by the Free Software Foundation, either version 3 of the
10: * License, or (at your option) any later version.
11: *
12: * This program is distributed in the hope that it will be useful,
13: * but WITHOUT ANY WARRANTY; without even the implied warranty of
14: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15: * GNU General Public License for more details.
16: *
17: * You should have received a copy of the GNU General Public
18: * License along with this program. If not, see
19: * <http://www.gnu.org/licenses/gpl-3.0.html>.
20: * #~%
21: */
22: package org.overture.ide.plugins.latex.utility;
23:
24: import java.io.File;
25: import java.io.FileNotFoundException;
26: import java.io.IOException;
27: import java.io.PrintWriter;
28: import java.util.List;
29: import java.util.Vector;
30: import java.util.stream.Collectors;
31:
32: import org.eclipse.core.resources.IFile;
33: import org.eclipse.core.resources.IProject;
34: import org.eclipse.core.resources.IResource;
35: import org.eclipse.core.runtime.Assert;
36: import org.eclipse.core.runtime.CoreException;
37: import org.eclipse.core.runtime.IProgressMonitor;
38: import org.eclipse.core.runtime.IStatus;
39: import org.eclipse.core.runtime.Status;
40: import org.eclipse.core.runtime.jobs.Job;
41: import org.eclipse.swt.widgets.Shell;
42: import org.overture.ast.definitions.SClassDefinition;
43: import org.overture.ast.intf.lex.ILexLocation;
44: import org.overture.ast.lex.CoverageUtil;
45: import org.overture.ast.lex.Dialect;
46: import org.overture.ast.lex.LexLocation;
47: import org.overture.ast.modules.AModuleModules;
48: import org.overture.config.Settings;
49: import org.overture.ide.core.IVdmModel;
50: import org.overture.ide.core.resources.IVdmProject;
51: import org.overture.ide.plugins.latex.LatexPlugin;
52: import org.overture.ide.ui.VdmUIPlugin;
53: import org.overture.ide.ui.utility.VdmTypeCheckerUi;
54: import org.overture.interpreter.runtime.LatexSourceFile;
55:
56: public class LatexUtils extends LatexUtilsBase
57: {
58:         private Shell shell;
59:
60:         public LatexUtils(Shell shell)
61:         {
62:                 this.shell = shell;
63:         }
64:
65:         public void makeLatex(final IVdmProject selectedProject,
66:                         final Dialect dialect)
67:         {
68:                 final Job expandJob = new Job("Generating tex files.")
69:                 {
70:
71:                         @Override
72:                         protected IStatus run(IProgressMonitor monitor)
73:                         {
74:
75:                                 monitor.worked(IProgressMonitor.UNKNOWN);
76:                                 try
77:                                 {
78:                                         IProject project = (IProject) selectedProject.getAdapter(IProject.class);
79:                                         IVdmProject vdmProject = (IVdmProject) project.getAdapter(IVdmProject.class);
80:                                         Assert.isNotNull(project, "Project could not be adapted");
81:
82:                                         File projectRoot = project.getLocation().toFile();
83:                                         File outputFolder = LatexBuilder.makeOutputFolder(project);
84:                                         
85:                                         PdfBuilder latexBuilder = null;
86:                                         if (LatexPlugin.usePdfLatex())
87:                                         {
88:                                                 latexBuilder = new LatexBuilder();
89:                                         } else
90:                                         {
91:                                                 latexBuilder = new XetexBuilder();
92:                                         }
93:
94:                                         latexBuilder.prepare(project, dialect);
95:
96:                                         File outputFolderForGeneratedModelFiles = new File(outputFolder, "specification");
97:                                         if (!outputFolderForGeneratedModelFiles.exists())
98:                                         {
99:                                                 outputFolderForGeneratedModelFiles.mkdirs();
100:                                         }
101:
102:                                         IVdmModel model = selectedProject.getModel();
103:                                         if (model == null || !model.isTypeCorrect())
104:                                         {
105:                                                 shell.getDisplay().asyncExec(new Runnable()
106:                                                 {
107:
108:                                                         public void run()
109:                                                         {
110:                                                                 VdmTypeCheckerUi.typeCheck(shell, selectedProject);
111:
112:                                                         }
113:                                                 });
114:
115:                                         }
116:                                         // TODO: Check whether this must be the else case of (model == null || !model.isTypeCorrect())
117:                                         // if ()
118:                                         // {
119:                                                 // Set the dialect to be used in the objects generating the TeX files
120:                                                 Settings.dialect = dialect;
121:
122:                                                 // Obtain user settings for TeX generation options
123:                                                 boolean modelOnly = modelOnly(vdmProject);
124:                                                 boolean coverageTable = insertCoverageTable(vdmProject);
125:                                                 boolean markCoverage = markCoverage(vdmProject);
126:
127:                                                 
128:                                                 // Prepare coverage highlighting
129:                                                 LexLocation.resetLocations();
130:                                                 
131:                                                 // Compute the model files (either VDM module or class containing files)
132:                                                 List<File> modelFiles = new Vector<File>();
133:
134:                                                 if (selectedProject.getDialect() == Dialect.VDM_PP
135:                                                                 || selectedProject.getDialect() == Dialect.VDM_RT)
136:                                                         modelFiles = parseClasses(selectedProject)
137:                                                                         .stream()
138:                                                                         .map((SClassDefinition::getLocation))
139:                                                                         .map(ILexLocation::getFile)
140:                                                                         .collect(Collectors.toList());
141:                                                 
142:                                          if (selectedProject.getDialect() == Dialect.VDM_SL)                        
143:                                                  modelFiles = parseModules(selectedProject)
144:                                                                  .stream()
145:                                                                  .map(AModuleModules::getFiles)
146:                                                                  .flatMap(List::stream)
147:                                                                  .collect(Collectors.toList());
148:
149:
150:                                                 
151:                                                 if (markCoverage || coverageTable)
152:                                                 {
153:                                                         List<File> outputFiles = getFileChildern(vdmProject.getModelBuildPath()
154:                                                                          .getOutput()
155:                                                                          .getLocation()
156:                                                                          .toFile())
157:                                                                          .stream().filter(file -> file.getName()
158:                                                                          .toLowerCase()
159:                                                                          .endsWith(".covtbl"))
160:                                                                          .collect(Collectors.toList());
161:
162:                                                         for (File modelFile : modelFiles)
163:                                                         {
164:                                                                 for (int i = 0; i < outputFiles.size(); i++)
165:                                                                 {
166:                                                                         File file = outputFiles.get(i);
167:                                                                                 
168:                                                                         if (file.getName().toLowerCase().endsWith(".covtbl")
169:                                                                                         && modelFile.getName().equals(getFileName(file)))
170:                                                                         {
171:                                                                                 LexLocation.mergeHits(modelFile, file);
172:                                                                                 outputFiles.remove(i);
173:
174:                                                                         }
175:                                                                 }
176:                                                         }                
177:                                                 }
178:                                                         
179:                                                 CoverageUtil coverageUtil = new CoverageUtil(LexLocation.getAllLocations(), LexLocation.getNameSpans());
180:                                                 
181:                                                 // Create TeX files for each model file
182:                                                 for (File modelFile : modelFiles)
183:                                                 {
184:                                                                 createTeXFile(latexBuilder,
185:                                                                                 outputFolderForGeneratedModelFiles,
186:                                                                                 modelFile,
187:                                                                                 modelOnly,
188:                                                                                 markCoverage,
189:                                                                                 coverageTable,
190:                                                                                 coverageUtil);
191:                                                 }
192:                                                 
193:                                                         
194:                                         //}
195:
196:                                         // Create main TeX file
197:                                         String documentFileName = selectedProject.getName() + ".tex";
198:
199:                                         latexBuilder.saveDocument(project, projectRoot, documentFileName, modelOnly);
200:                                         
201:                                         // Build the Pdf
202:                                         if (hasGenerateMainDocument(vdmProject))
203:                                         {
204:                                                 buildPdf(project, monitor, outputFolder, documentFileName);
205:                                         } else
206:                                         {
207:                                                 documentFileName = getDocument(vdmProject);
208:                                                 if (!new File(documentFileName).exists())
209:                                                 {
210:                                                         return new Status(IStatus.ERROR, LatexPlugin.PLUGIN_ID, IStatus.OK, "Main document does not exist: "
211:                                                                         + documentFileName, null);
212:                                                 }
213:                                                 outputFolder = LatexBuilder.makeOutputFolder(project);
214:                                                 buildPdf(project, monitor, outputFolder, documentFileName);
215:                                         }
216:                                 } catch (Exception e)
217:                                 {
218:
219:                                         e.printStackTrace();
220:                                         return new Status(IStatus.ERROR, LatexPlugin.PLUGIN_ID, "Unknown error", e);
221:                                 }
222:
223:                                 monitor.done();
224:
225:                                 return new Status(IStatus.OK, LatexPlugin.PLUGIN_ID, IStatus.OK, "Translation completed", null);
226:
227:                         }
228:
229:                         private void buildPdf(final IProject selectedProject,
230:                                         IProgressMonitor monitor, File outputFolder,
231:                                         String documentFileName) throws InterruptedException,
232:                                         CoreException
233:                         {
234:                                 PdfGenerator pdflatex = null;
235:                                 if (LatexPlugin.usePdfLatex())
236:                                 {
237:                                         pdflatex = new PdfLatex(selectedProject, outputFolder, documentFileName);
238:                                 } else
239:                                 {
240:                                         pdflatex = new Xetex(selectedProject, outputFolder, documentFileName);
241:                                 }
242:                                 pdflatex.start();
243:
244:                                 while (!monitor.isCanceled() && !pdflatex.isFinished()
245:                                                 && !pdflatex.hasFailed())
246:                                 {
247:                                         Thread.sleep(500);
248:                                 }
249:
250:                                 if (monitor.isCanceled() || pdflatex.hasFailed())
251:                                 {
252:                                         pdflatex.kill();
253:                                         if (pdflatex.hasFailed())
254:                                         {
255:                                                 VdmUIPlugin.logErrorMessage("PDF creation failed. Please inspect the pdf console for further information.");
256:                                         }
257:                                 } else
258:                                 {
259:                                         PdfGenerator pdflatex2 = null;
260:
261:                                         if (LatexPlugin.usePdfLatex())
262:                                         {
263:                                                 pdflatex2 = new PdfLatex(selectedProject, outputFolder, documentFileName);
264:                                         } else
265:                                         {
266:                                                 pdflatex2 = new Xetex(selectedProject, outputFolder, documentFileName);
267:                                         }
268:                                         pdflatex2.start();
269:
270:                                         while (!monitor.isCanceled() && !pdflatex2.isFinished()
271:                                                         && !pdflatex.hasFailed())
272:                                         {
273:                                                 Thread.sleep(500);
274:                                         }
275:
276:                                         if (monitor.isCanceled() || pdflatex.hasFailed())
277:                                         {
278:                                                 pdflatex2.kill();
279:                                                 if (pdflatex.hasFailed())
280:                                                 {
281:                                                         VdmUIPlugin.logErrorMessage("PDF creation failed. Please inspect the pdf console for further information.");
282:                                                 }
283:                                         }
284:                                 }
285:
286:                                 selectedProject.refreshLocal(IResource.DEPTH_INFINITE, null);
287:                         }
288:
289:                         private void createTeXFile(PdfBuilder latexBuilder,
290:                                         File outputFolder,
291:                                  File modelFile, boolean modelOnly,boolean markCoverage, boolean includeCoverageTable, CoverageUtil coverageUtil)
292:                                         throws IOException, FileNotFoundException, CoreException
293:                         {
294:                                 // Standard library files not generated
295:                                 if (modelFile.getParentFile().getName().equalsIgnoreCase("lib"))
296:                                 {
297:                                         return;
298:                                 }
299:
300:                                 // Prepare output folder
301:                                 if (!outputFolder.exists())
302:                                 {
303:                                         outputFolder.mkdirs();
304:                                 }
305:
306:
307:                                 // Prepare the TeX file for this module deleting previous version
308:                                 File texFile = new File(outputFolder, modelFile.getName().replace(" ", "") + ".tex");
309:                                 if (texFile.exists())
310:                                 {
311:                                         texFile.delete();
312:                                 }
313:
314:                                 // Compute file encoding
315:                                 IFile selectedModelFile = selectedProject.findIFile(modelFile);
316:                                 String charset = selectedModelFile.getCharset();
317:                                 
318:                                 // Generate the TeX file
319:                                 PrintWriter pw = new PrintWriter(texFile, charset);
320:                                 
321:                                 if (LatexPlugin.usePdfLatex())
322:                                 {
323:                                         new LatexSourceFile(modelFile, charset).print(pw, false, modelOnly, includeCoverageTable, markCoverage, coverageUtil);
324:                                 } else
325:                                 {
326:                                         new XetexSourceFile(modelFile, charset).print(pw, false, modelOnly, includeCoverageTable, markCoverage, coverageUtil);
327:                                 }
328:                                 pw.close();
329:                                 
330:                                 // Add the current successfully generated TeX file to the main file include list
331:                                 latexBuilder.addInclude(texFile.getAbsolutePath());
332:
333:                         }
334:
335:                 };
336:                 expandJob.setPriority(Job.BUILD);
337:                 expandJob.schedule(0);
338:
339:         }
340: }