📜 ⬆️ ⬇️

CEF, ES6, Angular 2, WebPack 2 .Net Core desktop application without server side

This is a continuation of the articles:

CEF, ES6, Angular 2, TypeScript using .Net Core classes. Creating a cross-platform GUI for .Net using CEF
CEF, Angular 2 using .Net Core class events

The main idea of ​​these articles is to create cross-platform CEF applications using Angular 2 and .Net Core. To get rid of the server, use the fresh WebPack and configure it for local file use.

First, create package.json.
')
Package.json Contents
{ "name": "helloapp", "version": "1.0.0", "scripts": { "start": "tsc && concurrently \"tsc -w\" \"lite-server\" ", "lite": "lite-server", "tsc": "tsc", "tsc:w": "tsc -w" }, "dependencies": { "@angular/common": "~2.4.0", "@angular/compiler": "~2.4.0", "@angular/core": "~2.4.0", "@angular/forms": "~2.4.0", "@angular/http": "~2.4.0", "@angular/platform-browser": "~2.4.0", "@angular/platform-browser-dynamic": "~2.4.0", "@angular/router": "~3.4.0", "@angular/upgrade": "~2.4.0", "angular-in-memory-web-api": "~0.2.4", "babel-preset-es2015": "^6.22.0", "babel-preset-es2016": "^6.22.0", "babel-preset-react": "^6.23.0", "bootstrap": "^3.3.7", "core-js": "^2.4.1", "css-loader": "^0.26.1", "jquery": "^3.1.1", "postcss-loader": "^1.3.0", "raw-loader": "^0.5.1", "reflect-metadata": "^0.1.9", "rxjs": "^5.1.1", "sass-loader": "^6.0.0", "style-loader": "^0.13.1", "systemjs": "^0.20.7", "to-string-loader": "^1.1.5", "ts-loader": "^2.0.0", "typescript": "^2.1.6", "webpack": "^2.2.0", "webpack-fail-plugin": "^1.0.5", "webpack-notifier": "^1.5.0", "zone.js": "^0.7.7" }, "devDependencies": { "@types/core-js": "^0.9.35", "@types/node": "^6.0.46", "babel-core": "6.23.1", "babel-eslint": "7.1.1", "babel-loader": "6.3.0", "babel-plugin-__coverage__": "^11.0.0", "babel-polyfill": "^6.0.0", "babel-preset-angular2": "^0.0.2", "babel-preset-es2015": "^6.22.0", "bootstrap-loader": "^2.0.0-beta.20", "bootstrap-sass": "^3.3.7", "chunk-manifest-webpack-plugin": "^1.0.0", "concurrently": "^3.1.0", "css-loader": "^0.26.1", "css-to-string-loader": "^0.1.2", "extract-text-webpack-plugin": "^2.0.0-rc.3", "file-loader": "^0.10.0", "html-webpack-plugin": "^2.28.0", "jquery": "^3.1.1", "lite-server": "^2.2.2", "node-sass": "^4.5.0", "resolve-url-loader": "^1.6.1", "sass-loader": "^6.0.0", "style-loader": "^0.13.1", "typescript": "^2.1.5", "url-loader": "^0.5.7" } } 


Here are the uploaders, links to the necessary files, etc., which were selected by long searches.

You also need tsconfig.json to compile TypeScript files.

Content tsconfig.json
 { "compilerOptions": { "target": "es6", "module": "commonjs", "moduleResolution": "node", "sourceMap": true, "emitDecoratorMetadata": true, "experimentalDecorators": true, "removeComments": false, "noImplicitAny": true, "suppressImplicitAnyIndexErrors": true, "lib": [ "es6", "dom" ], "types": [ "node" ], "typeRoots": [ "node_modules/@types" ] }, "exclude": [ "node_modules", "wwwroot", "**/*.spec.ts" ], "compileOnSave": true } 


Now we can create a node_modules directory based on package.json using the npm install command from the application directory.

Before calling WebPack, you need to create several polyfills.ts files.

Content polyfills.ts
 import 'core-js/es6'; import 'core-js/es7/reflect'; require('zone.js/dist/zone'); if (process.env.ENV === 'production') { // Production } else { // Development and test Error['stackTraceLimit'] = Infinity; require('zone.js/dist/long-stack-trace-zone'); } 


Add Bootstap and JQuery links to main.ts:

 import 'jquery'; import 'bootstrap-loader'; import 'bootstrap/dist/css/bootstrap.css'; import 'bootstrap/dist/css/bootstrap-theme.css'; 

Now we have styles, glyphicons, and so on. Now let's get to the main point, namely webpack.config.js, on the basis of which the files we need will be collected.

 var webpack = require('webpack'); var HtmlWebpackPlugin = require('html-webpack-plugin'); var ExtractTextPlugin = require("extract-text-webpack-plugin"); var helpers = require('./helpers'); var babelOptions = { "presets": [ "react", [ "es2015", { "modules": false } ], "es2016" ] }; module.exports = { cache: true, entry: { polyfills: './app/polyfills.ts', main: './app/main.ts', vendor: [ 'babel-polyfill' ] }, output: { path: './wwwroot', filename: './scripts/[name].js', chunkFilename: './scripts/[chunkhash].js', publicPath: './' }, module: { rules: [{ test: /\.ts(x?)$/, exclude: /node_modules/, include: /app/, use: [ { loader: 'babel-loader', options: babelOptions }, { loader: 'ts-loader' } ] }, { test: /\.js$/, exclude: /node_modules/, include: /app/, use: [ { loader: 'babel-loader', options: babelOptions } ] }, { test: /\.html$/, loader: 'raw-loader', exclude: [helpers.root('app/index.html')] }, { test: /\.(png|jpg|jpeg|gif|svg)$/, loader: 'url-loader', query: { limit: 25000 } }, { test: /\.css$/, loader: 'css-to-string-loader!css-loader' }, { test: /\.scss$/, loaders: ['style', 'css', 'postcss', 'sass'] }, { test: /\.(woff2?|ttf|eot|svg)$/, loader: 'url-loader?limit=10000' }, { test: /bootstrap\/dist\/js\/umd\//, loader: 'imports?jQuery=jquery' } ] }, resolve: { extensions: ['.ts', '.tsx', '.js','.css'] }, plugins: [ // Workaround for angular/angular#11580 new webpack.optimize.CommonsChunkPlugin({ name: ['app', 'vendor', 'polyfills'] }), new HtmlWebpackPlugin({ template: 'app/index.html' }), new ExtractTextPlugin( { filename: 'styles.css', disable: false, allChunks: true } ), new webpack.ProvidePlugin({ jQuery: 'jquery', $: 'jquery', jquery: 'jquery' }) ] }; 

Everything is collected here to use es6 and everything is collected in several files in a directory
'./wwwroot'. Now you can run webpack --config webpack.config.js, which will create the files we need.

But we have to tweak the output index.html. For some reason for:

 <script type="text/javascript" src="././scripts/polyfills.js"></script> <script type="text/javascript" src="././scripts/vendor.js"> </script><script type="text/javascript" src="././scripts/main.js"></script> 

The extra ./ are added - by removing ./, we can run index.html in any browser. But we are interested in our cefsimple.exe:

In the file address, specify the path to index.html, for example, d: \ CEF \ CefProgects \ TestTypeScript \ TestTypeScript \ wwwroot \ index.html

And Voila, we work offline, without a Web server. If you need to connect to the server, we have everything on .Net. For example, .Net Core, WCF and ODATA clients .

It is necessary to add that I refused Routing in favor of NgSwitch

Since the project is built on systemjs.config.js, there is no support for require
which is necessary for WebPack, so that all Html code is integrated into js code.

Since I didn’t find conditional compilation in TS, for debugging you need to comment out require

 @Component({ selector: 'nav-menu', template:require('./navmenu.component.html'), styles: [require('./navmenu.component.css')] // templateUrl: 'app/navmenu/navmenu.component.html', // styleUrls: ['app/navmenu/navmenu.component.css'] }) 


And uncomment

 // templateUrl: 'app/navmenu/navmenu.component.html', // styleUrls: ['app/navmenu/navmenu.component.css'] 


source codes and programs and instructions for use can be found in previous articles at the very bottom.

Source: https://habr.com/ru/post/321898/


All Articles