/*
 * Copyright (C) 2022 Savoir-faire Linux Inc.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU Affero General Public License as
 * published by the Free Software Foundation; either version 3 of the
 * License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Affero General Public License for more details.
 *
 * You should have received a copy of the GNU Affero General Public
 * License along with this program.  If not, see
 * <https://www.gnu.org/licenses/>.
 */
import { createContext, useState } from 'react';

import { SetState, WithChildren } from '../utils/utils';

interface ICallContext {
  micOn: boolean;
  setMicOn: SetState<boolean>;
  camOn: boolean;
  setCamOn: SetState<boolean>;
}

const defaultCallContext: ICallContext = {
  micOn: false,
  setMicOn: () => {},
  camOn: false,
  setCamOn: () => {},
};

export const CallContext = createContext<ICallContext>(defaultCallContext);

type CallProviderProps = WithChildren & {
  micOn?: boolean;
  camOn?: boolean;
};

export default ({
  children,
  micOn: _micOn = defaultCallContext.micOn,
  camOn: _camOn = defaultCallContext.camOn,
}: CallProviderProps) => {
  const [micOn, setMicOn] = useState(_micOn);
  const [camOn, setCamOn] = useState(_camOn);

  return (
    <CallContext.Provider
      value={{
        micOn,
        setMicOn,
        camOn,
        setCamOn,
      }}
    >
      {children}
    </CallContext.Provider>
  );
};
