<commit_before>import { AudioAsset, AudioPlayer, AudioPlayerEvent, ResourceFactory, AudioSystem as PdiAudioSystem } from "@akashic/pdi-types";
import { ExceptionFactory } from "./ExceptionFactory";

export interface AudioSystemParameterObject {
	/**
	 * オーディオシステムのID
	 */
	id: string;

	/**
	 * オーディオのボリューム
	 */
	volume?: number;

	/**
	 * ミュート中か否か。
	 */
	muted?: boolean;

	/**
	 * 各種リソースのファクトリ
	 */
	resourceFactory: ResourceFactory;
}

export abstract class AudioSystem implements PdiAudioSystem {
	id: string;

	/**
	 * @private
	 */
	_volume: number;

	/**
	 * @private
	 */
	_muted: boolean;

	/**
	 * @private
	 */
	_destroyRequestedAssets: { [key: string]: AudioAsset };

	/**
	 * 再生速度が等倍以外に指定された等の要因により、音声再生が抑制されているかどうか。
	 * @private
	 */
	_suppressed: boolean;

	/**
	 * @private
	 */
	_resourceFactory: ResourceFactory;

	/**
	 * 明示的に設定された、ミュート中か否か。
	 * @private
	 */
	_explicitMuted: boolean;

	// volumeの変更時には通知が必要なのでアクセサを使う。
	// 呼び出し頻度が少ないため許容。
	get volume(): number {
		return this._volume;
	}

	set volume(value: number) {
		if (value < 0 || value > 1 || isNaN(value) || typeof value !== "number")
			throw ExceptionFactory.createAssertionError("AudioSystem#volume: expected: 0.0-1.0, actual: " + value);

		this._volume = value;
		this._onVolumeChanged();
	}

	constructor(param: AudioSystemParameterObject) {
		this.id = param.id;
		this._volume = param.volume || 1;
		this._destroyRequestedAssets = {};
		this._explicitMuted = param.muted || false;
		this._suppressed = false;
		this._muted = false;
		this._resourceFactory = param.resourceFactory;
		this._updateMuted();
	}

	abstract stopAll(): void;

	abstract findPlayers(asset: AudioAsset): AudioPlayer[];

	abstract createPlayer(): AudioPlayer;

	requestDestroy(asset: AudioAsset): void {
		this._destroyRequestedAssets[asset.id] = asset;
	}

	/**
	 * `this.requestDestroy()` により破棄要求されているアセットの破棄を取り消す。
	 * @param asset アセット。
	 */
	// NOTE: akashic-engine の独自仕様
	cancelRequestDestroy(asset: AudioAsset): void {
		delete this._destroyRequestedAssets[asset.id];
	}

	/**
	 * `this.requestDestroy()` により破棄要求されていて、まだ実際には破棄されていないアセット。
	 * 対象のアセットが破棄要求されていなければ `null` を返す。
	 * @param assetId アセットID。
	 */
	// NOTE: akashic-engine の独自仕様
	getDestroyRequestedAsset(assetId: string): AudioAsset | null {
		return this._destroyRequestedAssets[assetId] ?? null;
	}

	/**
	 * @private
	 */
	_reset(): void {<commit_msg>fix: use hasOwnProperty()<commit_after>import { AudioAsset, AudioPlayer, AudioPlayerEvent, ResourceFactory, AudioSystem as PdiAudioSystem } from "@akashic/pdi-types";
import { ExceptionFactory } from "./ExceptionFactory";

export interface AudioSystemParameterObject {
	/**
	 * オーディオシステムのID
	 */
	id: string;

	/**
	 * オーディオのボリューム
	 */
	volume?: number;

	/**
	 * ミュート中か否か。
	 */
	muted?: boolean;

	/**
	 * 各種リソースのファクトリ
	 */
	resourceFactory: ResourceFactory;
}

export abstract class AudioSystem implements PdiAudioSystem {
	id: string;

	/**
	 * @private
	 */
	_volume: number;

	/**
	 * @private
	 */
	_muted: boolean;

	/**
	 * @private
	 */
	_destroyRequestedAssets: { [key: string]: AudioAsset };

	/**
	 * 再生速度が等倍以外に指定された等の要因により、音声再生が抑制されているかどうか。
	 * @private
	 */
	_suppressed: boolean;

	/**
	 * @private
	 */
	_resourceFactory: ResourceFactory;

	/**
	 * 明示的に設定された、ミュート中か否か。
	 * @private
	 */
	_explicitMuted: boolean;

	// volumeの変更時には通知が必要なのでアクセサを使う。
	// 呼び出し頻度が少ないため許容。
	get volume(): number {
		return this._volume;
	}

	set volume(value: number) {
		if (value < 0 || value > 1 || isNaN(value) || typeof value !== "number")
			throw ExceptionFactory.createAssertionError("AudioSystem#volume: expected: 0.0-1.0, actual: " + value);

		this._volume = value;
		this._onVolumeChanged();
	}

	constructor(param: AudioSystemParameterObject) {
		this.id = param.id;
		this._volume = param.volume || 1;
		this._destroyRequestedAssets = {};
		this._explicitMuted = param.muted || false;
		this._suppressed = false;
		this._muted = false;
		this._resourceFactory = param.resourceFactory;
		this._updateMuted();
	}

	abstract stopAll(): void;

	abstract findPlayers(asset: AudioAsset): AudioPlayer[];

	abstract createPlayer(): AudioPlayer;

	requestDestroy(asset: AudioAsset): void {
		this._destroyRequestedAssets[asset.id] = asset;
	}

	/**
	 * `this.requestDestroy()` により破棄要求されているアセットの破棄を取り消す。
	 * @param asset アセット。
	 */
	// NOTE: akashic-engine の独自仕様
	cancelRequestDestroy(asset: AudioAsset): void {
		delete this._destroyRequestedAssets[asset.id];
	}

	/**
	 * `this.requestDestroy()` により破棄要求されていて、まだ実際には破棄されていないアセット。
	 * 対象のアセットが破棄要求されていなければ `null` を返す。
	 * @param assetId アセットID。
	 */
	// NOTE: akashic-engine の独自仕様
	getDestroyRequestedAsset(assetId: string): AudioAsset | null {
		if (this._destroyRequestedAssets.hasOwnProperty(assetId)) {
			return this._destroyRequestedAssets[assetId];
		}

		return null;
	}

	/**
	 * @private
	 */
	_reset(): void {
{'fraction_non_alphanumeric': 0.13822983288632143, 'fraction_numerical': 0.0028883845677738808, 'mean_word_length': 4.04474505723205, 'pattern_counts': {'":': 0, '<': 5, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2085149', 'n_tokens_mistral': 2087, 'n_tokens_neox': 1905, 'n_words': 313}