public EditGlyphForm( Glyph glyph, ReadOnlyCollection<string> existingNames ) { InitializeComponent( ); this.glyph = glyph; if ( glyph.UserData == null ) glyph.UserData = new GlyphVisualizationData( Color.Red ); visualizationData = (GlyphVisualizationData) glyph.UserData; forbiddenNames = existingNames; // show information about the glyph glyphEditor.GlyphData = (byte[,]) glyph.Data.Clone( ); nameBox.Text = glyph.Name; colorButton.BackColor = visualizationData.Color; UpdateGlyphIcon( ); }
// Load information about databases and glyphs from XML reader public void Load( XmlTextReader xmlIn ) { // read to the first node xmlIn.Read( ); int startingDept = xmlIn.Depth; while ( ( xmlIn.Name == databaseTag ) && ( xmlIn.NodeType == XmlNodeType.Element ) && ( xmlIn.Depth >= startingDept ) ) { string name = xmlIn.GetAttribute( nameAttr ); int size = int.Parse( xmlIn.GetAttribute( sizeAttr ) ); int count = int.Parse( xmlIn.GetAttribute( countAttr ) ); // create new database and add it to collection GlyphDatabase db = new GlyphDatabase( size ); AddGlyphDatabase( name, db ); if ( count > 0 ) { // read all glyphs for ( int i = 0; i < count; i++ ) { // read to the next glyph node xmlIn.Read( ); string glyphName = xmlIn.GetAttribute( nameAttr ); string glyphStrData = xmlIn.GetAttribute( dataAttr ); // create new glyph and add it database Glyph glyph = new Glyph( glyphName, GlyphDataFromString( glyphStrData, size ) ); db.Add( glyph ); // read visualization params GlyphVisualizationData visualization = new GlyphVisualizationData( Color.Red ); visualization.ImageName = xmlIn.GetAttribute( iconAttr ); visualization.ModelName = xmlIn.GetAttribute( modelAttr ); string colorStr = xmlIn.GetAttribute( colorAttr ); if ( colorStr != null ) { string[] rgbStr = colorStr.Split( ',' ); visualization.Color = Color.FromArgb( int.Parse( rgbStr[0] ), int.Parse( rgbStr[1] ), int.Parse( rgbStr[2] ) ); } glyph.UserData = visualization; } // read to the end tag xmlIn.Read( ); } // read to the next node xmlIn.Read( ); } }
// Add new glyph to the active collection private void newGlyphToolStripMenuItem_Click( object sender, EventArgs e ) { if ( activeGlyphDatabase != null ) { // create new glyph ... Glyph glyph = new Glyph( string.Empty, activeGlyphDatabase.Size ); glyphNameInEditor = string.Empty; // ... and pass it the glyph editting form EditGlyphForm glyphForm = new EditGlyphForm( glyph, activeGlyphDatabase.GetGlyphNames( ) ); glyphForm.Text = "New Glyph"; // set glyph data checking handler glyphForm.SetGlyphDataCheckingHandeler( new GlyphDataCheckingHandeler( CheckGlyphData ) ); if ( glyphForm.ShowDialog( ) == DialogResult.OK ) { try { lock ( sync ) { // add glyph to active database activeGlyphDatabase.Add( glyph ); } // create an icon for it glyphsImageList.Images.Add( glyph.Name, CreateGlyphIcon( glyph ) ); // add it to list view ListViewItem lvi = glyphList.Items.Add( glyph.Name ); lvi.ImageKey = glyph.Name; } catch { ShowErrorBox( string.Format( "A glyph with the name '{0}' already exists in the database.", glyph.Name ) ); } } } }
private Bitmap CreateGlyphImage( Glyph glyph, int width ) { Bitmap bitmap = new Bitmap( width, width, System.Drawing.Imaging.PixelFormat.Format32bppArgb ); int cellSize = width / glyph.Size; int glyphSize = glyph.Size; for ( int i = 0; i < width; i++ ) { int yCell = i / cellSize; for ( int j = 0; j < width; j++ ) { int xCell = j / cellSize; if ( ( yCell >= glyphSize ) || ( xCell >= glyphSize ) ) { // set pixel to transparent if it outside of the glyph bitmap.SetPixel( j, i, Color.Transparent ); } else { // set pixel to black or white depending on glyph value bitmap.SetPixel( j, i, ( glyph.Data[yCell, xCell] == 0 ) ? Color.Black : Color.White ); } } } return bitmap; }
// Create icon for a glyph private Bitmap CreateGlyphIcon( Glyph glyph ) { return CreateGlyphImage( glyph, 32 ); }
/// <summary> /// Clone the glyph. /// </summary> /// /// <returns>Returns clone of the glyph.</returns> /// /// <remarks><para><note>It is user's responsibility to clone <see cref="UserData"/> property if it is /// set to reference type object.</note></para></remarks> /// public object Clone( ) { Glyph clone = new Glyph( name, (byte[,]) data.Clone( ) ); clone.userData = userData; return clone; }
/// <summary> /// Refresh the list displaying available databases of glyphss /// </summary> private void LoadGlyphDatabases5() { const string dbName = "ExampleSize5"; const int glyphSize = 5; // Create glyph. string glyphName1 = "Test1"; byte[,] glyphData1 = new byte[glyphSize, glyphSize] { {0, 0, 0, 0, 0}, {0, 0, 1, 0, 0}, {0, 1, 1, 1, 0}, {0, 1, 0, 0, 0}, {0, 0, 0, 0, 0} }; Glyph testGlyph1 = new Glyph(glyphName1, glyphData1); testGlyph1.UserData = new GlyphVisualizationData(Color.Purple); // Create glyph. string glyphName2 = "Test2"; byte[,] glyphData2 = new byte[glyphSize, glyphSize] { {0, 0, 0, 0, 0}, {0, 1, 0, 1, 0}, {0, 0, 1, 0, 0}, {0, 1, 0, 0, 0}, {0, 0, 0, 0, 0} }; Glyph testGlyph2 = new Glyph(glyphName2, glyphData2); testGlyph2.UserData = new GlyphVisualizationData(Color.Blue); // Create glyph. string glyphName3 = "Test3"; byte[,] glyphData3 = new byte[glyphSize, glyphSize] { {0, 0, 0, 0, 0}, {0, 1, 0, 1, 0}, {0, 0, 1, 0, 0}, {0, 0, 1, 1, 0}, {0, 0, 0, 0, 0} }; Glyph testGlyph3 = new Glyph(glyphName3, glyphData3); testGlyph3.UserData = new GlyphVisualizationData(Color.Green); // Create database. GlyphDatabase lGlyphDatabase = new GlyphDatabase(glyphSize); // Add glyph to database. lGlyphDatabase.Add(testGlyph1); lGlyphDatabase.Add(testGlyph2); lGlyphDatabase.Add(testGlyph3); // Add database. this.glyphDatabases.AddGlyphDatabase(dbName, lGlyphDatabase); this.recognizer = new GlyphRecognizer(glyphSize); // set the database to image processor ... this.recognizer.GlyphDatabase = this.glyphDatabases[dbName]; ; }
/// <summary> /// Refresh the list displaying available databases of glyphss /// </summary> private void LoadGlyphDatabases12() { const int glyphSize = 12; // Create glyph. string glyphName4 = "Test4"; byte[,] glyphData4 = new byte[glyphSize, glyphSize] { {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, {0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0}, {0, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0}, {0, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 0}, {0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0}, {0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0}, {0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0}, {0, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0}, {0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0}, {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} }; Glyph testGlyph4 = new Glyph(glyphName4, glyphData4); testGlyph4.UserData = new GlyphVisualizationData(Color.Purple); // Create database. const string dbName = "ExampleSize12"; // Create database. GlyphDatabase lGlyphDatabase = new GlyphDatabase(glyphSize); // Add glyph to database. lGlyphDatabase.Add(testGlyph4); // Add database. this.glyphDatabases.AddGlyphDatabase(dbName, lGlyphDatabase); this.recognizer = new GlyphRecognizer(glyphSize); // set the database to image processor ... this.recognizer.GlyphDatabase = this.glyphDatabases[dbName]; }
/// <summary> /// Create glyph data. /// This method is example. /// </summary> private void CreateGlyph() { // Glyph name. string glyphName = "Test1"; // Glyph size. const int glyphSize = 5; // Glyph data. byte[,] glyphData = new byte[glyphSize, glyphSize] { {0, 0, 0, 0, 0}, {0, 0, 1, 0, 0}, {0, 1, 1, 1, 0}, {0, 1, 0, 0, 0}, {0, 0, 0, 0, 0} }; // Create glyph. Glyph testGlyph = new Glyph(glyphName, glyphData); // Glyph user data. testGlyph.UserData = new GlyphVisualizationData(Color.Blue); // Generate image from the glyph. Bitmap image = testGlyph.CreateGlyphImage(500); string fileName = String.Format("Glyph_{0}_{1}x{1}.PNG", glyphName, glyphSize); // Save it to file. image.Save(fileName); }
// Get ID of the specified glyph // Note (todo?): glyph tracking needs to be improved since current implementation // is not reliable enough for the case when several glyphs of the same type are // found and those do not move smoothely. private int GetGlyphID(ExtractedGlyphData glyph) { int glyphID = -1; // get CoG of the provided glyph Point glyphCog = PointsCloud.GetCenterOfGravity(glyph.Quadrilateral); // distance to the closest simlar glyph kept in history float minDistance = float.MaxValue; // name of the passed specifed glyph string glyphName = (glyph.RecognizedGlyph != null) ? glyph.RecognizedGlyph.Name : string.Empty; // check all currently tracked glyphs foreach (TrackedGlyph trackedGlyph in trackedGlyphs.Values) { if (trackedGlyph.Age == 0) { // skip glyph whichs were already taken or just added continue; } if ( // recognized case - compare names ((trackedGlyph.Glyph.RecognizedGlyph != null) && (trackedGlyph.Glyph.RecognizedGlyph.Name == glyphName)) || // unrecognized case - compare raw data (Glyph.CheckForMatching(glyph.RawData, trackedGlyph.Glyph.RawData) != -1)) { float distance = glyphCog.DistanceTo(trackedGlyph.Position); if (distance < minDistance) { // get ID of the closest glyph with the same name minDistance = distance; glyphID = trackedGlyph.ID; } } } // if the glyph is further away than the maximum specified limit, // then it is no way can be treated as smooth motion, so reset ID // (TODO: should probably depend on glyph size ...) if ((glyphID != -1) && (minDistance > MaxAllowedDistance)) { glyphID = -1; } // if glyph was not found within tracked glyphs, then add new // glyph to tracker if (glyphID == -1) { glyphID = counter++; trackedGlyphs.Add(glyphID, new TrackedGlyph(glyphID, (ExtractedGlyphData)glyph.Clone( ), glyphCog)); } else { TrackedGlyph trackedGlyph = trackedGlyphs[glyphID]; try { if ((glyph.RecognizedGlyph != null) && (!IsCoordinatesDifferenceSignificant(glyph.RecognizedQuadrilateral, trackedGlyphs[glyphID].Glyph.RecognizedQuadrilateral))) { // correct coordinates of recognized glyphs to eliminate small noisy shaking glyph.RecognizedQuadrilateral = trackedGlyph.Glyph.RecognizedQuadrilateral; glyphCog = trackedGlyph.Position; } else { // update glyph with the latest CoG and recognized info trackedGlyph.Position = glyphCog; trackedGlyph.Glyph = (ExtractedGlyphData)glyph.Clone(); } } catch (Exception) { } // reset age of the tracked glyph trackedGlyph.Age = 0; // add glyph's position to history trackedGlyph.AddMotionHistory(glyphCog); } return(glyphID); }
private void initGlyphs() { database = new GlyphDatabase(5); Glyph glyph1 = new Glyph("1 ", new byte[,] { {0, 0, 0, 0, 0}, {0, 0, 1, 1, 0}, {0, 1, 0, 1, 0}, {0, 0, 1, 0, 0}, {0, 0, 0, 0, 0} }); Glyph glyph2 = new Glyph("2 ", new byte[,] { {0, 0, 0, 0, 0}, {0, 1, 0, 1, 0}, {0, 1, 1, 1, 0}, {0, 0, 1, 0, 0}, {0, 0, 0, 0, 0} }); database.Add(glyph1); database.Add(glyph2); recogniser = new GlyphRecognizer(database); }