修改展示时长bug
This commit is contained in:
parent
94b9271184
commit
eaad2642a8
@ -591,11 +591,11 @@ func (r *socialRepositoryImpl) GetMyLikedAssets(userID, starID int64, page, page
|
||||
}
|
||||
|
||||
// 计数查询(使用 DISTINCT 因为一个资产可能在多个展位展出)
|
||||
// 显示:展品存在且未领取(is_processed=false),无论是否过期
|
||||
// 不显示:已领取的(is_processed=true)或从未展出过的
|
||||
// 显示:展品未下架(deleted_at IS NULL),无论是否过期
|
||||
// 不显示:已领取下架的(deleted_at IS NOT NULL)或从未展出过的
|
||||
countQuery := r.db.Model(&models.AssetLike{}).
|
||||
Joins("JOIN assets a ON a.id = asset_likes.asset_id").
|
||||
Joins("JOIN exhibitions e ON e.asset_id = a.id AND e.deleted_at IS NULL AND e.is_processed = false").
|
||||
Joins("JOIN exhibitions e ON e.asset_id = a.id AND e.deleted_at IS NULL").
|
||||
Where("asset_likes.user_id = ? AND asset_likes.star_id = ?", userID, starID).
|
||||
Where("a.deleted_at IS NULL AND a.is_active = ?", true)
|
||||
|
||||
@ -603,14 +603,14 @@ func (r *socialRepositoryImpl) GetMyLikedAssets(userID, starID int64, page, page
|
||||
return nil, 0, err
|
||||
}
|
||||
|
||||
// 数据查询:只过滤已下架的,不过滤过期(已过期但未领取的仍显示)
|
||||
// 数据查询:只过滤已下架的,不过滤过期(用户领取收益后才下架)
|
||||
offset := (page - 1) * pageSize
|
||||
err := r.db.Model(&models.AssetLike{}).
|
||||
Select(`asset_likes.asset_id, a.name, a.cover_url, a.like_count,
|
||||
asset_likes.created_at as liked_at,
|
||||
(a.tags @> '["craft:lenticular"]') as is_lenticular`).
|
||||
Joins("JOIN assets a ON a.id = asset_likes.asset_id").
|
||||
Joins("JOIN exhibitions e ON e.asset_id = a.id AND e.deleted_at IS NULL AND e.is_processed = false").
|
||||
Joins("JOIN exhibitions e ON e.asset_id = a.id AND e.deleted_at IS NULL").
|
||||
Where("asset_likes.user_id = ? AND asset_likes.star_id = ?", userID, starID).
|
||||
Where("a.deleted_at IS NULL AND a.is_active = ?", true).
|
||||
Group("asset_likes.asset_id, a.name, a.cover_url, a.like_count, asset_likes.created_at, is_lenticular").
|
||||
|
||||
@ -163,9 +163,6 @@ func (s *revenueService) ClaimExhibitionRevenue(ctx context.Context, userID, sta
|
||||
// 增加用户累计上架时长(触发升级检查)
|
||||
// 计算上架时长(毫秒转小时)
|
||||
exhibitionHours := (record.CycleEndTime - record.CycleStartTime) / 3600000
|
||||
if exhibitionHours < 1 {
|
||||
exhibitionHours = 1 // 最少1小时
|
||||
}
|
||||
if s.userRPCClient != nil {
|
||||
newLevel, levelDelta, crystalReward, err := s.userRPCClient.AddExhibitionHours(ctx, userID, starID, exhibitionHours,
|
||||
fmt.Sprintf("%d", record.ID))
|
||||
@ -341,9 +338,6 @@ func (s *revenueService) OnExhibitionCompleted(ctx context.Context, req *pb.OnEx
|
||||
startTime := req.StartTime
|
||||
expireAt := req.ExpireAt
|
||||
actualHours := (expireAt - startTime) / 3600000
|
||||
if actualHours < 1 {
|
||||
actualHours = 1
|
||||
}
|
||||
|
||||
// sourceID 用于去重,避免重复累计
|
||||
sourceID := fmt.Sprintf("exhibition_%d", req.ExhibitionId)
|
||||
|
||||
@ -133,7 +133,17 @@
|
||||
<view class="liked-item" :class="index === 0 ? 'liked-item-first' : ''">
|
||||
<!-- 作品封面 -->
|
||||
<view class="liked-cover-wrap" :class="index === 0 ? 'liked-cover-wrap-first' : ''">
|
||||
<image class="liked-cover" :src="item.cover_url || '/static/nft/placeholder.png'"
|
||||
<LenticularCard
|
||||
v-if="item.is_lenticular"
|
||||
class="liked-lenticular"
|
||||
:layers="getLikedLenticularLayers(item.id)"
|
||||
:transforms="getLikedLenticularTransforms(item.id)"
|
||||
:gyro-source="gyroSourceLabel"
|
||||
:skip-built-in-touch="false"
|
||||
:shimmer-mid-opacity="0.16"
|
||||
@simulate="(x, y) => onLikedLenticularSimulate(item.id, x, y)"
|
||||
/>
|
||||
<image v-else class="liked-cover" :src="item.cover_url || '/static/nft/placeholder.png'"
|
||||
mode="aspectFill"></image>
|
||||
<image class="liked-cover-frame" src="/static/square/cangpinkuang1.png"
|
||||
mode="aspectFill"></image>
|
||||
@ -518,6 +528,10 @@ const lenticularLayersByAsset = ref({});
|
||||
const activeLenticularId = ref(null);
|
||||
const gyroSourceLabel = ref('device');
|
||||
|
||||
// 点赞作品光栅卡数据
|
||||
const likedLenticularLayersByAsset = ref({});
|
||||
const likedLenticularTransformsMap = ref({});
|
||||
|
||||
// 创建单一引擎供模拟倾斜使用
|
||||
const lenticularPhysics = ref(null);
|
||||
const lenticularEngine = ref(null);
|
||||
@ -534,6 +548,86 @@ function getLenticularTransforms(assetId) {
|
||||
return lenticularTransformsMap.value[assetId] || {};
|
||||
}
|
||||
|
||||
// 点赞作品光栅卡相关函数
|
||||
function getLikedLenticularLayers(assetId) {
|
||||
return likedLenticularLayersByAsset.value[assetId] || [];
|
||||
}
|
||||
|
||||
function getLikedLenticularTransforms(assetId) {
|
||||
return likedLenticularTransformsMap.value[assetId] || {};
|
||||
}
|
||||
|
||||
function onLikedLenticularSimulate(assetId, x, y) {
|
||||
simulateLikedLenticularTilt(assetId, x, y);
|
||||
}
|
||||
|
||||
function simulateLikedLenticularTilt(assetId, x, y) {
|
||||
if (!lenticularEngine.value) return;
|
||||
const layers = likedLenticularLayersByAsset.value[assetId];
|
||||
if (!layers || layers.length === 0) return;
|
||||
|
||||
lenticularEngine.value.setLayers(layers);
|
||||
const renderState = lenticularEngine.value.feedSimulatedTilt(x, y ? y : 0);
|
||||
|
||||
const transforms = {};
|
||||
for (const l of layers) {
|
||||
const rs = renderState.layerOffsets.get(l.id);
|
||||
const op = renderState.layerOpacities.get(l.id);
|
||||
transforms[l.id] = {
|
||||
x: rs ? rs.x : 0,
|
||||
y: rs ? rs.y : 0,
|
||||
opacity: op != null ? op : l.opacity,
|
||||
};
|
||||
}
|
||||
likedLenticularTransformsMap.value = { ...likedLenticularTransformsMap.value, [assetId]: transforms };
|
||||
}
|
||||
|
||||
async function loadLikedLenticularLayersForAsset(assetId) {
|
||||
const item = likedWorks.value.find(w => w.id === assetId);
|
||||
if (!item) return;
|
||||
|
||||
try {
|
||||
const materialsRes = await getAssetMaterialsApi(assetId);
|
||||
if (materialsRes.code === 200 && materialsRes.data) {
|
||||
const materialsList = Array.isArray(materialsRes.data) ? materialsRes.data : materialsRes.data.materials || [];
|
||||
let subjectUrl = item.cover_url;
|
||||
let bgUrl = '';
|
||||
for (const mat of materialsList) {
|
||||
if (mat.material_type === 'main' && mat.material_url_signed) {
|
||||
subjectUrl = mat.material_url_signed;
|
||||
}
|
||||
if (mat.material_type === 'bg' && mat.material_url_signed) {
|
||||
bgUrl = mat.material_url_signed;
|
||||
}
|
||||
}
|
||||
if (bgUrl) {
|
||||
const { buildLenticularLayersTwo } = await import('@/utils/castloveMintForm.js');
|
||||
likedLenticularLayersByAsset.value[assetId] = buildLenticularLayersTwo(bgUrl, subjectUrl);
|
||||
} else {
|
||||
likedLenticularLayersByAsset.value[assetId] = buildLenticularLayers(subjectUrl);
|
||||
}
|
||||
initLikedTransformsForAsset(assetId);
|
||||
} else {
|
||||
likedLenticularLayersByAsset.value[assetId] = buildLenticularLayers(item.cover_url);
|
||||
initLikedTransformsForAsset(assetId);
|
||||
}
|
||||
} catch (e) {
|
||||
console.error('[myWorks] 获取点赞作品素材列表失败:', e);
|
||||
likedLenticularLayersByAsset.value[assetId] = buildLenticularLayers(item.cover_url);
|
||||
initLikedTransformsForAsset(assetId);
|
||||
}
|
||||
}
|
||||
|
||||
function initLikedTransformsForAsset(assetId) {
|
||||
const layers = likedLenticularLayersByAsset.value[assetId];
|
||||
if (!layers || layers.length === 0) return;
|
||||
const transforms = {};
|
||||
for (const l of layers) {
|
||||
transforms[l.id] = { x: 0, y: 0, opacity: l.opacity || 1 };
|
||||
}
|
||||
likedLenticularTransformsMap.value = { ...likedLenticularTransformsMap.value, [assetId]: transforms };
|
||||
}
|
||||
|
||||
async function loadLenticularLayersForAsset(assetId) {
|
||||
// 需要获取 bg + subject 素材构建 layers
|
||||
// 目前使用 buildLenticularLayers(coverUrl) 作为占位
|
||||
@ -650,6 +744,24 @@ function startLenticularRenderLoop() {
|
||||
}
|
||||
lenticularTransformsMap.value = { ...lenticularTransformsMap.value, [assetId]: transforms };
|
||||
}
|
||||
// 遍历点赞作品的光栅卡
|
||||
for (const assetId of Object.keys(likedLenticularLayersByAsset.value)) {
|
||||
const layers = likedLenticularLayersByAsset.value[assetId];
|
||||
if (!layers || layers.length === 0) continue;
|
||||
lenticularEngine.value.setLayers(layers);
|
||||
const renderState = lenticularEngine.value.feedSimulatedTilt(0, 0);
|
||||
const transforms = {};
|
||||
for (const l of layers) {
|
||||
const rs = renderState.layerOffsets.get(l.id);
|
||||
const op = renderState.layerOpacities.get(l.id);
|
||||
transforms[l.id] = {
|
||||
x: rs ? rs.x : 0,
|
||||
y: rs ? rs.y : 0,
|
||||
opacity: op != null ? op : l.opacity,
|
||||
};
|
||||
}
|
||||
likedLenticularTransformsMap.value = { ...likedLenticularTransformsMap.value, [assetId]: transforms };
|
||||
}
|
||||
lenticularRafId = requestAnimationFrame(tick);
|
||||
};
|
||||
lenticularRafId = requestAnimationFrame(tick);
|
||||
@ -667,6 +779,9 @@ const switchLikedTab = async (tab) => {
|
||||
if (likedTab.value === tab) return;
|
||||
likedTab.value = tab;
|
||||
likedWorks.value = [];
|
||||
// 清理点赞作品光栅卡数据
|
||||
likedLenticularLayersByAsset.value = {};
|
||||
likedLenticularTransformsMap.value = {};
|
||||
await loadLikedAssets();
|
||||
};
|
||||
|
||||
@ -726,11 +841,19 @@ const loadLikedAssets = async () => {
|
||||
earnings: item.earnings,
|
||||
liked_at: item.liked_at,
|
||||
name: item.name,
|
||||
is_lenticular: item.is_lenticular ?? false,
|
||||
// 暂时用排名模拟状态文字
|
||||
status_text: index < 3 ? '排名进榜' : '潜力待挖',
|
||||
score: item.like_count,
|
||||
reward: Math.floor(item.earnings || 0),
|
||||
}));
|
||||
|
||||
// 为每个光栅卡加载层级数据
|
||||
for (const item of likedWorks.value) {
|
||||
if (item.is_lenticular) {
|
||||
loadLikedLenticularLayersForAsset(item.id);
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (err) {
|
||||
console.error('加载点赞作品失败:', err);
|
||||
@ -1318,6 +1441,17 @@ onShow(() => {
|
||||
padding: 0.25rem;
|
||||
}
|
||||
|
||||
.liked-lenticular {
|
||||
width: 90%;
|
||||
height: 90%;
|
||||
border-radius: 24rpx;
|
||||
transform: rotate(-22deg);
|
||||
transform-origin: center center;
|
||||
position: relative;
|
||||
z-index: 3;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.liked-cover-frame {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
|
||||
Loading…
Reference in New Issue
Block a user