29 KiB
29 KiB
分层管理功能重构技术实现指南
技术架构概览
系统组件关系图
┌─────────────────────────────────────────────────────────────┐
│ LogisticsControlPanel │
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌────────┐ │
│ │ 类别设置 │ │ 路径编辑 │ │ 检测动画 │ │ 分层管理 │ │
│ │ Tab │ │ Tab │ │ Tab │ │ Tab │ │
│ └─────────────┘ └─────────────┘ └─────────────┘ └────────┘ │
└─────────────────────────────────────────────────────────────┘
│
┌───────────────────────────────┘
│
┌─────────────────────────────────────────────────────────────┐
│ ModelLayerManagementView │
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ ┌────────┐ │
│ │ 楼层分析 │ │ 设置层属性 │ │ 分层保存 │ │选中保存 │ │
│ │ 功能区 │ │ 功能区 │ │ 功能区 │ │ 功能区 │ │
│ └─────────────┘ └─────────────┘ └─────────────┘ └────────┘ │
└─────────────────────────────────────────────────────────────┘
│
┌───────────────┼───────────────┐
│ │ │
┌─────────┐ ┌──────────────┐ ┌─────────────┐
│ViewModel│ │ Service │ │ Existing │
│ Layer │ │ Layer │ │ Components │
│ │ │ │ │ │
└─────────┘ └──────────────┘ └─────────────┘
核心技术栈
- UI框架: WPF (XAML + C#)
- 架构模式: MVVM (Model-View-ViewModel)
- API集成: Navisworks 2026 Native + COM API
- 异步处理: async/await + Task
- 事件驱动: EventHandler + INotifyPropertyChanged
详细实现方案
1. 楼层分析功能实现
1.1 核心数据结构
/// <summary>
/// 楼层分析结果数据模型
/// </summary>
public class FloorAnalysisResult : INotifyPropertyChanged
{
public string AttributeName { get; set; } // 属性名称
public int FloorCount { get; set; } // 检测到的楼层数
public double QualityScore { get; set; } // 质量评分 (0-100)
public List<string> FloorNames { get; set; } // 楼层名称列表
public bool IsFeasible { get; set; } // 是否可行
public string RecommendationText { get; set; } // 建议文本
public ObservableCollection<FloorInfo> Floors { get; set; } // 详细楼层信息
}
1.2 分析算法实现
/// <summary>
/// 执行楼层分析
/// </summary>
public async Task<FloorAnalysisResult> AnalyzeFloorsAsync()
{
try
{
OnStatusChanged("正在分析模型楼层结构...");
// 1. 获取可用的楼层属性
var availableAttributes = FloorDetector.GetAvailableFloorAttributes();
// 2. 为每个属性计算质量评分
var bestAttribute = await FindBestFloorAttributeAsync(availableAttributes);
// 3. 基于最佳属性检测楼层
var detectedFloors = await FloorDetector.DetectFloorsByAttributeAsync(bestAttribute);
// 4. 计算分析结果
var result = new FloorAnalysisResult
{
AttributeName = bestAttribute,
FloorCount = detectedFloors.Count,
QualityScore = CalculateQualityScore(detectedFloors),
FloorNames = detectedFloors.Select(f => f.FloorName).ToList(),
IsFeasible = detectedFloors.Count >= 2 && CalculateQualityScore(detectedFloors) > 60,
Floors = new ObservableCollection<FloorInfo>(detectedFloors)
};
result.RecommendationText = GenerateRecommendation(result);
OnStatusChanged($"楼层分析完成: 检测到 {result.FloorCount} 个楼层");
return result;
}
catch (Exception ex)
{
LogManager.Error($"楼层分析失败: {ex.Message}");
throw;
}
}
/// <summary>
/// 计算楼层属性质量评分
/// </summary>
private double CalculateQualityScore(List<FloorInfo> floors)
{
if (floors == null || floors.Count == 0) return 0;
double score = 0;
// 1. 楼层数量评分 (30%)
var countScore = Math.Min(floors.Count * 10, 30);
// 2. 命名规范性评分 (40%)
var namingScore = CalculateNamingQuality(floors) * 40;
// 3. 高程分布评分 (30%)
var elevationScore = CalculateElevationQuality(floors) * 30;
return countScore + namingScore + elevationScore;
}
1.3 UI实现 (XAML片段)
<!-- 楼层分析功能区 -->
<GroupBox Header="楼层分析" Margin="5" Height="300">
<Grid Margin="10">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<!-- 分析控制区 -->
<StackPanel Grid.Row="0" Orientation="Horizontal" Margin="0,0,0,10">
<Button Content="开始分析" Command="{Binding AnalyzeFloorsCommand}"
Padding="10,5" Margin="0,0,10,0"/>
<TextBlock Text="{Binding AnalysisStatus}" VerticalAlignment="Center"
Foreground="Blue"/>
</StackPanel>
<!-- 分析结果展示 -->
<DataGrid Grid.Row="1" ItemsSource="{Binding AnalysisResult.Floors}"
AutoGenerateColumns="False" IsReadOnly="True">
<DataGrid.Columns>
<DataGridTextColumn Header="楼层名称" Binding="{Binding FloorName}" Width="120"/>
<DataGridTextColumn Header="标高(m)" Binding="{Binding Elevation, StringFormat=F2}" Width="80"/>
<DataGridTextColumn Header="构件数量" Binding="{Binding ItemCount}" Width="80"/>
<DataGridCheckBoxColumn Header="有效" Binding="{Binding IsValid}" Width="60"/>
</DataGrid.Columns>
</DataGrid>
<!-- 质量评分显示 -->
<StackPanel Grid.Row="2" Margin="0,10,0,0">
<TextBlock Text="{Binding AnalysisResult.QualityScore, StringFormat='质量评分: {0:F1}/100'}"
FontWeight="Bold"/>
<TextBlock Text="{Binding AnalysisResult.RecommendationText}"
Foreground="DarkGreen" TextWrapping="Wrap"/>
</StackPanel>
</Grid>
</GroupBox>
2. 设置层属性功能实现
2.1 属性设置服务
/// <summary>
/// 层属性设置服务
/// </summary>
public class LayerAttributeService
{
private readonly CategoryAttributeManager _attributeManager;
public LayerAttributeService()
{
_attributeManager = new CategoryAttributeManager();
}
/// <summary>
/// 为选中的模型项设置层属性
/// </summary>
public async Task<bool> SetLayerAttributeAsync(ModelItemCollection items, string layerName)
{
try
{
OnStatusChanged($"正在为 {items.Count} 个构件设置层属性...");
// 使用COM API确保属性持久化
var success = await Task.Run(() =>
{
return _attributeManager.SetLogisticsAttribute(items, "Layer", layerName);
});
if (success)
{
OnStatusChanged($"成功为 {items.Count} 个构件设置层属性: {layerName}");
LayerAttributeChanged?.Invoke(this, new LayerAttributeChangedEventArgs(items, layerName));
}
return success;
}
catch (Exception ex)
{
LogManager.Error($"设置层属性失败: {ex.Message}");
return false;
}
}
/// <summary>
/// 批量设置多个楼层的属性
/// </summary>
public async Task<Dictionary<string, bool>> BatchSetLayerAttributesAsync(
Dictionary<string, ModelItemCollection> layerGroups)
{
var results = new Dictionary<string, bool>();
foreach (var group in layerGroups)
{
var success = await SetLayerAttributeAsync(group.Value, group.Key);
results[group.Key] = success;
// 添加延迟避免API过载
await Task.Delay(100);
}
return results;
}
public event EventHandler<LayerAttributeChangedEventArgs> LayerAttributeChanged;
public event EventHandler<string> StatusChanged;
private void OnStatusChanged(string status) => StatusChanged?.Invoke(this, status);
}
2.2 选择树操作界面
<!-- 设置层属性功能区 -->
<GroupBox Header="设置层属性" Margin="5" Height="350">
<Grid Margin="10">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<!-- 操作控制区 -->
<StackPanel Grid.Row="0" Orientation="Horizontal" Margin="0,0,0,10">
<Label Content="目标楼层:" VerticalAlignment="Center"/>
<ComboBox ItemsSource="{Binding AvailableFloors}"
SelectedItem="{Binding SelectedTargetFloor}"
Width="120" Margin="5,0"/>
<Button Content="设置选中项" Command="{Binding SetSelectedItemsLayerCommand}"
Padding="10,5" Margin="10,0"/>
</StackPanel>
<!-- 选择树视图 -->
<TreeView Grid.Row="1" ItemsSource="{Binding ModelTreeItems}"
BorderBrush="LightGray" BorderThickness="1">
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding Children}">
<StackPanel Orientation="Horizontal">
<CheckBox IsChecked="{Binding IsSelected}"
Command="{Binding DataContext.ToggleSelectionCommand,
RelativeSource={RelativeSource AncestorType=UserControl}}"
CommandParameter="{Binding}"/>
<TextBlock Text="{Binding Name}" Margin="5,0"/>
<TextBlock Text="{Binding ItemCount, StringFormat='({0})'}"
Foreground="Gray" Margin="5,0"/>
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
<!-- 状态信息 -->
<StackPanel Grid.Row="2" Margin="0,10,0,0">
<TextBlock Text="{Binding SelectedItemsInfo}" FontWeight="Bold"/>
<TextBlock Text="{Binding AttributeSetStatus}" Foreground="Green"/>
</StackPanel>
</Grid>
</GroupBox>
3. 分层保存功能实现
3.1 简化的分层配置
/// <summary>
/// 简化的分层保存配置
/// </summary>
public class SimpleSplitConfiguration
{
public SplitStrategy Strategy { get; set; } = SplitStrategy.ByFloor;
public string AttributeName { get; set; } = "Layer";
public string OutputDirectory { get; set; }
public string FileNameTemplate { get; set; } = "{ProjectName}_{LayerName}";
public bool EnablePreview { get; set; } = true;
public bool GenerateReport { get; set; } = true;
/// <summary>
/// 转换为完整的ModelSplitter配置
/// </summary>
public SplitConfiguration ToFullConfiguration()
{
return new SplitConfiguration
{
Strategy = this.Strategy,
AttributeName = this.AttributeName,
OutputDirectory = this.OutputDirectory,
FileNamePattern = this.FileNameTemplate,
IncludeEmptyLayers = false,
PreserveOriginalStructure = true,
GenerateReport = this.GenerateReport,
CreateSubDirectories = false
};
}
}
3.2 预览功能实现
/// <summary>
/// 生成分层保存预览
/// </summary>
public async Task<List<LayerPreviewInfo>> GenerateLayerPreviewAsync(SimpleSplitConfiguration config)
{
try
{
OnStatusChanged("正在生成分层预览...");
// 复用ModelSplitterManager的预览功能
var fullConfig = config.ToFullConfiguration();
var previewResults = await _modelSplitter.PreviewSplit(fullConfig);
var previewInfos = previewResults.Select(result => new LayerPreviewInfo
{
LayerName = result.LayerName,
ItemCount = result.ItemCount,
EstimatedFileSize = EstimateFileSize(result.Items),
OutputPath = result.OutputFilePath,
IsValid = result.ItemCount > 0
}).ToList();
OnStatusChanged($"预览生成完成: {previewInfos.Count} 个图层");
return previewInfos;
}
catch (Exception ex)
{
LogManager.Error($"生成预览失败: {ex.Message}");
throw;
}
}
/// <summary>
/// 执行分层保存
/// </summary>
public async Task<bool> ExecuteLayerSplitAsync(SimpleSplitConfiguration config,
IProgress<SplitProgressInfo> progress = null)
{
try
{
OnStatusChanged("开始分层保存...");
var fullConfig = config.ToFullConfiguration();
// 设置进度回调
if (progress != null)
{
_modelSplitter.ProgressChanged += (s, e) =>
{
progress.Report(new SplitProgressInfo
{
CurrentLayer = e.UserState?.ToString(),
ProgressPercentage = e.ProgressPercentage,
StatusText = $"正在处理: {e.UserState}"
});
};
}
var results = await _modelSplitter.ExecuteSplitAsync(fullConfig);
var successCount = results.Count(r => r.Success);
OnStatusChanged($"分层保存完成: {successCount}/{results.Count} 个文件成功保存");
return successCount == results.Count;
}
catch (Exception ex)
{
LogManager.Error($"分层保存失败: {ex.Message}");
return false;
}
}
3.3 分层保存UI
<!-- 分层保存功能区 -->
<GroupBox Header="分层保存" Margin="5" Height="400">
<Grid Margin="10">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<!-- 配置区 -->
<StackPanel Grid.Row="0" Margin="0,0,0,10">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"/>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<Label Grid.Row="0" Grid.Column="0" Content="分层依据:"/>
<ComboBox Grid.Row="0" Grid.Column="1"
ItemsSource="{Binding SplitStrategies}"
SelectedItem="{Binding SelectedSplitStrategy}"
Margin="5,0"/>
<Label Grid.Row="1" Grid.Column="0" Content="输出目录:"/>
<TextBox Grid.Row="1" Grid.Column="1"
Text="{Binding OutputDirectory}" Margin="5,0"/>
<Button Grid.Row="1" Grid.Column="2" Content="浏览"
Command="{Binding BrowseOutputDirectoryCommand}" Margin="5,0"/>
</Grid>
</StackPanel>
<!-- 操作按钮 -->
<StackPanel Grid.Row="1" Orientation="Horizontal" Margin="0,0,0,10">
<Button Content="生成预览" Command="{Binding GeneratePreviewCommand}"
Padding="10,5" Margin="0,0,10,0"/>
<Button Content="开始保存" Command="{Binding StartSplitCommand}"
Padding="10,5" Margin="0,0,10,0"/>
<CheckBox Content="生成报告" IsChecked="{Binding GenerateReport}"
VerticalAlignment="Center" Margin="10,0"/>
</StackPanel>
<!-- 预览列表 -->
<DataGrid Grid.Row="2" ItemsSource="{Binding LayerPreviews}"
AutoGenerateColumns="False" IsReadOnly="True">
<DataGrid.Columns>
<DataGridCheckBoxColumn Header="导出" Binding="{Binding IsSelected}" Width="50"/>
<DataGridTextColumn Header="图层名称" Binding="{Binding LayerName}" Width="150"/>
<DataGridTextColumn Header="构件数量" Binding="{Binding ItemCount}" Width="80"/>
<DataGridTextColumn Header="预估大小" Binding="{Binding EstimatedFileSize}" Width="80"/>
<DataGridTextColumn Header="输出路径" Binding="{Binding OutputPath}" Width="*"/>
</DataGrid.Columns>
</DataGrid>
<!-- 进度显示 -->
<StackPanel Grid.Row="3" Margin="0,10,0,0">
<TextBlock Text="{Binding SplitStatus}" FontWeight="Bold"/>
<ProgressBar Value="{Binding SplitProgress}" Maximum="100" Height="20" Margin="0,5"/>
</StackPanel>
</Grid>
</GroupBox>
4. 选中保存功能实现
4.1 选中内容保存服务
/// <summary>
/// 选中内容保存服务
/// </summary>
public class SelectionExportService
{
/// <summary>
/// 导出当前选中的内容
/// </summary>
public async Task<bool> ExportCurrentSelectionAsync(string outputPath,
IProgress<int> progress = null)
{
try
{
// 获取当前选择
var selection = NavisApplication.ActiveDocument.CurrentSelection;
if (selection.IsEmpty)
{
throw new InvalidOperationException("当前没有选中任何内容");
}
OnStatusChanged($"正在导出 {selection.Count} 个选中项...");
// 创建临时文档
var tempDoc = new Document();
// 复制选中内容到临时文档
await Task.Run(() =>
{
tempDoc.CurrentSelection.CopyFrom(selection);
// 报告进度
progress?.Report(50);
// 保存文档
tempDoc.SaveFile(outputPath);
progress?.Report(100);
});
OnStatusChanged($"选中内容已成功导出到: {outputPath}");
return true;
}
catch (Exception ex)
{
LogManager.Error($"导出选中内容失败: {ex.Message}");
return false;
}
}
/// <summary>
/// 获取选中内容的统计信息
/// </summary>
public SelectionInfo GetSelectionInfo()
{
var selection = NavisApplication.ActiveDocument.CurrentSelection;
return new SelectionInfo
{
ItemCount = selection.Count,
IsEmpty = selection.IsEmpty,
BoundingBox = selection.IsEmpty ? null : selection.ComputeBoundingBox(),
Categories = GetSelectionCategories(selection)
};
}
public event EventHandler<string> StatusChanged;
private void OnStatusChanged(string status) => StatusChanged?.Invoke(this, status);
}
/// <summary>
/// 选中内容信息
/// </summary>
public class SelectionInfo
{
public int ItemCount { get; set; }
public bool IsEmpty { get; set; }
public BoundingBox3D BoundingBox { get; set; }
public Dictionary<string, int> Categories { get; set; }
public string Summary => IsEmpty ? "未选中任何内容" :
$"已选中 {ItemCount} 个构件,范围: {FormatBounds()}";
private string FormatBounds()
{
if (BoundingBox == null) return "未知";
var size = BoundingBox.Max - BoundingBox.Min;
return $"{size.X:F1}×{size.Y:F1}×{size.Z:F1}m";
}
}
4.2 选中保存UI
<!-- 选中保存功能区 -->
<GroupBox Header="选中保存" Margin="5" Height="250">
<Grid Margin="10">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<!-- 选中信息显示 -->
<StackPanel Grid.Row="0" Margin="0,0,0,10">
<TextBlock Text="{Binding SelectionInfo.Summary}" FontWeight="Bold"/>
<TextBlock Text="{Binding SelectionInfo.Categories,
Converter={StaticResource DictionaryToStringConverter}}"
Foreground="Gray" FontSize="10"/>
</StackPanel>
<!-- 类别分布 -->
<ListView Grid.Row="1" ItemsSource="{Binding SelectionInfo.Categories}"
Visibility="{Binding SelectionInfo.IsEmpty,
Converter={StaticResource BoolToVisibilityConverter},
ConverterParameter=Invert}">
<ListView.View>
<GridView>
<GridViewColumn Header="类别" DisplayMemberBinding="{Binding Key}" Width="120"/>
<GridViewColumn Header="数量" DisplayMemberBinding="{Binding Value}" Width="60"/>
</GridView>
</ListView.View>
</ListView>
<!-- 导出控制 -->
<StackPanel Grid.Row="2" Margin="0,10,0,0">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"/>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
<Label Grid.Column="0" Content="文件名:" VerticalAlignment="Center"/>
<TextBox Grid.Column="1" Text="{Binding ExportFileName}" Margin="5,0"/>
<Button Grid.Column="2" Content="导出"
Command="{Binding ExportSelectionCommand}"
IsEnabled="{Binding SelectionInfo.IsEmpty,
Converter={StaticResource InverseBooleanConverter}}"
Padding="10,5" Margin="5,0"/>
</Grid>
<ProgressBar Value="{Binding ExportProgress}" Maximum="100"
Height="15" Margin="0,5"/>
<TextBlock Text="{Binding ExportStatus}" Foreground="Green"/>
</StackPanel>
</Grid>
</GroupBox>
性能优化策略
1. 内存管理优化
/// <summary>
/// 大模型处理的内存优化策略
/// </summary>
public class MemoryOptimizedProcessor
{
private const int BATCH_SIZE = 1000; // 批处理大小
/// <summary>
/// 分批处理大型模型
/// </summary>
public async Task<List<TResult>> ProcessInBatchesAsync<TSource, TResult>(
IEnumerable<TSource> source,
Func<IEnumerable<TSource>, Task<IEnumerable<TResult>>> processor,
IProgress<int> progress = null)
{
var results = new List<TResult>();
var batches = source.Batch(BATCH_SIZE).ToList();
for (int i = 0; i < batches.Count; i++)
{
var batch = batches[i];
var batchResults = await processor(batch);
results.AddRange(batchResults);
// 强制垃圾回收
if (i % 10 == 0)
{
GC.Collect();
GC.WaitForPendingFinalizers();
}
// 报告进度
progress?.Report((i + 1) * 100 / batches.Count);
}
return results;
}
}
2. 异步操作取消支持
/// <summary>
/// 支持取消的异步操作基类
/// </summary>
public abstract class CancellableAsyncOperation
{
protected CancellationTokenSource _cancellationTokenSource;
public bool IsCancelled => _cancellationTokenSource?.Token.IsCancellationRequested ?? false;
public void Cancel()
{
_cancellationTokenSource?.Cancel();
OnStatusChanged("操作已取消");
}
protected virtual void OnStatusChanged(string status)
{
StatusChanged?.Invoke(this, status);
}
public event EventHandler<string> StatusChanged;
}
错误处理与日志记录
1. 统一异常处理
/// <summary>
/// 分层管理异常处理器
/// </summary>
public class LayerManagementExceptionHandler
{
public static async Task<TResult> ExecuteWithExceptionHandlingAsync<TResult>(
Func<Task<TResult>> operation,
string operationName,
TResult defaultValue = default(TResult))
{
try
{
return await operation();
}
catch (UnauthorizedAccessException ex)
{
var message = $"{operationName}失败: 文件访问权限不足 - {ex.Message}";
LogManager.Error(message);
MessageBox.Show(message, "权限错误", MessageBoxButton.OK, MessageBoxImage.Warning);
return defaultValue;
}
catch (OutOfMemoryException ex)
{
var message = $"{operationName}失败: 内存不足,请尝试分批处理 - {ex.Message}";
LogManager.Error(message);
MessageBox.Show(message, "内存错误", MessageBoxButton.OK, MessageBoxImage.Error);
return defaultValue;
}
catch (Exception ex)
{
var message = $"{operationName}失败: {ex.Message}";
LogManager.Error(message, ex);
MessageBox.Show(message, "操作失败", MessageBoxButton.OK, MessageBoxImage.Error);
return defaultValue;
}
}
}
2. 操作日志记录
/// <summary>
/// 分层管理操作日志
/// </summary>
public class LayerManagementAuditLog
{
public static void LogLayerAnalysis(FloorAnalysisResult result)
{
LogManager.Info($"楼层分析完成: 属性={result.AttributeName}, " +
$"楼层数={result.FloorCount}, 质量评分={result.QualityScore:F1}");
}
public static void LogAttributeSetting(string layerName, int itemCount, bool success)
{
var status = success ? "成功" : "失败";
LogManager.Info($"层属性设置{status}: 楼层={layerName}, 构件数={itemCount}");
}
public static void LogLayerSplit(string strategy, int layerCount, int successCount)
{
LogManager.Info($"分层保存完成: 策略={strategy}, " +
$"总层数={layerCount}, 成功={successCount}");
}
public static void LogSelectionExport(int itemCount, string outputPath, bool success)
{
var status = success ? "成功" : "失败";
LogManager.Info($"选中导出{status}: 构件数={itemCount}, 路径={outputPath}");
}
}
集成测试方案
1. 单元测试示例
[TestClass]
public class LayerManagementTests
{
[TestMethod]
public async Task AnalyzeFloors_WithValidModel_ReturnsValidResult()
{
// Arrange
var viewModel = new ModelLayerManagementViewModel();
// Act
var result = await viewModel.AnalyzeFloorsAsync();
// Assert
Assert.IsNotNull(result);
Assert.IsTrue(result.FloorCount > 0);
Assert.IsTrue(result.QualityScore >= 0 && result.QualityScore <= 100);
}
[TestMethod]
public async Task SetLayerAttribute_WithValidSelection_ReturnsTrue()
{
// Arrange
var service = new LayerAttributeService();
var mockItems = CreateMockModelItems();
// Act
var success = await service.SetLayerAttributeAsync(mockItems, "TestFloor");
// Assert
Assert.IsTrue(success);
}
}
2. 集成测试检查清单
- 楼层分析功能在不同模型类型下的表现
- 属性设置在大型选择集下的性能
- 分层保存的文件完整性验证
- 选中导出的数据一致性检查
- 内存使用情况监控
- 异常恢复机制验证
文档创建时间: 2025-08-18
技术架构版本: v1.0
适用范围: NavisworksTransport分层管理功能重构