mirror of
https://gitee.com/dcloud/uni-preset-vue
synced 2025-04-09 15:23:08 +08:00
feat: 增加 TypeScript 默认模板
This commit is contained in:
parent
17e4396c78
commit
5d6e63dca4
142
generator.js
142
generator.js
@ -2,85 +2,95 @@ const fs = require('fs')
|
||||
const path = require('path')
|
||||
|
||||
const isBinary = require('isbinaryfile')
|
||||
// const stripJsonComments = require('strip-json-comments')
|
||||
|
||||
async function generate(dir, files, base = '') {
|
||||
async function generate (dir, files, base = '') {
|
||||
const glob = require('glob')
|
||||
|
||||
const glob = require('glob')
|
||||
|
||||
glob.sync('**/*', {
|
||||
cwd: dir,
|
||||
nodir: true
|
||||
}).forEach(rawPath => {
|
||||
const sourcePath = path.resolve(dir, rawPath)
|
||||
const filename = path.join(base, rawPath)
|
||||
|
||||
if (isBinary.sync(sourcePath)) {
|
||||
files[filename] = fs.readFileSync(sourcePath) // return buffer
|
||||
} else {
|
||||
const content = fs.readFileSync(sourcePath, 'utf-8')
|
||||
//不再移除注释,需要通过注释支持条件编译(之前移除注释,主要为了 ui.js 操作 json 文件)
|
||||
// if (sourcePath.indexOf('manifest.json') !== -1 || sourcePath.indexOf('pages.json') !== -1) {
|
||||
// files[filename] = JSON.stringify(JSON.parse(stripJsonComments(content)), null, 2)
|
||||
// } else
|
||||
if (filename.charAt(0) === '_' && filename.charAt(1) !== '_') {
|
||||
files[`.${filename.slice(1)}`] = content
|
||||
} else if (filename.charAt(0) === '_' && filename.charAt(1) === '_') {
|
||||
files[`${filename.slice(1)}`] = content
|
||||
} else {
|
||||
files[filename] = content
|
||||
}
|
||||
}
|
||||
})
|
||||
glob.sync('**/*', {
|
||||
cwd: dir,
|
||||
nodir: true
|
||||
}).forEach(rawPath => {
|
||||
const sourcePath = path.resolve(dir, rawPath)
|
||||
const filename = path.join(base, rawPath)
|
||||
|
||||
if (isBinary.sync(sourcePath)) {
|
||||
files[filename] = fs.readFileSync(sourcePath) // return buffer
|
||||
} else {
|
||||
const content = fs.readFileSync(sourcePath, 'utf-8')
|
||||
if (filename.charAt(0) === '_' && filename.charAt(1) !== '_') {
|
||||
files[`.${filename.slice(1)}`] = content
|
||||
} else if (filename.charAt(0) === '_' && filename.charAt(1) === '_') {
|
||||
files[`${filename.slice(1)}`] = content
|
||||
} else {
|
||||
files[filename] = content
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
module.exports = (api, options, rootOptions) => {
|
||||
if (options.template === 'default-ts') { // 启用 typescript
|
||||
api.extendPackage(pkg => {
|
||||
return {
|
||||
dependencies: {
|
||||
'vue-class-component': '^6.3.2',
|
||||
'vue-property-decorator': '^7.2.0'
|
||||
},
|
||||
devDependencies: {
|
||||
'@babel/plugin-syntax-typescript': '^7.2.0',
|
||||
'@dcloudio/types': '*',
|
||||
'@vue/cli-plugin-typescript': '^3.2.2',
|
||||
'typescript': api.hasPlugin('eslint') ? '~3.1.1' : '^3.0.0'
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
api.render(async function(files) {
|
||||
api.render(async function (files) {
|
||||
Object.keys(files).forEach(name => {
|
||||
delete files[name]
|
||||
})
|
||||
|
||||
Object.keys(files).forEach(name => {
|
||||
delete files[name]
|
||||
})
|
||||
const template = options.repo || options.template
|
||||
|
||||
const template = options.repo || options.template
|
||||
const base = 'src'
|
||||
|
||||
const base = 'src'
|
||||
if (template === 'default') {
|
||||
await generate(path.resolve(__dirname, './template/default'), files, base)
|
||||
} else if (template === 'default-ts') {
|
||||
await generate(path.resolve(__dirname, './template/common-ts'), files)
|
||||
await generate(path.resolve(__dirname, './template/default-ts'), files, base)
|
||||
} else {
|
||||
const ora = require('ora')
|
||||
const home = require('user-home')
|
||||
const download = require('download-git-repo')
|
||||
|
||||
if (template === 'default') {
|
||||
await generate(path.resolve(__dirname, './template/default'), files, base)
|
||||
} else {
|
||||
const ora = require('ora')
|
||||
const home = require('user-home')
|
||||
const download = require('download-git-repo')
|
||||
const spinner = ora('模板下载中...')
|
||||
spinner.start()
|
||||
|
||||
const spinner = ora('模板下载中...')
|
||||
spinner.start()
|
||||
const tmp = path.join(home, '.uni-app/templates', template.replace(/[/:]/g, '-'), 'src')
|
||||
|
||||
const tmp = path.join(home, '.uni-app/templates', template.replace(/[\/:]/g, '-'), 'src')
|
||||
if (fs.existsSync(tmp)) {
|
||||
try {
|
||||
require('rimraf').sync(tmp)
|
||||
} catch (e) {
|
||||
console.error(e)
|
||||
}
|
||||
}
|
||||
|
||||
if (fs.existsSync(tmp)) {
|
||||
try {
|
||||
require('rimraf').sync(tmp)
|
||||
} catch (e) {
|
||||
console.error(e)
|
||||
}
|
||||
}
|
||||
await new Promise((resolve, reject) => {
|
||||
download(template, tmp, err => {
|
||||
spinner.stop()
|
||||
if (err) {
|
||||
return reject(err)
|
||||
}
|
||||
resolve()
|
||||
})
|
||||
})
|
||||
|
||||
await new Promise((resolve, reject) => {
|
||||
download(template, tmp, err => {
|
||||
spinner.stop()
|
||||
if (err) {
|
||||
return reject(err)
|
||||
}
|
||||
resolve()
|
||||
})
|
||||
})
|
||||
await generate(tmp, files, base)
|
||||
}
|
||||
|
||||
await generate(tmp, files, base)
|
||||
}
|
||||
|
||||
await generate(path.resolve(__dirname, './template/common'), files)
|
||||
|
||||
})
|
||||
}
|
||||
await generate(path.resolve(__dirname, './template/common'), files)
|
||||
})
|
||||
}
|
||||
|
24
preset.json
24
preset.json
@ -1,14 +1,14 @@
|
||||
{
|
||||
"useConfigFiles": false,
|
||||
"plugins": {
|
||||
"@dcloudio/vue-cli-plugin-uni": {},
|
||||
"@vue/cli-plugin-babel": {
|
||||
"version": "3.1.1",
|
||||
"presets": [
|
||||
["@vue/app", {
|
||||
"useBuiltIns": "entry"
|
||||
}]
|
||||
]
|
||||
}
|
||||
}
|
||||
"useConfigFiles": false,
|
||||
"plugins": {
|
||||
"@dcloudio/vue-cli-plugin-uni": {},
|
||||
"@vue/cli-plugin-babel": {
|
||||
"version": "3.2.2",
|
||||
"presets": [
|
||||
["@vue/app", {
|
||||
"useBuiltIns": "entry"
|
||||
}]
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
86
prompts.js
86
prompts.js
@ -1,43 +1,47 @@
|
||||
module.exports = [{
|
||||
type: 'list',
|
||||
name: 'template',
|
||||
message: '请选择 uni-app 模板',
|
||||
choices: [{
|
||||
name: '默认模板',
|
||||
value: 'default'
|
||||
},
|
||||
{
|
||||
name: 'Hello uni-app',
|
||||
value: 'dcloudio/hello-uniapp'
|
||||
},
|
||||
{
|
||||
name: '登录模板',
|
||||
value: 'dcloudio/uni-template-login'
|
||||
},
|
||||
{
|
||||
name: '看图模板',
|
||||
value: 'dcloudio/uni-template-picture'
|
||||
},
|
||||
{
|
||||
name: '自定义模板',
|
||||
value: 'custom'
|
||||
}
|
||||
],
|
||||
default: 'None',
|
||||
},
|
||||
{
|
||||
when: answers => answers.template === 'custom',
|
||||
type: 'input',
|
||||
name: 'repo',
|
||||
message: '请输入自定义 uni-app 模板地址',
|
||||
filter(input) {
|
||||
return new Promise(function(resolve, reject) {
|
||||
if (input) {
|
||||
resolve(input)
|
||||
} else {
|
||||
reject('uni-app 模板地址不能为空')
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
type: 'list',
|
||||
name: 'template',
|
||||
message: '请选择 uni-app 模板',
|
||||
choices: [{
|
||||
name: '默认模板',
|
||||
value: 'default'
|
||||
},
|
||||
{
|
||||
name: '默认模板(TypeScript)',
|
||||
value: 'default-ts'
|
||||
},
|
||||
{
|
||||
name: 'Hello uni-app',
|
||||
value: 'dcloudio/hello-uniapp'
|
||||
},
|
||||
{
|
||||
name: '登录模板',
|
||||
value: 'dcloudio/uni-template-login'
|
||||
},
|
||||
{
|
||||
name: '看图模板',
|
||||
value: 'dcloudio/uni-template-picture'
|
||||
},
|
||||
{
|
||||
name: '自定义模板',
|
||||
value: 'custom'
|
||||
}
|
||||
],
|
||||
default: 'None'
|
||||
},
|
||||
{
|
||||
when: answers => answers.template === 'custom',
|
||||
type: 'input',
|
||||
name: 'repo',
|
||||
message: '请输入自定义 uni-app 模板地址',
|
||||
filter (input) {
|
||||
return new Promise(function (resolve, reject) {
|
||||
if (input) {
|
||||
resolve(input)
|
||||
} else {
|
||||
reject(new Error('uni-app 模板地址不能为空'))
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
]
|
||||
|
34
template/common-ts/tsconfig.json
Normal file
34
template/common-ts/tsconfig.json
Normal file
@ -0,0 +1,34 @@
|
||||
{
|
||||
"compilerOptions": {
|
||||
"target": "esnext",
|
||||
"module": "esnext",
|
||||
"strict": true,
|
||||
"jsx": "preserve",
|
||||
"importHelpers": true,
|
||||
"moduleResolution": "node",
|
||||
"esModuleInterop": true,
|
||||
"allowSyntheticDefaultImports": true,
|
||||
"experimentalDecorators":true,
|
||||
"sourceMap": true,
|
||||
"baseUrl": ".",
|
||||
"types": [
|
||||
"webpack-env",
|
||||
"@dcloudio/types/uni-app"
|
||||
],
|
||||
"paths": {
|
||||
"@/*": [
|
||||
"./src/*"
|
||||
]
|
||||
},
|
||||
"lib": [
|
||||
"esnext",
|
||||
"dom",
|
||||
"dom.iterable",
|
||||
"scripthost"
|
||||
]
|
||||
},
|
||||
"exclude": [
|
||||
"node_modules",
|
||||
"unpackage"
|
||||
]
|
||||
}
|
@ -1,24 +1,24 @@
|
||||
const plugins = []
|
||||
process.UNI_LIBRARIES = process.UNI_LIBRARIES || ['@dcloudio/uni-ui']
|
||||
process.UNI_LIBRARIES.forEach(libraryName => {
|
||||
plugins.push([
|
||||
'import',
|
||||
{
|
||||
'libraryName': libraryName,
|
||||
'customName': (name) => {
|
||||
return `${libraryName}/lib/${name}/${name}`
|
||||
}
|
||||
}
|
||||
])
|
||||
plugins.push([
|
||||
'import',
|
||||
{
|
||||
'libraryName': libraryName,
|
||||
'customName': (name) => {
|
||||
return `${libraryName}/lib/${name}/${name}`
|
||||
}
|
||||
}
|
||||
])
|
||||
})
|
||||
module.exports = {
|
||||
presets: [
|
||||
[
|
||||
'@vue/app',
|
||||
{
|
||||
useBuiltIns: 'entry'
|
||||
}
|
||||
]
|
||||
],
|
||||
plugins
|
||||
presets: [
|
||||
[
|
||||
'@vue/app',
|
||||
{
|
||||
useBuiltIns: 'entry'
|
||||
}
|
||||
]
|
||||
],
|
||||
plugins
|
||||
}
|
||||
|
@ -1,9 +1,9 @@
|
||||
const pkg = require('./package.json')
|
||||
module.exports = {
|
||||
plugins: [
|
||||
require('autoprefixer')({
|
||||
browsers: pkg.browserslist
|
||||
}),
|
||||
require('@dcloudio/vue-cli-plugin-uni/packages/postcss')
|
||||
]
|
||||
plugins: [
|
||||
require('autoprefixer')({
|
||||
browsers: pkg.browserslist
|
||||
}),
|
||||
require('@dcloudio/vue-cli-plugin-uni/packages/postcss')
|
||||
]
|
||||
}
|
||||
|
19
template/default-ts/App.vue
Executable file
19
template/default-ts/App.vue
Executable file
@ -0,0 +1,19 @@
|
||||
<script lang="ts">
|
||||
import Vue from 'vue';
|
||||
export default Vue.extend({
|
||||
mpType: 'app',
|
||||
onLaunch() {
|
||||
console.log('App Launch')
|
||||
},
|
||||
onShow() {
|
||||
console.log('App Show')
|
||||
},
|
||||
onHide() {
|
||||
console.log('App Hide')
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
||||
<style>
|
||||
/*每个页面公共css */
|
||||
</style>
|
6
template/default-ts/main.ts
Executable file
6
template/default-ts/main.ts
Executable file
@ -0,0 +1,6 @@
|
||||
import Vue from 'vue'
|
||||
import App from './App.vue'
|
||||
|
||||
Vue.config.productionTip = false
|
||||
|
||||
new App().$mount()
|
55
template/default-ts/manifest.json
Executable file
55
template/default-ts/manifest.json
Executable file
@ -0,0 +1,55 @@
|
||||
{
|
||||
"name": "",
|
||||
"appid": "",
|
||||
"description": "",
|
||||
"versionName": "1.0.0",
|
||||
"versionCode": "100",
|
||||
"transformPx":false,
|
||||
"app-plus": { /* 5+App特有相关 */
|
||||
"modules": { /* 模块配置 */
|
||||
|
||||
},
|
||||
"distribute": { /* 应用发布信息 */
|
||||
"android": { /* android打包配置 */
|
||||
"permissions": ["<uses-permission android:name=\"android.permission.CHANGE_NETWORK_STATE\"/>",
|
||||
"<uses-permission android:name=\"android.permission.MOUNT_UNMOUNT_FILESYSTEMS\"/>",
|
||||
"<uses-permission android:name=\"android.permission.READ_CONTACTS\"/>",
|
||||
"<uses-permission android:name=\"android.permission.VIBRATE\"/>",
|
||||
"<uses-permission android:name=\"android.permission.READ_LOGS\"/>",
|
||||
"<uses-permission android:name=\"android.permission.ACCESS_WIFI_STATE\"/>",
|
||||
"<uses-feature android:name=\"android.hardware.camera.autofocus\"/>",
|
||||
"<uses-permission android:name=\"android.permission.WRITE_CONTACTS\"/>",
|
||||
"<uses-permission android:name=\"android.permission.ACCESS_NETWORK_STATE\"/>",
|
||||
"<uses-permission android:name=\"android.permission.CAMERA\"/>",
|
||||
"<uses-permission android:name=\"android.permission.RECORD_AUDIO\"/>",
|
||||
"<uses-permission android:name=\"android.permission.GET_ACCOUNTS\"/>",
|
||||
"<uses-permission android:name=\"android.permission.MODIFY_AUDIO_SETTINGS\"/>",
|
||||
"<uses-permission android:name=\"android.permission.READ_PHONE_STATE\"/>",
|
||||
"<uses-permission android:name=\"android.permission.CHANGE_WIFI_STATE\"/>",
|
||||
"<uses-permission android:name=\"android.permission.WAKE_LOCK\"/>",
|
||||
"<uses-permission android:name=\"android.permission.CALL_PHONE\"/>",
|
||||
"<uses-permission android:name=\"android.permission.FLASHLIGHT\"/>",
|
||||
"<uses-permission android:name=\"android.permission.ACCESS_COARSE_LOCATION\"/>",
|
||||
"<uses-feature android:name=\"android.hardware.camera\"/>",
|
||||
"<uses-permission android:name=\"android.permission.ACCESS_FINE_LOCATION\"/>",
|
||||
"<uses-permission android:name=\"android.permission.WRITE_SETTINGS\"/>"
|
||||
]
|
||||
},
|
||||
"ios": { /* ios打包配置 */
|
||||
|
||||
},
|
||||
"sdkConfigs": { /* SDK配置 */
|
||||
|
||||
}
|
||||
}
|
||||
},
|
||||
"quickapp": { /* 快应用特有相关 */
|
||||
|
||||
},
|
||||
"mp-weixin": { /* 小程序特有相关 */
|
||||
"appid": "",
|
||||
"setting" : {
|
||||
"urlCheck" : true
|
||||
}
|
||||
}
|
||||
}
|
16
template/default-ts/pages.json
Executable file
16
template/default-ts/pages.json
Executable file
@ -0,0 +1,16 @@
|
||||
{
|
||||
"pages": [ //pages数组中第一项表示应用启动页,参考:https://uniapp.dcloud.io/collocation/pages
|
||||
{
|
||||
"path": "pages/index/index",
|
||||
"style": {
|
||||
"navigationBarTitleText": "uni-app"
|
||||
}
|
||||
}
|
||||
],
|
||||
"globalStyle": {
|
||||
"navigationBarTextStyle": "black",
|
||||
"navigationBarTitleText": "uni-app",
|
||||
"navigationBarBackgroundColor": "#F8F8F8",
|
||||
"backgroundColor": "#F8F8F8"
|
||||
}
|
||||
}
|
41
template/default-ts/pages/index/index.vue
Normal file
41
template/default-ts/pages/index/index.vue
Normal file
@ -0,0 +1,41 @@
|
||||
<template>
|
||||
<view class="content">
|
||||
<image class="logo" src="../../static/logo.png"></image>
|
||||
<view>
|
||||
<text class="title">{{title}}</text>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
import Vue from 'vue';
|
||||
export default Vue.extend({
|
||||
data() {
|
||||
return {
|
||||
title: 'Hello'
|
||||
}
|
||||
},
|
||||
onLoad() {
|
||||
|
||||
},
|
||||
methods: {
|
||||
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
||||
<style>
|
||||
.content {
|
||||
text-align: center;
|
||||
height: 400upx;
|
||||
}
|
||||
.logo{
|
||||
height: 200upx;
|
||||
width: 200upx;
|
||||
margin-top: 200upx;
|
||||
}
|
||||
.title {
|
||||
font-size: 36upx;
|
||||
color: #8f8f94;
|
||||
}
|
||||
</style>
|
BIN
template/default-ts/static/logo.png
Executable file
BIN
template/default-ts/static/logo.png
Executable file
Binary file not shown.
After ![]() (image error) Size: 3.9 KiB |
@ -6,6 +6,6 @@ Vue.config.productionTip = false
|
||||
App.mpType = 'app'
|
||||
|
||||
const app = new Vue({
|
||||
...App
|
||||
...App
|
||||
})
|
||||
app.$mount()
|
||||
|
Loading…
x
Reference in New Issue
Block a user