perf: remove unless code

This commit is contained in:
vben 2021-02-09 23:06:00 +08:00
parent 2b466eaf9a
commit 23657547ab
31 changed files with 108 additions and 170 deletions

View File

@ -14,7 +14,8 @@
"clean:cache": "rimraf node_modules/.cache/ && rimraf node_modules/.vite", "clean:cache": "rimraf node_modules/.cache/ && rimraf node_modules/.vite",
"clean:lib": "npx rimraf node_modules", "clean:lib": "npx rimraf node_modules",
"typecheck": "vuedx-typecheck .", "typecheck": "vuedx-typecheck .",
"lint:eslint": "eslint \"{src,mock}/**/*.{vue,ts,tsx}\" --fix", "lint:eslint": "eslint \"{src,mock}/**/*.{vue,ts,tsx}\" ",
"lint:eslint:fix": "eslint \"{src,mock}/**/*.{vue,ts,tsx}\" --fix",
"lint:prettier": "prettier --write --loglevel warn \"src/**/*.{js,json,tsx,css,less,scss,vue,html,md}\"", "lint:prettier": "prettier --write --loglevel warn \"src/**/*.{js,json,tsx,css,less,scss,vue,html,md}\"",
"lint:stylelint": "stylelint --fix \"**/*.{vue,less,postcss,css,scss}\" --cache --cache-location node_modules/.cache/stylelint/", "lint:stylelint": "stylelint --fix \"**/*.{vue,less,postcss,css,scss}\" --cache --cache-location node_modules/.cache/stylelint/",
"lint:ls-lint": "ls-lint", "lint:ls-lint": "ls-lint",

View File

@ -1,7 +1,6 @@
import { createAsyncComponent } from '/@/utils/factory/createAsyncComponent'; import { createAsyncComponent } from '/@/utils/factory/createAsyncComponent';
import AppLogo from './src/AppLogo.vue'; import AppLogo from './src/AppLogo.vue';
import AppProvider from './src/AppProvider.vue'; import AppProvider from './src/AppProvider.vue';
import { withInstall } from '../util';
export const AppLocalePicker = createAsyncComponent(() => import('./src/AppLocalePicker.vue')); export const AppLocalePicker = createAsyncComponent(() => import('./src/AppLocalePicker.vue'));
export const AppSearch = createAsyncComponent(() => import('./src/search/AppSearch.vue'), { export const AppSearch = createAsyncComponent(() => import('./src/search/AppSearch.vue'), {
@ -10,5 +9,3 @@ export const AppSearch = createAsyncComponent(() => import('./src/search/AppSear
export { useAppProviderContext } from './src/useAppContext'; export { useAppProviderContext } from './src/useAppContext';
export { AppLogo, AppProvider }; export { AppLogo, AppProvider };
withInstall(AppLogo, AppProvider);

View File

@ -17,19 +17,18 @@
</Dropdown> </Dropdown>
</template> </template>
<script lang="ts"> <script lang="ts">
import { defineComponent, ref, watchEffect, unref, computed } from 'vue'; import type { LocaleType } from '/@/locales/types';
import type { DropMenu } from '/@/components/Dropdown';
import { Dropdown, DropMenu } from '/@/components/Dropdown'; import { defineComponent, ref, watchEffect, unref, computed } from 'vue';
import { Dropdown } from '/@/components/Dropdown';
import Icon from '/@/components/Icon';
import { useLocale } from '/@/locales/useLocale'; import { useLocale } from '/@/locales/useLocale';
import { useLocaleSetting } from '/@/hooks/setting/useLocaleSetting'; import { useLocaleSetting } from '/@/hooks/setting/useLocaleSetting';
import { LocaleType } from '/@/locales/types';
import { propTypes } from '/@/utils/propTypes';
import { useDesign } from '/@/hooks/web/useDesign'; import { useDesign } from '/@/hooks/web/useDesign';
import { propTypes } from '/@/utils/propTypes';
import Icon from '/@/components/Icon';
export default defineComponent({ export default defineComponent({
name: 'AppLocalPicker', name: 'AppLocalPicker',
components: { Dropdown, Icon }, components: { Dropdown, Icon },

View File

@ -20,13 +20,11 @@
import { useGlobSetting } from '/@/hooks/setting'; import { useGlobSetting } from '/@/hooks/setting';
import { useGo } from '/@/hooks/web/usePage'; import { useGo } from '/@/hooks/web/usePage';
import { useMenuSetting } from '/@/hooks/setting/useMenuSetting'; import { useMenuSetting } from '/@/hooks/setting/useMenuSetting';
import { useDesign } from '/@/hooks/web/useDesign';
import { PageEnum } from '/@/enums/pageEnum'; import { PageEnum } from '/@/enums/pageEnum';
import { propTypes } from '/@/utils/propTypes'; import { propTypes } from '/@/utils/propTypes';
import { useDesign } from '/@/hooks/web/useDesign';
export default defineComponent({ export default defineComponent({
name: 'AppLogo', name: 'AppLogo',
props: { props: {

View File

@ -1,6 +1,3 @@
<template>
<slot></slot>
</template>
<script lang="ts"> <script lang="ts">
import type { PropType } from 'vue'; import type { PropType } from 'vue';
import { defineComponent, toRefs, ref } from 'vue'; import { defineComponent, toRefs, ref } from 'vue';
@ -19,7 +16,7 @@
default: designSetting.prefixCls, default: designSetting.prefixCls,
}, },
}, },
setup(props) { setup(props, { slots }) {
const isMobileRef = ref(false); const isMobileRef = ref(false);
createBreakpointListen(({ screenMap, sizeEnum, width }) => { createBreakpointListen(({ screenMap, sizeEnum, width }) => {
@ -31,7 +28,7 @@
const { prefixCls } = toRefs(props); const { prefixCls } = toRefs(props);
createAppProviderContext({ prefixCls, isMobile: isMobileRef }); createAppProviderContext({ prefixCls, isMobile: isMobileRef });
return {}; return () => slots.default?.();
}, },
}); });
</script> </script>

View File

@ -1,23 +1,11 @@
<template> <script lang="tsx">
<div :class="prefixCls" v-if="getShowSearch" @click.stop="handleSearch"> import { defineComponent, ref, unref } from 'vue';
<Tooltip>
<template #title>
{{ t('common.searchText') }}
</template>
<SearchOutlined />
</Tooltip>
<AppSearchModal @close="handleClose" :visible="showModal" />
</div>
</template>
<script lang="ts">
import { defineComponent, ref } from 'vue';
import { Tooltip } from 'ant-design-vue'; import { Tooltip } from 'ant-design-vue';
import { SearchOutlined } from '@ant-design/icons-vue';
import AppSearchModal from './AppSearchModal.vue';
import { useDesign } from '/@/hooks/web/useDesign'; import { useDesign } from '/@/hooks/web/useDesign';
import AppSearchModal from './AppSearchModal.vue';
import { useHeaderSetting } from '/@/hooks/setting/useHeaderSetting'; import { useHeaderSetting } from '/@/hooks/setting/useHeaderSetting';
import { SearchOutlined } from '@ant-design/icons-vue';
import { useI18n } from '/@/hooks/web/useI18n'; import { useI18n } from '/@/hooks/web/useI18n';
export default defineComponent({ export default defineComponent({
@ -32,15 +20,26 @@
function handleSearch() { function handleSearch() {
showModal.value = true; showModal.value = true;
} }
return {
t, function handleClose() {
prefixCls, showModal.value = false;
showModal, }
getShowSearch,
handleClose: () => { return () => {
showModal.value = false; if (!getShowSearch.value) {
}, return null;
handleSearch, }
return (
<div class={prefixCls} onClick={handleSearch}>
<Tooltip>
{{
title: () => t('common.searchText'),
default: () => <SearchOutlined />,
}}
</Tooltip>
<AppSearchModal onClose={handleClose} visible={unref(showModal)} />
</div>
);
}; };
}, },
}); });

View File

@ -18,12 +18,13 @@
<span>{{ t('common.closeText') }}</span> <span>{{ t('common.closeText') }}</span>
</div> </div>
</template> </template>
<script lang="ts"> <script lang="ts">
import { defineComponent } from 'vue'; import { defineComponent } from 'vue';
import Icon from '/@/components/Icon';
import { useDesign } from '/@/hooks/web/useDesign'; import { useDesign } from '/@/hooks/web/useDesign';
import { useI18n } from '/@/hooks/web/useI18n'; import { useI18n } from '/@/hooks/web/useI18n';
import Icon from '/@/components/Icon';
export default defineComponent({ export default defineComponent({
name: 'AppSearchFooter', name: 'AppSearchFooter',
components: { Icon }, components: { Icon },

View File

@ -56,17 +56,18 @@
</template> </template>
<script lang="ts"> <script lang="ts">
import { defineComponent, computed, unref, ref } from 'vue'; import { defineComponent, computed, unref, ref } from 'vue';
import { SearchOutlined } from '@ant-design/icons-vue';
import { Input } from 'ant-design-vue';
import AppSearchFooter from './AppSearchFooter.vue';
import Icon from '/@/components/Icon';
import clickOutside from '/@/directives/clickOutside';
import { useDesign } from '/@/hooks/web/useDesign'; import { useDesign } from '/@/hooks/web/useDesign';
import { useRefs } from '/@/hooks/core/useRefs'; import { useRefs } from '/@/hooks/core/useRefs';
import { useMenuSearch } from './useMenuSearch'; import { useMenuSearch } from './useMenuSearch';
import { SearchOutlined } from '@ant-design/icons-vue';
import AppSearchFooter from './AppSearchFooter.vue';
import { useI18n } from '/@/hooks/web/useI18n'; import { useI18n } from '/@/hooks/web/useI18n';
import { useAppInject } from '/@/hooks/web/useAppInject'; import { useAppInject } from '/@/hooks/web/useAppInject';
import clickOutside from '/@/directives/clickOutside';
import { Input } from 'ant-design-vue';
import Icon from '/@/components/Icon';
export default defineComponent({ export default defineComponent({
name: 'AppSearchModal', name: 'AppSearchModal',
@ -108,6 +109,11 @@
]; ];
}); });
function handleClose() {
searchResult.value = [];
emit('close');
}
return { return {
t, t,
prefixCls, prefixCls,
@ -120,10 +126,7 @@
setRefs, setRefs,
scrollWrap, scrollWrap,
handleMouseenter, handleMouseenter,
handleClose: () => { handleClose,
searchResult.value = [];
emit('close');
},
}; };
}, },
}); });

View File

@ -1,13 +1,17 @@
import { cloneDeep } from 'lodash-es';
import { ref, onBeforeMount, unref, Ref, nextTick } from 'vue';
import { useI18n } from '/@/hooks/web/useI18n';
import { getMenus } from '/@/router/menus';
import type { Menu } from '/@/router/types'; import type { Menu } from '/@/router/types';
import { ref, onBeforeMount, unref, Ref, nextTick } from 'vue';
import { getMenus } from '/@/router/menus';
import { cloneDeep } from 'lodash-es';
import { filter, forEach } from '/@/utils/helper/treeHelper'; import { filter, forEach } from '/@/utils/helper/treeHelper';
import { useDebounce } from '/@/hooks/core/useDebounce'; import { useDebounce } from '/@/hooks/core/useDebounce';
import { useGo } from '/@/hooks/web/usePage'; import { useGo } from '/@/hooks/web/usePage';
import { useScrollTo } from '/@/hooks/event/useScrollTo'; import { useScrollTo } from '/@/hooks/event/useScrollTo';
import { useKeyPress } from '/@/hooks/event/useKeyPress'; import { useKeyPress } from '/@/hooks/event/useKeyPress';
import { useI18n } from '/@/hooks/web/useI18n';
export interface SearchResult { export interface SearchResult {
name: string; name: string;

View File

@ -1,7 +1,3 @@
import { withInstall } from '../util';
import Authority from './src/index.vue'; import Authority from './src/index.vue';
withInstall(Authority);
export { Authority }; export { Authority };

View File

@ -10,9 +10,11 @@
<script lang="ts"> <script lang="ts">
import { defineComponent, computed } from 'vue'; import { defineComponent, computed } from 'vue';
import { RightOutlined } from '@ant-design/icons-vue'; import { RightOutlined } from '@ant-design/icons-vue';
import { propTypes } from '/@/utils/propTypes';
import { useDesign } from '/@/hooks/web/useDesign'; import { useDesign } from '/@/hooks/web/useDesign';
import { propTypes } from '/@/utils/propTypes';
export default defineComponent({ export default defineComponent({
name: 'BasicArrow', name: 'BasicArrow',
components: { RightOutlined }, components: { RightOutlined },

View File

@ -1,4 +1,4 @@
<script lang="ts"> <script lang="tsx">
import type { CSSProperties, PropType } from 'vue'; import type { CSSProperties, PropType } from 'vue';
import { defineComponent, computed, unref, h } from 'vue'; import { defineComponent, computed, unref, h } from 'vue';
@ -9,7 +9,9 @@
import { isString, isArray } from '/@/utils/is'; import { isString, isArray } from '/@/utils/is';
import { getSlot } from '/@/utils/helper/tsxHelper'; import { getSlot } from '/@/utils/helper/tsxHelper';
import { propTypes } from '/@/utils/propTypes'; import { propTypes } from '/@/utils/propTypes';
import { useDesign } from '/@/hooks/web/useDesign'; import { useDesign } from '/@/hooks/web/useDesign';
export default defineComponent({ export default defineComponent({
name: 'BasicHelp', name: 'BasicHelp',
components: { Tooltip }, components: { Tooltip },
@ -40,7 +42,7 @@
setup(props, { slots }) { setup(props, { slots }) {
const { prefixCls } = useDesign('basic-help'); const { prefixCls } = useDesign('basic-help');
const getOverlayStyleRef = computed( const getOverlayStyle = computed(
(): CSSProperties => { (): CSSProperties => {
return { return {
maxWidth: props.maxWidth, maxWidth: props.maxWidth,
@ -48,7 +50,7 @@
} }
); );
const getWrapStyleRef = computed( const getWrapStyle = computed(
(): CSSProperties => { (): CSSProperties => {
return { return {
color: props.color, color: props.color,
@ -65,12 +67,19 @@
const list = props.text; const list = props.text;
if (isString(list)) { if (isString(list)) {
return h('p', list); return <p>{list}</p>;
} }
if (isArray(list)) { if (isArray(list)) {
return list.map((item, index) => { return list.map((item, index) => {
return h('p', { key: item }, [props.showIndex ? `${index + 1}. ` : '', item]); return (
<p key={item}>
<>
{props.showIndex ? `${index + 1}. ` : ''}
{item}
</>
</p>
);
}); });
} }
@ -78,34 +87,19 @@
}; };
return () => { return () => {
return h( return (
// @ts-ignores <Tooltip
Tooltip, title={<div style={unref(getWrapStyle)}>{renderTitle()}</div>}
{ overlayClassName={`${prefixCls}__wrap`}
title: h( autoAdjustOverflow={true}
'div', overlayStyle={unref(getOverlayStyle)}
{ placement={props.placement as 'left'}
style: unref(getWrapStyleRef), getPopupContainer={() => getPopupContainer()}
}, >
[renderTitle()] <span class={prefixCls} style={unref(getMainStyleRef)}>
), {getSlot(slots) || <InfoCircleOutlined />}
overlayClassName: `${prefixCls}__wrap`, </span>
autoAdjustOverflow: true, </Tooltip>
overlayStyle: unref(getOverlayStyleRef),
placement: props.placement,
getPopupContainer: () => getPopupContainer(),
},
{
default: () =>
h(
'span',
{
class: prefixCls,
style: unref(getMainStyleRef),
},
getSlot(slots) || h(InfoCircleOutlined)
),
}
); );
}; };
}, },

View File

@ -8,11 +8,12 @@
import type { PropType } from 'vue'; import type { PropType } from 'vue';
import { defineComponent } from 'vue'; import { defineComponent } from 'vue';
import BasicHelp from './BasicHelp.vue'; import BasicHelp from './BasicHelp.vue';
import { propTypes } from '/@/utils/propTypes';
import { useDesign } from '/@/hooks/web/useDesign'; import { useDesign } from '/@/hooks/web/useDesign';
import { propTypes } from '/@/utils/propTypes';
export default defineComponent({ export default defineComponent({
name: 'BasicTitle', name: 'BasicTitle',
components: { BasicHelp }, components: { BasicHelp },

View File

@ -1,6 +1,4 @@
import Button from './src/BasicButton.vue'; import Button from './src/BasicButton.vue';
import PopConfirmButton from './src/PopConfirmButton.vue'; import PopConfirmButton from './src/PopConfirmButton.vue';
import { withInstall } from '../util';
withInstall(Button, PopConfirmButton);
export { Button, PopConfirmButton }; export { Button, PopConfirmButton };

View File

@ -12,6 +12,7 @@
import { Button } from 'ant-design-vue'; import { Button } from 'ant-design-vue';
import Icon from '/@/components/Icon'; import Icon from '/@/components/Icon';
import { propTypes } from '/@/utils/propTypes'; import { propTypes } from '/@/utils/propTypes';
export default defineComponent({ export default defineComponent({

View File

@ -2,12 +2,15 @@
import { defineComponent, h, unref, computed } from 'vue'; import { defineComponent, h, unref, computed } from 'vue';
import { Popconfirm } from 'ant-design-vue'; import { Popconfirm } from 'ant-design-vue';
import BasicButton from './BasicButton.vue'; import BasicButton from './BasicButton.vue';
import { propTypes } from '/@/utils/propTypes'; import { propTypes } from '/@/utils/propTypes';
import { useI18n } from '/@/hooks/web/useI18n';
import { extendSlots } from '/@/utils/helper/tsxHelper'; import { extendSlots } from '/@/utils/helper/tsxHelper';
import { omit } from 'lodash-es'; import { omit } from 'lodash-es';
import { useAttrs } from '/@/hooks/core/useAttrs'; import { useAttrs } from '/@/hooks/core/useAttrs';
import { useI18n } from '/@/hooks/web/useI18n';
export default defineComponent({ export default defineComponent({
name: 'PopButton', name: 'PopButton',

View File

@ -1,7 +1,3 @@
import { withInstall } from '../util';
import ClickOutSide from './src/index.vue'; import ClickOutSide from './src/index.vue';
withInstall(ClickOutSide);
export { ClickOutSide }; export { ClickOutSide };

View File

@ -1,8 +1,6 @@
import { withInstall } from '../util';
import CollapseContainer from './src/collapse/CollapseContainer.vue'; import CollapseContainer from './src/collapse/CollapseContainer.vue';
import ScrollContainer from './src/ScrollContainer.vue'; import ScrollContainer from './src/ScrollContainer.vue';
import LazyContainer from './src/LazyContainer.vue'; import LazyContainer from './src/LazyContainer.vue';
withInstall(ScrollContainer, CollapseContainer, LazyContainer);
export { CollapseContainer, ScrollContainer, LazyContainer }; export { CollapseContainer, ScrollContainer, LazyContainer };
export * from './src/types'; export * from './src/types';

View File

@ -1,9 +1,5 @@
import { withInstall } from '../util';
import BasicDrawer from './src/BasicDrawer.vue'; import BasicDrawer from './src/BasicDrawer.vue';
export { BasicDrawer }; export { BasicDrawer };
export * from './src/types'; export * from './src/types';
export { useDrawer, useDrawerInner } from './src/useDrawer'; export { useDrawer, useDrawerInner } from './src/useDrawer';
withInstall(BasicDrawer);

View File

@ -1,7 +1,4 @@
import { withInstall } from '../util';
import Dropdown from './src/Dropdown.vue'; import Dropdown from './src/Dropdown.vue';
withInstall(Dropdown);
export * from './src/types'; export * from './src/types';
export { Dropdown }; export { Dropdown };

View File

@ -1,7 +1,4 @@
import BasicForm from './src/BasicForm.vue'; import BasicForm from './src/BasicForm.vue';
import { withInstall } from '../util';
withInstall(BasicForm);
export * from './src/types/form'; export * from './src/types/form';
export * from './src/types/formItem'; export * from './src/types/formItem';

View File

@ -1,7 +1,4 @@
import { withInstall } from '../util';
import Icon from './src/index.vue'; import Icon from './src/index.vue';
withInstall(Icon);
export { Icon }; export { Icon };
export default Icon; export default Icon;

View File

@ -1,9 +1,6 @@
import './src/index.less'; import './src/index.less';
import { withInstall } from '../util';
import BasicModal from './src/BasicModal.vue'; import BasicModal from './src/BasicModal.vue';
withInstall(BasicModal);
export { BasicModal }; export { BasicModal };
export { useModalContext } from './src/hooks/useModalContext'; export { useModalContext } from './src/hooks/useModalContext';
export { useModal, useModalInner } from './src/hooks/useModal'; export { useModal, useModalInner } from './src/hooks/useModal';

View File

@ -2,10 +2,7 @@
* copy from element-ui * copy from element-ui
*/ */
import { withInstall } from '../util';
import Scrollbar from './src/index.vue'; import Scrollbar from './src/index.vue';
withInstall(Scrollbar);
export { Scrollbar }; export { Scrollbar };
export type { ScrollbarType } from './src/types'; export type { ScrollbarType } from './src/types';

View File

@ -1,13 +1,4 @@
import type { VNodeChild } from 'vue'; import type { VNodeChild } from 'vue';
import type { App } from 'vue';
export function withInstall(...components: any[]) {
components.forEach((comp) => {
comp.install = (app: App) => {
app.component(comp.displayName || comp.name, comp);
};
});
}
export function convertToUnit( export function convertToUnit(
str: string | number | null | undefined, str: string | number | null | undefined,

View File

@ -1,4 +1,4 @@
// button重置 // button reset
.ant-btn { .ant-btn {
// display: inline-flex; // display: inline-flex;
// justify-content: center; // justify-content: center;

View File

@ -28,17 +28,6 @@
} }
} }
// =================================
// ==============descriptions=======
// =================================
// .ant-descriptions-bordered .ant-descriptions-item-label {
// background-color: @background-color-light;
// }
// .ant-descriptions .ant-descriptions-item-content {
// color: @text-color-call-out;
// }
// ================================= // =================================
// ==============modal message====== // ==============modal message======
// ================================= // =================================
@ -57,18 +46,3 @@
.modal-icon-info { .modal-icon-info {
color: @primary-color !important; color: @primary-color !important;
} }
// =================================
// ==============empty==============
// =================================
.ant-empty-image {
max-height: 144px;
min-height: 60px;
}
.ant-empty-description {
margin-top: 16px;
font-size: 14px;
line-height: 24px;
color: @text-color-call-out;
}

View File

@ -1,4 +1,4 @@
import { Directive } from 'vue'; import type { Directive } from 'vue';
import './index.less'; import './index.less';
export interface RippleOptions { export interface RippleOptions {
event: string; event: string;

View File

@ -2,7 +2,7 @@ export default {
prefixCls: 'vben', prefixCls: 'vben',
}; };
// header preset color // app theme preset color
export const APP_PRESET_COLOR_LIST: string[] = [ export const APP_PRESET_COLOR_LIST: string[] = [
'#0084f4', '#0084f4',
'#009688', '#009688',

View File

@ -1,22 +1,25 @@
import type { GlobEnvConfig } from '/@/types/config'; import type { GlobEnvConfig } from '/@/types/config';
/**
* Get the global configuration (the configuration will be extracted independently when packaging)
*/
export function getGlobEnvConfig(): GlobEnvConfig { export function getGlobEnvConfig(): GlobEnvConfig {
const env = import.meta.env; const env = import.meta.env;
return (env as unknown) as GlobEnvConfig; return (env as unknown) as GlobEnvConfig;
} }
/** /**
* @description: * @description: Development model
*/ */
export const devMode = 'development'; export const devMode = 'development';
/** /**
* @description: * @description: Production mode
*/ */
export const prodMode = 'production'; export const prodMode = 'production';
/** /**
* @description: * @description: Get environment variables
* @returns: * @returns:
* @example: * @example:
*/ */
@ -25,7 +28,7 @@ export function getEnv(): string {
} }
/** /**
* @description: * @description: Is it a development mode
* @returns: * @returns:
* @example: * @example:
*/ */
@ -34,7 +37,7 @@ export function isDevMode(): boolean {
} }
/** /**
* @description: * @description: Is it a production mode
* @returns: * @returns:
* @example: * @example:
*/ */
@ -43,7 +46,7 @@ export function isProdMode(): boolean {
} }
/** /**
* @description: mock * @description: Whether to open mock
* @returns: * @returns:
* @example: * @example:
*/ */

View File

@ -2,6 +2,7 @@ const hexList: string[] = [];
for (let i = 0; i <= 15; i++) { for (let i = 0; i <= 15; i++) {
hexList[i] = i.toString(16); hexList[i] = i.toString(16);
} }
export function buildUUID(): string { export function buildUUID(): string {
let uuid = ''; let uuid = '';
for (let i = 1; i <= 36; i++) { for (let i = 1; i <= 36; i++) {