setting.vue 8.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277
  1. <!--
  2. 修改了语音开关,提供语音安装包下载途径,实际实现了语音控制
  3. 编写人:吴宝松
  4. 最后修改时间:2024.9.28
  5. 本代码是设置页面,提供设置选项。设置包括使用说明书、联系人排序方式、地理位置显示、语音播报、版本查询及更新。
  6. 编写人:张志宏
  7. 最后更新时间:8.21
  8. 修改联系人排序及来电地址显示框高度
  9. -->
  10. <template>
  11. <view class="content">
  12. <!-- 使用说明书 -->
  13. <view class="using-manual">
  14. <p class="text-left">使用说明书</p>
  15. <image class="enter-right" src="../../static/pics/enter-right.png" mode=""></image>
  16. </view>
  17. <!-- 语音播报 -->
  18. <view class="voice-broadcast" @click="toggleSwitch()">
  19. <p class="text-left">语音播报</p>
  20. <view class="icon">
  21. <image v-if="switchStatus" class="voice-switch" src="../../static/pics/switch-on.png" mode=""></image>
  22. <image v-else class="voice-switch" src="../../static/pics/switch-off.png" mode=""></image>
  23. </view>
  24. </view>
  25. <!-- 版本信息 -->
  26. <view class="version-details">
  27. <p class="text-left">当前版本</p>
  28. {{version_number}}
  29. </view>
  30. <view class="version-details" @click="contactUs">
  31. <p class="text-left">联系我们</p>
  32. <image class="enter-right" src="../../static/pics/enter-right.png" mode=""></image>
  33. </view>
  34. </view>
  35. </template>
  36. <script>
  37. export default{
  38. data(){
  39. return{
  40. version_number:"",
  41. switchStatus:false,//语音播报开关初始为关闭状态
  42. };
  43. },
  44. methods: {
  45. currentVersion() {
  46. this.version_number = "24.1";
  47. },
  48. // 判断是否为 Android 平台的 App 环境
  49. isApp() {
  50. const platform = uni.getSystemInfoSync().platform;
  51. return platform === 'android' && typeof plus !== 'undefined';
  52. },
  53. // 检测 TTS 引擎是否已安装
  54. checkTTSInstalled(packageName) {
  55. if (this.isApp()) {
  56. try {
  57. return plus.runtime.isApplicationExist({ pname: packageName });
  58. } catch (error) {
  59. console.error("检测TTS安装失败: ", error);
  60. }
  61. }
  62. return false;
  63. },
  64. // 请求 Android 权限
  65. requestAndroidPermissions(callback) {
  66. if (this.isApp()) {
  67. const main = plus.android.runtimeMainActivity();
  68. const permissions = [
  69. "android.permission.WRITE_EXTERNAL_STORAGE",
  70. "android.permission.REQUEST_INSTALL_PACKAGES"
  71. ];
  72. const ActivityCompat = plus.android.importClass("androidx.core.app.ActivityCompat");
  73. permissions.forEach(permission => {
  74. const hasPermission = ActivityCompat.checkSelfPermission(main, permission);
  75. if (hasPermission !== 0) {
  76. ActivityCompat.requestPermissions(main, [permission], 0);
  77. }
  78. });
  79. callback();
  80. }
  81. },
  82. // 安装 APK
  83. installAPK() {
  84. if (this.isApp()) {
  85. const apkPath = plus.io.convertLocalFileSystemURL("/static/tts_engine.apk");
  86. plus.runtime.install(apkPath, {}, () => {
  87. console.log('APK安装成功');
  88. this.switchStatus = true; // 安装成功后开启开关
  89. this.saveSwitchStatus(); // 保存当前开关状态
  90. }, (error) => {
  91. console.error('APK安装失败: ', error.message);
  92. });
  93. }
  94. },
  95. // 切换开关状态
  96. toggleSwitch() {
  97. const ttsPackageName = "com.iflytek.speechcloud";
  98. if (this.switchStatus) {
  99. // 关闭语音播报的逻辑
  100. console.log("关闭语音播报");
  101. // 可以添加其他关闭逻辑,例如停止 TTS 服务
  102. this.switchStatus = false; // 切换状态为关闭
  103. } else {
  104. // 开启语音播报,先请求权限再检测 TTS 是否已安装
  105. this.requestAndroidPermissions(() => {
  106. if (!this.checkTTSInstalled(ttsPackageName)) {
  107. this.installAPK();
  108. } else {
  109. console.log('TTS引擎已安装');
  110. this.switchStatus = true; // 切换状态为开启
  111. }
  112. });
  113. }
  114. this.saveSwitchStatus(); // 保存当前开关状态
  115. },
  116. // 保存当前开关状态到本地存储
  117. saveSwitchStatus() {
  118. uni.setStorageSync('voiceBroadcastSwitch', this.switchStatus);
  119. },
  120. // 初始化应用时读取本地存储的开关状态
  121. initializeApp() {
  122. const ttsPackageName = "com.iflytek.speechcloud";
  123. console.log("1111");
  124. // 从本地存储中读取开关状态
  125. const storedSwitchStatus = uni.getStorageSync('voiceBroadcastSwitch');
  126. console.log("读取的本地存储状态:", storedSwitchStatus);
  127. // 检测 TTS 引擎是否存在
  128. const isTTSInstalled = this.checkTTSInstalled(ttsPackageName);
  129. if (typeof storedSwitchStatus === 'boolean') {
  130. // 如果本地存储的开关状态为开启,但 TTS 引擎已被卸载
  131. if (storedSwitchStatus && !isTTSInstalled) {
  132. console.log("检测到本地存储为开启状态,但 TTS 引擎已被卸载,重置为关闭状态");
  133. this.switchStatus = false;
  134. uni.setStorageSync('voiceBroadcastSwitch', false); // 更新存储状态为关闭
  135. } else {
  136. this.switchStatus = storedSwitchStatus;
  137. }
  138. } else if (isTTSInstalled) {
  139. // 如果没有存储的状态,但检测到 TTS 引擎已安装,默认开启
  140. console.log("检测到 TTS 引擎已安装,默认开启语音播报");
  141. this.switchStatus = true;
  142. uni.setStorageSync('voiceBroadcastSwitch', true); // 存储状态为开启
  143. } else {
  144. // 如果没有存储的状态,且 TTS 引擎未安装,则默认关闭
  145. console.log("TTS 引擎未安装,默认关闭语音播报");
  146. this.switchStatus = false;
  147. }
  148. },
  149. contactUs() {
  150. uni.showModal({
  151. title: '联系我们',
  152. content: '邮箱:example@example.com',
  153. showCancel: false, // 是否显示取消按钮
  154. confirmText: '确定', // 确认按钮文字
  155. success: (res) => {
  156. if (res.confirm) {
  157. console.log('用户点击确定');
  158. }
  159. }
  160. });
  161. }
  162. },
  163. mounted() {
  164. this.initializeApp(); // 初始化应用
  165. },
  166. //创建时启动方法
  167. created() {
  168. this.currentVersion();
  169. }
  170. }
  171. </script>
  172. <style>
  173. .content{
  174. /*整体容器,flex布局,垂直排列子元素并居中对齐,子元素从上开始对齐,高度占满整个视口*/
  175. display: flex;
  176. align-items: center;
  177. flex-direction: column;
  178. justify-content: flex-start;
  179. width: 100vw;
  180. height: 100vh;
  181. background-color: #f0efef;
  182. }
  183. .using-manual{
  184. /*使用说明书,flex布局,文本与enter-right两侧对齐*/
  185. display: flex;
  186. align-items: center;
  187. justify-content: space-between;
  188. height: 90rpx;
  189. margin-top: 30rpx;
  190. font-size: 60rpx;
  191. font-weight: 60;
  192. }
  193. .enter-right{
  194. /*使用说明书右侧按钮,右对齐,高度,宽度。*/
  195. margin-right: 10rpx;
  196. height: 60rpx;
  197. width: 60rpx;
  198. }
  199. .numbers-of-call{
  200. margin-top: 10rpx;
  201. }
  202. .voice-broadcast{
  203. /*语音播报flex布局,space-between水平均匀分布,为每个块元素之间添加间距*/
  204. display: flex;
  205. align-items: center;
  206. justify-content: space-between;
  207. height: 90rpx;
  208. margin-bottom: 10rpx;
  209. font-size: 60rpx;
  210. font-weight: 60;
  211. }
  212. .voice-switch{
  213. margin-top: 10rpx;
  214. width: 120rpx;
  215. height: 130rpx;
  216. }
  217. .version-details {
  218. display: flex;
  219. align-items: center;
  220. justify-content: space-between;
  221. height: 90rpx;
  222. font-size: 60rpx;
  223. font-weight: 60;
  224. }
  225. .using-manual,.contact-sorting, .incoming-call-address-display,.voice-broadcast,.version-details {
  226. /*所有组件的间距、宽度、边框、内间距、背景颜色、边框弧度、左右外间距、字体类型*/
  227. margin-bottom: 10rpx;
  228. width: 90%;
  229. border: 1px solid #e0e0e0;
  230. padding: 10rpx;
  231. background-color: #ffffff;
  232. border-radius: 20rpx;
  233. margin-left: 10rpx;
  234. margin-right: 10rpx;
  235. margin-bottom: 10rpx;
  236. }
  237. .line{
  238. /*分隔线,宽度、height参数为分隔线的粗细、颜色、上下间隔*/
  239. width: 96%;
  240. height: 1rpx;
  241. background-color: #dbdbdb;
  242. margin: 9rpx 0;
  243. }
  244. .initial{
  245. text-align: left;
  246. }
  247. .text-left{
  248. text-align: left;
  249. }
  250. </style>