1// Copyright (C) 2023 The Android Open Source Project 2// 3// Licensed under the Apache License, Version 2.0 (the "License"); 4// you may not use size 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 15import m from 'mithril'; 16 17import {BottomTab, bottomTabRegistry, NewBottomTabArgs} from './bottom_tab'; 18import {globals} from './globals'; 19import {ThreadStateSqlId} from './sql_types'; 20import {getThreadState, ThreadState, threadStateToDict} from './thread_state'; 21import {renderDict} from './value'; 22 23interface ThreadStateTabConfig { 24 // Id into |thread_state| sql table. 25 readonly id: ThreadStateSqlId; 26} 27 28export class ThreadStateTab extends BottomTab<ThreadStateTabConfig> { 29 static readonly kind = 'org.perfetto.ThreadStateTab'; 30 31 state?: ThreadState; 32 loaded: boolean = false; 33 34 static create(args: NewBottomTabArgs): ThreadStateTab { 35 return new ThreadStateTab(args); 36 } 37 38 constructor(args: NewBottomTabArgs) { 39 super(args); 40 41 getThreadState(this.engine, this.config.id).then((state?: ThreadState) => { 42 this.loaded = true; 43 this.state = state; 44 globals.rafScheduler.scheduleFullRedraw(); 45 }); 46 } 47 48 getTitle() { 49 // TODO(altimin): Support dynamic titles here. 50 return 'Current Selection'; 51 } 52 53 renderTabContents(): m.Child { 54 if (!this.loaded) { 55 return m('h2', 'Loading'); 56 } 57 if (!this.state) { 58 return m('h2', `Thread state ${this.config.id} does not exist`); 59 } 60 return renderDict(threadStateToDict(this.state)); 61 } 62 63 viewTab() { 64 // TODO(altimin): Create a reusable component for showing the header and 65 // differentiate between "Current Selection" and "Pinned" views. 66 return m( 67 'div.details-panel', 68 m('header.overview', m('span', 'Thread State')), 69 this.renderTabContents()); 70 } 71 72 isLoading() { 73 return this.state === undefined; 74 } 75 76 renderTabCanvas(): void {} 77} 78 79bottomTabRegistry.register(ThreadStateTab); 80