1fb726d48Sopenharmony_ci/* 2fb726d48Sopenharmony_ci * Copyright (C) 2022 Huawei Device Co., Ltd. 3fb726d48Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License"); 4fb726d48Sopenharmony_ci * you may not use this file except in compliance with the License. 5fb726d48Sopenharmony_ci * You may obtain a copy of the License at 6fb726d48Sopenharmony_ci * 7fb726d48Sopenharmony_ci * http://www.apache.org/licenses/LICENSE-2.0 8fb726d48Sopenharmony_ci * 9fb726d48Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software 10fb726d48Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS, 11fb726d48Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12fb726d48Sopenharmony_ci * See the License for the specific language governing permissions and 13fb726d48Sopenharmony_ci * limitations under the License. 14fb726d48Sopenharmony_ci */ 15fb726d48Sopenharmony_ciimport { query } from '../../database/SqlLite'; 16fb726d48Sopenharmony_ciimport { TraceRow } from '../trace/base/TraceRow'; 17fb726d48Sopenharmony_ciimport { FlagsConfig } from '../../component/SpFlags'; 18fb726d48Sopenharmony_ciinterface VSyncData { 19fb726d48Sopenharmony_ci startTime: number; 20fb726d48Sopenharmony_ci dur: number; 21fb726d48Sopenharmony_ci value?: number; 22fb726d48Sopenharmony_ci} 23fb726d48Sopenharmony_ci 24fb726d48Sopenharmony_cilet vSyncDataList: VSyncData[] = []; 25fb726d48Sopenharmony_cilet vSyncEnable = false; 26fb726d48Sopenharmony_cilet isSingle = false; 27fb726d48Sopenharmony_ci 28fb726d48Sopenharmony_ciexport function resetVSync(): void { 29fb726d48Sopenharmony_ci vSyncEnable = false; 30fb726d48Sopenharmony_ci} 31fb726d48Sopenharmony_ci 32fb726d48Sopenharmony_ciexport const querySfVSyncData = (): Promise<Array<VSyncData>> => 33fb726d48Sopenharmony_ci query( 34fb726d48Sopenharmony_ci 'querySfVSyncData', 35fb726d48Sopenharmony_ci `SELECT value, c.ts - tb.start_ts startTime 36fb726d48Sopenharmony_ci FROM process_measure c, 37fb726d48Sopenharmony_ci trace_range tb 38fb726d48Sopenharmony_ci WHERE c.filter_id IN (SELECT process_measure_filter.id AS traceId 39fb726d48Sopenharmony_ci FROM process_measure_filter 40fb726d48Sopenharmony_ci JOIN process USING (ipid) 41fb726d48Sopenharmony_ci WHERE process.name = ${ 42fb726d48Sopenharmony_ci `'` + 43fb726d48Sopenharmony_ci String.fromCharCode(115, 117, 114, 102, 97, 99, 101, 102, 108, 105, 110, 103, 101, 114) + 44fb726d48Sopenharmony_ci `'` 45fb726d48Sopenharmony_ci } 46fb726d48Sopenharmony_ci AND process_measure_filter.name = ${ 47fb726d48Sopenharmony_ci `'` + String.fromCharCode(86, 83, 89, 78, 67, 45, 97, 112, 112) + `'` 48fb726d48Sopenharmony_ci })` 49fb726d48Sopenharmony_ci ); 50fb726d48Sopenharmony_ci 51fb726d48Sopenharmony_ci export const querySingleVSyncData = (): Promise<Array<VSyncData>> => { 52fb726d48Sopenharmony_ci let flagsItem = window.localStorage.getItem(FlagsConfig.FLAGS_CONFIG_KEY); 53fb726d48Sopenharmony_ci let flagsItemJson = JSON.parse(flagsItem!); 54fb726d48Sopenharmony_ci let vsyncValue = flagsItemJson.vsyncValue; 55fb726d48Sopenharmony_ci let vsyncCondition = ''; 56fb726d48Sopenharmony_ci if (vsyncValue === 'H:VsyncGenerator' || vsyncValue === '') { 57fb726d48Sopenharmony_ci vsyncCondition = ` AND (callstack.name like 'H:GenerateVsyncCount%'))`; 58fb726d48Sopenharmony_ci } else { 59fb726d48Sopenharmony_ci vsyncCondition = ` AND callstack.name like '${vsyncValue}%' )`; 60fb726d48Sopenharmony_ci } 61fb726d48Sopenharmony_ci 62fb726d48Sopenharmony_ci let sql = 63fb726d48Sopenharmony_ci `SELECT c.ts - tb.start_ts startTime 64fb726d48Sopenharmony_ci FROM callstack c, 65fb726d48Sopenharmony_ci trace_range tb 66fb726d48Sopenharmony_ci WHERE c.id IN (SELECT callstack.id AS trackId 67fb726d48Sopenharmony_ci FROM callstack 68fb726d48Sopenharmony_ci JOIN process 69fb726d48Sopenharmony_ci WHERE process.name = 'render_service'` 70fb726d48Sopenharmony_ci + vsyncCondition; 71fb726d48Sopenharmony_ci return query('querySingleVSyncData', sql); 72fb726d48Sopenharmony_ci } 73fb726d48Sopenharmony_ci 74fb726d48Sopenharmony_ci/** 75fb726d48Sopenharmony_ci * load single vsync data 76fb726d48Sopenharmony_ci */ 77fb726d48Sopenharmony_ciexport async function setVSyncData(): Promise<void> { 78fb726d48Sopenharmony_ci let sfvSyncData = await querySfVSyncData(); 79fb726d48Sopenharmony_ci if (sfvSyncData.length === 0) { 80fb726d48Sopenharmony_ci sfvSyncData = await querySingleVSyncData(); 81fb726d48Sopenharmony_ci isSingle = true; 82fb726d48Sopenharmony_ci } 83fb726d48Sopenharmony_ci sfvSyncData.forEach((it, index, array): void => { 84fb726d48Sopenharmony_ci if (index < array.length - 1) { 85fb726d48Sopenharmony_ci it.dur = array[index + 1].startTime - it.startTime; 86fb726d48Sopenharmony_ci } else { 87fb726d48Sopenharmony_ci it.dur = window.totalNS - it.startTime; 88fb726d48Sopenharmony_ci } 89fb726d48Sopenharmony_ci }); 90fb726d48Sopenharmony_ci vSyncDataList = sfvSyncData; 91fb726d48Sopenharmony_ci} 92fb726d48Sopenharmony_ci 93fb726d48Sopenharmony_ci/** 94fb726d48Sopenharmony_ci * draw chart 95fb726d48Sopenharmony_ci */ 96fb726d48Sopenharmony_ciexport function drawVSync(ctx: CanvasRenderingContext2D, width: number, height: number): void { 97fb726d48Sopenharmony_ci if (!vSyncEnable) { 98fb726d48Sopenharmony_ci return; 99fb726d48Sopenharmony_ci } 100fb726d48Sopenharmony_ci function draw(it: VSyncData): void { 101fb726d48Sopenharmony_ci let x = ns2x(it.startTime, width); 102fb726d48Sopenharmony_ci let x2 = ns2x(it.startTime + it.dur, width); 103fb726d48Sopenharmony_ci ctx.fillRect(x, 0, x2 - x, height); 104fb726d48Sopenharmony_ci } 105fb726d48Sopenharmony_ci ctx.beginPath(); 106fb726d48Sopenharmony_ci ctx.fillStyle = '#555555'; 107fb726d48Sopenharmony_ci ctx.lineWidth = 1; 108fb726d48Sopenharmony_ci ctx.globalAlpha = 0.3; 109fb726d48Sopenharmony_ci if (isSingle) { 110fb726d48Sopenharmony_ci // 单框架灰白交替 111fb726d48Sopenharmony_ci for (let i = 0; i < vSyncDataList.length; i++) { 112fb726d48Sopenharmony_ci if (i % 2 === 1) { 113fb726d48Sopenharmony_ci continue; 114fb726d48Sopenharmony_ci } 115fb726d48Sopenharmony_ci draw(vSyncDataList[i]); 116fb726d48Sopenharmony_ci } 117fb726d48Sopenharmony_ci } else { 118fb726d48Sopenharmony_ci // 双框架绘制vSync 信号为1的数据为灰 119fb726d48Sopenharmony_ci vSyncDataList 120fb726d48Sopenharmony_ci ?.filter((it) => it.value === 1) 121fb726d48Sopenharmony_ci .forEach((it) => { 122fb726d48Sopenharmony_ci draw(it); 123fb726d48Sopenharmony_ci }); 124fb726d48Sopenharmony_ci } 125fb726d48Sopenharmony_ci ctx.stroke(); 126fb726d48Sopenharmony_ci ctx.globalAlpha = 1.0; 127fb726d48Sopenharmony_ci ctx.closePath(); 128fb726d48Sopenharmony_ci} 129fb726d48Sopenharmony_ci 130fb726d48Sopenharmony_ci/** 131fb726d48Sopenharmony_ci * enable/disable SingleVSync 132fb726d48Sopenharmony_ci */ 133fb726d48Sopenharmony_ciexport function enableVSync(press: boolean, ev: KeyboardEvent, handler?: Function): void { 134fb726d48Sopenharmony_ci if (ev.key.toLocaleLowerCase() === 'v' && !ev.ctrlKey) { 135fb726d48Sopenharmony_ci window.publish(window.SmartEvent.UI.Loading, { loading: true, text: 'Query VSync' }); 136fb726d48Sopenharmony_ci setVSyncData(); 137fb726d48Sopenharmony_ci window.publish(window.SmartEvent.UI.Loading, { loading: false, text: 'Query VSync' }); 138fb726d48Sopenharmony_ci vSyncEnable = !vSyncEnable; 139fb726d48Sopenharmony_ci handler?.(); 140fb726d48Sopenharmony_ci } 141fb726d48Sopenharmony_ci} 142fb726d48Sopenharmony_ci 143fb726d48Sopenharmony_ci/** 144fb726d48Sopenharmony_ci * ns to px 145fb726d48Sopenharmony_ci */ 146fb726d48Sopenharmony_cifunction ns2x(ns: number, width: number): number { 147fb726d48Sopenharmony_ci let startNS = TraceRow.range?.startNS || 0; 148fb726d48Sopenharmony_ci let endNS = TraceRow.range?.endNS || 0; 149fb726d48Sopenharmony_ci if (endNS === 0) { 150fb726d48Sopenharmony_ci //@ts-ignore 151fb726d48Sopenharmony_ci endNS = (window as unknown).totalNS; 152fb726d48Sopenharmony_ci } 153fb726d48Sopenharmony_ci let xWidth: number = ((ns - startNS) * width) / (endNS - startNS); 154fb726d48Sopenharmony_ci if (xWidth < 0) { 155fb726d48Sopenharmony_ci xWidth = 0; 156fb726d48Sopenharmony_ci } else if (xWidth > width) { 157fb726d48Sopenharmony_ci xWidth = width; 158fb726d48Sopenharmony_ci } 159fb726d48Sopenharmony_ci return xWidth; 160fb726d48Sopenharmony_ci} 161