[Test] public void CreateFrom3() { var rng = new Random(123456789); var a2b = m4x4.Transform(v4.Random3N(0.0f, rng), rng.FloatC(0.0f, 1.0f), v4.Random3(0.0f, 10.0f, 1.0f, rng)); var b2a = Math_.Invert(a2b); var a2a = b2a * a2b; Assert.True(Math_.FEql(m4x4.Identity, a2a)); var b2a_fast = Math_.InvertFast(a2b); Assert.True(Math_.FEql(b2a_fast, b2a)); }
public void TestInversion() { var rng = new Random(); { var m = m3x4.Random(v4.Random3N(0, rng), -Math_.TauF, +Math_.TauF, rng); var inv_m0 = Math_.InvertFast(m); var inv_m1 = Math_.Invert(m); Assert.True(Math_.FEqlRelative(inv_m0, inv_m1, 0.001f)); } { for (; ;) { var m = m3x4.Random(-5.0f, +5.0f, 0, rng); if (!Math_.IsInvertible(m)) { continue; } var inv_m = Math_.Invert(m); var I0 = inv_m * m; var I1 = m * inv_m; Assert.True(Math_.FEqlRelative(I0, m3x4.Identity, 0.001f)); Assert.True(Math_.FEqlRelative(I1, m3x4.Identity, 0.001f)); break; } } { var m = new m3x4( new v4(0.25f, 0.5f, 1.0f, 0.0f), new v4(0.49f, 0.7f, 1.0f, 0.0f), new v4(1.0f, 1.0f, 1.0f, 0.0f)); var INV_M = new m3x4( new v4(10.0f, -16.666667f, 6.66667f, 0.0f), new v4(-17.0f, 25.0f, -8.0f, 0.0f), new v4(7.0f, -8.333333f, 2.333333f, 0.0f)); var inv_m = Math_.Invert(m); Assert.True(Math_.FEqlRelative(inv_m, INV_M, 0.001f)); } }
/// <summary>Set up UI elements</summary> private void SetupUI() { #region Hot Spots // Distance m_tb_snap_distance.ValueType = typeof(float); m_tb_snap_distance.ValidateText = t => float.TryParse(t, out var f) && f >= 0; m_tb_snap_distance.Value = 0.1f; m_tb_snap_distance.ValueCommitted += InvalidateGfxMeasure; // Snap types m_chk_verts.Checked = true; m_chk_edges.Checked = true; m_chk_faces.Checked = true; m_chk_verts.CheckedChanged += InvalidateGfxMeasure; m_chk_edges.CheckedChanged += InvalidateGfxMeasure; m_chk_faces.CheckedChanged += InvalidateGfxMeasure; // Spot colour m_panel_spot_colour.Click += (s, a) => { using (var dlg = new ColorDialog { Color = SpotColour, AllowFullOpen = true, AnyColor = true, SolidColorOnly = true }) { if (dlg.ShowDialog(this) != DialogResult.OK) { return; } SpotColour = dlg.Color; } }; #endregion #region Start/End point m_chk_point0.Checked = false; m_chk_point0.CheckedChanged += (s, a) => { if (m_chk_point0.Checked) { ActiveHit = Hit0; (Control.TopLevelControl as Form)?.Activate(); } }; m_chk_point1.Checked = false; m_chk_point1.CheckedChanged += (s, a) => { if (m_chk_point1.Checked) { ActiveHit = Hit1; (Control.TopLevelControl as Form)?.Activate(); } }; #endregion #region Measurement Grid // Measurement coordinate system m_cb_space.DataSource = Enum <EReferenceFrame> .ValuesArray; m_cb_space.Format += (s, a) => { a.Value = ((EReferenceFrame)a.ListItem).Desc(); }; m_cb_space.DropDownClosed += (s, a) => { InvalidateGfxMeasure(); Window.Invalidate(); InvalidateMeasurementsGrid(); }; // Measurement data grid m_grid_measurement.VirtualMode = true; m_grid_measurement.AutoGenerateColumns = false; m_grid_measurement.Columns.Add(new DataGridViewTextBoxColumn { HeaderText = "Quantity", }); m_grid_measurement.Columns.Add(new DataGridViewTextBoxColumn { HeaderText = "Value", }); m_grid_measurement.CellValueNeeded += (s, a) => { if (!m_grid_measurement.Within(a.ColumnIndex, a.RowIndex, out DataGridViewCell cell)) { return; } // Display the quantities var quantity = (EQuantity)a.RowIndex; switch (a.ColumnIndex) { default: throw new Exception("Unknown column"); case 0: { a.Value = quantity.Desc(); break; } case 1: { // Convert the points into the selected space var w2rf = Math_.InvertFast(RefSpaceToWorld); var pt0 = w2rf * Hit0.PointWS; var pt1 = w2rf * Hit1.PointWS; switch (quantity) { default: { throw new Exception($"Unknown quantity: {quantity}"); } case EQuantity.Distance: { a.Value = MeasurementValid ? (pt1 - pt0).Length.ToString() : "---"; break; } case EQuantity.DistanceX: { a.Value = MeasurementValid ? Math.Abs(pt1.x - pt0.x).ToString() : "---"; break; } case EQuantity.DistanceY: { a.Value = MeasurementValid ? Math.Abs(pt1.y - pt0.y).ToString() : "---"; break; } case EQuantity.DistanceZ: { a.Value = MeasurementValid ? Math.Abs(pt1.z - pt0.z).ToString() : "---"; break; } case EQuantity.AngleXY: { a.Value = MeasurementValid ? Math_.RadiansToDegrees(Math.Atan2(Math.Abs(pt1.y - pt0.y), Math.Abs(pt1.x - pt0.x))).ToString() : "---"; break; } case EQuantity.AngleXZ: { a.Value = MeasurementValid ? Math_.RadiansToDegrees(Math.Atan2(Math.Abs(pt1.z - pt0.z), Math.Abs(pt1.x - pt0.x))).ToString() : "---"; break; } case EQuantity.AngleYZ: { a.Value = MeasurementValid ? Math_.RadiansToDegrees(Math.Atan2(Math.Abs(pt1.z - pt0.z), Math.Abs(pt1.y - pt0.y))).ToString() : "---"; break; } case EQuantity.Instance0: { a.Value = Hit0.IsValid ? Hit0.Obj.Name : "---"; break; } case EQuantity.Instance1: { a.Value = Hit1.IsValid ? Hit1.Obj.Name : "---"; break; } } break; } } }; m_grid_measurement.KeyDown += DataGridView_.Copy; m_grid_measurement.ContextMenuStrip = DataGridView_.CMenu(m_grid_measurement, DataGridView_.EEditOptions.ReadOnly); m_grid_measurement.RowCount = Enum <EQuantity> .Count; #endregion }