import React from 'react';
import { Stack, Text, PrimaryButton, Label, Link, loadTheme } from 'office-ui-fabric-react';
import { BoolToggleSettingsControl } from './BoolToggleSettingsControl'
import { ChoiceGroupSettingsControl } from './ChoiceGroupSettingsControl'
import { Separator } from 'office-ui-fabric-react/lib/Separator';
import { CustomActionSettingsControl } from './CustomActionSettingsControl';

export class GeneralSettings extends React.Component <any, any> {
  references: any = {};
  download_updates_automatically_reference: any;
  startup_reference: any;
  elevated_reference: any;
  restart_reference: any;
  theme_reference: any;
  parent_on_change: Function;
  constructor(props: any) {
    super(props);
    this.references = {};
    this.download_updates_automatically_reference = null;
    this.startup_reference = null;
    this.elevated_reference = null;
    this.restart_reference = null;
    this.parent_on_change = props.on_change;
    this.state = {
      settings_key: props.settings_key,
      settings: props.settings,
    }
  }

  shouldComponentUpdate(nextProps:any, nextState:any) {
    // This component and its children manage their state.
    // React only to state changes when forceUpdate is called by the App component.
    return false;
  }

  componentWillReceiveProps(props: any) {
    this.setState({ settings: props.settings })
  }

  public get_data(): any {
    let enabled : any = {};
    Object.keys(this.references).forEach(key => {
      enabled[key]=this.references[key].get_value().value;
    });
    let result : any = {};
    result[this.state.settings_key]= {
      download_updates_automatically: this.download_updates_automatically_reference != null && this.download_updates_automatically_reference.get_value().value,
      startup: this.startup_reference.get_value().value,
      run_elevated: this.elevated_reference != null && this.elevated_reference.get_value().value,
      theme: this.theme_reference.get_value().value,
      enabled: enabled
    };
    return result;
  }

  public render(): JSX.Element {
    let power_toys_enabled = this.state.settings.general.enabled;
    return (
      <Stack tokens={{childrenGap:20}}>
        <Text variant='xLarge'>Available PowerToys</Text>
        { Object.keys(power_toys_enabled).map(
          (key) => {
            let enabled_value=power_toys_enabled[key];
            let is_active=this.state.settings.powertoys[key].description.substr(0, 21) !== 'This feature requires';
            return <Stack key={key}>
              <Stack horizontal tokens={{childrenGap:5}}>
                <Label>{key}</Label>
                {(
                  this.state.settings.powertoys &&
                  this.state.settings.powertoys.hasOwnProperty(key) &&
                  this.state.settings.powertoys[key].hasOwnProperty('overview_link'))
                  ?
                  <Link
                    styles = {{
                      root: {
                        alignSelf:'center'
                      }
                    }}
                    href={this.state.settings.powertoys[key].overview_link}
                    target='_blank'
                  >(Overview)</Link>
                  :
                  null
                }
                {(
                  this.state.settings.powertoys &&
                  this.state.settings.powertoys.hasOwnProperty(key) &&
                  this.state.settings.powertoys[key].hasOwnProperty('video_link'))
                  ?
                  <Link
                    styles = {{
                      root: {
                        alignSelf:'center'
                      }
                    }}
                    href={this.state.settings.powertoys[key].video_link}
                    target='_blank'
                  >(Video)</Link>
                  :
                  null
                }
              </Stack>
              {(
                this.state.settings.powertoys &&
                this.state.settings.powertoys.hasOwnProperty(key) &&
                this.state.settings.powertoys[key].hasOwnProperty('description'))
                ?
                <Text
                  styles = {{
                    root: {
                      paddingBottom: '5px'
                    }
                  }}
                >{this.state.settings.powertoys[key].description}</Text>
                :
                null
              }
              <BoolToggleSettingsControl

                setting={{value: enabled_value && is_active}}
                disabled={!is_active}
                on_change={this.parent_on_change}
                ref={(input) => {this.references[key]=input;}}
              />
            </Stack>;
          })
        }
        <Separator />
        <Text variant='xLarge'>General</Text>

        {this.state.settings.general.is_admin &&
        (<Stack>
          <Label>Download updates automatically (Except on metered connections)</Label>
          <BoolToggleSettingsControl
            setting={{value: this.state.settings.general.download_updates_automatically}}
            disabled={!this.state.settings.general.is_admin}
            on_change={this.parent_on_change}
            ref={(input) => {this.download_updates_automatically_reference=input;}}
          />
        </Stack>)}


        <Stack>
          {this.state.settings.general.startup_disabled_reason != null && 
            <span style={{color:"#c50500"}} dangerouslySetInnerHTML={{__html: this.state.settings.general.startup_disabled_reason }} />
          }
          <Label>Run at Startup</Label>
          <BoolToggleSettingsControl
            disabled={this.state.settings.general.startup_disabled_reason}
            setting={{value: this.state.settings.general.startup}}
            on_change={this.parent_on_change}
            ref={(input) => {this.startup_reference=input;}}
          />
        </Stack>
        
        {this.state.settings.general.is_elevated && (<Label>Currently running as administrator</Label>)}

        {this.state.settings.general.is_admin &&
        (<BoolToggleSettingsControl
          setting={{display_name: this.state.settings.general.is_elevated ? 'Always run as administrator' : 'Always run as administrator (Restart as administrator to change this)', value: this.state.settings.general.run_elevated}}
          disabled={!this.state.settings.general.is_elevated}
          on_change={this.parent_on_change}
          ref={(input) => {this.elevated_reference=input;}}
        />)
        }
        {this.state.settings.general.is_admin && !this.state.settings.general.is_elevated &&
        (<CustomActionSettingsControl
          setting={{
            display_name: '',
            value: 'Running as user. Do you wish to run as administrator instead?',
            button_text: 'Restart as administrator',
            help_link_url: "https://aka.ms/powertoysDetectedElevatedHelp",
            help_link_text: "(Learn more about Admin mode)"
          }}
          action_name={'restart_elevation'}
          action_callback={(action_name: any, value:any) => {
            (window as any).output_from_webview(JSON.stringify({
              action: {
                general: {
                  action_name,
                  value
                }
              }
            }));
          }}
          ref={(input) => {this.restart_reference=input;}}
        />)
        }
        <ChoiceGroupSettingsControl
          setting={{display_name: 'Choose Settings color',
                    value: this.state.settings.general.theme,
                    options: [
                      { key: 'system', text: 'System default app mode'},
                      { key: 'light', text: 'Light' },
                      { key: 'dark', text: 'Dark' }
                    ]}}
          on_change={() => {
            const dark_mode = this.theme_reference.get_value().value === 'dark' ||
                             (this.theme_reference.get_value().value === 'system' && this.state.settings.general.system_theme === 'dark');
            if (dark_mode) {
              loadTheme({
                palette: {
                  themePrimary: '#0088e4',
                  themeLighterAlt: '#000509',
                  themeLighter: '#001624',
                  themeLight: '#002944',
                  themeTertiary: '#005288',
                  themeSecondary: '#0078c8',
                  themeDarkAlt: '#1793e6',
                  themeDark: '#38a3ea',
                  themeDarker: '#69baef',
                  neutralLighterAlt: '#0b0b0b',
                  neutralLighter: '#151515',
                  neutralLight: '#252525',
                  neutralQuaternaryAlt: '#2f2f2f',
                  neutralQuaternary: '#373737',
                  neutralTertiaryAlt: '#595959',
                  neutralTertiary: '#eaeaea',
                  neutralSecondary: '#eeeeee',
                  neutralPrimaryAlt: '#f1f1f1',
                  neutralPrimary: '#e0e0e0',
                  neutralDark: '#f8f8f8',
                  black: '#fbfbfb',
                  white: '#000000',
                }
              });
            } else {
              loadTheme({
                palette: {
                  themePrimary: '#0078d4',
                  themeLighterAlt: '#f3f9fd',
                  themeLighter: '#d0e7f8',
                  themeLight: '#a9d3f2',
                  themeTertiary: '#5ca9e5',
                  themeSecondary: '#1a86d9',
                  themeDarkAlt: '#006cbe',
                  themeDark: '#005ba1',
                  themeDarker: '#004377',
                  neutralLighterAlt: '#f8f8f8',
                  neutralLighter: '#f4f4f4',
                  neutralLight: '#eaeaea',
                  neutralQuaternaryAlt: '#dadada',
                  neutralQuaternary: '#d0d0d0',
                  neutralTertiaryAlt: '#c8c8c8',
                  neutralTertiary: '#bab8b7',
                  neutralSecondary: '#a3a2a0',
                  neutralPrimaryAlt: '#8d8b8a',
                  neutralPrimary: '#323130',
                  neutralDark: '#605e5d',
                  black: '#494847',
                  white: '#ffffff',
                }
              });
            }
            this.parent_on_change();
          }}
          ref={(input) => {this.theme_reference=input;}}
        />
        <Stack>
          <Text variant='xLarge'>About PowerToys (Preview)</Text>
          <Label>Version {this.state.settings.general.powertoys_version}</Label>
            <PrimaryButton
              styles={{
                  root: {
                    alignSelf: "start"
                  }
              }}
              href='https://github.com/microsoft/PowerToys/releases'
              target='_blank'
            >Check for updates</PrimaryButton>
            <Link
              href="https://github.com/microsoft/PowerToys/issues/new?assignees=&labels=&template=bug_report.md&title="
              target='_blank'
              styles = {{
                root: {
                  paddingTop: '10px'
                }
              }}
            >Report a bug</Link>
            <Link
              href="https://github.com/microsoft/PowerToys/issues/new?assignees=&labels=&template=feature_request.md&title="
              target='_blank'
            >Request a feature</Link>
            <Link
              href="https://github.com/microsoft/PowerToys#privacy-statement"
              target='_blank'
            >Privacy statement</Link>
        </Stack>
        {/* An empty span to always give 30px padding in Edge. */}
        <span />
      </Stack>
    )
  }
}
