sdk: 增量同步主仓新模块(box/anim/scroll/dispatch/listvirt/str/sb_icons/img)
subtree pull sdk 来自主仓 pub/sdk(主仓 commit 68ce46a 等)。新增: - 布局引擎 meow_ui_box / 动画基座 meow_ui_anim / 滚动物理 meow_ui_scroll - §6.4 事件分发形式化 / W_LISTVIEW 虚拟化多行 / meow_str 字符串资源 i18n - sb_icons 动作图标扩充 + topbar 位图图标 / meow_img_downscale - tools/ 图标生成脚本与 SVG 源 - 对应宿主 test_*.c 与 demo_box_scroll.c build_sdk.sh 冲突解析:保留公开仓自包含版(vendored meow_font + -Iinclude -I.), OBJS 手工并入 4 个新模块(meow_ui_box/anim/scroll/str)。保留 vendored meow_font.c/ meow_ipc.h/meow_font.h/meow_notif.h,剔除宿主测试二进制与编译产物。
This commit is contained in:
commit
4b094d62a5
56 files changed
+4327
-117
No files matched your search
@@ -0,0 +1,128 @@
|
||||
/*
|
||||
* meow_ui_anim.c — 动画基座 + UI 节拍器(§12.2)。
|
||||
*
|
||||
* 时间驱动 tween:start 记录起始时刻(meow_ui_time_ms,单调),tick 按经过时间求 t,
|
||||
* 代入 ease 得 v = from + (to-from)*ease(t),回调 update;t 到 1 → 回调 done(canceled=0) 并回收。
|
||||
* 取消 → 回调 done(canceled=1) 并回收。静态池(≤MEOW_ANIM_MAX),热路径零 malloc。
|
||||
* 无动画时 meow_anim_tick() 仅查活动计数即返回(零开销)。
|
||||
*
|
||||
* 节拍挂接:由 meow_ui_run 主循环(on_tick 之后)与 meow_ui_feed_tick(阻塞 IME 循环)调用,
|
||||
* 不引入常驻高频轮询。modal/dialog 阻塞循环不喂 tick(动画暂停,符合「模态期不做动画」惯例)。
|
||||
*/
|
||||
#include "meow_ui.h"
|
||||
#include "include/meow_ui_anim.h"
|
||||
#include <string.h>
|
||||
|
||||
struct meow_anim {
|
||||
int active;
|
||||
float from, to;
|
||||
uint32_t duration_ms;
|
||||
meow_ease ease;
|
||||
uint64_t start_ms;
|
||||
float value;
|
||||
int region_set;
|
||||
int rx, ry, rw, rh;
|
||||
meow_anim_update_fn update;
|
||||
meow_anim_done_fn done;
|
||||
void *ctx;
|
||||
};
|
||||
|
||||
static struct meow_anim g_pool[MEOW_ANIM_MAX];
|
||||
static unsigned g_active = 0; /* 活动动画计数(0 = 空闲,tick 直退) */
|
||||
|
||||
/* ---- 缓动 ---- */
|
||||
float meow_ease_apply(meow_ease e, float t)
|
||||
{
|
||||
if (e == MEOW_EASE_OUT) {
|
||||
/* ease-out quad */
|
||||
float u = 1.0f - t;
|
||||
return 1.0f - u * u;
|
||||
}
|
||||
if (e == MEOW_EASE_IN_OUT) {
|
||||
/* ease-in-out quad */
|
||||
if (t < 0.5f) return 2.0f * t * t;
|
||||
float u = -2.0f * t + 2.0f;
|
||||
return 1.0f - u * u * 0.5f;
|
||||
}
|
||||
if (e == MEOW_EASE_OVERSHOOT) {
|
||||
/* ease-out-back(越过目标再回稳);t=1 → 恰为 1 */
|
||||
const float c1 = 1.70158f;
|
||||
const float c3 = c1 + 1.0f;
|
||||
float u = t - 1.0f;
|
||||
return 1.0f + c3 * u * u * u + c1 * u * u;
|
||||
}
|
||||
/* MEOW_EASE_LINEAR */
|
||||
return t;
|
||||
}
|
||||
|
||||
/* ---- 生命周期 ---- */
|
||||
meow_anim *meow_anim_start(const meow_anim_desc *d)
|
||||
{
|
||||
if (!d) return NULL;
|
||||
for (int i = 0; i < MEOW_ANIM_MAX; i++) {
|
||||
struct meow_anim *a = &g_pool[i];
|
||||
if (a->active) continue;
|
||||
a->active = 1;
|
||||
a->from = d->from;
|
||||
a->to = d->to;
|
||||
a->duration_ms = d->duration_ms ? d->duration_ms : 1; /* 0 → 瞬发(下一 tick 完成) */
|
||||
a->ease = d->ease;
|
||||
a->start_ms = meow_ui_time_ms();
|
||||
a->update = d->update;
|
||||
a->done = d->done;
|
||||
a->ctx = d->ctx;
|
||||
a->region_set = 0;
|
||||
a->value = d->from;
|
||||
g_active++;
|
||||
if (a->update) a->update(a, a->value, a->ctx); /* 起始帧回调(t=0) */
|
||||
return a;
|
||||
}
|
||||
return NULL; /* 池满 */
|
||||
}
|
||||
|
||||
void meow_anim_cancel(meow_anim *a)
|
||||
{
|
||||
if (!a || !a->active) return;
|
||||
a->active = 0;
|
||||
if (g_active > 0) g_active--;
|
||||
if (a->done) a->done(a, 1, a->ctx);
|
||||
}
|
||||
|
||||
int meow_anim_active(meow_anim *a) { return (a && a->active) ? 1 : 0; }
|
||||
float meow_anim_value(meow_anim *a) { return a ? a->value : 0.0f; }
|
||||
|
||||
void meow_anim_set_region(meow_anim *a, int x, int y, int w, int h)
|
||||
{
|
||||
if (!a) return;
|
||||
if (x < 0) { a->region_set = 0; return; }
|
||||
a->region_set = 1;
|
||||
a->rx = x; a->ry = y; a->rw = w > 0 ? w : 0; a->rh = h > 0 ? h : 0;
|
||||
}
|
||||
|
||||
/* ---- 节拍器 ---- */
|
||||
unsigned meow_anim_count(void) { return (unsigned)g_active; }
|
||||
|
||||
void meow_anim_tick(void)
|
||||
{
|
||||
if (g_active == 0) return; /* 无动画:零开销直接返回 */
|
||||
uint64_t now = meow_ui_time_ms();
|
||||
for (int i = 0; i < MEOW_ANIM_MAX; i++) {
|
||||
struct meow_anim *a = &g_pool[i];
|
||||
if (!a->active) continue;
|
||||
uint64_t elapsed = now - a->start_ms;
|
||||
float t = (float)(elapsed) / (float)a->duration_ms;
|
||||
int finished = (t >= 1.0f);
|
||||
if (t > 1.0f) t = 1.0f;
|
||||
if (t < 0.0f) t = 0.0f;
|
||||
float v = a->from + (a->to - a->from) * meow_ease_apply(a->ease, t);
|
||||
a->value = v;
|
||||
if (a->update) a->update(a, v, a->ctx);
|
||||
if (a->region_set && a->rw > 0 && a->rh > 0)
|
||||
meow_ui_flush_region(a->rx, a->ry, a->rw, a->rh); /* 只刷动画影响区 */
|
||||
if (finished) {
|
||||
a->active = 0;
|
||||
if (g_active > 0) g_active--;
|
||||
if (a->done) a->done(a, 0, a->ctx);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user