v8:观影落地(MovieLog 整体迁入统一事件原语)+ 三处 UI 撤除
- Schema v8:events / movie_details / event_attendees / event_photos 四张表, uk_event_source(family_id, source_ref) 作迁移幂等锚 - Movie 模型:时间线/详情/增删改、同行人整组替换、照片逐张管理、感受英→中映射 - ImageSlot 新增 poster(2:3) / ticket(free) / photo(free) 三槽位; free 槽位不裁剪、整图等比缩进框(只缩不放大) - OssDriver::copyObject:同桶 CopyObject(手写 V1 签名,x-oss-* 头按字典序进签名串) - 路由:movies 时间线/详情/新增/编辑/删除/补照片/删照片;同行人按家庭过滤; 访客只读(requireWrite) - UI 撤除:首页「我的一句话」、家谱页「补充我的亲属关系 / 看整个名册」两个按钮; 顶栏加「观影」入口 - 修潜伏 bug:ImageSlot::parseRatio 的正则用 / 作分隔符,字符类里的 / 把模式 提前截断(Unknown modifier ']')—— ratio() 只在上传 POST 里被调到,一直没被观察到 - 线上数据迁移(临时 token 门禁页,用完即删):MovieLog 219 条观影 → events, 14 位观影人新增进名册(带 MovieLog 头像),431 个 OSS 对象同桶拷贝 (movielog/uploads/<dir>/x → family/<dir>/x),review/feelings/影院三段/照片全量搬
This commit is contained in:
+26
-12
@@ -102,20 +102,34 @@ final class Upload
|
||||
$w = imagesx($src);
|
||||
$h = imagesy($src);
|
||||
|
||||
// 先按目标比例、在「用户挑的区域」里定位 —— 区域非法时退回整图居中
|
||||
$region = self::readCrop($cropRaw, $w, $h);
|
||||
[$sx, $sy, $sw, $sh] = self::fitRegion($region ?? [0.0, 0.0, 1.0, 1.0], $w, $h, ImageSlot::ratio($slot));
|
||||
// 「框小到没有意义」要明确拒绝(放大之后就是一坨马赛克)。
|
||||
// ⚠️ 只在**用户真的给了裁剪框**时判:源图本身很小(比如 8×8 的老头像、
|
||||
// 或者是张一像素级的测试图)时,居中裁出来的区域自然也小 ——
|
||||
// 那种情况必须照常接受,否则一张本来能用的图会被"太小"挡在外面。
|
||||
if ($region !== null && ($sw < 16 || $sh < 16)) {
|
||||
imagedestroy($src);
|
||||
return ['ok' => false, 'error' => '裁剪区域太小了,请把框放大一点'];
|
||||
$free = ImageSlot::ratio($slot) === 0.0; // free 槽位(票根/照片):不裁剪,整图等比缩
|
||||
if ($free) {
|
||||
// 用户挑的裁剪框对 free 槽位没有意义 —— 忽略,用整张图。
|
||||
// (票根是随手拍,比例五花八门,硬裁只会把票面裁掉一角。)
|
||||
$sx = 0; $sy = 0; $sw = $w; $sh = $h;
|
||||
} else {
|
||||
// 先按目标比例、在「用户挑的区域」里定位 —— 区域非法时退回整图居中
|
||||
$region = self::readCrop($cropRaw, $w, $h);
|
||||
[$sx, $sy, $sw, $sh] = self::fitRegion($region ?? [0.0, 0.0, 1.0, 1.0], $w, $h, ImageSlot::ratio($slot));
|
||||
// 「框小到没有意义」要明确拒绝(放大之后就是一坨马赛克)。
|
||||
// ⚠️ 只在**用户真的给了裁剪框**时判:源图本身很小(比如 8×8 的老头像、
|
||||
// 或者是张一像素级的测试图)时,居中裁出来的区域自然也小 ——
|
||||
// 那种情况必须照常接受,否则一张本来能用的图会被"太小"挡在外面。
|
||||
if ($region !== null && ($sw < 16 || $sh < 16)) {
|
||||
imagedestroy($src);
|
||||
return ['ok' => false, 'error' => '裁剪区域太小了,请把框放大一点'];
|
||||
}
|
||||
}
|
||||
|
||||
$outW = (int)$slot['w'];
|
||||
$outH = (int)$slot['h'];
|
||||
if ($free) {
|
||||
// 等比缩到槽位的 w×h **框内**(只缩不放大),保持原始比例
|
||||
$scale = min((int)$slot['w'] / $sw, (int)$slot['h'] / $sh, 1.0);
|
||||
$outW = max(1, (int)round($sw * $scale));
|
||||
$outH = max(1, (int)round($sh * $scale));
|
||||
} else {
|
||||
$outW = (int)$slot['w'];
|
||||
$outH = (int)$slot['h'];
|
||||
}
|
||||
$canvas = imagecreatetruecolor($outW, $outH);
|
||||
// PNG/GIF 的透明区转成纸白,不然头像会是黑底
|
||||
$bg = imagecolorallocate($canvas, 253, 251, 245);
|
||||
|
||||
Reference in New Issue
Block a user