added settings tab, add language chooser

This commit is contained in:
Amruth Pillai
2020-03-30 13:50:47 +05:30
parent e27655aeea
commit 1b2bae43be
11 changed files with 110 additions and 7 deletions

View File

@ -15,6 +15,7 @@ module.exports = {
'/templates/', '/templates/',
'/technology/', '/technology/',
'/contributing/', '/contributing/',
'/translation/',
'/building-from-source/', '/building-from-source/',
'/deployment/', '/deployment/',
'/changelog/', '/changelog/',

View File

@ -30,9 +30,7 @@ Something that's missing on the app that's halting your progress from making the
## Translation ## Translation
Currently, there is no translation engine in place that allows for people to easily make translations. I'm still figuring out the most elegant way to implement this feature with minimal code and maximum reach. For now, if you would like to see this feature, please vote in the GitHub Issue linked below and if you are willing to contribute, mention in the comments of the issue which language you would like to translate to. For information on how to translate the app into your own language, please visit the [Translation](/translation/) section of the documentation.
[Vote for Translation Engine Feature ](https://github.com/AmruthPillai/Reactive-Resume/issues/18)
## Commit Code ## Commit Code

View File

@ -0,0 +1,5 @@
---
title: Translation
---
# Translation

View File

@ -8,22 +8,25 @@ import ColorsTab from './tabs/Colors';
import FontsTab from './tabs/Fonts'; import FontsTab from './tabs/Fonts';
import ActionsTab from './tabs/Actions'; import ActionsTab from './tabs/Actions';
import AboutTab from './tabs/About'; import AboutTab from './tabs/About';
import SettingsTab from './tabs/Settings';
const RightSidebar = () => { const RightSidebar = () => {
const { t } = useTranslation('rightSidebar'); const { t } = useTranslation('rightSidebar');
const context = useContext(AppContext); const context = useContext(AppContext);
const { state, dispatch } = context; const { state, dispatch } = context;
const { data, theme } = state; const { data, theme, settings } = state;
const tabs = [ const tabs = [
t('templates.title'), t('templates.title'),
t('colors.title'), t('colors.title'),
t('fonts.title'), t('fonts.title'),
t('actions.title'), t('actions.title'),
t('settings.title'),
t('about.title'), t('about.title'),
]; ];
const [currentTab, setCurrentTab] = useState(t('about.title')); const [currentTab, setCurrentTab] = useState(t('settings.title'));
const onChange = (key, value) => { const onChange = (key, value) => {
dispatch({ dispatch({
type: 'on_input', type: 'on_input',
@ -46,6 +49,8 @@ const RightSidebar = () => {
return <FontsTab theme={theme} onChange={onChange} />; return <FontsTab theme={theme} onChange={onChange} />;
case t('actions.title'): case t('actions.title'):
return <ActionsTab data={data} theme={theme} dispatch={dispatch} />; return <ActionsTab data={data} theme={theme} dispatch={dispatch} />;
case t('settings.title'):
return <SettingsTab settings={settings} onChange={onChange} />;
case t('about.title'): case t('about.title'):
return <AboutTab />; return <AboutTab />;
default: default:

View File

@ -0,0 +1,47 @@
import React from 'react';
import { useTranslation, Trans } from 'react-i18next';
import { languages } from '../../../i18n';
import Dropdown from '../../../shared/Dropdown';
const SettingsTab = ({ settings, onChange }) => {
const { t, i18n } = useTranslation('rightSidebar');
const onChangeLanguage = code => {
i18n.changeLanguage(code);
onChange('settings.language', code);
};
return (
<div>
<Dropdown
label={t('settings.language.label')}
value={settings.language}
onChange={onChangeLanguage}
options={languages}
optionItem={x => (
<option key={x.code} value={x.code}>
{x.name}
</option>
)}
/>
<p className="text-gray-800 text-xs">
<Trans t={t} i18nKey="settings.language.helpText">
If you would like to help translate the app into your own language, please refer the
<a
className="text-blue-600 hover:underline"
target="_blank"
rel="noopener noreferrer"
href="https://docs.rxresu.me/translation/"
>
Translation Documentation
</a>
.
</Trans>
</p>
</div>
);
};
export default SettingsTab;

View File

@ -80,6 +80,9 @@ const initialState = {
accent: '#f44336', accent: '#f44336',
}, },
}, },
settings: {
language: 'en',
},
}; };
const reducer = (state, { type, payload }) => { const reducer = (state, { type, payload }) => {
@ -120,8 +123,7 @@ const reducer = (state, { type, payload }) => {
return { return {
...state, ...state,
data: payload.data, ...payload,
theme: payload.theme,
}; };
case 'load_dummy_data': case 'load_dummy_data':
return { return {

View File

@ -3,6 +3,13 @@ import { initReactI18next } from 'react-i18next';
import resources from './resources'; import resources from './resources';
const languages = [
{
code: 'en',
name: 'English',
},
];
i18n.use(initReactI18next).init({ i18n.use(initReactI18next).init({
lng: 'en', lng: 'en',
fallbackLng: 'en', fallbackLng: 'en',
@ -12,4 +19,6 @@ i18n.use(initReactI18next).init({
defaultNS: 'app', defaultNS: 'app',
}); });
export { languages };
export default i18n; export default i18n;

View File

@ -2,6 +2,7 @@ import templates from './templates.json';
import colors from './colors.json'; import colors from './colors.json';
import fonts from './fonts.json'; import fonts from './fonts.json';
import actions from './actions.json'; import actions from './actions.json';
import settings from './settings.json';
import about from './about.json'; import about from './about.json';
export default { export default {
@ -9,5 +10,6 @@ export default {
colors, colors,
fonts, fonts,
actions, actions,
settings,
about, about,
}; };

View File

@ -0,0 +1,7 @@
{
"title": "Settings",
"language": {
"label": "Language",
"helpText": "If you would like to help translate the app into your own language, please refer the <1>Translation Documentation</1>."
}
}

View File

@ -1,5 +1,7 @@
import en from './en'; import en from './en';
import kn from './kn';
export default { export default {
en, en,
kn,
}; };

25
src/shared/Dropdown.js Normal file
View File

@ -0,0 +1,25 @@
import React from 'react';
const Dropdown = ({ label, value, onChange, options, optionItem }) => (
<div className="flex flex-col mb-2">
{label && (
<label className="uppercase tracking-wide text-gray-600 text-xs font-semibold mb-2">
{label}
</label>
)}
<div className="inline-flex relative w-full bg-gray-200 text-gray-800 rounded py-3 px-4 leading-tight focus:outline-none">
<select
className="block appearance-none w-full bg-gray-200 text-gray-800 focus:outline-none"
value={value}
onChange={e => onChange(e.target.value)}
>
{options.map(optionItem)}
</select>
<div className="pointer-events-none absolute inset-y-0 right-0 flex justify-center items-center px-2 bg-gray-200">
<i className="material-icons">expand_more</i>
</div>
</div>
</div>
);
export default Dropdown;