up uniapp

This commit is contained in:
全栈小学生 2026-03-20 15:57:45 +08:00
parent 81f85d8b92
commit 1bc4217bef
34 changed files with 949 additions and 921 deletions

File diff suppressed because it is too large Load Diff

View File

@ -24,7 +24,7 @@
"build:app-android": "uni build -p app-android",
"build:app-ios": "uni build -p app-ios",
"build:custom": "uni build -p",
"build:h5": "uni build && node publish.cjs h5 build",
"build:h5": "cross-env NODE_OPTIONS=--max-old-space-size=4096 && uni build && node publish.cjs h5 build",
"build:h5:ssr": "uni build --ssr",
"build:mp-alipay": "uni build -p mp-alipay",
"build:mp-baidu": "uni build -p mp-baidu",
@ -33,7 +33,7 @@
"build:mp-lark": "uni build -p mp-lark",
"build:mp-qq": "uni build -p mp-qq",
"build:mp-toutiao": "uni build -p mp-toutiao",
"build:mp-weixin": "uni build -p mp-weixin && node publish.cjs mp-weixin build",
"build:mp-weixin": "cross-env NODE_OPTIONS=--max-old-space-size=4096 && uni build -p mp-weixin && node publish.cjs mp-weixin build",
"build:quickapp-webview": "uni build -p quickapp-webview",
"build:quickapp-webview-huawei": "uni build -p quickapp-webview-huawei",
"build:quickapp-webview-union": "uni build -p quickapp-webview-union",
@ -83,6 +83,7 @@
"vite": "4.0.4",
"vite-plugin-windicss": "^1.8.10",
"vue-tsc": "^1.0.24",
"windicss": "^3.5.6"
"windicss": "^3.5.6",
"cross-env": "^7.0.3"
}
}

View File

@ -15,6 +15,7 @@ const main = () => {
if (mode == 'build') {
handleWeappAddonComponents(mode)
handleWeappLanguage(mode)
handleProjectConfig(mode)
} else if (mode == 'dev') {
listenWeappRunDev()
}
@ -96,6 +97,19 @@ const handleWeappLanguage = (mode) => {
}
}
const handleProjectConfig = (mode) => {
const src = `./dist/${mode}/mp-weixin/project.config.json`
try {
let content = fs.readFileSync(src, 'utf8');
const config = JSON.parse(content)
config.setting.minifyWXML = false
fs.writeFileSync(src, JSON.stringify(config))
} catch (err) {
console.log(err)
}
}
const listenWeappRunDev = () => {
const devProcess = spawn('npm', ['run', 'dev:niu-mp-weixin'], {
stdio: ['pipe', 'pipe', 'pipe'],
@ -112,6 +126,7 @@ const listenWeappRunDev = () => {
serverReady = true;
handleWeappAddonComponents('dev')
handleWeappLanguage('dev')
handleProjectConfig('dev')
}
});

View File

@ -1,172 +1,199 @@
<template>
<view class="diy-group" id="componentList">
<top-tabbar :scrollBool="diyGroup.componentsScrollBool.TopTabbar" v-if="data.global && Object.keys(data.global).length && data.global.topStatusBar && data.global.topStatusBar.isShow" ref="topTabbarRef" :data="data.global" />
<pop-ads v-if="data.global && Object.keys(data.global).length && data.global.popWindow && data.global.popWindow.show" ref="popAbsRef" :data="data.global" />
<top-tabbar
v-if="data.global && Object.keys(data.global).length && data.global.topStatusBar && data.global.topStatusBar.isShow"
:scrollBool="diyGroup.componentsScrollBool.TopTabbar" ref="topTabbarRef" :data="data.global"/>
<pop-ads
v-if="data.global && Object.keys(data.global).length && data.global.popWindow && data.global.popWindow.show"
ref="popAbsRef" :data="data.global"/>
<template v-for="(component, index) in data.value" :key="component.id">
<view v-show="component.componentIsShow"
@click="diyStore.changeCurrentIndex(index, component)"
<view v-show="component.componentIsShow" @click="diyStore.changeCurrentIndex(index, component)"
:class="diyGroup.getComponentClass(index,component)" :style="component.pageStyle">
<view class="relative" :style="{ marginTop : component.margin.top < 0 ? (component.margin.top * 2) + 'rpx' : '0', marginBottom : component.margin.bottom < 0 ? (component.margin.bottom * 2) + 'rpx' : '0' }">
<view class="relative"
:style="{ marginTop : component.margin.top < 0 ? (component.margin.top * 2) + 'rpx' : '0', marginBottom : component.margin.bottom < 0 ? (component.margin.bottom * 2) + 'rpx' : '0' }">
<!-- 装修模式下设置负上边距后超出的内容禁止选中设置 -->
<view v-if="diyGroup.isShowPlaceHolder(index,component)" class="absolute w-full z-1" :style="{ height : (component.margin.top * 2 * -1) + 'rpx' }" @click.stop="diyGroup.placeholderEvent"></view>
<template v-if="component.componentName == 'ActiveCube'">
<diy-active-cube ref="diyActiveCubeRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.ActiveCube" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'CarouselSearch'">
<diy-carousel-search ref="diyCarouselSearchRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.CarouselSearch" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FloatBtn'">
<diy-float-btn ref="diyFloatBtnRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FloatBtn" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormAddress'">
<diy-form-address ref="diyFormAddressRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormAddress" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormCheckbox'">
<diy-form-checkbox ref="diyFormCheckboxRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormCheckbox" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormDate'">
<diy-form-date ref="diyFormDateRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormDate" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormDateScope'">
<diy-form-date-scope ref="diyFormDateScopeRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormDateScope" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormEmail'">
<diy-form-email ref="diyFormEmailRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormEmail" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormFile'">
<diy-form-file ref="diyFormFileRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormFile" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormIdentity'">
<diy-form-identity ref="diyFormIdentityRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormIdentity" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormIdentityPrivacy'">
<diy-form-identity-privacy ref="diyFormIdentityPrivacyRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormIdentityPrivacy" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormImage'">
<diy-form-image ref="diyFormImageRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormImage" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormInput'">
<diy-form-input ref="diyFormInputRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormInput" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormLocation'">
<diy-form-location ref="diyFormLocationRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormLocation" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormMobile'">
<diy-form-mobile ref="diyFormMobileRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormMobile" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormNumber'">
<diy-form-number ref="diyFormNumberRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormNumber" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormPrivacy'">
<diy-form-privacy ref="diyFormPrivacyRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormPrivacy" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormPrivacyPop'">
<diy-form-privacy-pop ref="diyFormPrivacyPopRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormPrivacyPop" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormRadio'">
<diy-form-radio ref="diyFormRadioRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormRadio" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormSubmit'">
<diy-form-submit ref="diyFormSubmitRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormSubmit" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormTable'">
<diy-form-table ref="diyFormTableRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormTable" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormTextarea'">
<diy-form-textarea ref="diyFormTextareaRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormTextarea" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormTime'">
<diy-form-time ref="diyFormTimeRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormTime" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormTimeScope'">
<diy-form-time-scope ref="diyFormTimeScopeRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormTimeScope" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormVideo'">
<diy-form-video ref="diyFormVideoRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormVideo" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'FormWechatName'">
<diy-form-wechat-name ref="diyFormWechatNameRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.FormWechatName" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<view v-if="diyGroup.isShowPlaceHolder(index,component)" class="absolute w-full z-1"
:style="{ height : (component.margin.top * 2 * -1) + 'rpx' }"
@click.stop="diyGroup.placeholderEvent"></view>
<template v-if="component.componentName == 'GraphicNav'">
<diy-graphic-nav ref="diyGraphicNavRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.GraphicNav" @update:componentIsShow="component.componentIsShow = $event" />
<diy-graphic-nav :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'HorzBlank'">
<diy-horz-blank ref="diyHorzBlankRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.HorzBlank" @update:componentIsShow="component.componentIsShow = $event" />
<diy-horz-blank :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'HorzLine'">
<diy-horz-line ref="diyHorzLineRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.HorzLine" @update:componentIsShow="component.componentIsShow = $event" />
<diy-horz-line :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'HotArea'">
<diy-hot-area ref="diyHotAreaRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.HotArea" @update:componentIsShow="component.componentIsShow = $event" />
<diy-hot-area :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'ImageAds'">
<diy-image-ads ref="diyImageAdsRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.ImageAds" @update:componentIsShow="component.componentIsShow = $event" />
<diy-image-ads :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'MemberInfo'">
<diy-member-info ref="diyMemberInfoRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.MemberInfo" @update:componentIsShow="component.componentIsShow = $event" />
<diy-member-info :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'MemberLevel'">
<diy-member-level ref="diyMemberLevelRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.MemberLevel" @update:componentIsShow="component.componentIsShow = $event" />
<diy-member-level :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'Notice'">
<diy-notice ref="diyNoticeRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.Notice" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'PictureShow'">
<diy-picture-show ref="diyPictureShowRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.PictureShow" @update:componentIsShow="component.componentIsShow = $event" />
</template>
<template v-if="component.componentName == 'RichText'">
<diy-rich-text ref="diyRichTextRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.RichText" @update:componentIsShow="component.componentIsShow = $event" />
<diy-notice :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'RubikCube'">
<diy-rubik-cube ref="diyRubikCubeRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.RubikCube" @update:componentIsShow="component.componentIsShow = $event" />
<diy-rubik-cube :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'Text'">
<diy-text ref="diyTextRef" :component="component" :global="data.global" :index="index" :scrollBool="diyGroup.componentsScrollBool.Text" @update:componentIsShow="component.componentIsShow = $event" />
<diy-text :component="component" :global="data.global" :index="index"/>
</template>
</view>
</view>
<template v-if="component.componentName == 'RichText'">
<diy-rich-text :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="diyStore.mode == '' && data.global && diyGroup.showCopyright.value && data.global.copyright && data.global.copyright.isShow">
<copy-right :textColor="data.global.copyright.textColor" />
<template v-if="component.componentName == 'ActiveCube'">
<diy-active-cube :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'FloatBtn'">
<diy-float-btn :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'CarouselSearch'">
<diy-carousel-search :scrollBool="diyGroup.componentsScrollBool.CarouselSearch"
:component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'PictureShow'">
<diy-picture-show :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'FormSubmit'">
<diy-form-submit :component="component" :global="data.global" :index="index"/>
</template>
<template v-if="component.componentName == 'FormInput'">
<diy-form-input ref="diyFormInputRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormTextarea'">
<diy-form-textarea ref="diyFormTextareaRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormIdentity'">
<diy-form-identity ref="diyFormIdentityRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormEmail'">
<diy-form-email ref="diyFormEmailRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormMobile'">
<diy-form-mobile ref="diyFormMobileRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormWechatName'">
<diy-form-wechat-name ref="diyFormWechatNameRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormNumber'">
<diy-form-number ref="diyFormNumberRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormRadio'">
<diy-form-radio ref="diyFormRadioRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormCheckbox'">
<diy-form-checkbox ref="diyFormCheckboxRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormTable'">
<diy-form-table ref="diyFormTableRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormDate'">
<diy-form-date ref="diyFormDateRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormDateScope'">
<diy-form-date-scope ref="diyFormDateScopeRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormTime'">
<diy-form-time ref="diyFormTimeRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormTimeScope'">
<diy-form-time-scope ref="diyFormTimeScopeRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormLocation'">
<diy-form-location ref="diyFormLocationRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormAddress'">
<diy-form-address ref="diyFormAddressRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormImage'">
<diy-form-image ref="diyFormImageRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormVideo'">
<diy-form-video ref="diyFormVideoRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="component.componentName == 'FormFile'">
<diy-form-file ref="diyFormFileRef" :component="component" :global="data.global"
:index="index"/>
</template>
<template v-if="diyStore.mode == '' && data.global && data.global.bottomTabBar && data.global.bottomTabBar.isShow">
</view>
</view>
</template>
<template
v-if="data.global && diyGroup.showCopyright.value && data.global.copyright && data.global.copyright.isShow">
<copy-right :textColor="data.global.copyright.textColor"/>
</template>
<template
v-if="diyStore.mode == '' && data.global && data.global.bottomTabBar && data.global.bottomTabBar.isShow">
<view class="pt-[20rpx]"></view>
<tabbar :addon="data.global.bottomTabBar.designNav.key" />
<tabbar :addon="data.global.bottomTabBar.designNav?.key"/>
</template>
</view>
</template>
<script lang="ts" setup>
import topTabbar from '@/components/top-tabbar/top-tabbar.vue'
import popAds from '@/components/pop-ads/pop-ads.vue'
import useDiyStore from '@/app/stores/diy';
import { useDiyGroup } from './useDiyGroup';
import { ref,getCurrentInstance } from 'vue';
const props = defineProps(['data']);
const instance: any = getCurrentInstance();
const getFormRef = () => {
import topTabbar from '@/components/top-tabbar/top-tabbar.vue'
import popAds from '@/components/pop-ads/pop-ads.vue'
import { useDiyGroup } from './useDiyGroup'
import useDiyStore from '@/app/stores/diy';
import { ref, getCurrentInstance } from 'vue';
const props = defineProps(['data']);
const instance: any = getCurrentInstance();
const getFormRef = () => {
return {
componentRefs: instance.refs
}
}
const diyStore = useDiyStore();
const diyGroup = useDiyGroup({
}
const diyStore = useDiyStore();
const diyGroup = useDiyGroup({
...props,
getFormRef
});
const data = ref(diyGroup.data);
});
//
diyGroup.onMounted();
const data = ref(diyGroup.data)
//
diyGroup.onPageScroll();
defineExpose({
//
diyGroup.onMounted()
//
diyGroup.onPageScroll()
defineExpose({
refresh: diyGroup.refresh,
getFormRef
})
})
</script>
<style lang="scss" scoped>
@import './index.scss';
@import './index.scss';
</style>

View File

@ -152,6 +152,7 @@ export function useDiyGroup(params: any = {}) {
})
onHide(() => {
isPagesHide.value = true;
diyStore.global.bottomTabBar.isShow = false
})
// 监听滚动事件

View File

@ -46,7 +46,7 @@ export function sendSms(data: AnyObject) {
* jssdk config
*/
export function getWechatSdkConfig(data: AnyObject) {
return request.get('wechat/jssdkconfig', data, { showErrorMessage: false })
return request.get('wechat/jssdkconfig', data, { showErrorMessage: true })
}
/**
@ -76,6 +76,15 @@ export function fetchBase64Image(data: AnyObject) {
export function uploadVideo(data: AnyObject) {
return request.upload('file/video', data, { showErrorMessage: true })
}
/**
*
*/
export function uploadConfig() {
return request.get('file/config')
}
/**
*
*/

View File

@ -72,9 +72,9 @@
</view>
<view class="calendar-wrap">
<u-calendar :show="calendarShow" mode="range" @confirm="confirm" @close="calendarShow=false"
closeOnClickOverlay="true"
closeOnClickOverlay="true" :min-date="calendarMinDate" monthNum="12"
:defaultDate="defaultDate" startText="开始" endText="结束" confirmDisabledText="禁止选择"
color="var(--primary-color)" ref="calendar" monthNum="2"></u-calendar>
color="var(--primary-color)" ref="calendar"></u-calendar>
</view>
<!-- 遮罩层装修使用 -->
@ -94,6 +94,8 @@ const diyStore = useDiyStore();
const calendarShow = ref(false);
const errorInfo: any = ref(null);
let currentDateTime = new Date();
const calendarMinDate = ref(new Date(currentDateTime.getFullYear(), currentDateTime.getMonth() - 9, currentDateTime.getDate()));
const diyComponent = computed(() => {
if (diyStore.mode == 'decorate') {

View File

@ -61,8 +61,8 @@
</view>
<view class="calendar-wrap">
<u-calendar :show="calendarShow" mode="single" @confirm="confirm" @close="calendarShow=false"
closeOnClickOverlay="true"
:formatter="formatter" confirmDisabledText="禁止选择" color="var(--primary-color)"
closeOnClickOverlay="true" :min-date="calendarMinDate"
:formatter="formatter" confirmDisabledText="禁止选择" color="var(--primary-color)" monthNum="12"
ref="calendar" :maxDate="maxDate"></u-calendar>
<u-datetime-picker :show="show" v-model="diyComponent.field.value.date" mode="datetime" @cancel="show=false"
closeOnClickOverlay="true" @confirm="calendarConfirm" @close="show=false"
@ -86,6 +86,7 @@ const maxDate = ref(currentDate.getTime());
let currentDateTime = new Date();
const minDate = ref(currentDateTime.getTime());
const calendarMinDate = ref(new Date(currentDateTime.getFullYear(), currentDateTime.getMonth() - 9, currentDateTime.getDate()));
const props = defineProps(['component', 'index', 'global']);
const diyStore = useDiyStore();

View File

@ -32,7 +32,10 @@
<view class="w-full flex items-center justify-center mb-[40rpx]" v-if="loginConfig.is_auth_register">
<!-- 开启强制绑定手机号或者手机号登录的情况排除强制获取用户信息的情况is_force_access_user_info为0 -->
<button v-if="!wapMemberMobile && loginConfig.is_bind_mobile && !loginConfig.is_force_access_user_info" class="w-[630rpx] h-[88rpx] !bg-[var(--primary-color)] !mx-[0] text-[26rpx] rounded-[44rpx] leading-[88rpx] font-500 !text-[#fff]" :open-type="openType" @getphonenumber="mobileAuth" @click="checkWxPrivacy">{{ t('quickLoginOrLogout') }}</button>
<template v-if="!wapMemberMobile && loginConfig.is_bind_mobile && !loginConfig.is_force_access_user_info">
<button v-if="!privacyAgreed" class="w-[630rpx] h-[88rpx] !bg-[var(--primary-color)] !mx-[0] text-[26rpx] rounded-[44rpx] leading-[88rpx] font-500 !text-[#fff]" @click="callProtocolFn">{{ t('quickLoginOrLogout') }}</button>
<button v-else class="w-[630rpx] h-[88rpx] !bg-[var(--primary-color)] !mx-[0] text-[26rpx] rounded-[44rpx] leading-[88rpx] font-500 !text-[#fff]" :open-type="openType" @getphonenumber="mobileAuth" @click="checkWxPrivacy">{{ t('quickLoginOrLogout') }}</button>
</template>
<!-- 授权登录/注册 -->
<button v-else class="w-[630rpx] h-[88rpx] !mx-[0] !bg-[var(--primary-color)] text-[26rpx] rounded-[44rpx] leading-[88rpx] font-500 !text-[#fff]" @click="oneClickLogin()">{{ t('quickLoginOrLogout') }}</button>
@ -41,12 +44,15 @@
<!-- 未开启第三方登录/注册但是开启了手机号登录则一键手机号登录/注册 -->
<view class="w-full flex items-center justify-center mb-[40rpx]" v-else-if="!loginConfig.is_auth_register && loginConfig.is_mobile">
<button v-if="!wapMemberMobile" class="w-[630rpx] h-[88rpx] !bg-[var(--primary-color)] !mx-[0] text-[26rpx] rounded-[44rpx] leading-[88rpx] font-500 !text-[#fff]" :open-type="openType" @getphonenumber="mobileAuth" @click="checkWxPrivacy('mobileAuth')">{{ t('quickLoginOrLogout') }}</button>
<template v-if="!wapMemberMobile">
<button v-if="!privacyAgreed" class="w-[630rpx] h-[88rpx] !bg-[var(--primary-color)] !mx-[0] text-[26rpx] rounded-[44rpx] leading-[88rpx] font-500 !text-[#fff]" @click="callProtocolFn">{{ t('quickLoginOrLogout') }}</button>
<button v-else class="w-[630rpx] h-[88rpx] !bg-[var(--primary-color)] !mx-[0] text-[26rpx] rounded-[44rpx] leading-[88rpx] font-500 !text-[#fff]" :open-type="openType" @getphonenumber="mobileAuth" @click="checkWxPrivacy('mobileAuth')">{{ t('quickLoginOrLogout') }}</button>
</template>
<button v-else class="w-[630rpx] h-[88rpx] !bg-[var(--primary-color)] !mx-[0] text-[26rpx] rounded-[44rpx] leading-[88rpx] font-500 !text-[#fff]" @click="oneClickLogin()">{{ t('quickLoginOrLogout') }}</button>
</view>
<!-- 小程序隐私协议 -->
<wx-privacy-popup ref="wxPrivacyPopupRef"></wx-privacy-popup>
<wx-privacy-popup ref="wxPrivacyPopupRef" @disagree="checkPrivacyStatus" @agree="checkPrivacyStatus"></wx-privacy-popup>
<!-- #endif -->
@ -237,6 +243,20 @@ onShow(() => {
loginLoading.value = false;
})
//
const privacyAgreed = ref(true)
const checkPrivacyStatus = () => {
// uniapp
wx.getPrivacySetting({
success(res) {
privacyAgreed.value = !res.needAuthorization;
},
fail(err) {
console.error('检查隐私协议失败:', err);
}
});
}
const warpStyle = computed(() => {
let style = '';
if (configStore.login.bg_url) {
@ -249,6 +269,7 @@ const warpStyle = computed(() => {
})
//
const checkWxPrivacy = (status: any = '') => {
if (!isAgree.value && configStore.login.agreement_show) {
//
@ -262,6 +283,15 @@ const checkWxPrivacy = (status: any = '') => {
return false;
}
const callProtocolFn = ()=>{
// #ifdef MP
if (wxPrivacyPopupRef.value) {
wxPrivacyPopupRef.value.proactive();
return true
}
// #endif
}
//
const oneClickLogin = (callback: any = null, data: any = null) => {
if (checkWxPrivacy()) return;

View File

@ -19,6 +19,9 @@
<wx-privacy-popup ref="wxPrivacyPopupRef"></wx-privacy-popup>
<!-- #endif -->
<template v-if="diyStore && diyStore.mode == '' && diyStore.global && diyStore.global.bottomTabBar && diyStore.global.bottomTabBar.isShow">
<tabbar :addon="diyStore.global.bottomTabBar.designNav?.key" />
</template>
</view>
</template>
@ -27,9 +30,10 @@ import { ref, nextTick } from 'vue';
import { useDiy } from '@/hooks/useDiy'
import { useShare } from '@/hooks/useShare'
import diyGroup from '@/addon/components/diy/group/index.vue'
import useDiyStore from '@/app/stores/diy'
const { setShare } = useShare()
const diyStore = useDiyStore()
const diy = useDiy({})
const diyGroupRef = ref(null)

View File

@ -23,6 +23,10 @@
<!-- #ifdef APP -->
<update-version ref="updateVersionRef"></update-version>
<!-- #endif -->
<template v-if="diyStore && diyStore.mode == '' && diyStore.global && diyStore.global.bottomTabBar && diyStore.global.bottomTabBar.isShow">
<tabbar :addon="diyStore.global.bottomTabBar.designNav?.key" />
</template>
</view>
</template>
@ -34,9 +38,12 @@ import { useShare } from '@/hooks/useShare'
import diyGroup from '@/addon/components/diy/group/index.vue'
import updateVersion from '@/components/update-version/update-version.vue'
import useSystemStore from '@/stores/system';
import useDiyStore from '@/app/stores/diy'
const { setShare } = useShare()
const diyStore = useDiyStore()
uni.hideTabBar() // tabbar
const diy = useDiy({

View File

@ -74,14 +74,15 @@
</template>
<script setup lang="ts">
import { ref, computed, nextTick } from 'vue'
import { ref, computed, nextTick, onMounted } from 'vue'
import { onLoad } from '@dcloudio/uni-app'
import { redirect } from '@/utils/common'
import { deepClone, redirect } from '@/utils/common'
import { t } from '@/locale'
import { addAddress, editAddress, getAddressInfo } from '@/app/api/member'
import manifestJson from '@/manifest.json'
import { getAddressByLatlng,getAreatree } from '@/app/api/system'
import useSystemStore from '@/stores/system';
import { useLocation } from '@/hooks/useLocation'
const systemStore = useSystemStore();
const formData: any = ref({
@ -296,7 +297,6 @@ const chooseLocation = () => {
// #ifdef H5
const urlencode = formData.value;
uni.setStorageSync('addressInfo', urlencode);
let backurl = location.origin + location.pathname + '?source=' + source.value;
if (isSelectMap.value) {
backurl = backurl + '&isSelectMap=' + isSelectMap.value
@ -318,6 +318,7 @@ const getAddress = (latlng: any) => {
formData.value.full_address += res.data.district != undefined ? '' + res.data.district : '';
formData.value.address_name = formData.value.full_address.replace(/-/g, '');
formData.value.area = (res.data.province + res.data.city + res.data.district) || res.data.full_address;
formData.value.province_id = res.data.province_id != undefined ? res.data.province_id : 0;
formData.value.city_id = res.data.city_id != undefined ? res.data.city_id : 0;
@ -362,6 +363,7 @@ const findIdByNameAndParentId = (list, name, parentId = 0) => {
}
return '';
};
const loadingchoosegAddress = ref(false)
const choosegAddress = () =>{
loadingchoosegAddress.value = true
@ -386,6 +388,35 @@ const choosegAddress = () =>{
}
});
}
onMounted(()=>{
// #ifdef MP
uni.authorize({
scope: 'scope.userLocation',
success: (res) => {},
fail: () => {
//
uni.showModal({
title: '位置授权',
content: '需要位置授权才能快速选地址,是否前往设置?',
confirmText: '去设置',
success: (res) => {
if (res.confirm) {
uni.openSetting({
success: (settingRes) => {
if (settingRes.authSetting['scope.userLocation']) {
const locationVal = useLocation(true);
locationVal.init();
}
}
});
}
}
});
}
})
// #endif
})
</script>
<style lang="scss" scoped>

View File

@ -1,6 +1,6 @@
<template>
<view class="min-h-[100vh] !bg-[var(--page-bg-color)]" :style="themeColor()" v-if="memberStore.info">
<view class="fixed w-full z-2 !bg-[var(--page-bg-color)]">
<view class="fixed w-full z-2 !bg-[var(--page-bg-color)] container">
<view class="pb-[190rpx] text-[#fff] w-full" :style="headerStyle">
<!-- #ifdef MP-WEIXIN || APP-PLUS -->
<top-tabbar :data="param" class="top-header" />
@ -125,7 +125,7 @@ onShow(() => {
for (let key in res.data) {
cashOutConfigObj[key] = res.data[key];
}
setTimeout(() => calculateMescrollTop(), 200);
})
if (systemStore.siteAddons.includes('recharge')) {
rechargeConfig().then((res: any) => {
@ -145,24 +145,38 @@ const headerStyle = computed(() => {
}
})
const mescrollTop = computed(() => {
// ref
const mescrollTop = ref('0rpx');
//
const calculateMescrollTop = () => {
const query = uni.createSelectorQuery()
query.select('.container').boundingClientRect(rect => {
if (rect) {
//
const topVal = pxToRpx(rect.height)
mescrollTop.value = topVal + 'rpx';
} else {
//
if ((cashOutConfigObj.is_open == 1 || rechargeConfigObj.is_use == 1)) {
if (Object.keys(systemStore.menuButtonInfo).length) {
return (pxToRpx(Number(systemStore.menuButtonInfo.height)) + pxToRpx(systemStore.menuButtonInfo.top) + pxToRpx(8) + 700) + 'rpx'
mescrollTop.value = (pxToRpx(Number(systemStore.menuButtonInfo.height)) + pxToRpx(systemStore.menuButtonInfo.top) + pxToRpx(8) + 700) + 'rpx'
} else {
return '718rpx'
mescrollTop.value = '718rpx'
}
} else {
// #ifdef APP-PLUS
return (pxToRpx(Number(systemStore.systemInfo.statusBarHeight)) + pxToRpx(8) + 632) + 'rpx'
mescrollTop.value = (pxToRpx(Number(systemStore.systemInfo.statusBarHeight)) + pxToRpx(8) + 632) + 'rpx'
// #endif
if (Object.keys(systemStore.menuButtonInfo).length) {
return (pxToRpx(Number(systemStore.menuButtonInfo.height)) + pxToRpx(systemStore.menuButtonInfo.top) + pxToRpx(8) + 632) + 'rpx'
mescrollTop.value = (pxToRpx(Number(systemStore.menuButtonInfo.height)) + pxToRpx(systemStore.menuButtonInfo.top) + pxToRpx(8) + 632) + 'rpx'
} else {
return '650rpx'
mescrollTop.value = '650rpx'
}
}
})
}
}).exec();
};
//
const accountTypeList = ref([

View File

@ -18,6 +18,9 @@
<wx-privacy-popup ref="wxPrivacyPopupRef"></wx-privacy-popup>
<!-- #endif -->
<template v-if="diyStore && diyStore.mode == '' && diyStore.global && diyStore.global.bottomTabBar && diyStore.global.bottomTabBar.isShow">
<tabbar :addon="diyStore.global.bottomTabBar.designNav?.key" />
</template>
</view>
</template>
@ -28,9 +31,11 @@ import { useShare } from '@/hooks/useShare'
import { redirect } from '@/utils/common';
import diyGroup from '@/addon/components/diy/group/index.vue'
import useMemberStore from '@/stores/member'
import useDiyStore from '@/app/stores/diy'
//
const memberStore = useMemberStore()
const diyStore = useDiyStore()
const userInfo = computed(() => memberStore.info)
const { setShare } = useShare()

View File

@ -1,6 +1,6 @@
<template>
<view class="bg-[var(--page-bg-color)] min-h-[100vh]" :style="themeColor()">
<view class="fixed left-0 right-0 top-0 z-10085">
<view class="fixed left-0 right-0 top-0 z-10085 container">
<view class="bg-[#f6f6f6] px-[30rpx] h-[88rpx] pt-[10rpx] flex-center relative z-10084">
<view class="search-input bg-[#fff]">
<view class="flex-1 text-[24rpx] leading-[60rpx] text-[var(--text-color-light9)]" :class="{'!text-[#333]':from_type}" @click="typePopup = true">{{ from_type_name || '请选择来源用途' }}</view>
@ -31,7 +31,7 @@
</view>
</view>
</view>
<mescroll-body ref="mescrollRef" @init="mescrollInit" :down="{ use: false }" @up="getPointListFn" top="185rpx">
<mescroll-body ref="mescrollRef" @init="mescrollInit" :down="{ use: false }" @up="getPointListFn" :top="mescrollTop">
<view v-for="(item,index) in pointList" :key="index"
class="sidebar-margin card-template mt-[var(--top-m)]">
<view class="flex justify-between items-center">
@ -73,7 +73,7 @@
<script setup lang="ts">
import { reactive, ref } from 'vue'
import { t } from '@/locale'
import { redirect, img } from '@/utils/common';
import { redirect, img ,pxToRpx} from '@/utils/common';
import { getPointList, getPointType } from '@/app/api/member';
import MescrollBody from '@/components/mescroll/mescroll-body/mescroll-body.vue';
import MescrollEmpty from '@/components/mescroll/mescroll-empty/mescroll-empty.vue';
@ -96,6 +96,21 @@ const typeList = ref([
{ name: '支出', status: 'disburse' }
])
const mescrollTop = ref('0rpx');
//
const calculateMescrollTop = () => {
const query = uni.createSelectorQuery()
query.select('.container').boundingClientRect(rect => {
if (rect) {
//
const topVal = pxToRpx(rect.height)
mescrollTop.value = topVal + 'rpx';
} else {
//
mescrollTop.value = '185rpx';
}
}).exec();
};
const getPointListFn = (mescroll: any) => {
let data = {
page: mescroll.num,
@ -129,6 +144,7 @@ const getPointTypeFn = () => {
getPointType('point').then((res: any) => {
pointType.value = res.data
})
setTimeout(() => calculateMescrollTop(), 200);
}
getPointTypeFn()
//

View File

@ -58,9 +58,10 @@
<text class="text-[28rpx] text-[#333]">{{ subItem.value }}</text>
</view>
</view>
<view class="common-tab-bar w-[100%]"></view>
<view class="common-tab-bar w-[100%]">
<view class="common-tab-bar-placeholder"></view>
<view class="verify-tab-bar fixed flex-center !text-[26rpx] rounded-[50rpx] h-[80rpx] left-[20rpx] right-[20rpx] text-[#fff] font-500" :class="verifyInfo.is_can_use ? 'primary-btn-bg' : 'bg-[#ccc]'" @click="verifyFn">确定</view>
</view>
</template>
<loading-page :loading="loading"></loading-page>
</view>

View File

@ -5,7 +5,7 @@
示例版权信息
</view>
</template>
<tempalte v-else>
<template v-else>
<view class="flex flex-col justify-center items-center p-[30rpx]" :style="{ color:textColor}">
<img :src="img(systemStore.copyright.logo)" mode="heightFix" class="max-h-[60rpx]" v-if="systemStore.copyright?.logo" />
<view class="text-[22rpx] mt-[20rpx]" v-if="systemStore.copyright?.copyright_desc" @click="systemStore.copyright?.copyright_link && redirect({ url: systemStore.copyright.copyright_link})">
@ -19,7 +19,7 @@
{{ systemStore.copyright.gov_record }}
</view>
</view>
</tempalte>
</template>
</view>
</template>

View File

@ -148,7 +148,7 @@ const confirmPay = () => {
// #ifndef H5
uni.requestPayment({
provider: 'alipay',
...res.data,
orderInfo: res.data,
success: (res: any) => {
toPayResult()
},

View File

@ -1,11 +1,13 @@
<template>
<template v-if="tabbar && Object.keys(tabbar).length">
<u-tabbar :value="value" zIndex="9999" :fixed="true" :placeholder="true" :safeAreaInsetBottom="true" :inactive-color="tabbar.value.textColor" :active-color="tabbar.value.textHoverColor" :border="props.border" class="custom-tabbar">
<u-tabbar :value="value" zIndex="9999" :fixed="true" :placeholder="true" :safeAreaInsetBottom="false" :inactive-color="tabbar.value.textColor" :active-color="tabbar.value.textHoverColor" :border="props.border" class="custom-tabbar">
<view class="safe-area flex bg-white" :style="{'background-color': tabbar.value.backgroundColor}">
<template v-for="item in tabbar.value.list">
<u-tabbar-item class="py-[5rpx]" :custom-style="{'background-color': tabbar.value.backgroundColor}" :text="item.text" :icon="img(value == item.link.url ? item.iconSelectPath : item.iconPath)" :name="item.link.url" v-if="tabbar.value.type == 1" @click="itemBtn(item.link.url)"></u-tabbar-item>
<u-tabbar-item class="py-[5rpx]" :custom-style="{'background-color': tabbar.value.backgroundColor}" :icon="img(value == item.link.url ? item.iconSelectPath : item.iconPath)" :name="item.link.url" v-if="tabbar.value.type == 2" @click="itemBtn(item.link.url)"></u-tabbar-item>
<u-tabbar-item class="py-[5rpx]" :custom-style="{'background-color': tabbar.value.backgroundColor}" :text="item.text" :name="item.link.url" v-if="tabbar.value.type == 3" @click="itemBtn(item.link.url)"></u-tabbar-item>
</template>
</view>
</u-tabbar>
<view class="tab-bar-placeholder"></view>
</template>
@ -201,6 +203,12 @@ nextTick(() => {
padding-bottom: calc(constant(safe-area-inset-bottom) + 50px);
padding-bottom: calc(env(safe-area-inset-bottom) + 50px);
}
.safe-area {
background: white;
width: 100%;
padding-bottom: calc(constant(safe-area-inset-bottom) + 1px);
padding-bottom: calc(env(safe-area-inset-bottom) + 1px);
}
</style>
<style lang="scss">
@ -226,6 +234,5 @@ nextTick(() => {
font-size: 20rpx !important;
}
}
/* #endif */
</style>

View File

@ -194,7 +194,7 @@ const isBackShow = computed(() => {
let bool = false;
if (props.isBack && pages.length > 1) {
bool = true;
} else if (currRoute() == 'app/pages/auth/index') {
} else if (currRoute() == 'app/pages/auth/index' || currRoute() == 'app/pages/auth/login') {
bool = true;
}
return bool;

View File

@ -143,6 +143,9 @@ export function useDiy(params: any = {}) {
}
});
diyStore.global = diyData.global
diyStore.value = diyData.value
// 控制自定义头部是否出现 | 微信小程序
isShowTopTabbar.value = diyData.value.some((item: any) => {
return item && item.position && item.position == 'top_fixed'

View File

@ -42,5 +42,187 @@
"pages.verify.record": "核销记录",
"pages.friendspay.share": "找朋友帮忙付",
"pages.friendspay.money": "",
"pages.webview.index": ""
"pages.webview.index": "",
"tourism.pages.way.list": "线路列表",
"tourism.pages.way.detail": "线路详情",
"tourism.pages.way.order": "线路订单",
"tourism.pages.hotel.list": "酒店列表",
"tourism.pages.hotel.detail": "酒店详情",
"tourism.pages.hotel.order": "酒店订单",
"tourism.pages.scenic.list": "景点列表",
"tourism.pages.scenic.detail": "景点详情",
"tourism.pages.scenic.order": "景点订单",
"tourism.pages.order.list": "旅游订单",
"tourism.pages.order.detail": "订单详情",
"tourism.pages.verify.index": "核销",
"tourism.pages.verify.record": "核销记录",
"tourism.pages.verify.detail": "核销详情",
"vipcard.pages.verify.index": "核销",
"vipcard.pages.verify.record": "核销记录",
"vipcard.pages.verify.detail": "核销详情",
"vipcard.pages.order.payment": "订单结算",
"vipcard.pages.order.list": "订单列表",
"vipcard.pages.order.my_reserved": "我的预约",
"vipcard.pages.order.my_reserved_detail": "我的预约详情",
"vipcard.pages.order.my_card": "我的卡项",
"vipcard.pages.order.detail": "订单详情",
"vipcard.pages.service.list": "项目列表",
"vipcard.pages.card.list": "卡项列表",
"vipcard.pages.card.detail": "卡项详情",
"recharge.pages.recharge": "充值",
"recharge.pages.recharge_record": "充值记录",
"recharge.pages.recharge_record_detail": "充值记录详情",
"shop.pages.goods.search": "搜索",
"shop.pages.goods.cart": "购物车",
"shop.pages.goods.collect": "商品收藏",
"shop.pages.goods.browse": "我的足迹",
"shop.pages.goods.category": "商品分类",
"shop.pages.goods.detail": "商品详情",
"shop.pages.goods.list": "商品列表",
"shop.pages.goods.rank": "排行榜",
"shop.pages.member.index": "个人中心",
"shop.pages.member.my_coupon": "我的优惠券",
"shop.pages.order.list": "订单列表",
"shop.pages.order.detail": "订单详情",
"shop.pages.order.payment": "待付款订单",
"shop.pages.evaluate.order_evaluate": "商品评价",
"shop.pages.evaluate.order_evaluate_view": "商品评价",
"shop.pages.evaluate.list": "评价列表",
"shop.pages.coupon.list": "优惠券列表",
"shop.pages.coupon.detail": "优惠券详情",
"shop.pages.discount.list": "限时折扣",
"shop.pages.refund.list": "退款列表",
"shop.pages.refund.detail": "退款详情",
"shop.pages.refund.apply": "申请退款",
"shop.pages.refund.edit_apply": "编辑退款信息",
"shop.pages.refund.log": "协商记录",
"shop.pages.point.index": "积分商城",
"shop.pages.point.list": "积分商品列表",
"shop.pages.point.detail": "积分商品详情",
"shop.pages.point.payment": "待付款订单",
"shop.pages.point.order_list": "积分兑换记录",
"shop.pages.newcomer.list": "新人专享",
"shop.pages.invoice.list": "发票管理",
"shop.pages.invoice.detail": "发票详情",
"shop.pages.invoice.invoice": "申请发票",
"shop.pages.invoice.invoice_edit": "编辑发票信息",
"shop.pages.invoice.invoice_order": "发票订单",
"cms.pages.list": "资讯中心",
"cms.pages.detail": "文章详情",
"shop_fenxiao.pages.index": "分销中心",
"shop_fenxiao.pages.zone": "分销专区",
"shop_fenxiao.pages.level": "分销商等级",
"shop_fenxiao.pages.child_fenxiao": "分销商",
"shop_fenxiao.pages.goods": "分销商品",
"shop_fenxiao.pages.team": "我的团队",
"shop_fenxiao.pages.ranking_list": "排行榜",
"shop_fenxiao.pages.agent_list": "渠道代理",
"shop_fenxiao.pages.bill": "账单",
"shop_fenxiao.pages.order": "分销订单",
"shop_fenxiao.pages.order_detail": "订单详情",
"shop_fenxiao.pages.apply": "分销商申请",
"shop_fenxiao.pages.task_rewards": "任务奖励",
"shop_fenxiao.pages.task_detail": "任务奖励详情",
"shop_fenxiao.pages.task_rewards_detail": "任务奖励明细",
"shop_fenxiao.pages.sale": "销售奖励",
"shop_fenxiao.pages.sale_detail": "销售奖励详情",
"shop_fenxiao.pages.sale_ranking": "销售奖励排行榜",
"shop_fenxiao.pages.promote_code": "分享海报",
"shop_giftcard.pages.index": "礼品卡首页",
"shop_giftcard.pages.list": "礼品卡列表",
"shop_giftcard.pages.detail": "加载中",
"shop_giftcard.pages.order_list": "礼品卡订单列表",
"shop_giftcard.pages.order_detail": "礼品卡订单详情",
"shop_giftcard.pages.member": "我的",
"shop_giftcard.pages.my_card_list": "我的卡包",
"shop_giftcard.pages.card_bag": "我的卡包",
"shop_giftcard.pages.activate": "卡密激活",
"shop_giftcard.pages.receive_list": "收到的礼品卡",
"shop_giftcard.pages.give_list": "送出的礼品卡",
"shop_giftcard.pages.give_detail": "送出礼品卡详情",
"shop_giftcard.pages.give": "礼品卡赠送",
"shop_giftcard.pages.receive_info": "领取礼品卡",
"shop_giftcard.pages.use_card": "礼品卡使用",
"shop_giftcard.pages.use_goods_select": "选择兑换商品",
"shop_giftcard.pages.payment": "待付款订单",
"shop.pages.pay.index": "待支付",
"shop.pages.pay.result": "",
"shop_fenxiao.pages.promote": "邀请好友",
"shop_fenxiao.pages.team_dividend": "团队分红",
"o2o.pages.address.edit": "编辑地址",
"o2o.pages.address.index": "地址",
"o2o.pages.goods.category": "项目分类",
"o2o.pages.goods.detail": "项目详情",
"o2o.pages.goods.list": "项目列表",
"o2o.pages.index": "首页",
"o2o.pages.master.statistics.index": "技师中心",
"o2o.pages.master.task.add": "师傅报单",
"o2o.pages.master.task.detail": "任务详情",
"o2o.pages.master.task.list": "任务列表",
"o2o.pages.master.task.refund": "查看退款",
"o2o.pages.master.task.show": "报单详情",
"o2o.pages.member.index": "个人中心",
"o2o.pages.order.detail": "订单详情",
"o2o.pages.order.list": "订单列表",
"o2o.pages.order.payment": "订单结算",
"o2o.pages.refund.apply": "申请退款",
"o2o.pages.refund.detail": "退款详情",
"o2o.pages.refund.list": "退款列表",
"o2o.pages.refund.log": "协商记录",
"o2o.pages.technician.detail": "技师详情",
"o2o.pages.technician.list": "技师列表",
"shop_giftcard.pages.member_give_info": "送出礼品卡详情",
"shop_giftcard.pages.give_info": "领取礼品卡",
"sow_community.pages.index": "种草社区",
"sow_community.pages.search": "搜索",
"sow_community.pages.image.detail": "内容详情",
"sow_community.pages.video.detail": "内容详情",
"sow_community.pages.member": "个人主页",
"sow_community.pages.create": "发布内容",
"sow_community.pages.follow": "关注列表",
"sow_community.pages.sow_show": "种草秀",
"sow_community.pages.topic_list": "话题列表",
"template_flower_industry.pages.goods.list": "商品列表",
"seckill.pages.goods.detail": "商品详情",
"seckill.pages.goods.list": "商品列表",
"seckill.pages.member.index": "个人中心",
"seckill.pages.order.list": "订单列表",
"seckill.pages.order.detail": "订单详情",
"seckill.pages.order.payment": "待付款订单",
"seckill.pages.refund.list": "退款列表",
"seckill.pages.refund.detail": "退款详情",
"seckill.pages.refund.apply": "申请退款",
"seckill.pages.refund.edit_apply": "编辑退款信息",
"seckill.pages.refund.log": "协商记录",
"pintuan.pages.index": "拼团首页",
"pintuan.pages.goods.list": "商品列表",
"pintuan.pages.goods.detail": "商品详情",
"pintuan.pages.my_spell": "我的拼团",
"pintuan.pages.member.index": "个人中心",
"pintuan.pages.share": "拼团分享页面",
"pintuan.pages.order.payment": "拼团待付款订单",
"pintuan.pages.order.list": "拼团订单列表",
"pintuan.pages.order.detail": "拼团订单详情",
"pintuan.pages.refund.apply": "申请退款",
"pintuan.pages.refund.detail": "退款详情",
"pintuan.pages.refund.edit_apply": "编辑退款信息",
"pintuan.pages.refund.list": "退款列表",
"pintuan.pages.refund.log": "退款协商记录",
"pintuan.pages.order.card_record": "核销记录",
"friend_help.pages.index": "好友助力首页",
"friend_help.pages.goods.list": "商品列表",
"friend_help.pages.goods.detail": "商品详情",
"friend_help.pages.member.index": "个人中心",
"friend_help.pages.order.payment": "好友助力待付款订单",
"friend_help.pages.order.list": "好友助力订单列表",
"friend_help.pages.order.detail": "好友助力订单详情",
"friend_help.pages.refund.apply": "申请退款",
"friend_help.pages.refund.detail": "退款详情",
"friend_help.pages.refund.edit_apply": "编辑退款信息",
"friend_help.pages.refund.list": "退款列表",
"friend_help.pages.refund.log": "退款协商记录",
"friend_help.pages.order.card_record": "核销记录",
"friend_help.pages.my_help": "我的助力列表",
"friend_help.pages.goods.share": "好友助力",
"friend_help.pages.goods.bargain": "好友砍价"
}

View File

@ -113,36 +113,10 @@
"addAddress": "新增收货地址",
"selectAddress": "选择地址",
"coupon": "优惠劵",
"notHave": "无",
"onceCard": "次卡",
"cardUnit": "张",
"o2o.reserveBtn": "去抢购",
"o2o.noHomeAddress": "没有更多内容啦~",
"o2o.soldOut": "已售",
"o2o.orderNo": "订单号",
"o2o.actualPayment": "实付款",
"o2o.orderDetail": "详情",
"recharge.orderNo": "订单号",
"shop.orderNo": "订单号",
"shop.actualPayment": "实付款",
"shop.orderClose": "关闭订单",
"shop.orderFinish": "确认收货",
"shop.coupon": "优惠劵",
"shop.emptyAddress": "暂无收货地址,请先创建地址",
"shop.addAddress": "新增收货地址",
"shop.selectAddress": "选择地址",
"shop_fenxiao.orderNo": "订单号",
"shop_giftcard.actualPayment": "实付款",
"shop_giftcard.orderClose": "关闭订单",
"shop_giftcard.orderNo": "订单号",
"tourism.orderNo": "订单号",
"tourism.rise": "起",
"tourism.starLevel": "星级",
"tourism.star": "星",
"tourism.scenic": "景点",
"tourism.way": "线路",
"tourism.hotel": "酒店",
"tourism.seeMore": "查看更多",
"vipcard.cardReserve": "项目预约",
"vipcard.card": "办理次卡",
"vipcard.reserveSuccess": "预约成功",
@ -154,5 +128,35 @@
"vipcard.orderNo": "订单号",
"vipcard.myLink": "我的",
"vipcard.memberCode": "会员码",
"vipcard.seeMore": "查看更多"
"recharge.orderNo": "订单号",
"shop.orderNo": "订单号",
"shop.actualPayment": "实付款",
"shop.orderClose": "关闭订单",
"shop.orderFinish": "确认收货",
"shop.coupon": "优惠劵",
"o2o.way": "线路",
"o2o.hotel": "酒店",
"o2o.scenic": "景点",
"o2o.reserveBtn": "去抢购",
"o2o.noHomeAddress": "没有更多内容啦~",
"o2o.soldOut": "已售",
"o2o.orderNo": "订单号",
"o2o.actualPayment": "实付款",
"o2o.orderDetail": "详情",
"notHave": "无",
"tourism.scenic": "景点",
"tourism.way": "线路",
"tourism.hotel": "酒店",
"tourism.seeMore": "查看更多",
"vipcard.seeMore": "查看更多",
"shop.emptyAddress": "暂无收货地址,请先创建地址",
"shop.addAddress": "新增收货地址",
"shop.selectAddress": "选择地址",
"shop_fenxiao.orderNo": "订单号",
"shop_giftcard.actualPayment": "实付款",
"shop_giftcard.orderClose": "关闭订单",
"shop_giftcard.orderNo": "订单号",
"notHave": "无",
"onceCard": "次卡",
"cardUnit": "张"
}

View File

@ -6,9 +6,6 @@
"versionCode": "100",
"transformPx": false,
"app-plus": {
"compatible" : {
"ignoreVersion" : true
},
"usingComponents": true,
"nvueStyleCompiler": "uni-app",
"compilerVersion": 3,
@ -18,16 +15,7 @@
"autoclose": true,
"delay": 0
},
"modules" : {
"Camera" : {},
"Barcode" : {},
"Contacts" : {},
"Geolocation" : {},
"Payment" : {},
"VideoPlayer" : {},
"Maps" : {},
"Share" : {}
},
"modules": {},
"distribute": {
"android": {
"permissions": [
@ -48,16 +36,8 @@
"<uses-permission android:name=\"android.permission.WRITE_SETTINGS\"/>"
]
},
"ios" : {
"dSYMs" : false
},
"sdkConfigs" : {
"maps" : {
"tencent" : {
"key" : "6ZDBZ-CLSLX-66747-7MVM4-HLK47-XMBXU"
}
}
}
"ios": {},
"sdkConfigs": {}
}
},
"quickapp": {},

View File

@ -378,7 +378,8 @@
"backgroundColorBottom": "#F6F6F6"
},
"tabBar": {
"list": [{
"list": [
{
"pagePath": "app/pages/index/index"
},
{
@ -390,9 +391,9 @@
"easycom": {
"custom": {
"diy-group": "@/addon/components/diy/group/index.vue",
"^u-(.*)": "uview-plus/components/u-$1/u-$1.vue",
"^up-(.*)": "uview-plus/components/u-$1/u-$1.vue",
"^u-([^-].*)": "uview-plus/components/u-$1/u-$1.vue",
"u--(.*)": "uview-plus/components/u-$1/u-$1.vue",
"up-(.*)": "uview-plus/components/u-$1/u-$1.vue",
"u-(.*)": "uview-plus/components/u-$1/u-$1.vue",
"diy-(\W.*)": "@/app/components/diy/$1/index.vue"
}
}

View File

@ -1,41 +0,0 @@
.account-info-wrap{
@apply bg-[#F5F6FA] min-h-[100vh];
.account-info-head{
@apply relative h-40;
.name{
@apply ml-4 pt-7 text-white text-lg mb-3;
}
.content{
@apply absolute bg-white left-3 right-3 rounded-lg p-5;
.money{
@apply text-xl font-bold;
}
.text{
@apply text-xs text-slate-500 mt-2;
}
.money-wrap{
@apply mt-5 flex;
.money-item{
@apply flex-1;
}
.money{
@apply text-lg;
}
.text{
@apply mt-1;
}
}
}
}
.account-info-btn{
@apply flex mt-24 ml-3 mr-3;
.btn{
&:first-of-type{
@apply mr-1 rounded;
}
&:last-of-type{
@apply ml-1 rounded;
}
}
}
}

View File

@ -244,7 +244,7 @@ button[type='primary'],uni-button[type='primary']{
margin-right: 40rpx;
color: #333;
line-height: 40rpx;
font-size: 28rpx;
font-size: 26rpx;
&.class-select{
position: relative;
font-weight: 700;
@ -288,7 +288,7 @@ button[type='primary'],uni-button[type='primary']{
.tab-items{
line-height: 88rpx;
font-weight: 400;
font-size: 28rpx;
font-size: 26rpx;
&.class-select{
position: relative;
font-weight: 700;
@ -317,7 +317,7 @@ button[type='primary'],uni-button[type='primary']{
@apply flex-1;
line-height: 88rpx;
font-weight: 400;
font-size: 28rpx;
font-size: 26rpx;
text-align: center;
margin:0 var(--sidebar-m);
&.class-select{
@ -568,3 +568,7 @@ button[type='primary'],uni-button[type='primary']{
min-width: 144rpx;
color: #333;
}
.u-tabbar__content__item-wrapper {
height: calc(env(safe-area-inset-bottom) + 100rpx)!important;
}

View File

@ -1,9 +1,9 @@
@font-face {
font-family: "iconfont";
/* Project id 3952239 */
src: url('//at.alicdn.com/t/c/font_3952239_waynfpfdr5.woff2?t=1762225321119') format('woff2'),
url('//at.alicdn.com/t/c/font_3952239_waynfpfdr5.woff?t=1762225321119') format('woff'),
url('//at.alicdn.com/t/c/font_3952239_waynfpfdr5.ttf?t=1762225321119') format('truetype');
src: url('https://at.alicdn.com/t/c/font_3952239_waynfpfdr5.woff2?t=1762225321119') format('woff2'),
url('https://at.alicdn.com/t/c/font_3952239_waynfpfdr5.woff?t=1762225321119') format('woff'),
url('https://at.alicdn.com/t/c/font_3952239_waynfpfdr5.ttf?t=1762225321119') format('truetype');
}
.iconfont {

View File

@ -1,25 +0,0 @@
page{
background-color: #f5f6fa;
@apply pt-4;
}
.member-record-detail{
@apply m-4 mt-0 bg-white rounded-md px-4 py-6;
.money-wrap{
@apply flex items-center flex-col mb-6;
text:first-of-type{
@apply text-3xl font-bold mt-1;
}
text:last-of-type{
@apply text-sm mt-3;
}
}
.line-wrap{
@apply flex justify-between text-sm mt-3;
.label{
@apply text-[#878787];
}
.value{
@apply text-[#222];
}
}
}

View File

@ -1,21 +0,0 @@
.member-record-list{
@apply min-h-[100vh];
.member-record-item{
@apply relative sidebar-margin border-solid border-t-0 border-l-0 border-r-0 border-b-1 border-[#ECEBEC] py-3 mx-[var(--sidebar-m)];
.name{
@apply text-sm;
}
.desc{
@apply text-xs text-[#8D8C8D] mt-1;
}
.text-active{
color: #FF0D3E;
}
.money{
@apply absolute right-0 top-4 text-base font-bold;
}
.state{
@apply absolute right-0 top-11 text-[#8D8C8D] text-xs;
}
}
}

View File

@ -2,8 +2,10 @@ import { getTabbarPages } from './pages'
import useDiyStore from '@/app/stores/diy'
import useMemberStore from '@/stores/member'
import useSystemStore from '@/stores/system'
import wechat from '@/utils/wechat'
import useConfigStore from '@/stores/config'
import { getNeedLoginPages } from '@/utils/pages'
import { useLocation } from '@/hooks/useLocation'
/**
*
@ -90,7 +92,6 @@ export const redirect = (redirect: any) => {
if (newLogin) {
uni.setStorage({ key: 'loginBack', data: { url: originalUrl } });
}
switch (mode) {
case 'switchTab':
uni.switchTab({
@ -306,8 +307,7 @@ export function img(path: string): string {
if (typeof path == 'string' && path.startsWith('/')) path = path.replace(/^\//, '')
if (typeof imgDomain == 'string' && imgDomain.endsWith('/')) imgDomain = imgDomain.slice(0, -1)
return isUrl(path) ? path : `${imgDomain}/${path}`
return isUrl(path) ? path : `${ imgDomain }/${ path }`
}
/**
@ -315,7 +315,7 @@ export function img(path: string): string {
* @param path
* @returns
*/
export function getUrl(path : string) : string {
export function getUrl(path: string): string {
// #ifdef H5
let urlDomain = import.meta.env.VITE_IMG_DOMAIN || location.origin
// #endif
@ -327,7 +327,7 @@ export function getUrl(path : string) : string {
if (typeof path == 'string' && path.startsWith('/')) path = path.replace(/^\//, '')
if (typeof urlDomain == 'string' && urlDomain.endsWith('/')) urlDomain = urlDomain.slice(0, -1)
return isUrl(path) ? path : `${urlDomain}/${path}`
return isUrl(path) ? path : `${ urlDomain }/${ path }`
}
/**
@ -643,7 +643,7 @@ export function deepClone(obj: any) {
* @param delay
* @returns
*/
export function debounce(fn: (args?: any) => any, delay: number = 300) {
export function debounce(fn: (args ?: any) => any, delay: number = 300) {
let timer: null | number = null
return function (...args) {
if (timer != null) {
@ -724,10 +724,10 @@ export function getValidTime(minutes: any = 1) {
*
* @param path
*/
export function setThemeColor (path: string) {
export function setThemeColor(path: string) {
let pathArr = path.split('/')
let index = !pathArr[0] ? 1 : 0;
let route = pathArr[index] == 'addon' ? pathArr[(index+1)] : 'app';
let route = pathArr[index] == 'addon' ? pathArr[(index + 1)] : 'app';
// 设置底部导航
const configStore = useConfigStore()
@ -742,38 +742,38 @@ export function setThemeColor (path: string) {
if (route != 'app') {
try {
currTheme = theme_color_list[route];
if(currTheme && currTheme.theme){
if (currTheme && currTheme.theme) {
configStore.themeColor = themeColorToHex(currTheme.theme)
uni.setStorageSync('current_theme_color', JSON.stringify(themeColorToHex(currTheme.theme)));
}else if( !currTheme && current_theme_color){
} else if (!currTheme && current_theme_color) {
configStore.themeColor = ''
}else{
} else {
currTheme = theme_color_list.app || Object.values(theme_color_list)[0];
configStore.themeColor = themeColorToHex(currTheme.theme)
uni.setStorageSync('current_theme_color', JSON.stringify(themeColorToHex(currTheme.theme)));
}
} catch (e) {
// 设置插件应用的主色调发生错误,若不存在则使用最后有效的主色调
if(!current_theme_color && theme_color_list && Object.keys(theme_color_list).length > 0){
if (!current_theme_color && theme_color_list && Object.keys(theme_color_list).length > 0) {
currTheme = theme_color_list.app || Object.values(theme_color_list)[0];
configStore.themeColor = themeColorToHex(currTheme.theme)
uni.setStorageSync('current_theme_color', JSON.stringify(themeColorToHex(currTheme.theme)));
}else{
} else {
configStore.themeColor = '';
}
}
}else if (!current_theme_color && theme_color_list && Object.keys(theme_color_list).length > 0) {
} else if (!current_theme_color && theme_color_list && Object.keys(theme_color_list).length > 0) {
currTheme = theme_color_list.app || Object.values(theme_color_list)[0]
configStore.themeColor = themeColorToHex(currTheme.theme)
uni.setStorageSync("current_theme_color", JSON.stringify(themeColorToHex(currTheme.theme)))
}
}
export function themeColorToHex (param: any) {
export function themeColorToHex(param: any) {
const hexRegex = /^#([A-Fa-f0-9]{6}|[A-Fa-f0-9]{3})$/
const rgbaRegex = /^rgba?\((\d+),\s*(\d+),\s*(\d+)(,\s*\d*\.?\d+)?\)$/
for(let key in param){
for (let key in param) {
if (rgbaRegex.test(param[key])) {
const values = param[key].replace('rgba(', '').replace(')', '').split(',');
// 提取 r, g, b, a 值,并将它们转换为合适的类型
@ -781,14 +781,14 @@ export function themeColorToHex (param: any) {
const g = parseInt(values[1].trim(), 10); // Green 分量
const b = parseInt(values[2].trim(), 10); // Blue 分量
const a = parseFloat(values[3].trim()); // Alpha 分量
param[key] = rgbaToHex(r,g,b,a)
param[key] = rgbaToHex(r, g, b, a)
}
}
return param
}
// rgba转十六进制颜色
export function rgbaToHex (r, g, b, a) {
export function rgbaToHex(r, g, b, a) {
// 计算混合后的RGB值假设背景是白色 (255, 255, 255)
let rBlend = Math.round((1 - a) * 255 + a * r)
let gBlend = Math.round((1 - a) * 255 + a * g)
@ -805,10 +805,17 @@ export function rgbaToHex (r, g, b, a) {
}
// 获取 topFixedStatus 缓存名称
export function getTopFixedStatusName(data : any = {}) {
export function getTopFixedStatusName(data: any = {}) {
let name = 'topFixedStatus'
if (data.id) name += '_' + data.id
if (data.site_id) name += '_' + data.site_id
if (data.type) name += '_' + data.type
return name
}
// 距离显示
export function distance(distance: string | number): string {
const dist = typeof distance === 'string' ? parseFloat(distance) : distance;
if (isNaN(dist)) return distance.toString();
return dist < 1 ? parseInt((dist * 1000).toString()) + 'm' : dist.toFixed(1) + 'km'
}

View File

@ -1,6 +1,6 @@
import { language } from '@/locale'
import { checkNeedLogin } from '@/utils/auth'
import { redirect, getToken,currRoute, setThemeColor } from '@/utils/common'
import { redirect, getToken, currRoute, setThemeColor } from '@/utils/common'
import { memberLog } from '@/app/api/auth'
import { useShare } from '@/hooks/useShare'
@ -14,7 +14,10 @@ export const redirectInterceptor = (route: { path: string, query: object }) => {
setThemeColor(route.path)
// #ifdef MP
route.path.indexOf('addon') != -1 && language.loadAllLocaleMessages('addon', uni.getLocale())
try {
language.loadAllLocaleMessages('addon', uni.getLocale())
} catch (e) {
}
// #endif
// 校验是否需要登录

View File

@ -24,7 +24,7 @@ class Wechat {
timestamp: data.timestamp, // 必填,生成签名的时间戳
nonceStr: data.nonceStr, // 必填,生成签名的随机串
signature: data.signature,// 必填,签名
jsApiList: ['chooseWXPay', 'updateAppMessageShareData', 'updateTimelineShareData', 'scanQRCode', 'getLocation','hideMenuItems'] // 必填需要使用的JS接口列表
jsApiList: ['chooseWXPay', 'updateAppMessageShareData', 'updateTimelineShareData', 'scanQRCode', 'getLocation', 'openLocation', 'hideMenuItems'] // 必填需要使用的JS接口列表
});
if (callback) callback();
})
@ -82,6 +82,28 @@ class Wechat {
})
}
/**
*
* @param {Object} callback
*/
public openLocation(data: any, callback: any = null) {
wx.ready(function() {
wx.openLocation({
latitude: data.latitude, // 纬度浮点数范围为90 ~ -90
longitude: data.longitude, // 经度浮点数范围为180 ~ -180
name: data.name, // 位置名
address: data.address, // 地址详情说明
scale: data.scale || 28, // 地图缩放级别,整形值,范围从1~28。默认为最大
success: function(res) {
typeof callback == 'function' && callback(res);
},
fail: function(res) {
typeof callback == 'function' && callback(res);
}
});
})
}
/**
*
* @param {Object} options