Git地址:flutter模板项目命令
搭配 VS Code 页面生成插件 效果更佳。
更新 24/06/19
先说抱歉,之前写文件生成的时候用的 Windows
办公,脚本选取上用了 bat
,然而在 MacOS
上并不适用,所以现在重新梳理一下,选择使用了 python
来干这件事(ps:Windows我还没测试过,理论没啥问题)。
这次把模版文件做了区分,分为单页面的架子和tabs复合页面的架子(.yaml暂时没做修改,自己增删就行了)。
后续可能会把更多的基础功能加进模版中:
- 检测网络变化;
- 页面状态处理;
- ...
直接上图:
更新 24/04/02
原模版template_getx没有更新了,这里直接通过bat的生成项目进行迭代。
项目去掉了一些没啥用的文件,规整了项目结构,往更纯粹的模板走了一小步。
核心插件:
-
集大成者:
get
,可以说是包罗万千了状态管理、路由、国际化、主题切换等等,用着还是蛮爽的,嘿嘿。 顺便吐槽下,作者好像很久没发版了,有点瑟瑟发抖...,在想要不要重新投入riverpod
的怀抱; -
网络请求:
dio
+retrofit
, 之前有个文章写到过有兴趣可以看看; -
刷新加载:
easy_refresh
+infinite_scroll_pagination
,前者不用多说,后者是一个分页控制器,之前也写过,唯一不同就是分页控制的使用,反正合理选择吧; -
数据模型:
freezed
也是注解操作,比较简单,就是文件太多之后就有点慢了,生成太多了...,推荐一个 json -> freezed 的工具网站;
大致就这样吧,其他pubspec.yaml
一些常用插件,没用的可以删掉;
部分插件阐述和个人理解:
-
本地存储插件替换:
hive 4.0
->get_storage
:其实
hive
和get_storage
使用都是十分简洁的,这里做替换的目的是减少额外插件的应用,hive 4.0
需要外应用插件isar_flutter_libs
。sp
挺好,但内置方法基本都是异步操作,个人感觉用起来不方便,没有同步来得快,某些场景同步确实好用点(虽然没啥太大的区别)。 -
引入
persistent_bottom_nav_bar_v2
创建项目根路径,与get route
结合使用:persistent_bottom_nav_bar_v2
样式蛮多的,大多数需求应该都可以满足了。原来的
tabbar
是自己写的,多少还是整复杂了些,这两天过了一下pub
的库,干脆就选了一个做了一下修改,persistent_bottom_nav_bar_v2
本身是基于go_router
的,非常强大的库,最早写项目也是用的provider / riverpod (注解模式是真的棒)
和go_router
这两黄金搭档。但后来入职公司同事们都用get
大缸了,那没办法按部就班的干呗。这里说下赋值
GetPage
中的binding
可以减少controller
书写创建相关的代码,或者说Bind.lazyPut(...)
后就不用特别去关心了,所以为了方便路由选择方面,也就使用了get route
了,但是个人理解来讲根导航是真没get到作者的点,所以重写tabbar
也是必经之路。get 5.0
中从作者的插件demo中可以了解到,bind (升级前是:binding)
和controller
两已然成为了不可分割的一个整体了,毕竟在GetPage
属性binding
继承于abstract class BindingsInterface<dynamic>?
,一个抽象类型,没错必须自己创建并继承他,我们才能更偷懒规范的书写路由配置列表。是的get 4.0
直接通过block赋值的操作没有了。
注:tabbar各个主页面的路由就不用写入 routes->app_pages.dart
中了,直接在TabbarBinding
中进行注入。
class TabbarBinding extends Binding {
@override
List<Bind> dependencies() {
return [
Bind.lazyPut<TabbarController>(
() => TabbarController(),
),
// tabbar 分页懒加载binding
...HomeBinding().dependencies(),
...MessageBinding().dependencies(),
...MineBinding().dependencies(),
];
}
部分贴图,没力码字了。
![]() | ![]() |
![]() | ![]() |
更新 23/09/13
文章中项目生成脚本同步升级。
原模版template_getx项目,使用get_cli
生成页面文件后目录结构过于复杂,现在更新基于 get: ^5.0.0-release-candidate-5 的VSCode文件生成插件 vsc_getx_create 生成对应文件结构(view.dart、page.dart、controller.dart ...),更灵活也更快捷。
vsc_getx_create
插件属于二次修改的VSCode插件,属于本地插件导入,详情可参见 README.md
。
具体结构如下图所示:
前言
对于flutter项目的配置从官方角度来说,其实已经够简单了。但是从实际业务出发,我们往往会多出一些公共的配置、插件、归纳甚至更多自定义的东西。这就对我们新起项目造成了不小的困扰:
- 公共的文件迁移(复制到新项目后一堆警告与错误);
- 公共插件的引入,在
.yaml
中补全插件; - 多文件的相互引用(
import
有时候会拼接项目名称,例如:import 'package:xxx/xxx.dart
,或者相对路径层级不对); - 对新项目
main.dart
文件的修改(这个其实可以抽离实现主体,在main.dart
文件中直接runApp(...)
,不做其他操作); - 基础图片资源的重复导入;
- 或者其他;
上述问题相信看到这里的小伙伴多少有点感同身受吧。博主一直想写一个自用模板项目的脚本,但苦于对文件生成脚本生疏(主要还是太懒 ( ̄▽ ̄)"),一直没有实现这个伟大的抱负,直到遇见了她 # batch: flutter插件工程模版的创建,好嘛,该我(依)大(葫)显(芦)身(画)手(瓢)的时候到了!!!
正文
我们先抛开文件的创建,文件内容的填充或者整体文件夹的复制,这些实际脚本操作是如何实现的。优先梳理一下对于我们想要生成的最终产物,需要得到些什么需要做什么。
这里针对我自己的模板项目 template_getx 而言
- 首先我们需要创建基础的项目结构
flutter create xxx ...
; - 然后再往创建的结构中添加下列内容(添加顺序随意):
- 常用插件的引入;
- 项目模块(文件夹分类)的划分;
- 公共文件的引入;
main.dart
文件的修改;- 基础资源
Assets
文件的引入;
- 完成添加后执行相应的
flutter
命令; - 最后得到完整的项目
最终得到的产物是一个可直接运行,带tabbar的模板项目。
1、使用脚本的过程
2、生成的模板项目结构
下面开始具体说说batch
的实现,因为不熟悉batch的所有命令,所以这里只对使用到的阐述一下( ( ̄▽ ̄)",其他使用可以谷歌、可以ChatGPT)。
1、脚本静态展示(LOGO+提示文本)
echo +---------------------------------------------------------------------------------+
call :showLogo
echo This script will guide you through creating a flutter project with specified
echo dependencies and file directories.
echo.
echo +---------------------------------------------------------------------------------+
echo
:可以为终端输出显示,后续也用到输出具体内容到目标文件
:showLogo
:自定义的标签,具体实现是为了显示打开终端显示自定义的LOGO;
:showLogo
if not exist .outlogo (
echo CiAgX18gICAgICAgX19fX18gICAgIF9fX19fXyAgICAgIF9fX19fICAgIAogL1xfXCAgICAgKSBfX18gKCAgIC9fL1xfX19cICAgICkgX19fICggICAKKCAoICggICAgLyAvXF8vXCBcICApICkgX19fLyAgIC8gL1xfL1wgXCAgCiBcIFxfXCAgLyAvXy8gKF9cIFwvXy8gLyAgX19fIC8gL18vIChfXCBcIAogLyAvIC9fX1wgXCApXy8gLyAvXCBcIFxfL1xfX1xcIFwgKV8vIC8gLyAKKCAoX19fX18oXCBcL19cLyAvICApXykgIFwvIF8vIFwgXC9fXC8gLyAgCiBcL19fX19fLyApX19fX18oICAgXF9cX19fXy8gICAgKV9fX19fKCAgIAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAK>.logo
certutil -decode .logo .outlogo>nul
del .logo
)
type .outlogo
goto :eof
判断是否添加自定义的LOGO,如果没有则输出默认内容。
.outlogo
:自己添加的LOGO内容的文件
goto :eof
:继续执行后续脚本
2、提示输入项目名称
:inputProjectName
set /p projectName= Input project name:
if "%projectName%"=="" goto input
if "%projectName%"=="test" (
call :error "'test' is not allowed as a project name, enter another name."
goto inputProjectName
)
给定固定的提示语句,提示用户输入需要生成的flutter
项目名称,如果不输入则重复提示输入。
goto inputProjectName
:指定执行bat命令的标签(提示重复输入)
3、提示输入flutter项目的组织机构
:inputProjecOrg
set /p projectOrg= Input project organization (such as com.example), or press Entry to use default:
if "%projectOrg%"=="" (
set "projectOrg=com.example"
)
定义变量projectOrg
接收用户输入内容,如果不输入则使用默认的组织机构名称,set "projectOrg=com.example"
为设置默认组织机构。
4、提示输入项目输出路径
:inputProject
set /p v= Input project path(such as D:\FlutterWorkspace\Porjects), or press Entry to use default:
if not "%v%"=="" call :changeDir %v%
set projectPath=%cd%\%projectName%
echo [INFO] Project path is: %projectPath%
提示输入项目输出路径,如果不输入则默认创建到create.bat
脚本的同级目录下,建议测试命令是否正常输出可以不输入,正常项目还是有必要输入具体的项目路径的。
:changeDir
:创建输入的项目路径,如果创建失败则返回重新输入。
5、执行flutter create
call :print "Start creating new flutter plugin project..."
echo flutter create --platforms=ios,android --org %projectOrg% --pub %projectName%>temp.bat
call temp.bat
if errorlevel 1 (
echo [INFO] Your flutter version is too low please update.
echo flutter create --org %projectOrg% --pub %projectName%>temp.bat
call temp.bat
)
del temp.bat
这里主要是创建基本的项目结构,方便后续修改为自己的项目模板。 flutter create --platforms=ios,android --org %projectOrg% --pub %projectName%
该命令可以拼接其他的操作,输入需要用书输入则可以提供终端输入变量的模式。
6、插入模板项目的文件(夹)
:createFolders
call :print "Generate configuration files..."
xcopy "%scriptPath%\files" "%1\lib\" /E /I /Y
set "source_folder=%scriptPath%\assets"
xcopy "%source_folder%" "%projectPath%\assets" /S /I /Y /V >nul
goto :eof
%1
:是标签:createFolders
传递的变量%projectPath%
具体值为flutter
项目路径;
%scriptPath%
:是当前脚本所在的目录路径;
xcopy "%scriptPath%\files" "%1\lib\" /E /I /Y
:复制当前脚本同级文件夹files
下的所有内容至,flutter
项目路径lib
下;
xcopy "%source_folder%" "%projectPath%\assets" /S /I /Y /V >nul
:复制静态资源至项目路径;
/E
:复制包括子文件夹和空文件夹在内的所有文件和文件夹;/I
:如果目标目录不存在,则会自动创建目标文件夹;/Y
:确认所有覆盖操作,即在目标文件夹中存在同名文件时自动覆盖;/S
参数表示递归复制子文件夹中的文件;/V
参数用于显示详细的复制操作日志;
7、.yaml文件中添加常用插件
@REM 添加设置依赖
:addFlutterDependency
call :print "Insert dependency..."
set pubspec=%1\pubspec.yaml
REM 读取 pubspec.yaml 文件内容
for /f "eol== delims=" %%a in (%pubspec%) do (
set "line=%%a"
setlocal enabledelayedexpansion
REM 将当前行写入临时文件
echo !line!>> %pubspec%.tmp
REM 查找 cupertino_icons 行
echo !line! | findstr /i /c:"cupertino_icons:" >nul
if !errorlevel! equ 0 (
REM 在 cupertino_icons 行之后插入新的依赖项
@REM echo !line!>> %pubspec%.tmp
echo flutter_localizations:>> %pubspec%.tmp
echo sdk: flutter>> %pubspec%.tmp
echo get: ^^5.0.0-release-candidate-4>> %pubspec%.tmp
echo json_annotation: ^^4.8.1>> %pubspec%.tmp
echo freezed_annotation: ^^2.2.0>> %pubspec%.tmp
echo flutter_hooks: ^^0.18.6>> %pubspec%.tmp
echo hive_flutter: ^^1.1.0>> %pubspec%.tmp
echo bot_toast: ^^4.0.3>> %pubspec%.tmp
echo easy_refresh: ^^3.0.5>> %pubspec%.tmp
echo dio: ^^5.0.2>> %pubspec%.tmp
echo retrofit: ^^4.0.1>> %pubspec%.tmp
echo flutter_spinkit: ^^5.1.0>> %pubspec%.tmp
echo simple_animations: ^^5.0.0+3>> %pubspec%.tmp
echo cached_network_image: ^^3.2.2>> %pubspec%.tmp
echo event_bus: ^^2.0.0>> %pubspec%.tmp
echo logger: ^^1.2.2>> %pubspec%.tmp
echo star_menu: ^^3.1.4>> %pubspec%.tmp
echo # 启动图: flutter pub run flutter_native_splash:create>> %pubspec%.tmp
echo # flutter_native_splash: ^^2.3.0>> %pubspec%.tmp
)
REM 查找 flutter_lints 行
echo !line! | findstr /i /c:"flutter_lints:" >nul
if !errorlevel! equ 0 (
REM 在 flutter_lints 行之后插入新的依赖项
@REM echo !line!>> %pubspec%.tmp
echo build_runner: ^^2.3.3>> %pubspec%.tmp
echo flutter_gen_runner: ^^5.2.0>> %pubspec%.tmp
echo json_serializable: ^^6.7.0>> %pubspec%.tmp
echo freezed: ^^2.3.5>> %pubspec%.tmp
echo retrofit_generator: ^^6.0.0+1>> %pubspec%.tmp
echo # 一键生成启动图标: flutter pub run flutter_launcher_icons>> %pubspec%.tmp
echo # flutter_launcher_icons: ^^0.13.1>> %pubspec%.tmp
)
REM 查找 assets 行
echo !line! | findstr /i /c:"uses-material-design:" >nul
if !errorlevel! equ 0 (
REM 在 uses-material-design 行之后插入新的依赖项
echo assets:>> %pubspec%.tmp
echo - assets/images/>> %pubspec%.tmp
)
endlocal
)
REM 在文件末尾插入自定义内容
echo.>> %pubspec%.tmp
echo flutter_gen:>> %pubspec%.tmp
echo output: lib/support_files/>> %pubspec%.tmp
echo line_length: 80>> %pubspec%.tmp
REM 将临时文件替换回原始文件
move /y %pubspec%.tmp %pubspec% >nul
goto :eof
-for /f "eol== delims=" %%a in (%pubspec%) do
:循环遍历.yaml文件每一行内容,判断是否有符合条件的行,并在该行后插入需要添加的插件。文末内容的添加直接添加至循环以外就可以了。
setlocal enabledelayedexpansion
:设置本地为延迟扩展。
在cmd执行命令前会对脚本进行预处理,其中有一个过程是变量识别过程,在这个过程中,如果有两个%括起来的如%value%类似这样的变量,就会对其进行识别,并且查找这个变量对应的值,再而将值替换掉这个变量,这个替换值的过程,就叫做变量扩展,然后再执行命令。
echo ... >> %pubspec%.tmp
:将内容写入到临时文件,结束所有操作后替换掉项目原有的pubspec.yaml
。
echo !line! | findstr /i /c:"cupertino_icons:" >nul
:执行输出当前行!line!
中是否包含cupertino_icons:
,如果成功执行则后续判断表示满足我们想要插入的内容的行,否则不插入自定义内容,具体内容按规划插入就可以了。后续的几个判断都是类似的处理方式。
!errorlevel!
:为前一句语句的执行状态,0
表示执行成功;1
表示执行失败。
move /y %pubspec%.tmp %pubspec% >nu
:将临时文件替换掉我们原有的项目文件,完成插件插值。
8、执行flutter命令
:flutterCLI
call :print "Run flutter CLI..."
REM 进入指定文件夹
cd /d "%projectPath%"
REM 运行命令
echo flutter pub get>temp.bat
call temp.bat
del temp.bat
echo flutter pub run build_runner build>temp.bat
call temp.bat
del temp.bat
REM 返回到原始目录
cd /d "%~dp0"
exit /b
goto :eof
在VS Code
编辑器下正常来说,我们完成了步骤7
编辑器会自动更新pubspec.yaml
文件,更新我们的插件管理文件。
但是在这里我的pubspec.yaml
文件中包含build_runner
的编译内容(retrofit_generator
、freezed
等),所以需要额外执行一次flutter pub run build_runner build
。由于让编辑器自动更新插件我们无法把握pub get
完成的时机,为避免dart
命令执行的冲突,这里我直接执行插件更新,然后执行build_runner
.
cd /d "%projectPath%"
:进入到项目路径,cd /d "%~dp0"
:返回bat脚本路径。
echo flutter pub get>temp.bat
:将执行命令写入临时文件temp.bat
,
call temp.bat
:执行脚本内容,del temp.bat
:执行完毕后移除临时文件。
exit /b
:当脚本运行到“exit /b”行时,不会执行此行之后的命令,并且调用当前脚本后的命令将继续执行。
到这里整个执行流程已经完成了。
总结
batch
属于Windows下的批量执行命令,在文件操作方面感觉还是挺简单的,前提还是得对它有基本了解,迎(硬)难(着)而(头)上,还是蛮累的...( ̄- ̄)"。
-
模板项目添加的文件内容,全是
.dart
格式(方便直接读写)打开会有编译错误,但不影响使用。后续可能会对这部分内容进行整改。之前试过使用.txt
格式存档文件内容,但是在进行批量复制的时候没办法把文件修改成.dart
格式(总是有问题( ̄▽ ̄)"),后面整改的时候再处理吧,哈哈。 -
后续可能会对
template_getx
项目的使用进行简单的介绍和梳理。
使用ChatGPT附图:
bat使用推荐:BAT 批处理 常用命令 [MD]
模板项目产出灵感:flutter插件工程模版的创建