├── .gitignore
├── README.md
├── coco.prototxt
├── csharp
├── App.config
├── Form1.Designer.cs
├── Form1.cs
├── Form1.resx
├── Onnx.cs
├── Program.cs
├── Properties
│ ├── AssemblyInfo.cs
│ ├── Resources.Designer.cs
│ ├── Resources.resx
│ ├── Settings.Designer.cs
│ └── Settings.settings
├── object_detection.csproj
├── object_detection.sln
└── packages.config
├── docs
├── csharp.jpg
└── python.jpg
├── images
├── airport.jpg
├── persons.jpg
└── school.jpg
├── object_detection_image_onnx.py
└── ssd_mobilenet_v1_coco_2018_01_28
├── frozen.onnx
└── model.onnx
/.gitignore:
--------------------------------------------------------------------------------
1 | ## Ignore Visual Studio temporary files, build results, and
2 | ## files generated by popular Visual Studio add-ons.
3 |
4 | # User-specific files
5 | *.suo
6 | *.user
7 | *.userosscache
8 | *.sln.docstates
9 |
10 | # .NET Core
11 | project.lock.json
12 | project.fragment.lock.json
13 | artifacts/
14 |
15 | # Build results
16 | [Dd]ebug/
17 | [Dd]ebugPublic/
18 | [Rr]elease/
19 | [Rr]eleases/
20 | x64/
21 | x86/
22 | build/
23 | bld/
24 | [Bb]in/
25 | [Oo]bj/
26 |
27 | # Roslyn cache directories
28 | *.ide/
29 |
30 | # MSTest test Results
31 | [Tt]est[Rr]esult*/
32 | [Bb]uild[Ll]og.*
33 |
34 | #NUNIT
35 | *.VisualState.xml
36 | TestResult.xml
37 |
38 | # Build Results of an ATL Project
39 | [Dd]ebugPS/
40 | [Rr]eleasePS/
41 | dlldata.c
42 |
43 | *_i.c
44 | *_p.c
45 | *_i.h
46 | *.ilk
47 | *.meta
48 | *.obj
49 | *.pch
50 | *.pdb
51 | *.pgc
52 | *.pgd
53 | *.rsp
54 | *.sbr
55 | *.tlb
56 | *.tli
57 | *.tlh
58 | *.tmp
59 | *.tmp_proj
60 | *.log
61 | *.vspscc
62 | *.vssscc
63 | .builds
64 | *.pidb
65 | *.svclog
66 | *.scc
67 |
68 | # Chutzpah Test files
69 | _Chutzpah*
70 |
71 | # Visual C++ cache files
72 | ipch/
73 | *.aps
74 | *.ncb
75 | *.opensdf
76 | *.sdf
77 | *.cachefile
78 |
79 | # Visual Studio profiler
80 | *.psess
81 | *.vsp
82 | *.vspx
83 |
84 | # TFS 2012 Local Workspace
85 | $tf/
86 |
87 | # Guidance Automation Toolkit
88 | *.gpState
89 |
90 | # ReSharper is a .NET coding add-in
91 | _ReSharper*/
92 | *.[Rr]e[Ss]harper
93 | *.DotSettings.user
94 |
95 | # JustCode is a .NET coding addin-in
96 | .JustCode
97 |
98 | # TeamCity is a build add-in
99 | _TeamCity*
100 |
101 | # DotCover is a Code Coverage Tool
102 | *.dotCover
103 |
104 | # NCrunch
105 | _NCrunch_*
106 | .*crunch*.local.xml
107 |
108 | # MightyMoose
109 | *.mm.*
110 | AutoTest.Net/
111 |
112 | # Web workbench (sass)
113 | .sass-cache/
114 |
115 | # Installshield output folder
116 | [Ee]xpress/
117 |
118 | # DocProject is a documentation generator add-in
119 | DocProject/buildhelp/
120 | DocProject/Help/*.HxT
121 | DocProject/Help/*.HxC
122 | DocProject/Help/*.hhc
123 | DocProject/Help/*.hhk
124 | DocProject/Help/*.hhp
125 | DocProject/Help/Html2
126 | DocProject/Help/html
127 |
128 | # Click-Once directory
129 | publish/
130 |
131 | # Publish Web Output
132 | *.[Pp]ublish.xml
133 | *.azurePubxml
134 | # TODO: Comment the next line if you want to checkin your web deploy settings
135 | # but database connection strings (with potential passwords) will be unencrypted
136 | *.pubxml
137 | *.publishproj
138 |
139 | # NuGet Packages
140 | *.nupkg
141 | # The packages folder can be ignored because of Package Restore
142 | **/packages/*
143 | # except build/, which is used as an MSBuild target.
144 | !**/packages/build/
145 | # If using the old MSBuild-Integrated Package Restore, uncomment this:
146 | #!**/packages/repositories.config
147 |
148 | # Windows Azure Build Output
149 | csx/
150 | *.build.csdef
151 |
152 | # Windows Store app package directory
153 | AppPackages/
154 |
155 | # Others
156 | *.Cache
157 | ClientBin/
158 | [Ss]tyle[Cc]op.*
159 | ~$*
160 | *~
161 | *.dbmdl
162 | *.dbproj.schemaview
163 | #*.pfx
164 | #*.publishsettings
165 | node_modules/
166 | bower_components/
167 |
168 | # RIA/Silverlight projects
169 | Generated_Code/
170 |
171 | # Backup & report files from converting an old project file
172 | # to a newer Visual Studio version. Backup files are not needed,
173 | # because we have git ;-)
174 | _UpgradeReport_Files/
175 | Backup*/
176 | UpgradeLog*.XML
177 | UpgradeLog*.htm
178 |
179 | # SQL Server files
180 | *.mdf
181 | *.ldf
182 |
183 | # Business Intelligence projects
184 | *.rdl.data
185 | *.bim.layout
186 | *.bim_*.settings
187 |
188 | # Microsoft Fakes
189 | FakesAssemblies/
190 |
191 | # Installer files
192 | Installer/Files
193 | Installer/Installer/output/
194 |
195 | # Visual Studio files
196 | *.VC.opendb
197 | .vs/
198 | .idea/
199 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Running TF object detection model using onnxruntime
2 |
3 |
4 | ## Installation
5 | Install **python 3+** dependencies.
6 | ```
7 | tensorflow: 1.12.0
8 | onnx: 1.6.0
9 | tf2onnx: 1.5.5
10 | onnxruntime: 1.1.0
11 | ```
12 |
13 | ## TF to ONNX
14 | Download TF object detection model trained on [**COCO dataset**](https://cocodataset.org/#home) from the [**Model Zoo**](https://github.com/tensorflow/models/blob/master/research/object_detection/g3doc/tf1_detection_zoo.md) and convert it to onnx model.
15 | For example download [**ssd_mobilenet_v1_coco_2018_01_28**](http://download.tensorflow.org/models/object_detection/ssd_mobilenet_v1_coco_2018_01_28.tar.gz) and convert it to onnx model from **saved_model.pb**
16 | ```
17 | python -m tf2onnx.convert
18 | --opset 11
19 | --fold_const
20 | --saved-model ssd_mobilenet_v1_coco_2018_01_28/saved_model/
21 | --output ssd_mobilenet_v1_coco_2018_01_28/model.onnx
22 | ```
23 | or from **frozen_inference_graph.pb**
24 | ```
25 | python -m tf2onnx.convert
26 | --opset 11
27 | --fold_const
28 | --graphdef ssd_mobilenet_v1_coco_2018_01_28/frozen_inference_graph.pb
29 | --output ssd_mobilenet_v1_coco_2018_01_28/frozen.onnx
30 | --inputs image_tensor:0
31 | --outputs detection_boxes:0,detection_classes:0,detection_scores:0,num_detections:0
32 | ```
33 | For run **python** and **C#** examples below download [**path**](https://yadi.sk/d/ap5F1VPma6qMGQ?w=1) with already-made **ssd_mobilenet_v1_coco_2018_01_28** onnx models and move it to repository root folder.
34 |
35 | ## Python script
36 | Run python script [**object_detection_image_onnx.py**](object_detection_image_onnx.py) to test converted onnx model.
37 |

38 | Figure 1. Python example
39 |
40 | ## C# application
41 | Build [**C#**](/csharp) source code and run application.
42 | 
43 | Figure 2. C# example
44 |
45 | ## References
46 | [1] TensorFlow detection [**model zoo**](https://github.com/tensorflow/models/blob/master/research/object_detection/g3doc/detection_model_zoo.md).
47 | [2] Tutorial: how to convert them to ONNX and run them under [**onnxruntime**](https://github.com/onnx/tensorflow-onnx/blob/master/tutorials/ConvertingSSDMobilenetToONNX.ipynb).
48 | [3] Microsoft: ONNX Runtime [**C#**](https://github.com/microsoft/onnxruntime/blob/master/docs/CSharp_API.md) API.
49 |
--------------------------------------------------------------------------------
/coco.prototxt:
--------------------------------------------------------------------------------
1 | person
2 | bicycle
3 | car
4 | motorcycle
5 | airplane
6 | bus
7 | train
8 | truck
9 | boat
10 | traffic light
11 | fire hydrant
12 | --unknown
13 | stop sign
14 | parking meter
15 | bench
16 | bird
17 | cat
18 | dog
19 | horse
20 | sheep
21 | cow
22 | elephant
23 | bear
24 | zebra
25 | giraffe
26 | --unknown
27 | backpack
28 | umbrella
29 | --unknown
30 | --unknown
31 | handbag
32 | tie
33 | suitcase
34 | frisbee
35 | skis
36 | snowboard
37 | sports ball
38 | kite
39 | baseball bat
40 | baseball glove
41 | skateboard
42 | surfboard
43 | tennis racket
44 | bottle
45 | --unknown
46 | wine glass
47 | cup
48 | fork
49 | knife
50 | spoon
51 | bowl
52 | banana
53 | apple
54 | sandwich
55 | orange
56 | broccoli
57 | carrot
58 | hot dog
59 | pizza
60 | donut
61 | cake
62 | chair
63 | couch
64 | potted plant
65 | bed
66 | --unknown
67 | dining table
68 | --unknown
69 | --unknown
70 | toilet
71 | --unknown
72 | tv
73 | laptop
74 | mouse
75 | remote
76 | keyboard
77 | cell phone
78 | microwave
79 | oven
80 | toaster
81 | sink
82 | refrigerator
83 | --unknown
84 | book
85 | clock
86 | vase
87 | scissors
88 | teddy bear
89 | hair drier
90 | toothbrush
--------------------------------------------------------------------------------
/csharp/App.config:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/csharp/Form1.Designer.cs:
--------------------------------------------------------------------------------
1 | namespace object_detection
2 | {
3 | partial class Form1
4 | {
5 | ///
6 | /// Required designer variable.
7 | ///
8 | private System.ComponentModel.IContainer components = null;
9 |
10 | ///
11 | /// Clean up any resources being used.
12 | ///
13 | /// true if managed resources should be disposed; otherwise, false.
14 | protected override void Dispose(bool disposing)
15 | {
16 | if (disposing && (components != null))
17 | {
18 | components.Dispose();
19 | }
20 | base.Dispose(disposing);
21 | }
22 |
23 | #region Windows Form Designer generated code
24 |
25 | ///
26 | /// Required method for Designer support - do not modify
27 | /// the contents of this method with the code editor.
28 | ///
29 | private void InitializeComponent()
30 | {
31 | this.SuspendLayout();
32 | //
33 | // Form1
34 | //
35 | this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
36 | this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
37 | this.BackgroundImageLayout = System.Windows.Forms.ImageLayout.Zoom;
38 | this.ClientSize = new System.Drawing.Size(550, 415);
39 | this.Name = "Form1";
40 | this.StartPosition = System.Windows.Forms.FormStartPosition.CenterScreen;
41 | this.Text = "Form1";
42 | this.Load += new System.EventHandler(this.Form1_Load);
43 | this.ResumeLayout(false);
44 |
45 | }
46 |
47 | #endregion
48 | }
49 | }
50 |
51 |
--------------------------------------------------------------------------------
/csharp/Form1.cs:
--------------------------------------------------------------------------------
1 | using Microsoft.ML.OnnxRuntime;
2 | using Microsoft.ML.OnnxRuntime.Tensors;
3 | using System;
4 | using System.Collections.Generic;
5 | using System.Drawing;
6 | using System.IO;
7 | using System.Linq;
8 | using System.Windows.Forms;
9 |
10 | namespace object_detection
11 | {
12 | public partial class Form1 : Form
13 | {
14 | #region Private data
15 |
16 | private readonly string model = @"..\..\..\ssd_mobilenet_v1_coco_2018_01_28\model.onnx";
17 | private readonly string prototxt = @"..\..\..\coco.prototxt";
18 | private readonly InferenceSession session;
19 |
20 | #endregion
21 |
22 | #region Form voids
23 |
24 | public Form1()
25 | {
26 | InitializeComponent();
27 | DragDrop += Form1_DragDrop;
28 | DragEnter += Form1_DragEnter;
29 | AllowDrop = true;
30 | session = new InferenceSession(model);
31 | string file = @"..\..\..\\images\airport.jpg";
32 | BackgroundImage = new Bitmap(file);
33 | }
34 |
35 | private void Form1_DragEnter(object sender, DragEventArgs e)
36 | {
37 | e.Effect = e.Data.GetDataPresent(DataFormats.FileDrop) ? DragDropEffects.All : DragDropEffects.None;
38 | }
39 |
40 | private void Form1_DragDrop(object sender, DragEventArgs e)
41 | {
42 | Cursor = Cursors.WaitCursor;
43 | var file = ((string[])e.Data.GetData(DataFormats.FileDrop, true))[0];
44 | BackgroundImage?.Dispose();
45 | BackgroundImage = new Bitmap(file, false);
46 | Process();
47 | Cursor = Cursors.Default;
48 | }
49 |
50 | private void Form1_Load(object sender, EventArgs e)
51 | {
52 | Process();
53 | }
54 |
55 | private void Process()
56 | {
57 | // params
58 | var threshold = 0.0f;
59 | var c = Color.Yellow;
60 | using var font = new Font("Arial", 22);
61 |
62 | // inference session
63 | Console.WriteLine("Starting inference session...");
64 | var tic = Environment.TickCount;
65 | var inputMeta = session.InputMetadata;
66 | var name = inputMeta.Keys.ToArray()[0];
67 | var labels = File.ReadAllLines(prototxt);
68 | Console.WriteLine("Session started in " + (Environment.TickCount - tic) + " mls.");
69 |
70 | // image
71 | Console.WriteLine("Creating image tensor...");
72 | tic = Environment.TickCount;
73 | var image = (Bitmap)BackgroundImage;
74 | var width = image.Width;
75 | var height = image.Height;
76 | var dimentions = new int[] { 1, height, width, 3 };
77 | var inputData = Onnx.ToTensor(image);
78 | Console.WriteLine("Tensor was created in " + (Environment.TickCount - tic) + " mls.");
79 |
80 | // prediction
81 | Console.WriteLine("Detecting objects...");
82 | tic = Environment.TickCount;
83 | var t1 = new DenseTensor(inputData, dimentions);
84 | var inputs = new List() { NamedOnnxValue.CreateFromTensor(name, t1) };
85 | var results = session.Run(inputs).ToArray();
86 |
87 | // dump the results
88 | foreach (var r in results)
89 | {
90 | Console.WriteLine(r.Name + "\n");
91 | Console.WriteLine(r.AsTensor().GetArrayString());
92 | }
93 | Console.WriteLine("Detecting was finished in " + (Environment.TickCount - tic) + " mls.");
94 |
95 | // drawing results
96 | Console.WriteLine("Drawing inference results...");
97 | tic = Environment.TickCount;
98 | var detection_boxes = results[0].AsTensor();
99 | var detection_classes = results[1].AsTensor();
100 | var detection_scores = results[2].AsTensor();
101 | var num_detections = results[3].AsTensor()[0];
102 |
103 | using (var g = Graphics.FromImage(image))
104 | {
105 | for (int i = 0; i < num_detections; i++)
106 | {
107 | var score = detection_scores[0, i];
108 |
109 | if (score > threshold)
110 | {
111 | var label = labels[(int)detection_classes[0, i] - 1];
112 |
113 | var x = (int)(detection_boxes[0, i, 0] * height);
114 | var y = (int)(detection_boxes[0, i, 1] * width);
115 | var w = (int)(detection_boxes[0, i, 2] * height);
116 | var h = (int)(detection_boxes[0, i, 3] * width);
117 |
118 | // python rectangle
119 | var rectangle = Rectangle.FromLTRB(y, x, h, w);
120 | using var brush = new SolidBrush(c);
121 | using var pen = new Pen(c) { Width = 3 };
122 | g.DrawString(label, font, brush, y, x);
123 | g.DrawRectangle(pen, rectangle);
124 | }
125 | }
126 | }
127 |
128 | BackgroundImage = image;
129 | Console.WriteLine("Drawing was finished in " + (Environment.TickCount - tic) + " mls.");
130 | }
131 |
132 | #endregion
133 | }
134 | }
135 |
--------------------------------------------------------------------------------
/csharp/Form1.resx:
--------------------------------------------------------------------------------
1 |
2 |
3 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 |
106 |
107 |
108 |
109 | text/microsoft-resx
110 |
111 |
112 | 2.0
113 |
114 |
115 | System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
116 |
117 |
118 | System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
119 |
120 |
--------------------------------------------------------------------------------
/csharp/Onnx.cs:
--------------------------------------------------------------------------------
1 | using System.Drawing;
2 | using System.Drawing.Imaging;
3 |
4 | namespace object_detection
5 | {
6 | public static class Onnx
7 | {
8 | #region Tensor
9 | ///
10 | /// Converts a Bitmap to an RGB tensor array.
11 | ///
12 | /// Bitmap
13 | /// RGB tensor array
14 | public static byte[] ToTensor(this Bitmap Data)
15 | {
16 | BitmapData bmData = Onnx.Lock24bpp(Data);
17 | byte[] rgb = Onnx.ToTensor(bmData);
18 | Onnx.Unlock(Data, bmData);
19 | return rgb;
20 | }
21 | ///
22 | /// Converts a Bitmap to an RGB tensor array.
23 | ///
24 | /// Bitmap data
25 | /// RGB tensor array
26 | public unsafe static byte[] ToTensor(this BitmapData bmData)
27 | {
28 | // params
29 | int width = bmData.Width, height = bmData.Height, stride = bmData.Stride;
30 | byte* p = (byte*)bmData.Scan0.ToPointer();
31 | byte[] t = new byte[3 * height * width];
32 | int pos = 0;
33 |
34 | // do job
35 | for (int j = 0; j < height; j++)
36 | {
37 | int k, jstride = j * stride;
38 |
39 | for (int i = 0; i < width; i++)
40 | {
41 | k = jstride + i * 3;
42 |
43 | t[pos++] = p[k + 2];
44 | t[pos++] = p[k + 1];
45 | t[pos++] = p[k + 0];
46 | }
47 | }
48 |
49 | return t;
50 | }
51 | ///
52 | /// Converts an RGB tensor array to a color image.
53 | ///
54 | /// RGB tensor array
55 | /// Bitmap width
56 | /// Bitmap height
57 | /// Bitmap
58 | public unsafe static Bitmap FromTensor(this byte[] tensor, int width, int height)
59 | {
60 | Bitmap bitmap = new Bitmap(width, height);
61 | FromTensor(tensor, width, height, bitmap);
62 | return bitmap;
63 | }
64 | ///
65 | /// Converts an RGB tensor array to a color image.
66 | ///
67 | /// RGBA tensor array
68 | /// Bitmap width
69 | /// Bitmap height
70 | /// Bitmap data
71 | public unsafe static void FromTensor(this byte[] tensor, int width, int height, BitmapData bmData)
72 | {
73 | // params
74 | int stride = bmData.Stride;
75 | byte* p = (byte*)bmData.Scan0.ToPointer();
76 | int pos = 0;
77 |
78 | // do job
79 | for (int j = 0; j < height; j++)
80 | {
81 | int k, jstride = j * stride;
82 |
83 | for (int i = 0; i < width; i++)
84 | {
85 | k = jstride + i * 3;
86 |
87 | // rgb
88 | p[k + 2] = tensor[pos++];
89 | p[k + 1] = tensor[pos++];
90 | p[k + 0] = tensor[pos++];
91 | }
92 | }
93 |
94 | return;
95 | }
96 | ///
97 | /// Converts an RGB tensor array to a color image.
98 | ///
99 | /// RGBA tensor array
100 | /// Bitmap width
101 | /// Bitmap height
102 | /// Bitmap
103 | public static void FromTensor(this byte[] tensor, int width, int height, Bitmap Data)
104 | {
105 | BitmapData bmData = Onnx.Lock24bpp(Data);
106 | FromTensor(tensor, width, height, bmData);
107 | Onnx.Unlock(Data, bmData);
108 | return;
109 | }
110 | #endregion
111 |
112 | #region BitmapData voids
113 | ///
114 | /// Blocks Bitmap in system memory.
115 | ///
116 | /// Bitmap
117 | /// Bitmap data
118 | public static BitmapData Lock24bpp(this Bitmap b)
119 | {
120 | return b.LockBits(new Rectangle(0, 0, b.Width, b.Height), ImageLockMode.ReadWrite, PixelFormat.Format24bppRgb);
121 | }
122 | ///
123 | /// Unblocks Bitmap in system memory.
124 | ///
125 | /// Bitmap
126 | /// Bitmap data
127 | public static void Unlock(this Bitmap b, BitmapData bmData)
128 | {
129 | b.UnlockBits(bmData);
130 | return;
131 | }
132 | #endregion
133 | }
134 | }
135 |
--------------------------------------------------------------------------------
/csharp/Program.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using System.Threading.Tasks;
5 | using System.Windows.Forms;
6 |
7 | namespace object_detection
8 | {
9 | static class Program
10 | {
11 | ///
12 | /// The main entry point for the application.
13 | ///
14 | [STAThread]
15 | static void Main()
16 | {
17 | Application.EnableVisualStyles();
18 | Application.SetCompatibleTextRenderingDefault(false);
19 | Application.Run(new Form1());
20 | }
21 | }
22 | }
23 |
--------------------------------------------------------------------------------
/csharp/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Reflection;
2 | using System.Runtime.CompilerServices;
3 | using System.Runtime.InteropServices;
4 |
5 | // General Information about an assembly is controlled through the following
6 | // set of attributes. Change these attribute values to modify the information
7 | // associated with an assembly.
8 | [assembly: AssemblyTitle("object_detection")]
9 | [assembly: AssemblyDescription("")]
10 | [assembly: AssemblyConfiguration("")]
11 | [assembly: AssemblyCompany("")]
12 | [assembly: AssemblyProduct("object_detection")]
13 | [assembly: AssemblyCopyright("Copyright © 2020")]
14 | [assembly: AssemblyTrademark("")]
15 | [assembly: AssemblyCulture("")]
16 |
17 | // Setting ComVisible to false makes the types in this assembly not visible
18 | // to COM components. If you need to access a type in this assembly from
19 | // COM, set the ComVisible attribute to true on that type.
20 | [assembly: ComVisible(false)]
21 |
22 | // The following GUID is for the ID of the typelib if this project is exposed to COM
23 | [assembly: Guid("1934e6a4-d235-4007-a918-96a0e72bdcaf")]
24 |
25 | // Version information for an assembly consists of the following four values:
26 | //
27 | // Major Version
28 | // Minor Version
29 | // Build Number
30 | // Revision
31 | //
32 | // You can specify all the values or you can default the Build and Revision Numbers
33 | // by using the '*' as shown below:
34 | // [assembly: AssemblyVersion("1.0.*")]
35 | [assembly: AssemblyVersion("1.0.0.0")]
36 | [assembly: AssemblyFileVersion("1.0.0.0")]
37 |
--------------------------------------------------------------------------------
/csharp/Properties/Resources.Designer.cs:
--------------------------------------------------------------------------------
1 | //------------------------------------------------------------------------------
2 | //
3 | // This code was generated by a tool.
4 | // Runtime Version:4.0.30319.42000
5 | //
6 | // Changes to this file may cause incorrect behavior and will be lost if
7 | // the code is regenerated.
8 | //
9 | //------------------------------------------------------------------------------
10 |
11 | namespace object_detection.Properties
12 | {
13 |
14 |
15 | ///
16 | /// A strongly-typed resource class, for looking up localized strings, etc.
17 | ///
18 | // This class was auto-generated by the StronglyTypedResourceBuilder
19 | // class via a tool like ResGen or Visual Studio.
20 | // To add or remove a member, edit your .ResX file then rerun ResGen
21 | // with the /str option, or rebuild your VS project.
22 | [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")]
23 | [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
24 | [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
25 | internal class Resources
26 | {
27 |
28 | private static global::System.Resources.ResourceManager resourceMan;
29 |
30 | private static global::System.Globalization.CultureInfo resourceCulture;
31 |
32 | [global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")]
33 | internal Resources()
34 | {
35 | }
36 |
37 | ///
38 | /// Returns the cached ResourceManager instance used by this class.
39 | ///
40 | [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
41 | internal static global::System.Resources.ResourceManager ResourceManager
42 | {
43 | get
44 | {
45 | if ((resourceMan == null))
46 | {
47 | global::System.Resources.ResourceManager temp = new global::System.Resources.ResourceManager("object_detection.Properties.Resources", typeof(Resources).Assembly);
48 | resourceMan = temp;
49 | }
50 | return resourceMan;
51 | }
52 | }
53 |
54 | ///
55 | /// Overrides the current thread's CurrentUICulture property for all
56 | /// resource lookups using this strongly typed resource class.
57 | ///
58 | [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
59 | internal static global::System.Globalization.CultureInfo Culture
60 | {
61 | get
62 | {
63 | return resourceCulture;
64 | }
65 | set
66 | {
67 | resourceCulture = value;
68 | }
69 | }
70 | }
71 | }
72 |
--------------------------------------------------------------------------------
/csharp/Properties/Resources.resx:
--------------------------------------------------------------------------------
1 |
2 |
3 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 |
106 | text/microsoft-resx
107 |
108 |
109 | 2.0
110 |
111 |
112 | System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
113 |
114 |
115 | System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
116 |
117 |
--------------------------------------------------------------------------------
/csharp/Properties/Settings.Designer.cs:
--------------------------------------------------------------------------------
1 | //------------------------------------------------------------------------------
2 | //
3 | // This code was generated by a tool.
4 | // Runtime Version:4.0.30319.42000
5 | //
6 | // Changes to this file may cause incorrect behavior and will be lost if
7 | // the code is regenerated.
8 | //
9 | //------------------------------------------------------------------------------
10 |
11 | namespace object_detection.Properties
12 | {
13 |
14 |
15 | [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
16 | [global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.VisualStudio.Editors.SettingsDesigner.SettingsSingleFileGenerator", "11.0.0.0")]
17 | internal sealed partial class Settings : global::System.Configuration.ApplicationSettingsBase
18 | {
19 |
20 | private static Settings defaultInstance = ((Settings)(global::System.Configuration.ApplicationSettingsBase.Synchronized(new Settings())));
21 |
22 | public static Settings Default
23 | {
24 | get
25 | {
26 | return defaultInstance;
27 | }
28 | }
29 | }
30 | }
31 |
--------------------------------------------------------------------------------
/csharp/Properties/Settings.settings:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/csharp/object_detection.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 | Debug
7 | AnyCPU
8 | {1934E6A4-D235-4007-A918-96A0E72BDCAF}
9 | Exe
10 | object_detection
11 | object_detection
12 | v4.7.2
13 | 10.0
14 | 512
15 | true
16 | true
17 |
18 |
19 |
20 |
21 | x86
22 | true
23 | full
24 | false
25 | bin\Debug\
26 | DEBUG;TRACE
27 | prompt
28 | 4
29 | true
30 |
31 |
32 | AnyCPU
33 | pdbonly
34 | true
35 | bin\Release\
36 | TRACE
37 | prompt
38 | 4
39 |
40 |
41 |
42 |
43 |
44 |
45 | packages\Microsoft.ML.OnnxRuntime.Managed.1.5.2\lib\netstandard1.1\Microsoft.ML.OnnxRuntime.dll
46 |
47 |
48 | packages\Microsoft.Win32.Primitives.4.3.0\lib\net46\Microsoft.Win32.Primitives.dll
49 | True
50 | True
51 |
52 |
53 |
54 | packages\System.AppContext.4.3.0\lib\net463\System.AppContext.dll
55 | True
56 | True
57 |
58 |
59 | packages\System.Buffers.4.4.0\lib\netstandard2.0\System.Buffers.dll
60 |
61 |
62 |
63 | packages\System.Console.4.3.0\lib\net46\System.Console.dll
64 | True
65 | True
66 |
67 |
68 |
69 | packages\System.Diagnostics.DiagnosticSource.4.3.0\lib\net46\System.Diagnostics.DiagnosticSource.dll
70 |
71 |
72 | packages\System.Diagnostics.Tracing.4.3.0\lib\net462\System.Diagnostics.Tracing.dll
73 | True
74 | True
75 |
76 |
77 | packages\System.Globalization.Calendars.4.3.0\lib\net46\System.Globalization.Calendars.dll
78 | True
79 | True
80 |
81 |
82 | packages\System.IO.4.3.0\lib\net462\System.IO.dll
83 | True
84 | True
85 |
86 |
87 | packages\System.IO.Compression.4.3.0\lib\net46\System.IO.Compression.dll
88 | True
89 | True
90 |
91 |
92 |
93 | packages\System.IO.Compression.ZipFile.4.3.0\lib\net46\System.IO.Compression.ZipFile.dll
94 | True
95 | True
96 |
97 |
98 | packages\System.IO.FileSystem.4.3.0\lib\net46\System.IO.FileSystem.dll
99 | True
100 | True
101 |
102 |
103 | packages\System.IO.FileSystem.Primitives.4.3.0\lib\net46\System.IO.FileSystem.Primitives.dll
104 | True
105 | True
106 |
107 |
108 | packages\System.Linq.4.3.0\lib\net463\System.Linq.dll
109 | True
110 | True
111 |
112 |
113 | packages\System.Linq.Expressions.4.3.0\lib\net463\System.Linq.Expressions.dll
114 | True
115 | True
116 |
117 |
118 | packages\System.Memory.4.5.3\lib\netstandard2.0\System.Memory.dll
119 |
120 |
121 | packages\System.Net.Http.4.3.0\lib\net46\System.Net.Http.dll
122 | True
123 | True
124 |
125 |
126 | packages\System.Net.Sockets.4.3.0\lib\net46\System.Net.Sockets.dll
127 | True
128 | True
129 |
130 |
131 |
132 | packages\System.Numerics.Vectors.4.4.0\lib\net46\System.Numerics.Vectors.dll
133 |
134 |
135 | packages\System.Reflection.4.3.0\lib\net462\System.Reflection.dll
136 | True
137 | True
138 |
139 |
140 | packages\System.Runtime.4.3.0\lib\net462\System.Runtime.dll
141 | True
142 | True
143 |
144 |
145 | packages\System.Runtime.CompilerServices.Unsafe.4.5.2\lib\netstandard2.0\System.Runtime.CompilerServices.Unsafe.dll
146 |
147 |
148 | packages\System.Runtime.Extensions.4.3.0\lib\net462\System.Runtime.Extensions.dll
149 | True
150 | True
151 |
152 |
153 | packages\System.Runtime.InteropServices.4.3.0\lib\net463\System.Runtime.InteropServices.dll
154 | True
155 | True
156 |
157 |
158 | packages\System.Runtime.InteropServices.RuntimeInformation.4.3.0\lib\net45\System.Runtime.InteropServices.RuntimeInformation.dll
159 | True
160 | True
161 |
162 |
163 | packages\System.Security.Cryptography.Algorithms.4.3.0\lib\net463\System.Security.Cryptography.Algorithms.dll
164 | True
165 | True
166 |
167 |
168 | packages\System.Security.Cryptography.Encoding.4.3.0\lib\net46\System.Security.Cryptography.Encoding.dll
169 | True
170 | True
171 |
172 |
173 | packages\System.Security.Cryptography.Primitives.4.3.0\lib\net46\System.Security.Cryptography.Primitives.dll
174 | True
175 | True
176 |
177 |
178 | packages\System.Security.Cryptography.X509Certificates.4.3.0\lib\net461\System.Security.Cryptography.X509Certificates.dll
179 | True
180 | True
181 |
182 |
183 | packages\System.Text.RegularExpressions.4.3.0\lib\net463\System.Text.RegularExpressions.dll
184 | True
185 | True
186 |
187 |
188 |
189 |
190 |
191 |
192 |
193 |
194 |
195 |
196 | packages\System.Xml.ReaderWriter.4.3.0\lib\net46\System.Xml.ReaderWriter.dll
197 | True
198 | True
199 |
200 |
201 |
202 |
203 | Form
204 |
205 |
206 | Form1.cs
207 |
208 |
209 |
210 |
211 |
212 | Form1.cs
213 |
214 |
215 | ResXFileCodeGenerator
216 | Resources.Designer.cs
217 | Designer
218 |
219 |
220 | True
221 | Resources.resx
222 |
223 |
224 |
225 | SettingsSingleFileGenerator
226 | Settings.Designer.cs
227 |
228 |
229 | True
230 | Settings.settings
231 | True
232 |
233 |
234 |
235 |
236 |
237 |
238 |
239 |
240 |
241 | This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.
242 |
243 |
244 |
245 |
246 |
247 |
248 |
--------------------------------------------------------------------------------
/csharp/object_detection.sln:
--------------------------------------------------------------------------------
1 |
2 | Microsoft Visual Studio Solution File, Format Version 12.00
3 | # Visual Studio Version 16
4 | VisualStudioVersion = 16.0.30413.136
5 | MinimumVisualStudioVersion = 10.0.40219.1
6 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "object_detection", "object_detection.csproj", "{1934E6A4-D235-4007-A918-96A0E72BDCAF}"
7 | EndProject
8 | Global
9 | GlobalSection(SolutionConfigurationPlatforms) = preSolution
10 | Debug|Any CPU = Debug|Any CPU
11 | Release|Any CPU = Release|Any CPU
12 | EndGlobalSection
13 | GlobalSection(ProjectConfigurationPlatforms) = postSolution
14 | {1934E6A4-D235-4007-A918-96A0E72BDCAF}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
15 | {1934E6A4-D235-4007-A918-96A0E72BDCAF}.Debug|Any CPU.Build.0 = Debug|Any CPU
16 | {1934E6A4-D235-4007-A918-96A0E72BDCAF}.Release|Any CPU.ActiveCfg = Release|Any CPU
17 | {1934E6A4-D235-4007-A918-96A0E72BDCAF}.Release|Any CPU.Build.0 = Release|Any CPU
18 | EndGlobalSection
19 | GlobalSection(SolutionProperties) = preSolution
20 | HideSolutionNode = FALSE
21 | EndGlobalSection
22 | GlobalSection(ExtensibilityGlobals) = postSolution
23 | SolutionGuid = {F20FE739-D4D4-4D7F-968F-53E66DF508F8}
24 | EndGlobalSection
25 | EndGlobal
26 |
--------------------------------------------------------------------------------
/csharp/packages.config:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
--------------------------------------------------------------------------------
/docs/csharp.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/asiryan/object-detection-tf/84ca341fe6e9094246b8792e796b5241a566cd1c/docs/csharp.jpg
--------------------------------------------------------------------------------
/docs/python.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/asiryan/object-detection-tf/84ca341fe6e9094246b8792e796b5241a566cd1c/docs/python.jpg
--------------------------------------------------------------------------------
/images/airport.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/asiryan/object-detection-tf/84ca341fe6e9094246b8792e796b5241a566cd1c/images/airport.jpg
--------------------------------------------------------------------------------
/images/persons.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/asiryan/object-detection-tf/84ca341fe6e9094246b8792e796b5241a566cd1c/images/persons.jpg
--------------------------------------------------------------------------------
/images/school.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/asiryan/object-detection-tf/84ca341fe6e9094246b8792e796b5241a566cd1c/images/school.jpg
--------------------------------------------------------------------------------
/object_detection_image_onnx.py:
--------------------------------------------------------------------------------
1 | import onnxruntime as rt
2 | import numpy as np
3 | from PIL import Image, ImageDraw, ImageColor, ImageFont
4 | import math
5 | import matplotlib.pyplot as plt
6 | import os
7 |
8 | # params
9 | MODEL = "ssd_mobilenet_v1_coco_2018_01_28/model.onnx"
10 | PROTOTXT = 'coco.prototxt'
11 | IMAGE = 'images/school.jpg'
12 |
13 | # force tf2onnx to cpu
14 | os.environ['CUDA_VISIBLE_DEVICES'] = "-1"
15 |
16 | # inference session
17 | img = Image.open(IMAGE)
18 | img_data = np.array(img.getdata()).reshape(img.size[1], img.size[0], 3)
19 | img_data = np.expand_dims(img_data.astype(np.uint8), axis=0)
20 | sess = rt.InferenceSession(MODEL)
21 | outputs = ["detection_boxes:0", "detection_classes:0", "detection_scores:0", "num_detections:0"]
22 | result = sess.run(outputs, {"image_tensor:0": img_data})
23 | detection_boxes, detection_classes, detection_scores, num_detections = result
24 |
25 | # draw results
26 | def draw_detection(draw, d, c):
27 | width, height = draw.im.size
28 | # the box is relative to the image size so we multiply with height and width to get pixels.
29 | top = d[0] * height
30 | left = d[1] * width
31 | bottom = d[2] * height
32 | right = d[3] * width
33 | top = max(0, np.floor(top + 0.5).astype('int32'))
34 | left = max(0, np.floor(left + 0.5).astype('int32'))
35 | bottom = min(height, np.floor(bottom + 0.5).astype('int32'))
36 | right = min(width, np.floor(right + 0.5).astype('int32'))
37 | label = coco_classes[c.astype('int32') - 1] # shift to zero element
38 | label_size = draw.textsize(label)
39 | text_origin = tuple(np.array([left + 1, top + 1]))
40 | color = ImageColor.getrgb("yellow")
41 | thickness = 0
42 | draw.rectangle([left + thickness, top + thickness, right - thickness, bottom - thickness], outline=color)
43 | draw.text(text_origin, label, fill=color, font=font)
44 |
45 | coco_classes = []
46 |
47 | with open(PROTOTXT) as lines:
48 | for line in lines:
49 | coco_classes.append(line.strip())
50 |
51 | font = ImageFont.truetype("C:\\Windows\\Fonts\\Arial.ttf", 22)
52 |
53 | batch_size = num_detections.shape[0]
54 | draw = ImageDraw.Draw(img)
55 | for batch in range(0, batch_size):
56 | for detection in range(0, int(num_detections[batch])):
57 | c = detection_classes[batch][detection]
58 | d = detection_boxes[batch][detection]
59 | draw_detection(draw, d, c)
60 |
61 | #print(detection_scores)
62 | plt.figure(figsize=(8, 8))
63 | plt.axis('off')
64 | plt.imshow(img)
65 | plt.show()
66 |
--------------------------------------------------------------------------------
/ssd_mobilenet_v1_coco_2018_01_28/frozen.onnx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/asiryan/object-detection-tf/84ca341fe6e9094246b8792e796b5241a566cd1c/ssd_mobilenet_v1_coco_2018_01_28/frozen.onnx
--------------------------------------------------------------------------------
/ssd_mobilenet_v1_coco_2018_01_28/model.onnx:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/asiryan/object-detection-tf/84ca341fe6e9094246b8792e796b5241a566cd1c/ssd_mobilenet_v1_coco_2018_01_28/model.onnx
--------------------------------------------------------------------------------