blob: 5e3a38f5f889653ef955bdd919d9978ec9f054b1 [file] [log] [blame]
// Copyright (C) 2022 The Android Open Source Project
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
import m from 'mithril';
import {
RecordingTargetV2,
TargetFactory,
} from '../../common/recordingV2/recording_interfaces_v2';
import {
RecordingPageController,
} from '../../common/recordingV2/recording_page_controller';
import {fullscreenModalContainer} from '../modal';
interface RecordingMultipleChoiceAttrs {
targetFactories: TargetFactory[];
// Reference to the controller which maintains the state of the recording
// page.
controller: RecordingPageController;
}
export class RecordingMultipleChoice implements
m.ClassComponent<RecordingMultipleChoiceAttrs> {
private selectedIndex: number = -1;
targetSelection(
targets: RecordingTargetV2[],
controller: RecordingPageController): m.Vnode|undefined {
const targetInfo = controller.getTargetInfo();
const targetNames = [];
this.selectedIndex = -1;
for (let i = 0; i < targets.length; i++) {
const targetName = targets[i].getInfo().name;
targetNames.push(m('option', targetName));
if (targetInfo && targetName === targetInfo.name) {
this.selectedIndex = i;
}
}
const selectedIndex = this.selectedIndex;
return m(
'label',
m('select',
{
selectedIndex,
onchange: (e: Event) => {
controller.onTargetSelection(
(e.target as HTMLSelectElement).value);
},
onupdate: (select) => {
// Work around mithril bug
// (https://github.com/MithrilJS/mithril.js/issues/2107): We
// may update the select's options while also changing the
// selectedIndex at the same time. The update of selectedIndex
// may be applied before the new options are added to the
// select element. Because the new selectedIndex may be
// outside of the select's options at that time, we have to
// reselect the correct index here after any new children were
// added.
(select.dom as HTMLSelectElement).selectedIndex =
this.selectedIndex;
},
...{size: targets.length, multiple: 'multiple'},
},
...targetNames),
);
}
view({attrs}: m.CVnode<RecordingMultipleChoiceAttrs>): m.Vnode[]|undefined {
const controller = attrs.controller;
if (!controller.shouldShowTargetSelection()) {
return undefined;
}
const targets: RecordingTargetV2[] = [];
for (const targetFactory of attrs.targetFactories) {
for (const target of targetFactory.listTargets()) {
targets.push(target);
}
}
if (targets.length === 0) {
return undefined;
}
return [
m('text', 'Select target:'),
m('.record-modal-command',
this.targetSelection(targets, controller),
m('button.record-modal-button-high',
{
disabled: this.selectedIndex === -1,
onclick: () => {
fullscreenModalContainer.close();
controller.onStartRecordingPressed();
},
},
'Connect')),
];
}
}