1/* 2 * Copyright (c) 2022 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16import DateUtil from '@ohos/utils/src/main/ets/default/baseUtil/DateUtil' 17import RdbStoreUtil from '@ohos/utils/src/main/ets/default/baseUtil/RdbStoreUtil' 18import FolderData from '@ohos/utils/src/main/ets/default/model/databaseModel/FolderData' 19import NoteData from '@ohos/utils/src/main/ets/default/model/databaseModel/NoteData' 20import { 21 TableName, 22 NoteTableColumn, 23 SysDefFolderUuid, 24 Favorite, 25 Delete 26} from '@ohos/utils/src/main/ets/default/model/databaseModel/EnumData' 27import StyleConstants from '@ohos/utils/src/main/ets/default/constants/StyleConstants' 28import { EditContentDialog, DeleteDialog, EditTitleDialog } from './CusDialogComp' 29import FolderUtil from '@ohos/utils/src/main/ets/default/baseUtil/FolderUtil' 30import NoteUtil from '@ohos/utils/src/main/ets/default/baseUtil/NoteUtil' 31import prompt from '@system.prompt' 32import util from '@ohos.util' 33import { LogUtil } from '@ohos/utils/src/main/ets/default/baseUtil/LogUtil' 34import OperationUtils from '@ohos/utils/src/main/ets/default/baseUtil/OperationUtils' 35import mediaquery from '@ohos.mediaquery' 36import inputMethod from '@ohos.inputMethod'; 37import { folderTextMap } from '@ohos/utils/src/main/ets/default/model/NoteBaseData' 38import abilityAccessCtrl from '@ohos.abilityAccessCtrl'; 39import webview from '@ohos.web.webview'; 40 41const TAG = "NoteContentComp" 42 43var timeId: number 44 45// Note content component 46let inSetValue = AppStorage.Link('inSetValue') 47 48@Component 49export struct NoteContentComp { 50 @Consume('SelectedNoteData') selectedNoteData: NoteData 51 @StorageLink('AllNoteArray') AllNoteArray: NoteData[] = AppStorage.Link('AllNoteArray') 52 @Consume('SelectedFolderData') selectedFolderData: FolderData 53 @Consume('RefreshFlag') refreshFlag: number 54 @Consume('EditModel') editModel: boolean 55 @Consume('SectionStatus') sectionStatus: number 56 @Consume('LastSectionStatus') lastSectionStatus: number 57 @Consume('Issave') issave: number 58 @Consume('Search') search: boolean 59 @StorageLink('dpi') dpi: number = 240 60 controllerShow: webview.WebviewController = new webview.WebviewController(); 61 private editContentFlag = false 62 @State uri1: string = "" 63 private context = getContext(this) 64 @StorageLink('ScrollTopPercent') scrollTopPercent: number = 0.0 65 @StorageLink('isUpdate') isUpdate: boolean = false 66 @StorageLink('refreshCurrentNote') @Watch('isDataChange') refreshCurrentNote: boolean = false 67 @Consume('AsideWidth') asideWidth: number 68 69 isDataChange() { 70 if (!this.refreshCurrentNote) { 71 return 72 } 73 try { 74 this.controllerShow.runJavaScript("RICH_EDITOR.setHtml('" + this.selectedNoteData.content_text + "')"); 75 LogUtil.info(TAG, `runJavaScript setHtml success.`); 76 } catch (error) { 77 LogUtil.error(TAG, `runJavaScript setHtml failed.code:${JSON.stringify(error.code)}, 78 message:${JSON.stringify(error.message)}`); 79 } 80 this.refreshCurrentNote = false 81 } 82 83 storeScrollTop(scrollTop: number) { 84 if (scrollTop < 0) { 85 return 86 } 87 AppStorage.SetOrCreate<number>('ScrollTopPercent', scrollTop / this.controllerShow.getPageHeight()) 88 } 89 90 restoreScrollTop() { 91 if (!AppStorage.Has('remoteScrollTopPercent')) { 92 return 93 } 94 var scrollTopPercent = AppStorage.Get<number>('remoteScrollTopPercent') 95 if (scrollTopPercent < 0) { 96 return 97 } 98 this.controllerShow.runJavaScript( 99 'document.documentElement.scrollTop = ' + this.controllerShow.getPageHeight() * scrollTopPercent 100 ) 101 } 102 103 restoreFocus() { 104 if (!AppStorage.Has('isRemoteFocusOnSearch')) { 105 return 106 } 107 let isRemoteFocusOnSearch = AppStorage.Get<boolean>('isRemoteFocusOnSearch') 108 if (isRemoteFocusOnSearch) { 109 focusControl.requestFocus('searchInput') 110 } 111 AppStorage.Delete('isRemoteFocusOnSearch') 112 } 113 114 noteContent = { 115 callbackhtml: (html) => { 116 LogUtil.info(TAG, 'note uuid is:' + this.selectedNoteData.uuid) 117 this.selectedNoteData.content_text = NoteUtil.contrastInitType(this.selectedNoteData.content_text); 118 if (this.selectedNoteData.content_text === html ) { 119 return; 120 }; 121 this.selectedNoteData.content_text = html 122 this.selectedNoteData.modified_time = new Date().getTime() 123 let predicates_note = RdbStoreUtil.getRdbPredicates(TableName.NoteTable) 124 predicates_note.equalTo(NoteTableColumn.Uuid, this.selectedNoteData.uuid) 125 RdbStoreUtil.update(this.selectedNoteData.toNoteObject(), predicates_note, null) 126 LogUtil.info(TAG, 'update note success:' + this.selectedNoteData.uuid) 127 // save continue data 128 let continueNote: string = JSON.stringify(this.selectedNoteData.toNoteObject()) 129 AppStorage.SetOrCreate<string>('ContinueNote', continueNote) 130 LogUtil.info(TAG, "callbackhtml, set continue note success") 131 return "AceString" 132 }, 133 callbackImagePath: (imgName) => { 134 // updata note image 135 LogUtil.info(TAG, 'note imgName is:' + imgName) 136 this.selectedNoteData.content_img = imgName 137 }, 138 139 callbackhtmlSave: (html) => { 140 LogUtil.info(TAG, 'note uuid is:' + this.selectedNoteData.uuid) 141 this.selectedNoteData.content_text = html 142 this.selectedNoteData.modified_time = new Date().getTime() 143 let predicates_note = RdbStoreUtil.getRdbPredicates(TableName.NoteTable) 144 predicates_note.equalTo(NoteTableColumn.Uuid, this.selectedNoteData.uuid) 145 RdbStoreUtil.update(this.selectedNoteData.toNoteObject(), predicates_note, null) 146 LogUtil.info(TAG, 'update note success:' + this.selectedNoteData.uuid) 147 this.sectionStatus = this.lastSectionStatus 148 this.sectionStatus = mediaquery.matchMediaSync('(width < 2000)').matches ? 2 : 3 149 // save continue data 150 let continueNote: string = JSON.stringify(this.selectedNoteData.toNoteObject()) 151 AppStorage.SetOrCreate<string>('ContinueNote', continueNote) 152 AppStorage.SetOrCreate<number>('ContinueSection', this.sectionStatus) 153 LogUtil.info(TAG, "callbackhtmlSave, set continue note and section success") 154 return "AceString" 155 }, 156 157 callbackScheduledSave: (html) => { 158 LogUtil.info(TAG, 'callbackScheduledSave') 159 if (this.selectedNoteData.content_text == html) { 160 LogUtil.info(TAG, 'callbackScheduledSave the same value return') 161 return; 162 } 163 this.selectedNoteData.content_text = html 164 this.selectedNoteData.modified_time = new Date().getTime() 165 let predicates_note = RdbStoreUtil.getRdbPredicates(TableName.NoteTable) 166 predicates_note.equalTo(NoteTableColumn.Uuid, this.selectedNoteData.uuid) 167 RdbStoreUtil.update(this.selectedNoteData.toNoteObject(), predicates_note, null) 168 LogUtil.info(TAG, 'callbackScheduledSave, update note success:' + this.selectedNoteData.uuid) 169 // save continue data 170 let continueNote: string = JSON.stringify(this.selectedNoteData.toNoteObject()) 171 AppStorage.SetOrCreate<string>('ContinueNote', continueNote) 172 LogUtil.info(TAG, 'callbackScheduledSave, set continue note success') 173 }, 174 175 callbackPasteImage: (html) => { 176 if (html) { 177 LogUtil.info(TAG, 'paste info' + html) 178 let realHtml = "" 179 let base64regex = /^([0-9a-zA-Z+/]{4})*(([0-9a-zA-Z+/]{2}==)|([0-9a-zA-Z+/]{3}=))?$/ 180 if (html && html.indexOf("base64") > 0) { 181 LogUtil.info(TAG, " getSrcFromHtml, src[1] : " + html) 182 let imgData = html.split(',')[1]; 183 let imgType = 'png' 184 if (html.indexOf("jpeg") > 0) { 185 imgType = 'jpg' 186 } else if (html.indexOf("gif") > 0) { 187 imgType = 'gif' 188 } 189 let filePath = "" 190 if (base64regex.test(imgData)) { 191 let base64 = new util.Base64() 192 let decodeArr = base64.decodeSync(imgData) 193 filePath = OperationUtils.saveImageData(decodeArr, imgType) 194 } else { 195 filePath = OperationUtils.saveImage(imgData, imgType) 196 } 197 realHtml = "file://" + filePath 198 } 199 LogUtil.info(TAG, 'paste info11-' + realHtml) 200 this.controllerShow.runJavaScript("javascript:RICH_EDITOR.insertImageHtml('" + realHtml + "')") 201 LogUtil.info(TAG, 'paste info11--' + realHtml) 202 } else { 203 LogUtil.info(TAG, 'paste info22225') 204 } 205 }, 206 callbackGetSize: (fontSize) => { 207 if (fontSize === 16) { 208 this.selectedNoteData.slider_value = 0 209 } else if (fontSize === 18) { 210 this.selectedNoteData.slider_value = 4 211 } else if (fontSize === 24) { 212 this.selectedNoteData.slider_value = 8 213 } else if (fontSize === 32) { 214 this.selectedNoteData.slider_value = 12 215 } else if (fontSize === 48) { 216 this.selectedNoteData.slider_value = 16 217 } 218 } 219 } 220 221 build() { 222 Stack({ alignContent: Alignment.Bottom }) { 223 Flex({ direction: FlexDirection.Column, wrap: FlexWrap.NoWrap, 224 alignItems: ItemAlign.Start, alignContent: FlexAlign.SpaceAround }) { 225 Column() { 226 ToolBarComp({ controllerShow: this.controllerShow }) 227 } 228 .margin({ left: 24, right: 24 }) 229 230 Column() { 231 NoteContentOverViewComp({ controllerShow: this.controllerShow }) 232 Text(this.refreshFlag.toString()).visibility(Visibility.None) 233 Text(this.AllNoteArray.length.toString()).visibility(Visibility.None) // 用于强制刷新使用 234 235 Web({ src: $rawfile('editor.html'), controller: this.controllerShow }) 236 .javaScriptAccess(true) 237 .javaScriptProxy({ 238 object: this.noteContent, 239 name: "callBackToApp", // html--> name.method 240 methodList: ["callbackhtml", "callbackhtmlSave", "callbackScheduledSave", "callbackGetSize", "callbackPasteImage", "callbackImagePath"], 241 controller: this.controllerShow 242 }) 243 .enabled(this.sectionStatus !== 1 ? false : true) 244 .onPageEnd((e) => { 245 if (this.dpi <= 240) { 246 this.controllerShow.runJavaScript("changeSizeToRk()") 247 } else if (this.dpi <= 320 && this.dpi > 240) { 248 this.controllerShow.runJavaScript("changeSizeToPhone()") 249 } else { 250 this.controllerShow.runJavaScript("changeSizeToTablet()") 251 } 252 if (AppStorage.Get('breakPoint') !== 'sm') { 253 this.controllerShow.runJavaScript("hiddenButton()") 254 } 255 LogUtil.info(TAG, "finish loadurl") 256 if (this.selectedNoteData) { 257 let self = this 258 this.controllerShow.runJavaScript( 259 "RICH_EDITOR.setHtml('" + this.selectedNoteData.content_text + "')", 260 () => { 261 // wait for the image in the note to load 262 setTimeout(function () { 263 self.restoreScrollTop() 264 self.restoreFocus() 265 }, 100) 266 } 267 ) 268 } 269 // 初次加载为为小屏预览模式 270 if (this.sectionStatus != 1) { 271 this.controllerShow.runJavaScript("RICH_EDITOR.setInputEnabled(false)") 272 } 273 }) 274 .imageAccess(true) 275 .onlineImageAccess(true) 276 .fileAccess(true) 277 .domStorageAccess(true) 278 .zoomAccess(false) 279 .height('88%') 280 .width('100%') 281 .onScroll((event) => { 282 this.storeScrollTop(event.yOffset) 283 }) 284 } 285 .margin({ left: 24, right: 24 }) 286 // .width(StyleConstants.PERCENTAGE_100) 287 .enabled(this.selectedNoteData && this.selectedNoteData.is_deleted == Delete.Yes ? false : true) 288 .onClick(() => { 289 this.issave = 0 290 LogUtil.info(TAG, "editModel : " + this.editModel + ", sectionStatus : " + this.sectionStatus) 291 let isContinue = AppStorage.Get<boolean>('IsContinue') 292 LogUtil.info(TAG, "isContinue : " + isContinue) 293 // 点击第三屏进入全屏编辑模式 294 if (this.sectionStatus != 1 || isContinue) { 295 this.asideWidth = 0 296 this.lastSectionStatus = this.sectionStatus 297 this.sectionStatus = 1 298 this.controllerShow.runJavaScript("RICH_EDITOR.setInputEnabled(true)") 299 // 添加定时器:3s自动保存 300 if (timeId) { 301 clearInterval(timeId) 302 } 303 timeId = setInterval(() => { 304 this.controllerShow.runJavaScript("scheduledSaveContent()") 305 }, 3000) 306 LogUtil.info(TAG, "setInterval timeId : " + timeId) 307 // save continue data 308 AppStorage.SetOrCreate<number>('ContinueSection', this.sectionStatus) 309 LogUtil.info(TAG, "set continue section success") 310 this.editModel = !this.editModel 311 AppStorage.SetOrCreate<boolean>('IsContinue', false) 312 } 313 }) 314 } 315 .id(this.isUpdate + '') 316 .height(StyleConstants.PERCENTAGE_100) 317 .visibility(FolderUtil.getNoteCount(AppStorage.Get('AllNoteArray'), this.selectedFolderData.uuid) == 0 ? Visibility.Hidden : Visibility.Visible) 318 319 Column() { 320 } 321 .height("100%") 322 .width("100%") 323 .backgroundColor("#18181A") 324 .opacity(0.1) 325 .visibility(this.search ? Visibility.Visible : Visibility.Hidden) 326 } 327 .height(StyleConstants.PERCENTAGE_100) 328 .width(StyleConstants.PERCENTAGE_100) 329 } 330 331 aboutToAppear(): void { 332 LogUtil.info(TAG, "aboutToAppear") 333 } 334 335 aboutToDisappear(): void { 336 clearInterval(timeId) 337 LogUtil.info(TAG, "aboutToDisappear") 338 } 339} 340 341@Component 342export struct NoteContentOverViewComp { 343 @Consume('SelectedNoteData') selectedNoteData: NoteData 344 @StorageLink('AllFolderArray') @Watch('getArray') AllFolderArray: FolderData[] = [] 345 @StorageLink('CheckedNoteArray') CheckedNoteArray: NoteData[] = [] 346 @StorageLink('AllNoteArray') AllNoteArray: NoteData[] = AppStorage.Link('AllNoteArray') 347 @Consume('SelectedFolderData') selectedFolderData: FolderData 348 @Consume('EditModel') editModel: boolean 349 @Consume('SectionStatus') sectionStatus: number 350 @Consume('RefreshFlag') refreshFlag: number 351 @StorageLink('isUpdate') isUpdate: boolean = false 352 NoteDataMoveArray: FolderData[] 353 controllerShow: WebviewController 354 editTitleDialogCtl: CustomDialogController = new CustomDialogController({ 355 builder: EditTitleDialog({ confirm: this.confirm.bind(this) }), 356 alignment: DialogAlignment.Center, 357 autoCancel: false, 358 customStyle: true, 359 }) 360 361 getArray() { 362 this.NoteDataMoveArray = this.AllFolderArray.slice(2, this.AllFolderArray.length); 363 if (this.AllFolderArray[1] === undefined || this.AllFolderArray[1] === null) { 364 LogUtil.info(TAG, "this AllFolderArray[1] undefined") 365 return 366 } 367 this.NoteDataMoveArray.push(this.AllFolderArray[1]); 368 } 369 370 aboutToAppear() { 371 this.NoteDataMoveArray = this.AllFolderArray.slice(2, this.AllFolderArray.length); 372 if (this.AllFolderArray[1] === undefined || this.AllFolderArray[1] === null) { 373 LogUtil.info(TAG, "this AllFolderArray[1] undefined") 374 return 375 } 376 this.NoteDataMoveArray.push(this.AllFolderArray[1]); 377 } 378 379 aboutToDisappear() { 380 this.editTitleDialogCtl = null 381 } 382 383 confirm(newTitle: string) { 384 this.selectedNoteData.title = newTitle 385 this.selectedNoteData.modified_time = new Date().getTime() 386 let predicates_note = RdbStoreUtil.getRdbPredicates(TableName.NoteTable) 387 predicates_note.equalTo(NoteTableColumn.Uuid, this.selectedNoteData.uuid) 388 RdbStoreUtil.update(this.selectedNoteData.toNoteObject(), predicates_note, null) 389 NoteUtil.refreshAll() 390 } 391 392 @Builder MenuBuilder() { 393 Flex({ direction: FlexDirection.Column, justifyContent: FlexAlign.Center, alignItems: ItemAlign.Center }) { 394 List() { 395 if (this.NoteDataMoveArray !== undefined && this.NoteDataMoveArray !== null && this.NoteDataMoveArray !== []) { 396 ForEach(this.NoteDataMoveArray, (item) => { 397 ListItem() { 398 NoteDataMoveItemCompTablet({ folderItem: item, uuid: this.selectedNoteData.folder_uuid }) 399 } 400 .onClick(() => { 401 this.selectedNoteData.folder_uuid = item.uuid 402 let predicates_note = RdbStoreUtil.getRdbPredicates(TableName.NoteTable) 403 predicates_note.equalTo(NoteTableColumn.Uuid, this.selectedNoteData.uuid) 404 RdbStoreUtil.update(this.selectedNoteData.toNoteObject(), predicates_note, null) 405 if (this.sectionStatus != 1) { 406 this.selectedNoteData = NoteUtil.getFirstNoteData(this.AllNoteArray, this.selectedFolderData.uuid) 407 this.controllerShow.runJavaScript( 408 "RICH_EDITOR.setHtml('" + this.selectedNoteData.content_text + "')" 409 ) 410 this.refreshFlag = (this.refreshFlag == 0 ? 1 : 0) 411 } else { 412 this.selectedFolderData = FolderUtil.getFolderData(AppStorage.Get('AllFolderArray'), item.uuid) 413 } 414 // save continue data 415 let continueNote: string = JSON.stringify(this.selectedNoteData.toNoteObject()) 416 AppStorage.SetOrCreate<string>('ContinueNote', continueNote) 417 LogUtil.info(TAG, "NoteContentOverViewComp, MenuBuilder, set continue note success") 418 NoteUtil.refreshAll() 419 }) 420 }, noteItem => noteItem.uuid) 421 } 422 }.listDirection(Axis.Vertical) 423 .edgeEffect(EdgeEffect.Spring) 424 .height(this.AllFolderArray.length > 12 ? 504 : (this.AllFolderArray.length - 3) * 56) 425 } 426 .width(148) 427 .backgroundColor($r("app.color.color_fffffB")) 428 .padding({ left: 24, right: 24 }) 429 } 430 431 build() { 432 if (this.selectedNoteData) { 433 Flex({ direction: FlexDirection.Column, wrap: FlexWrap.NoWrap, 434 justifyContent: FlexAlign.SpaceBetween, alignItems: ItemAlign.Center }) { 435 Row() { 436 Text(this.selectedNoteData.title) 437 .id(this.isUpdate + '') 438 .fontSize(30) 439 .margin({ left: 0, right: 24 }) 440 .onClick(() => { 441 clearInterval(timeId) 442 this.editTitleDialogCtl.open() 443 // save continue data 444 AppStorage.SetOrCreate<number>('ContinueSection', this.sectionStatus) 445 LogUtil.info(TAG, "NoteContentComp, set continue section success") 446 }) 447 }.height(40) 448 .width(StyleConstants.PERCENTAGE_100) 449 450 Row() { 451 Text(DateUtil.formateDateForNoteContent(new Date(this.selectedNoteData.modified_time))) 452 .id(this.isUpdate + '') 453 .fontSize(12) 454 .padding({ top: 4, bottom: 4 }) 455 .fontColor($r("app.color.modified_time_font_color")) 456 .margin({ left: 0 }) 457 Row() { 458 Text(FolderUtil.getFolderText(FolderUtil.getFolderData(AppStorage.Get('AllFolderArray'), this.selectedNoteData.folder_uuid)) == 459 folderTextMap["sys_def_myFavorites_uuid"] ? folderTextMap["sys_def_unClassified_uuid"] : 460 FolderUtil.getFolderText(FolderUtil.getFolderData(AppStorage.Get('AllFolderArray'), this.selectedNoteData.folder_uuid))) 461 .id(this.isUpdate + '') 462 .fontSize(12) 463 .fontColor($r("app.color.list_modified_time_font_color")) 464 .padding({ top: 1 }) 465 Image($r('app.media.triangle')) 466 .width(6) 467 .height(12) 468 .margin({ left: 4 }) 469 } 470 .id(this.isUpdate + '') 471 .padding({ left: 8, right: 8, top: 4, bottom: 4 }) 472 .margin({ left: 8 }) 473 .borderRadius(16) 474 .backgroundColor(NoteUtil.getNoteBgColor(AppStorage.Get('AllFolderArray'), this.selectedNoteData.folder_uuid, SysDefFolderUuid.AllNotes, false)) 475 .bindMenu(this.MenuBuilder) 476 }.alignItems(VerticalAlign.Top).height(40).width(StyleConstants.PERCENTAGE_100) 477 } 478 .opacity(this.selectedNoteData.is_deleted == Delete.Yes ? 0.4 : 1) 479 .width(StyleConstants.PERCENTAGE_100) 480 .height(80) 481 } 482 } 483} 484 485@Component 486export struct ToolBarComp { 487 @Consume('SelectedNoteData') selectedNoteData: NoteData 488 @Consume('RefreshFlag') refreshFlag: number 489 @Consume('SectionStatus') sectionStatus: number 490 @Consume('LastSectionStatus') lastSectionStatus: number 491 @Consume('SelectedFolderData') selectedFolderData: FolderData 492 @Consume('ChooseNote') chooseNote: boolean 493 @Consume('PortraitModel') portraitModel: boolean 494 @StorageLink('AllNoteArray') AllNoteArray: NoteData[] = AppStorage.Link('AllNoteArray') 495 @Consume('EditModel') editModel: boolean 496 @Consume('Issave') issave: number 497 controllerShow: webview.WebviewController = new webview.WebviewController(); 498 private context = getContext(this) 499 noteDataDeleteDialogCtl: CustomDialogController = new CustomDialogController({ 500 builder: DeleteDialog({ onConfirm: this.onDeleteConfirm.bind(this) }), 501 alignment: DialogAlignment.Center, 502 autoCancel: false, 503 customStyle: true, 504 }) 505 @Consume('AsideWidth') asideWidth: number 506 507 aboutToDisappear() { 508 this.noteDataDeleteDialogCtl = null 509 this.editContentDialogCtl = null 510 } 511 512 onDeleteConfirm() { 513 if (this.selectedFolderData.uuid != SysDefFolderUuid.RecentDeletes) { 514 this.selectedNoteData.is_deleted = Delete.Yes 515 this.selectedNoteData.deleted_time = new Date().getTime() 516 // update note to db 517 let predicates_note = RdbStoreUtil.getRdbPredicates(TableName.NoteTable) 518 predicates_note.equalTo(NoteTableColumn.Uuid, this.selectedNoteData.uuid) 519 RdbStoreUtil.update(this.selectedNoteData.toNoteObject(), predicates_note, null) 520 } else { 521 NoteUtil.removeNoteData(this.AllNoteArray, this.selectedNoteData.uuid) 522 // delete note from db 523 let predicates_note = RdbStoreUtil.getRdbPredicates(TableName.NoteTable) 524 predicates_note.equalTo(NoteTableColumn.Uuid, this.selectedNoteData.uuid) 525 RdbStoreUtil.delete(predicates_note, null) 526 } 527 this.refreshFlag = (this.refreshFlag == 0 ? 1 : 0) 528 this.selectedNoteData = NoteUtil.getFirstNoteData(AppStorage.Get('AllNoteArray'), this.selectedFolderData.uuid) 529 try { 530 this.controllerShow.runJavaScript("RICH_EDITOR.setHtml('" + this.selectedNoteData.content_text! + "')"); 531 } catch (error) { 532 LogUtil.info(TAG, `setHtml error. code:${JSON.stringify(error.code)},message:${error.message}`); 533 } 534 this.chooseNote = false 535 // save continue data 536 let continueNote: string = JSON.stringify(this.selectedNoteData.toNoteObject()) 537 AppStorage.SetOrCreate<string>('ContinueNote', continueNote) 538 LogUtil.info(TAG, "NoteContentOverViewComp, set continue note success") 539 AppStorage.SetOrCreate('isUpdate', true) 540 } 541 542 editContentDialogCtl: CustomDialogController = new CustomDialogController({ 543 builder: EditContentDialog({ confirm: this.confirm.bind(this) }), 544 alignment: DialogAlignment.Bottom, 545 autoCancel: true, 546 customStyle: true, 547 }) 548 549 confirm(excuteJs: string) { 550 this.controllerShow.runJavaScript(excuteJs) 551 } 552 553 build() { 554 Flex({ direction: FlexDirection.Row, wrap: FlexWrap.NoWrap, 555 justifyContent: FlexAlign.SpaceBetween, alignItems: ItemAlign.Center }) { 556 Image(this.sectionStatus == 1 ? $r('app.media.narrow') : $r('app.media.zoom')) 557 .height(24) 558 .width(24) 559 .onClick(() => { 560 if (this.sectionStatus != 1) { 561 this.lastSectionStatus = this.sectionStatus 562 this.sectionStatus = 1 563 this.asideWidth = 0 564 this.controllerShow.runJavaScript("RICH_EDITOR.setInputEnabled(true)") 565 } else { 566 if (this.lastSectionStatus != undefined) { 567 this.asideWidth = 200 568 // 切换为小屏预览模式 569 this.controllerShow.runJavaScript("RICH_EDITOR.setInputEnabled(false)") 570 this.sectionStatus = this.lastSectionStatus 571 // 退出全屏时存库 572 LogUtil.info(TAG, "close note" + this.selectedNoteData.uuid) 573 this.controllerShow.runJavaScript("saveHtmlContent()") 574 //退出键盘 575 // @ts-ignore 576 inputMethod.getController().stopInputSession(); 577 // 清除定时器 578 if (timeId != undefined) { 579 LogUtil.info(TAG, "zoom, clearInterval timeId : " + timeId) 580 clearInterval(timeId) 581 } 582 } else { 583 this.sectionStatus = 3 584 } 585 } 586 this.editModel = !this.editModel 587 // save continue data 588 AppStorage.SetOrCreate<number>('ContinueSection', this.sectionStatus) 589 LogUtil.info(TAG, "ToolBarComp, set continue section success") 590 NoteUtil.refreshAll() 591 }) 592 .visibility(!this.selectedNoteData ? Visibility.None : this.selectedNoteData.is_deleted == Delete.Yes ? Visibility.None : Visibility.Visible) 593 594 if (this.selectedNoteData) { 595 if (this.selectedNoteData.is_deleted == Delete.Yes) { 596 Row({ space: StyleConstants.SPACE_24 }) { 597 Image($r('app.media.delete')) 598 .height(24) 599 .width(24) 600 .onClick(() => { 601 this.noteDataDeleteDialogCtl.open() 602 }) 603 Image($r('app.media.recover')) 604 .height(24) 605 .width(24) 606 .onClick(() => { 607 this.selectedNoteData.is_deleted = Delete.No 608 this.selectedNoteData.deleted_time = 0 609 let context: any = getContext(this) 610 let resource = { 611 bundleName: "com.ohos.note", 612 moduleName: "default", 613 id: $r('app.string.restore').id 614 }; 615 context.resourceManager.getString(resource, (error, value) => { 616 if (error != null) { 617 LogUtil.error(TAG, "error is " + error); 618 } else { 619 prompt.showToast({ message: value, duration: 2000 }); 620 } 621 }); 622 this.refreshFlag = (this.refreshFlag == 0 ? 1 : 0) 623 this.chooseNote = false 624 // update note to db 625 let predicates_note = RdbStoreUtil.getRdbPredicates(TableName.NoteTable) 626 predicates_note.equalTo(NoteTableColumn.Uuid, this.selectedNoteData.uuid) 627 RdbStoreUtil.update(this.selectedNoteData.toNoteObject(), predicates_note, null) 628 629 this.selectedNoteData = NoteUtil.getFirstNoteData(AppStorage.Get('AllNoteArray'), this.selectedFolderData.uuid) 630 this.controllerShow.runJavaScript( 631 "RICH_EDITOR.setHtml('" + this.selectedNoteData.content_text + "')" 632 ) 633 // save continue data 634 let continueNote: string = JSON.stringify(this.selectedNoteData.toNoteObject()) 635 AppStorage.SetOrCreate<string>('ContinueNote', continueNote) 636 LogUtil.info(TAG, "recover, set continue note success") 637 NoteUtil.refreshAll() 638 }) 639 }.width(72) 640 } else if (this.editModel == true) { 641 Row({ space: StyleConstants.SPACE_6 }) { 642 Button({ type: ButtonType.Normal, stateEffect: true }) { 643 Image($r('app.media.circle_tick1')) 644 .height(24) 645 .width(24) 646 .onClick(() => { 647 // 清单 648 this.controllerShow.runJavaScript("javascript:RICH_EDITOR.setTodo()") 649 // 退出键盘 650 // @ts-ignore 651 inputMethod.getController().stopInputSession(); 652 }) 653 }.width(42) 654 .height(42) 655 .borderRadius(8) 656 .backgroundColor($r('app.color.color_fffffB')) 657 658 Button({ type: ButtonType.Normal, stateEffect: true }) { 659 Image($r('app.media.styles')) 660 .height(24) 661 .width(24) 662 .onClick(() => { 663 // 退出键盘 664 // @ts-ignore 665 inputMethod.getController().stopInputSession(); 666 this.editContentDialogCtl.open() 667 }) 668 }.width(42) 669 .height(42) 670 .borderRadius(8) 671 .backgroundColor($r('app.color.color_fffffB')) 672 673 Button({ type: ButtonType.Normal, stateEffect: true }) { 674 Image($r('app.media.picture_white')) 675 .height(24) 676 .width(24) 677 .onClick(async () => { 678 let permissionList: Array<string> = [ 679 "ohos.permission.READ_MEDIA", 680 "ohos.permission.WRITE_MEDIA", 681 ] 682 let context: any = getContext(this); 683 let AtManager = abilityAccessCtrl.createAtManager(); 684 // @ts-ignore 685 await AtManager.requestPermissionsFromUser(context, permissionList).then((data) => { 686 LogUtil.info(TAG, 'data permissions : ' + data.permissions) 687 LogUtil.info(TAG, 'data result: ' + data.authResults) 688 let sum = 0 689 for (let i = 0; i < data.authResults.length; i++) { 690 sum += data.authResults[i] 691 } 692 LogUtil.info(TAG, 'request permissions sum: ' + sum) 693 }).catch((err) => { 694 LogUtil.warn(TAG, 'failed to requestPermissionsFromUser : ' + err.code); 695 }) 696 // 退出键盘 697 // @ts-ignore 698 inputMethod.getController().stopInputSession(); 699 LogUtil.info(TAG, 'startAbility start') 700 await globalThis.noteContext.startAbilityForResult({ 701 parameters: { uri: "singleselect" }, 702 bundleName: "com.ohos.photos", 703 abilityName: "com.ohos.photos.MainAbility", 704 }) 705 .then(v => { 706 let want = v['want']; 707 if (want != null && want != undefined) { 708 let param = want['parameters']; 709 let imageUri = "" 710 if (param != null && param != undefined) { 711 let uri = param['select-item-list']; 712 imageUri = uri; 713 } 714 // 拷贝 715 if (imageUri != null && imageUri != "") { 716 OperationUtils.copy(imageUri).then((uriPath) => { 717 var path = "file://" + uriPath 718 LogUtil.info(TAG, 'image uri is:' + path) 719 this.controllerShow.runJavaScript( 720 "javascript:RICH_EDITOR.insertImage('" + path + "')" 721 ) 722 this.issave = 1 723 // 保存笔记信息到数据库 724 this.controllerShow.runJavaScript("getHtmlContent()") 725 }) 726 } 727 } 728 NoteUtil.refreshAll() 729 }); 730 }) 731 }.width(42) 732 .height(42) 733 .borderRadius(8) 734 .backgroundColor($r('app.color.color_fffffB')) 735 736 Button({ type: ButtonType.Normal, stateEffect: true }) { 737 Image($r('app.media.undo')) 738 .height(24) 739 .width(24) 740 .onClick(() => { 741 // 退出键盘 742 // @ts-ignore 743 inputMethod.getController().stopInputSession(); 744 this.controllerShow.runJavaScript("RICH_EDITOR.undo()") 745 }) 746 }.width(42) 747 .height(42) 748 .borderRadius(8) 749 .backgroundColor($r('app.color.color_fffffB')) 750 751 Button({ type: ButtonType.Normal, stateEffect: true }) { 752 Image($r('app.media.todo')) 753 .height(24) 754 .width(24) 755 .onClick(() => { 756 // 退出键盘 757 // @ts-ignore 758 inputMethod.getController().stopInputSession(); 759 this.controllerShow.runJavaScript("RICH_EDITOR.redo()") 760 }) 761 }.width(42) 762 .height(42) 763 .borderRadius(8) 764 .backgroundColor($r('app.color.color_fffffB')) 765 766 767 Button({ type: ButtonType.Normal, stateEffect: true }) { 768 Image($r('app.media.tick_thin')) 769 .height(24) 770 .width(24) 771 .fillColor(this.issave == 0 ? Color.Black : Color.Grey) 772 .onClick(() => { 773 // 保存笔记信息到数据库 774 this.controllerShow.runJavaScript("getHtmlContent()") 775 this.controllerShow.runJavaScript("javascript:RICH_EDITOR.getBlur()") 776 if (this.selectedNoteData.title == "标题" && this.selectedNoteData.content_text == "") { 777 LogUtil.info(TAG, "note is empty,save note failed") 778 } 779 this.issave = 1 780 }) 781 }.width(42) 782 .height(42) 783 .borderRadius(8) 784 .backgroundColor($r('app.color.color_fffffB')) 785 }.width(274) 786 } else { 787 Row({ space: StyleConstants.SPACE_24 }) { 788 Image(this.selectedNoteData.is_favorite == Favorite.Yes ? $r('app.media.favorite') : $r('app.media.favorite_cancel')) 789 .height(24) 790 .width(24) 791 .onClick(() => { 792 try { 793 this.selectedNoteData.is_favorite = (this.selectedNoteData.is_favorite == Favorite.Yes ? Favorite.No : Favorite.Yes) 794 this.refreshFlag = (this.refreshFlag == 0 ? 1 : 0) 795 // update note to db 796 let predicates_note = RdbStoreUtil.getRdbPredicates(TableName.NoteTable) 797 predicates_note.equalTo(NoteTableColumn.Uuid, this.selectedNoteData.uuid) 798 RdbStoreUtil.update(this.selectedNoteData.toNoteObject(), predicates_note, null) 799 if (this.selectedFolderData.uuid === SysDefFolderUuid.MyFavorites) { 800 this.selectedNoteData = NoteUtil.getFirstNoteData(AppStorage.Get('AllNoteArray'), SysDefFolderUuid.MyFavorites) 801 this.controllerShow.runJavaScript( 802 "RICH_EDITOR.setHtml('" + this.selectedNoteData.content_text + "')" 803 ) 804 // save continue data 805 let continueNote: string = JSON.stringify(this.selectedNoteData.toNoteObject()) 806 AppStorage.SetOrCreate<string>('ContinueNote', continueNote) 807 LogUtil.info(TAG, "ToolBarComp, set continue note success") 808 } 809 NoteUtil.refreshAll() 810 } catch (error) { 811 LogUtil.error(TAG, 'favorite error: ' + JSON.stringify(error)); 812 } 813 }) 814 Image($r('app.media.delete')) 815 .height(24) 816 .width(24) 817 .onClick(() => { 818 this.noteDataDeleteDialogCtl.open() 819 }) 820 }.width(72) 821 } 822 } 823 } 824 .width(StyleConstants.PERCENTAGE_100) 825 .height(80) 826 } 827} 828 829@Component 830struct NoteDataMoveItemCompTablet { 831 @StorageLink('CheckedNoteArray') CheckedNoteArray: NoteData[] = [] 832 @StorageLink('AllFolderArray') AllFolderArray: FolderData[] = [] 833 @StorageLink('isUpdate') isUpdate: boolean = false 834 folderItem: FolderData 835 uuid: String 836 837 build() { 838 Flex({ alignItems: ItemAlign.Center, wrap: FlexWrap.NoWrap, justifyContent: FlexAlign.Center }) { 839 Flex({ alignItems: ItemAlign.Center, wrap: FlexWrap.NoWrap }) { 840 Image(FolderUtil.getFolderIcon(this.folderItem.uuid)) 841 .id(this.isUpdate + '') 842 .objectFit(ImageFit.Fill) 843 .width(24) 844 .height(24) 845 .flexShrink(0) 846 .fillColor(FolderUtil.getFolderIconColor(this.AllFolderArray, this.folderItem.uuid, this.folderItem.uuid == this.uuid)) 847 } 848 .width(24) 849 850 Column() { 851 Flex({ alignItems: ItemAlign.Center, wrap: FlexWrap.NoWrap, justifyContent: FlexAlign.SpaceBetween }) { 852 Text(FolderUtil.getFolderText(this.folderItem)) 853 .id(this.isUpdate + '') 854 .padding({ top: 3 }) 855 .fontSize(16) 856 .fontColor(FolderUtil.getFolderIconColor(this.AllFolderArray, this.folderItem.uuid == this.uuid ? this.folderItem.uuid : '', this.folderItem.uuid == this.uuid)) 857 .textAlign(TextAlign.Center) 858 .maxLines(1) 859 .textOverflow({ overflow: TextOverflow.Ellipsis }) 860 .flexShrink(1) 861 } 862 .width('100%') 863 .height(55) 864 865 if (this.folderItem.uuid != SysDefFolderUuid.UnClassified) { 866 Divider() 867 .color($r("app.color.divider_color_e4e4e4")) 868 .strokeWidth(1) 869 } 870 } 871 .padding({ left: 16 }) 872 } 873 .id(this.isUpdate + '') 874 .width('100%') 875 .height(56) 876 .visibility(FolderUtil.isFolderMoveIn(this.folderItem) ? Visibility.Visible : Visibility.None) 877 } 878} 879