- 在房源添加页面添加卖价(元/平)和总价(万)输入字段 - 实现卖价变动时总价自动计算功能 - 在房源详情页显示卖价和总价信息 - 调整物业费显示位置提升界面布局合理性 - 更新服务器配置地址从gxwebsoft.com到websoft.top - 替换必看好房标签为特价好房标签统一显示 - 修复房源详情页分享功能和海报生成流程 - 添加跟进记录页面和相应跳转功能 - 优化房源管理页面删除按钮显示逻辑 - 实现闪屏页跳过功能和登录状态记忆 - 添加房源海报生成组件支持分享推广 - 修复分享路径参数传递和用户信息存储
207 lines
6.0 KiB
Vue
207 lines
6.0 KiB
Vue
<template>
|
||
<view class="house-poster-generator">
|
||
<!-- 海报生成器 -->
|
||
<l-painter
|
||
ref="painter"
|
||
custom-style="position: fixed; left: -9999px; top: -9999px;"
|
||
:isCanvasToTempFilePath="true"
|
||
@success="onPosterSuccess"
|
||
@fail="onPosterFail"
|
||
css="height: 800rpx; width: 600rpx;"
|
||
file-type="png"
|
||
>
|
||
<template v-if="shouldRender">
|
||
<l-painter-view css="height: 800rpx; width: 600rpx; backgroundColor: #fff; position: relative;">
|
||
<!-- 房源主图 -->
|
||
<l-painter-image
|
||
:src="mainImageUrl"
|
||
css="width: 600rpx; height: 400rpx; borderRadius: 0;"
|
||
/>
|
||
|
||
<!-- 房源标题 -->
|
||
<l-painter-text
|
||
:text="houseData.houseTitle || '房源标题'"
|
||
css="position: absolute; top: 420rpx; left: 30rpx; width: 540rpx; fontSize: 32rpx; fontWeight: bold; color: #333333;"
|
||
/>
|
||
|
||
<!-- 价格信息 -->
|
||
<l-painter-text
|
||
:text="priceText"
|
||
css="position: absolute; top: 480rpx; left: 30rpx; fontSize: 30rpx; fontWeight: bold; color: #ff4444;"
|
||
/>
|
||
|
||
<!-- 房源详情 -->
|
||
<l-painter-text
|
||
:text="houseDetailsText"
|
||
css="position: absolute; top: 530rpx; left: 30rpx; fontSize: 26rpx; color: #666666;"
|
||
/>
|
||
|
||
<!-- 地址信息 -->
|
||
<l-painter-text
|
||
:text="houseData.address || '地址信息'"
|
||
css="position: absolute; top: 580rpx; left: 30rpx; width: 540rpx; fontSize: 24rpx; color: #999999;"
|
||
/>
|
||
|
||
<!-- 分享文案 -->
|
||
<l-painter-text
|
||
text="扫码查看房源详情"
|
||
css="position: absolute; top: 650rpx; left: 30rpx; fontSize: 24rpx; color: #666666;"
|
||
/>
|
||
|
||
<!-- 小程序码预留位置 -->
|
||
<l-painter-view css="position: absolute; top: 630rpx; left: 470rpx; width: 100rpx; height: 100rpx; backgroundColor: #f5f5f5; borderRadius: 10rpx; display: flex; alignItems: center; justifyContent: center;">
|
||
<l-painter-text
|
||
text="小程序码"
|
||
css="fontSize: 18rpx; color: #cccccc;"
|
||
/>
|
||
</l-painter-view>
|
||
</l-painter-view>
|
||
</template>
|
||
</l-painter>
|
||
</view>
|
||
</template>
|
||
|
||
<script>
|
||
import LPainter from '@/uni_modules/lime-painter/components/l-painter/l-painter.vue'
|
||
|
||
export default {
|
||
name: 'HousePosterGenerator',
|
||
components: {
|
||
LPainter
|
||
},
|
||
props: {
|
||
// 房源数据
|
||
houseData: {
|
||
type: Object,
|
||
default: () => ({})
|
||
},
|
||
// 房源图片列表
|
||
swiperList: {
|
||
type: Array,
|
||
default: () => []
|
||
}
|
||
},
|
||
data() {
|
||
return {
|
||
// 海报生成状态
|
||
isGenerating: false,
|
||
// 当前生成的海报URL
|
||
currentPosterUrl: '',
|
||
// 是否应该渲染海报
|
||
shouldRender: false
|
||
}
|
||
},
|
||
computed: {
|
||
// 主图URL
|
||
mainImageUrl() {
|
||
if (this.swiperList && this.swiperList.length > 0) {
|
||
const firstImage = this.swiperList[0];
|
||
const imageUrl = firstImage.url || firstImage.image || firstImage.src || firstImage || '';
|
||
if (imageUrl && typeof imageUrl === 'string' && imageUrl.trim() !== '') {
|
||
return imageUrl.trim();
|
||
}
|
||
}
|
||
return 'https://dummyimage.com/600x400/f0f0f0/999999&text=暂无图片';
|
||
},
|
||
// 价格文本
|
||
priceText() {
|
||
return (this.houseData.monthlyRent || 0) + '元/月';
|
||
},
|
||
// 房源详情文本
|
||
houseDetailsText() {
|
||
const houseType = this.houseData.houseType || '户型';
|
||
const extent = this.houseData.extent || 0;
|
||
const floor = this.houseData.floor || '楼层';
|
||
return houseType + ' | ' + extent + 'm² | ' + floor;
|
||
}
|
||
},
|
||
methods: {
|
||
// 生成房源海报
|
||
async generatePoster() {
|
||
if (this.isGenerating) {
|
||
console.log('海报正在生成中,请稍候...');
|
||
return;
|
||
}
|
||
|
||
try {
|
||
this.isGenerating = true;
|
||
console.log('开始生成房源海报...');
|
||
|
||
// 检查房源数据
|
||
if (!this.houseData || !this.houseData.houseTitle) {
|
||
throw new Error('房源数据不完整');
|
||
}
|
||
|
||
// 启用渲染
|
||
this.shouldRender = true;
|
||
|
||
// 等待DOM更新
|
||
await this.$nextTick();
|
||
|
||
// 等待一段时间确保图片加载完成
|
||
await new Promise(resolve => setTimeout(resolve, 1000));
|
||
|
||
console.log('海报模板渲染完成,等待生成图片...');
|
||
|
||
// 由于设置了 isCanvasToTempFilePath="true",会自动触发 onPosterSuccess
|
||
return new Promise((resolve, reject) => {
|
||
this.resolveGenerate = resolve;
|
||
this.rejectGenerate = reject;
|
||
});
|
||
|
||
} catch (error) {
|
||
console.error('海报生成失败:', error);
|
||
this.isGenerating = false;
|
||
this.shouldRender = false;
|
||
this.$emit('posterFailed', error);
|
||
throw error;
|
||
}
|
||
},
|
||
|
||
|
||
|
||
// 海报生成成功回调
|
||
onPosterSuccess(tempFilePath) {
|
||
console.log('lime-painter 生成成功:', tempFilePath);
|
||
this.currentPosterUrl = tempFilePath;
|
||
this.isGenerating = false;
|
||
this.shouldRender = false;
|
||
|
||
// 触发生成完成事件
|
||
this.$emit('posterGenerated', tempFilePath);
|
||
|
||
// 如果有等待的Promise,resolve它
|
||
if (this.resolveGenerate) {
|
||
this.resolveGenerate(tempFilePath);
|
||
this.resolveGenerate = null;
|
||
this.rejectGenerate = null;
|
||
}
|
||
},
|
||
|
||
// 海报生成失败回调
|
||
onPosterFail(error) {
|
||
console.error('lime-painter 生成失败:', error);
|
||
this.isGenerating = false;
|
||
this.shouldRender = false;
|
||
|
||
// 触发生成失败事件
|
||
this.$emit('posterFailed', error);
|
||
|
||
// 如果有等待的Promise,reject它
|
||
if (this.rejectGenerate) {
|
||
this.rejectGenerate(error);
|
||
this.resolveGenerate = null;
|
||
this.rejectGenerate = null;
|
||
}
|
||
}
|
||
}
|
||
}
|
||
</script>
|
||
|
||
<style lang="scss" scoped>
|
||
.house-poster-generator {
|
||
// 隐藏组件,只用于生成海报
|
||
display: none;
|
||
}
|
||
</style>
|