質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.50%
C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

Visual Studio

Microsoft Visual StudioはMicrosoftによる統合開発環境(IDE)です。多種多様なプログラミング言語に対応しています。

XAML

XAML(Extensible Application Markup Language)はWPF、Silverlight、Windows PhoneそしてWindows Store appsでユーザーインターフェースを定義するために使われるXML言語です。

Arduino

Arduinoは、AVRマイコン、単純なI/O(入出力)ポートを備えた基板、C言語を元としたArduinoのプログラム言語と、それを実装した統合開発環境から構成されたシステムです。

WPF

Windows Presentation Foundation (WPF) は、魅力的な外観のユーザー エクスペリエンスを持つ Windows クライアント アプリケーションを作成するための次世代プレゼンテーション システムです

Q&A

解決済

1回答

764閲覧

arduinoで計測した座標の拡大を行いたい

rarar

総合スコア8

C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

Visual Studio

Microsoft Visual StudioはMicrosoftによる統合開発環境(IDE)です。多種多様なプログラミング言語に対応しています。

XAML

XAML(Extensible Application Markup Language)はWPF、Silverlight、Windows PhoneそしてWindows Store appsでユーザーインターフェースを定義するために使われるXML言語です。

Arduino

Arduinoは、AVRマイコン、単純なI/O(入出力)ポートを備えた基板、C言語を元としたArduinoのプログラム言語と、それを実装した統合開発環境から構成されたシステムです。

WPF

Windows Presentation Foundation (WPF) は、魅力的な外観のユーザー エクスペリエンスを持つ Windows クライアント アプリケーションを作成するための次世代プレゼンテーション システムです

1グッド

0クリップ

投稿2020/01/04 11:15

##現在できていること
テラテイルで質問をしながら何とかVisualStudioで画像がマウスに合わせて魚眼レンズ風に拡大されるプログラムを作ることができました.
現在は画像を拡大する座標をarduinoで計測した座標に置き換えようとしています

現在のプログラムはこんな感じです
MainWindow.xaml

xaml

1<Window 2 x:Class="Questions228869.MainWindow" 3 xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 4 xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 5 xmlns:local="clr-namespace:Questions228869" 6 xmlns:local1="clr-namespace:Primitive3DSurfaces" 7 Title="Sphere3D" 8 9 10 SizeToContent="WidthAndHeight"> 11 <Window.Resources> 12 <BitmapImage x:Key="earthImage" UriSource="Image/kyeboard.png" /> 13 </Window.Resources> 14 15 <Canvas Width="720" Height="480"> 16 <Image x:Name="sourceImage" Source="{StaticResource earthImage}" /> 17 <Viewport3D 18 x:Name="viewport" 19 Width="300" 20 Height="300"> 21 <Viewport3D.Camera> 22 <PerspectiveCamera 23 LookDirection="0,0,-1" 24 Position="0,0,3" 25 UpDirection="0,1,0" /> 26 </Viewport3D.Camera> 27 <ModelVisual3D> 28 <ModelVisual3D.Content> 29 <Model3DGroup> 30 <AmbientLight Color="#ffffff" /> 31 <DirectionalLight Direction="-1,-1,-1" Color="#ffffff" /> 32 </Model3DGroup> 33 </ModelVisual3D.Content> 34 </ModelVisual3D> 35 <local1:Sphere3D x:Name="sphere" /> 36 </Viewport3D> 37 <Button x:Name="Sencer" Content="start" Height="59" Width="211" FontSize="16" Click="Sencer_Click_1"/> 38 39 </Canvas> 40</Window>

MainWindow.xaml.cs

C#

1using System; 2using System.Windows; 3using System.Windows.Controls; 4using System.Windows.Input; 5using System.Windows.Media; 6using System.Windows.Media.Imaging; 7using System.Windows.Media.Media3D; 8using System.Collections.ObjectModel; 9using System.IO.Ports; 10using System.Text; 11using System.Windows.Forms; 12using System.Threading; 13using System.Threading.Tasks; 14 15namespace Questions228869 16{ 17 public partial class MainWindow : Window 18 { 19 SerialPort mySerialPort = new SerialPort("COM4"); 20 private readonly RenderTargetBitmap inflateImage; 21 // 倍率 それっぽくなるように現物合わせ 22 private const double scale = 1.2; 23 // 球に巻き始める余白部分 6時が正面とすると3時から反時計回り? 24 private const double offset = cropWidth / 4 * 3; 25 // 球に巻く画像の幅 高さから逆算 26 private const double cropWidth = Math.PI * cropHeight * scale; 27 // 球に巻く画像の高さ viewport.Height に合わせた 特に根拠なし 28 private const double cropHeight = 100 * scale; 29 30 string RxString; 31 int a; 32 33 public MainWindow() 34 { 35 InitializeComponent(); 36 37 // CroppedBitmapで例外が出るのでひと回り大きい画像を作る 38 // 上下右はもっと小さくていいが面倒なので全方向同じ数字で広げた 39 var image = (BitmapImage)Resources["earthImage"]; 40 var visual = new DrawingVisual(); 41 var dc = visual.RenderOpen(); 42 var rect = new Rect(0, 0, image.PixelWidth + offset * 2, image.PixelHeight + offset * 2); 43 dc.DrawRectangle(Brushes.White, null, rect); 44 dc.DrawImage(image, new Rect(offset, offset, image.PixelWidth, image.PixelHeight)); 45 dc.Close(); 46 47 inflateImage = new RenderTargetBitmap((int)rect.Width, (int)rect.Height, 96, 96, PixelFormats.Pbgra32); 48 inflateImage.Render(visual); 49 50 51 a = 1; 52 53 54 } 55 56 private void mySerialPort_DataReceived(object sender, SerialDataReceivedEventArgs e) 57 { 58 if (a == 1) 59 { 60 RxString = mySerialPort.ReadLine(); 61 a = 2; 62 Console.Write(RxString); 63 } 64 65 RxString = mySerialPort.ReadLine(); 66 67 68 string[] strArrayData = RxString.Split(','); 69 Console.Write(strArrayData[0]); 70 Console.Write(","); 71 Console.Write(strArrayData[1]); 72 float x = float.Parse(strArrayData[0]); 73 float y = float.Parse(strArrayData[1]); 74 75 // 魚眼レンズ風に拡大 76 viewport.SetValue(Canvas.LeftProperty, x - viewport.Width / 2); 77 viewport.SetValue(Canvas.TopProperty, y - viewport.Height / 2); 78 79 var ratioX = sourceImage.Source.Width / sourceImage.ActualWidth; 80 var ratioY = sourceImage.Source.Height / sourceImage.ActualHeight; 81 82 var sourceX = ratioX * x; 83 var sourceY = ratioY * y; 84 85 var X = sourceX; // 巻き始め分を大きくしたのでちょうどxで合う 86 var Y = sourceY - cropHeight / 2 + offset; 87 var rect = new Int32Rect((int)X, (int)Y, (int)cropWidth, (int)cropHeight); 88 try 89 { 90 var croppedBitmap = new CroppedBitmap(inflateImage, rect); 91 sphere.Material = new DiffuseMaterial(new ImageBrush(croppedBitmap)); 92 } 93 catch { /* NOP CroppedBitmapが範囲外 */ } 94 95 96 } 97 98 99 100 private void Sencer_Click_1(object sender, RoutedEventArgs e) 101 { 102 103 mySerialPort.BaudRate = 9600; 104 mySerialPort.Parity = Parity.None; 105 mySerialPort.Encoding = Encoding.UTF8; 106 mySerialPort.DataReceived += new SerialDataReceivedEventHandler(mySerialPort_DataReceived); 107 mySerialPort.Open(); 108 109 } 110 111 112 } 113 114}

Class1.cs

c#

1using System; 2using System.Windows; 3using System.Windows.Media; 4using System.Windows.Media.Media3D; 5 6namespace Primitive3DSurfaces 7{ 8 public abstract class Primitive3D : ModelVisual3D 9 { 10 public Primitive3D() 11 { 12 Content = _content; 13 _content.Geometry = Tessellate(); 14 } 15 16 public static DependencyProperty MaterialProperty = 17 DependencyProperty.Register( 18 "Material", 19 typeof(Material), 20 typeof(Primitive3D), new PropertyMetadata( 21 null, new PropertyChangedCallback(OnMaterialChanged))); 22 23 public Material Material 24 { 25 get { return (Material)GetValue(MaterialProperty); } 26 set { SetValue(MaterialProperty, value); } 27 } 28 29 internal static void OnMaterialChanged(Object sender, DependencyPropertyChangedEventArgs e) 30 { 31 Primitive3D p = ((Primitive3D)sender); 32 33 p._content.Material = p.Material; 34 } 35 36 internal static void OnGeometryChanged(DependencyObject d) 37 { 38 Primitive3D p = ((Primitive3D)d); 39 40 p._content.Geometry = p.Tessellate(); 41 } 42 43 internal double DegToRad(double degrees) 44 { 45 return (degrees / 180.0) * Math.PI; 46 } 47 48 internal abstract Geometry3D Tessellate(); 49 50 internal readonly GeometryModel3D _content = new GeometryModel3D(); 51 } 52}

Class2.cs

c#

1using System; 2using System.Windows; 3using System.Windows.Media; 4using System.Windows.Media.Media3D; 5 6namespace Primitive3DSurfaces 7{ 8 public sealed class Sphere3D : Primitive3D 9 { 10 internal Point3D GetPosition(double t, double y) 11 { 12 double r = Math.Sqrt(1 - y * y); 13 double x = r * Math.Cos(t); 14 double z = r * Math.Sin(t); 15 16 return new Point3D(x, y, z); 17 } 18 19 public Vector3D GetNormal(double t, double y) 20 { 21 return (Vector3D)GetPosition(t, y); 22 } 23 24 public Point GetTextureCoordinate(double t, double y) 25 { 26 Matrix TYtoUV = new Matrix(); 27 TYtoUV.Scale(1 / (2 * Math.PI), -0.5); 28 29 //Point p = new Point(t, y); 30 Point p = new Point(1 - t, y); 31 p = p * TYtoUV; 32 33 return p; 34 } 35 36 internal override Geometry3D Tessellate() 37 { 38 int tDiv = 32; 39 int yDiv = 32; 40 double maxTheta = DegToRad(360.0); 41 double minY = -1.0; 42 double maxY = 1.0; 43 44 double dt = maxTheta / tDiv; 45 double dy = (maxY - minY) / yDiv; 46 47 MeshGeometry3D mesh = new MeshGeometry3D(); 48 49 for (int yi = 0; yi <= yDiv; yi++) 50 { 51 double y = minY + yi * dy; 52 53 for (int ti = 0; ti <= tDiv; ti++) 54 { 55 double t = ti * dt; 56 57 mesh.Positions.Add(GetPosition(t, y)); 58 mesh.Normals.Add(GetNormal(t, y)); 59 mesh.TextureCoordinates.Add(GetTextureCoordinate(t, y)); 60 } 61 } 62 63 for (int yi = 0; yi < yDiv; yi++) 64 { 65 for (int ti = 0; ti < tDiv; ti++) 66 { 67 int x0 = ti; 68 int x1 = (ti + 1); 69 int y0 = yi * (tDiv + 1); 70 int y1 = (yi + 1) * (tDiv + 1); 71 72 mesh.TriangleIndices.Add(x0 + y0); 73 mesh.TriangleIndices.Add(x0 + y1); 74 mesh.TriangleIndices.Add(x1 + y0); 75 76 mesh.TriangleIndices.Add(x1 + y0); 77 mesh.TriangleIndices.Add(x0 + y1); 78 mesh.TriangleIndices.Add(x1 + y1); 79 } 80 } 81 82 mesh.Freeze(); 83 return mesh; 84 } 85 } 86} 87

##起こっているエラー
MainWindow.xaml.csの魚眼レンズ風に拡大する部分でこのオブジェクトは別のスレッドに所有されているため,呼び出しスレッドはこのオブジェクトにアクセスできませんというエラーが出ます

このエラーの解消の仕方がわかりませんどなたか知恵をお貸しください!

TN8001👍を押しています

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

viewport.SetValueのところか、そこ以下全部を

cs

1Dispatcher.Invoke((Action)(() => 2{ 3 // ここに 4}));

で囲ってみてください(BeginInvokeのほうがいいのかな??)

投稿2020/01/04 13:02

編集2023/07/17 13:32
TN8001

総合スコア9244

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

rarar

2020/01/05 01:53

できました! ありがとうございました
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.50%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問