bugfixes
This commit is contained in:
parent
f310804b4d
commit
d55c6b5854
@ -874,6 +874,12 @@ func mergeRatingActivitySegments(
|
||||
return valid[i].Label < valid[j].Label
|
||||
})
|
||||
|
||||
type segmentBounds struct {
|
||||
start float64
|
||||
end float64
|
||||
ok bool
|
||||
}
|
||||
|
||||
type activityBlock struct {
|
||||
start float64
|
||||
end float64
|
||||
@ -881,13 +887,28 @@ func mergeRatingActivitySegments(
|
||||
scoreWeight float64
|
||||
labels map[string]bool
|
||||
positionWeights map[string]float64
|
||||
positionBounds map[string]segmentBounds
|
||||
marker float64
|
||||
markerWeight float64
|
||||
}
|
||||
|
||||
var addRatingPositionWeight func(weights map[string]float64, label string, weight float64)
|
||||
var addRatingPositionSignal func(
|
||||
weights map[string]float64,
|
||||
bounds map[string]segmentBounds,
|
||||
label string,
|
||||
weight float64,
|
||||
start float64,
|
||||
end float64,
|
||||
)
|
||||
|
||||
addRatingPositionWeight = func(weights map[string]float64, label string, weight float64) {
|
||||
addRatingPositionSignal = func(
|
||||
weights map[string]float64,
|
||||
bounds map[string]segmentBounds,
|
||||
label string,
|
||||
weight float64,
|
||||
start float64,
|
||||
end float64,
|
||||
) {
|
||||
label = strings.ToLower(strings.TrimSpace(label))
|
||||
if label == "" {
|
||||
return
|
||||
@ -896,18 +917,45 @@ func mergeRatingActivitySegments(
|
||||
if strings.HasPrefix(label, "combo:") {
|
||||
raw := strings.TrimPrefix(label, "combo:")
|
||||
for _, part := range strings.Split(raw, "+") {
|
||||
addRatingPositionWeight(weights, part, weight)
|
||||
addRatingPositionSignal(weights, bounds, part, weight, start, end)
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
normalized := normalizeRatingSignalLabel(label)
|
||||
if strings.HasPrefix(normalized, "position:") {
|
||||
if !strings.HasPrefix(normalized, "position:") {
|
||||
return
|
||||
}
|
||||
|
||||
if end < start {
|
||||
end = start
|
||||
}
|
||||
|
||||
weights[normalized] += weight
|
||||
|
||||
b := bounds[normalized]
|
||||
if !b.ok {
|
||||
b = segmentBounds{
|
||||
start: start,
|
||||
end: end,
|
||||
ok: true,
|
||||
}
|
||||
} else {
|
||||
if start < b.start {
|
||||
b.start = start
|
||||
}
|
||||
if end > b.end {
|
||||
b.end = end
|
||||
}
|
||||
}
|
||||
|
||||
effectiveRatingLabelsForBlock := func(labels map[string]bool, positionWeights map[string]float64) map[string]bool {
|
||||
bounds[normalized] = b
|
||||
}
|
||||
|
||||
effectiveRatingLabelsForBlock := func(
|
||||
labels map[string]bool,
|
||||
positionWeights map[string]float64,
|
||||
) (map[string]bool, string) {
|
||||
out := map[string]bool{}
|
||||
|
||||
bestPosition := ""
|
||||
@ -940,7 +988,7 @@ func mergeRatingActivitySegments(
|
||||
out[bestPosition] = true
|
||||
}
|
||||
|
||||
return out
|
||||
return out, bestPosition
|
||||
}
|
||||
|
||||
segmentMarker := func(s aiSegmentMeta) float64 {
|
||||
@ -981,7 +1029,16 @@ func mergeRatingActivitySegments(
|
||||
}
|
||||
|
||||
positionWeights := map[string]float64{}
|
||||
addRatingPositionWeight(positionWeights, s.Label, conf*math.Max(1, dur))
|
||||
positionBounds := map[string]segmentBounds{}
|
||||
|
||||
addRatingPositionSignal(
|
||||
positionWeights,
|
||||
positionBounds,
|
||||
s.Label,
|
||||
conf*math.Max(1, dur),
|
||||
s.StartSeconds,
|
||||
s.EndSeconds,
|
||||
)
|
||||
|
||||
marker := segmentMarker(s)
|
||||
markerWeight := segmentMarkerWeight(s)
|
||||
@ -993,6 +1050,7 @@ func mergeRatingActivitySegments(
|
||||
scoreWeight: dur,
|
||||
labels: labels,
|
||||
positionWeights: positionWeights,
|
||||
positionBounds: positionBounds,
|
||||
marker: marker,
|
||||
markerWeight: markerWeight,
|
||||
}
|
||||
@ -1004,7 +1062,7 @@ func mergeRatingActivitySegments(
|
||||
return aiSegmentMeta{}, false
|
||||
}
|
||||
|
||||
effectiveLabels := effectiveRatingLabelsForBlock(b.labels, b.positionWeights)
|
||||
effectiveLabels, bestPosition := effectiveRatingLabelsForBlock(b.labels, b.positionWeights)
|
||||
label := buildRatingComboLabel(effectiveLabels)
|
||||
if label == "" {
|
||||
return aiSegmentMeta{}, false
|
||||
@ -1012,6 +1070,24 @@ func mergeRatingActivitySegments(
|
||||
|
||||
sev := ratingSegmentSeverity(label)
|
||||
|
||||
start := b.start
|
||||
|
||||
// Wenn der finale Block eine Position trägt, soll die Anzeige/der Klick
|
||||
// beim ersten echten Auftreten dieser Position starten — nicht schon bei
|
||||
// früheren Body-/Object-Signalen aus demselben Aktivitätsblock.
|
||||
if bestPosition != "" {
|
||||
if bounds, ok := b.positionBounds[bestPosition]; ok && bounds.ok {
|
||||
if bounds.start > start {
|
||||
start = bounds.start
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
dur = b.end - start
|
||||
if dur <= 0 {
|
||||
return aiSegmentMeta{}, false
|
||||
}
|
||||
|
||||
// Kurze Segmente dürfen bleiben, wenn sie stark genug sind.
|
||||
if dur < minDurationSec && sev < 0.72 {
|
||||
return aiSegmentMeta{}, false
|
||||
@ -1028,7 +1104,7 @@ func mergeRatingActivitySegments(
|
||||
return aiSegmentMeta{
|
||||
Label: label,
|
||||
Score: ratingClamp01(score),
|
||||
StartSeconds: b.start,
|
||||
StartSeconds: start,
|
||||
EndSeconds: b.end,
|
||||
DurationSeconds: dur,
|
||||
AutoSelected: true,
|
||||
@ -1095,7 +1171,14 @@ func mergeRatingActivitySegments(
|
||||
cur.scoreSum += conf * dur
|
||||
cur.scoreWeight += dur
|
||||
|
||||
addRatingPositionWeight(cur.positionWeights, n.Label, conf*math.Max(1, dur))
|
||||
addRatingPositionSignal(
|
||||
cur.positionWeights,
|
||||
cur.positionBounds,
|
||||
n.Label,
|
||||
conf*math.Max(1, dur),
|
||||
n.StartSeconds,
|
||||
n.EndSeconds,
|
||||
)
|
||||
}
|
||||
|
||||
nextMarkerWeight := segmentMarkerWeight(n)
|
||||
|
||||
@ -518,7 +518,7 @@ function readMetaDurationSeconds(metaRaw: unknown): number {
|
||||
return Number.isFinite(n) && n > 0 ? n : 0
|
||||
}
|
||||
|
||||
const RATING_SEGMENT_OPEN_PREROLL_SECONDS = 3
|
||||
const RATING_SEGMENT_OPEN_PREROLL_SECONDS = 0
|
||||
|
||||
function segmentAnchorTime(
|
||||
obj: Record<string, unknown>,
|
||||
@ -603,10 +603,41 @@ function segmentPreviewTime(
|
||||
return undefined
|
||||
}
|
||||
|
||||
function segmentStartTime(
|
||||
obj: Record<string, unknown>,
|
||||
durationSeconds: number
|
||||
): number | undefined {
|
||||
return firstSegmentTimeNumber(obj, [
|
||||
'openAtSec',
|
||||
'openSeconds',
|
||||
'seekSeconds',
|
||||
'seekSec',
|
||||
'jumpSeconds',
|
||||
'jumpSec',
|
||||
'startSec',
|
||||
'startSeconds',
|
||||
'start_s',
|
||||
'start',
|
||||
'from',
|
||||
'startMs',
|
||||
'startRatio',
|
||||
'startPercent',
|
||||
'startPct',
|
||||
], durationSeconds)
|
||||
}
|
||||
|
||||
function segmentOpenTime(
|
||||
obj: Record<string, unknown>,
|
||||
durationSeconds: number
|
||||
): number | undefined {
|
||||
// Klick soll auf den Segment-Anfang springen, nicht auf den Preview-/Peak-Marker.
|
||||
const start = segmentStartTime(obj, durationSeconds)
|
||||
|
||||
if (typeof start === 'number') {
|
||||
return Math.max(0, start - RATING_SEGMENT_OPEN_PREROLL_SECONDS)
|
||||
}
|
||||
|
||||
// Fallback für alte Daten ohne startSeconds.
|
||||
const anchor =
|
||||
segmentAnchorTime(obj, durationSeconds) ??
|
||||
segmentPreviewTime(obj, durationSeconds)
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user