Browse Source

feat(波形显示): 优化波形显示效果以填满整个区域

- 增加数据点密度,将采样间隔从2像素改为3像素
- 移除垂直时间参考线,仅保留水平中线
- 修改波形绘制逻辑,使其扩散到整个显示区域
- 调整波形透明度计算方式,中央区域更亮边缘渐暗
newdev_shunjiawei
lxm 1 year ago
parent
commit
bbddcf61cd
  1. 8
      lib/modules/meeting/controllers/meeting_record_controller.dart
  2. 67
      lib/modules/meeting/views/meeting_record_view.dart

8
lib/modules/meeting/controllers/meeting_record_controller.dart

@ -72,7 +72,7 @@ class MeetingRecordController extends GetxController
late Animation<double> waveformAnimation;
// 设置最大点数(根据屏幕宽度)
void setMaxPoints(double screenWidth) {
maxPoints = screenWidth ~/ 2; // 每2像素一个数据点
maxPoints = screenWidth ~/ 3; // 增加数据点密度以填满整个区域
}
@override
@ -377,7 +377,7 @@ class MeetingRecordController extends GetxController
return _currentPosition.value / waveData.length;
}
/// 添加处理后的音频数据 - 优化流动效果
/// 添加处理后的音频数据 - 优化全屏流动效果
void _addAudioData(Float32List newAudio) {
if (!isRecording.value) return;
@ -389,8 +389,8 @@ class MeetingRecordController extends GetxController
for (final sample in downsampled) {
waveData.add(sample);
//维护合理的数据长度 - 保持滑动窗口效果
if (waveData.length > maxPoints) {
// 维护合理的数据长度 - 保持足够的数据以填满整个屏幕
if (waveData.length > maxPoints * 2) {
waveData.removeAt(0); // 移除最旧的数据
}
}

67
lib/modules/meeting/views/meeting_record_view.dart

@ -477,10 +477,10 @@ class RealTimeWaveformPainter extends CustomPainter {
}
}
/// 绘制中央时间参考线
/// 绘制中央时间参考线(只保留水平线)
void _drawCenterLine(
Canvas canvas, Size size, double centerX, double centerY) {
// 绘制水平中线
// 只绘制水平中线
final horizontalLinePaint = Paint()
..color =
(isDarkMode ? Colors.white : Colors.black).withValues(alpha: 0.15)
@ -492,51 +492,25 @@ class RealTimeWaveformPainter extends CustomPainter {
horizontalLinePaint,
);
// 绘制垂直时间参考线(红色,更醒目)
final centerLinePaint = Paint()
..color = Colors.red.withValues(alpha: 0.8)
..strokeWidth = 2.0
..style = PaintingStyle.stroke;
canvas.drawLine(
Offset(centerX, centerY - size.height * 0.4),
Offset(centerX, centerY + size.height * 0.4),
centerLinePaint,
);
// 在参考线顶部绘制小三角形指示器
final trianglePath = Path();
final triangleSize = 4.0;
trianglePath.moveTo(centerX, centerY - size.height * 0.4);
trianglePath.lineTo(
centerX - triangleSize, centerY - size.height * 0.4 - triangleSize);
trianglePath.lineTo(
centerX + triangleSize, centerY - size.height * 0.4 - triangleSize);
trianglePath.close();
final trianglePaint = Paint()
..color = Colors.red
..style = PaintingStyle.fill;
canvas.drawPath(trianglePath, trianglePaint);
// 移除垂直时间参考线和三角形指示器
}
/// 绘制实时流动波形
/// 绘制实时流动波形(扩散到整个区域)
void _drawWaveform(Canvas canvas, Size size, double centerX, double centerY) {
final barWidth = 2.5; // 波形条宽度
final barSpacing = 0.5; // 波形条间距
final totalBarWidth = barWidth + barSpacing;
// 计算中央参考线左侧可以显示多少个波形条
final maxBarsOnLeft = (centerX / totalBarWidth).floor();
// 计算整个宽度可以显示多少个波形条
final maxBars = (size.width / totalBarWidth).floor();
// 绘制左侧流动波形(历史数据,从右向左流动)
_drawLeftWaveform(
canvas, centerX, centerY, barWidth, totalBarWidth, maxBarsOnLeft);
// 绘制扩散到整个区域的波形
_drawFullWaveform(
canvas, size, centerY, barWidth, totalBarWidth, maxBars);
}
/// 绘制左侧历史波形(从右向左流动)
void _drawLeftWaveform(Canvas canvas, double centerX, double centerY,
/// 绘制扩散到整个区域的波形
void _drawFullWaveform(Canvas canvas, Size size, double centerY,
double barWidth, double totalBarWidth, int maxBars) {
final dataLength = waveData.length;
if (dataLength == 0) return;
@ -544,24 +518,25 @@ class RealTimeWaveformPainter extends CustomPainter {
// 计算流动偏移量
final flowOffset = animationValue * totalBarWidth;
// 绘制最近的波形条(最多显示maxBars个)
// 绘制波形条,从左到右填满整个区域
final displayCount = min(dataLength, maxBars);
for (int i = 0; i < displayCount; i++) {
// 计算波形条的x位置:从参考线开始,向左排列,加上流动偏移
final x = centerX - (i + 1) * totalBarWidth + flowOffset;
// 计算波形条的x位置:从左边开始排列,加上流动偏移
final x = i * totalBarWidth + flowOffset;
// 如果波形条完全移出屏幕右侧,跳过绘制
if (x > size.width) continue;
// 如果波形条完全移出屏幕左侧,跳过绘制
if (x + barWidth < 0) continue;
// 获取对应的音频数据(最新的数据在数组末尾)
final dataIndex = dataLength - 1 - i;
if (dataIndex < 0) continue;
// 获取对应的音频数据(循环使用数据以填满整个区域)
final dataIndex = (dataLength - 1 - (i % dataLength)) % dataLength;
final amplitude = waveData[dataIndex];
// 计算透明度:越远的波形条越透明
final opacity = (1.0 - (i / displayCount) * 0.6).clamp(0.2, 1.0);
// 计算透明度:中央区域更亮,边缘渐暗
final distanceFromCenter = (x - size.width / 2).abs() / (size.width / 2);
final opacity = (1.0 - distanceFromCenter * 0.4).clamp(0.3, 1.0);
_drawWaveBar(canvas, x, centerY, barWidth, amplitude, opacity);
}

Loading…
Cancel
Save