create video from streamed images c# - c#

How can I build video from stream image (only image without sound) in C#?
Here is some code of my application:
static int ii = 1;
public void drawBitmap(byte[] data)
{
MemoryStream ms = new MemoryStream(data);
try
{
Bitmap b = new Bitmap(ms);
b.Save(#"c:\test\" + (ii++) + ".jpg");
Image i = (Image)b;
pictureBox1.Image = i;
ii++;
}
catch (Exception e)
{
}
}

I used the wrapper mentioned above, like this:
private static void hejHopp()
{
//http://www.codeproject.com/Articles/7388/A-Simple-C-Wrapper-for-the-AviFile-Library
//myReadyNAS device, got files via FTP from my webcam
var jpgFileList = Directory.EnumerateFiles(sourcePath,"*.jpg");
//load the first image
Bitmap bitmap = (Bitmap)Image.FromFile(jpgFileList.First());
//create a new AVI file
AviManager aviManager = new AviManager(sourcePath + "\\tada.avi", false);
//add a new video stream and one frame to the new file
//set IsCompressed = false
VideoStream aviStream = aviManager.AddVideoStream(false, 2, bitmap);
jpgFileList.Skip(1).ToList().ForEach(file =>
{
bitmap = (Bitmap)Bitmap.FromFile(file);
aviStream.AddFrame(bitmap);
bitmap.Dispose();
});
aviManager.Close();
}

You might want to take a look at this thread:
http://social.msdn.microsoft.com/Forums/en-US/csharpgeneral/thread/f23caf50-85a9-4074-8328-176c8bcc393e/
Same question. Some answers.
More is also available here:
http://www.codeproject.com/Articles/7388/A-Simple-C-Wrapper-for-the-AviFile-Library

Related

Drawing an image from svg url in wpf C#

This is the URL with image-https://dev.w3.org/SVG/tools/svgweb/samples/svg-files/acid.svg
What I have tried
Sample 1-
-I am using SharpVectors package
public void DrawImage()
{
Image svgImage = new Image();
WpfDrawingSettings settings = new WpfDrawingSettings();
settings.IncludeRuntime = false;
settings.TextAsGeometry = true;
FileSvgReader converter = new FileSvgReader(settings);
DrawingGroup drawing = converter.Read(new Uri("https://dev.w3.org/SVG/tools/svgweb/samples/svg-files/acid.svg"));
if (drawing != null)
{
svgImage.Source = new DrawingImage(drawing);
}
}
sample 1 works perfectly but it's latency is very high, So I wanted to improve the performance.
Sample 2 - I tried using bitmap to improve performance below is code, but the issue is I need to download the image or store in folder and use as path as string which works fine but my condition is my URLs are coming form JSON file in .SVG format, they are dynamic and I am not using any .XAMl files for UI.
UI built in code behind programmatically.
Is there any other way I can display SVG image in WPF?
public void DrawImage()
{
Image dynamicImage = new Image();
dynamicImage.Width = 300;
dynamicImage.Height = 200;
stcdock.Children.Add(dynamicImage);
WpfDrawingSettings settings = new WpfDrawingSettings();
settings.IncludeRuntime = true;
settings.TextAsGeometry = false;
string svgTestFile = #"\Downloads\acid.svg";
StreamSvgConverter converter = new StreamSvgConverter(settings);
MemoryStream memStream = new MemoryStream();
if (converter.Convert(svgTestFile, memStream))
{
BitmapImage bitmap = new BitmapImage();
bitmap.BeginInit();
bitmap.CacheOption = BitmapCacheOption.OnLoad;
bitmap.StreamSource = memStream;
bitmap.EndInit();
dynamicImage.Source = bitmap;
}
}
.svg are not nativly supported in wpf.
https://www.nuget.org/packages/svg
This package promisses to add this functionality.

About enlarging the captured screenshot size

I am trying to enlarge the size of screenshot without losing quality (as possible), but I can not do this. I am processing this picture in another method and filestream stop working. Actually tesseract can not read because of the screenshot's size so I am trying to enlarge the size of screenshot but I can not change the size of screenshot during capturing.
private void button1_Click(object sender, EventArgs e)
{
System.Threading.Thread.Sleep(4000);
Snapshot().Save("D:\\program_goruntusu.jpg");
string s = FotoAnaliz();
}
private Bitmap Snapshot()
{
Bitmap Screenshot = new Bitmap(20, 20);
Graphics GFX = Graphics.FromImage(Screenshot);
GFX.CopyFromScreen(1243, 349, 0, 0, new Size(20, 20));
return Screenshot;
}
private string FotoAnaliz()
{
FileStream fs = new FileStream("D:\\program_goruntusu.jpg", FileMode.OpenOrCreate);
//string fotopath = #"D:\\program_goruntusu.jpg";
Bitmap images = new Bitmap(fs);
using (var engine = new TesseractEngine(#"./tessdata", "eng"))
{
engine.SetVariable("tessedit_char_whitelist", "0123456789");
// have to load Pix via a bitmap since Pix doesn't support loading a stream.
using (var image = new Bitmap(images))
{
using (var pix = PixConverter.ToPix(image))
{
using (var page = engine.Process(pix))
{
sayı = page.GetText();
MessageBox.Show(sayı);
fs.Close();
}
}
}
}
return sayı;
}

How to override(use) BitmapFrame.Thumbnail property in WPF C#?

Hello! The problem is? that I've got a multipage Tiff file to show, and I use
BitmapFrame.Thumbnail property to show small size thumbnail of every frame(page) of my multipage Tiff file. But< for some reason? the property returns null. Please, give step by step description, of how this should be done?
I've already tried to create my own BitmapSource thumbnail with this method:
public static BitmapImage GetThumbnail(BitmapFrame bitmapFrame)
{
try
{
JpegBitmapEncoder encoder = new JpegBitmapEncoder();
MemoryStream memorystream = new MemoryStream();
BitmapImage tmpImage = new BitmapImage();
encoder.Frames.Add(bitmapFrame);
encoder.Save(memorystream);
tmpImage.BeginInit();
tmpImage.CacheOption = BitmapCacheOption.OnLoad;
tmpImage.StreamSource = new MemoryStream(memorystream.ToArray());
File.WriteAllBytes( $"{Path.GetTempFileName()}.jpg", memorystream.ToArray());
tmpImage.UriSource = new Uri($"{Path.GetTempFileName()}.jpg");
tmpImage.DecodePixelWidth = 80;
tmpImage.DecodePixelHeight = 120;
tmpImage.EndInit();
memorystream.Close();
return tmpImage;
}
catch (Exception ex)
{
return null;
throw ex;
}
}
then I convert the result to BitmapSource and create a list of BitmapFrames using:
List<BitmapFrame> tiffImageList = new List<BitmapFrame>();
tiffImageList.Add(new TiffImage() { index = imageIndex, image = BitmapFrame.Create(frame, (BitmapSource)GetThumbnail(frame))});
In the end I try to get property, but it returns null:
foreach (var tiffImage in tiffImageList)
{
Image image = new Image();
image.Source = tiffImage.image.Thumbnail;
}
I ran into a similar issue, modifying with the SDK PhotoViewerDemo example. Some valid jpg's are shown as white square thumbnails.
I think I found why the question code does not work. Ivan's question provides a correct constructor of BitmapFrame, but the functions have to create a BitmapSource, not a BitmapImage.
C# BitmapFrame.Thumbnail property is null for some images
I got it working with the function provided in that topic, using Ivan's call to the constructor, using the two bitmapsource arguments.
Code in the SDK example I now use is..
private BitmapSource CreateBitmapSource(Uri path)
{
BitmapImage bmpImage = new BitmapImage();
bmpImage.BeginInit();
bmpImage.UriSource = path;
bmpImage.EndInit();
return bmpImage;
}
private BitmapSource CreateThumbnail(Uri path)
{
BitmapImage bmpImage = new BitmapImage();
bmpImage.BeginInit();
bmpImage.UriSource = path;
bmpImage.DecodePixelWidth = 120;
bmpImage.EndInit();
return bmpImage;
}
// it has to be plugged in here,
public Photo(string path)
{
Source = path;
_source = new Uri(path);
// replaced.. Image = BitmapFrame.Create(_source);
// with this:
Image = BitmapFrame.Create(CreateBitmapSource(_source),CreateThumbnail(_source));
Metadata = new ExifMetadata(_source);
}

Merge multiple multi-page tiff images to a single tiff C#

In my scenario I have 3 or more multi-page tiff images which I need to merge into a single tiff image.
Below is the the code I have tried. It merges in to a single tiff image but only with first page of all tiff images.
private static void MergeTiff(string[] sourceFiles)
{
string[] sa = sourceFiles;
//get the codec for tiff files
ImageCodecInfo info = null;
foreach (ImageCodecInfo ice in ImageCodecInfo.GetImageEncoders())
if (ice.MimeType == "image/tiff")
info = ice;
//use the save encoder
Encoder enc = Encoder.SaveFlag;
EncoderParameters ep = new EncoderParameters(1);
ep.Param[0] = new EncoderParameter(enc, (long)EncoderValue.MultiFrame);
Bitmap pages = null;
int frame = 0;
foreach (string s in sa)
{
if (frame == 0)
{
MemoryStream ms = new MemoryStream(File.ReadAllBytes(Path.Combine(Environment.CurrentDirectory, #"C:\Data_Warehouse\SVNRepository\CD.BNS.W5555.LT45555C.D180306.T113850.Z0101\", s)));
pages = (Bitmap)Image.FromStream(ms);
var appDataPath = #"C:\Data_Warehouse\SVNRepository\Tiffiles\";
var filePath = Path.Combine(appDataPath, Path.GetRandomFileName() + ".tif");
//save the first frame
pages.Save(filePath, info, ep);
}
else
{
//save the intermediate frames
ep.Param[0] = new EncoderParameter(enc, (long)EncoderValue.FrameDimensionPage);
try
{
MemoryStream mss = new MemoryStream(File.ReadAllBytes(Path.Combine(Environment.CurrentDirectory, #"C:\Data_Warehouse\SVNRepository\CD.BNS.W5555.LT45555C.D180306.T113850.Z0101\", s)));
Bitmap bm = (Bitmap)Image.FromStream(mss);
pages.SaveAdd(bm, ep);
}
catch (Exception e)
{
//LogError(e, s);
}
}
if (frame == sa.Length - 1)
{
//flush and close.
ep.Param[0] = new EncoderParameter(enc, (long)EncoderValue.Flush);
pages.SaveAdd(ep);
}
frame++;
}
}
I need to join multiple tiff images with all pages from each tiff image. Please advise!
Thanks
EDIT: Updated from below answer
if (frame == 0)
{
MemoryStream ms = new MemoryStream(File.ReadAllBytes(Path.Combine(Environment.CurrentDirectory, #"C:\OMTest\Working\", s)));
pages = (Bitmap)Image.FromStream(ms);
var appDataPath = #"C:\Data_Warehouse\SVNRepository\Tiffiles\";
var filePath = Path.Combine(appDataPath, Path.GetRandomFileName() + ".tif");
//save the first frame
pages.Save(filePath, info, ep);
//Save the second frame if any
int frameCount1 = pages.GetFrameCount(FrameDimension.Page);
if (frameCount1 > 1)
{
for (int i = 1; i < frameCount1; i++)
{
ep.Param[0] = new EncoderParameter(enc, (long)EncoderValue.FrameDimensionPage);
pages.SelectActiveFrame(FrameDimension.Page, i);
pages.SaveAdd(pages, ep);
}
}
}
else
{
//save the intermediate frames
ep.Param[0] = new EncoderParameter(enc, (long)EncoderValue.FrameDimensionPage);
try
{
MemoryStream mss = new MemoryStream(File.ReadAllBytes(Path.Combine(Environment.CurrentDirectory, #"C:\OMTest\Working\", s)));
Bitmap bm = (Bitmap)Image.FromStream(mss);
int frameCount = bm.GetFrameCount(FrameDimension.Page);
for (int i = 0; i < frameCount; i++)
{
bm.SelectActiveFrame(FrameDimension.Page, i);
pages.SaveAdd(bm, ep);
}
}
catch (Exception e)
{
//LogError(e, s);
}
}
You need to select the active frame to ensure you are getting all pages on the TIFF. In your code you need to get the count of frames and loop through these.
The code in your else block might look something like this:
MemoryStream mss = new MemoryStream(File.ReadAllBytes(Path.Combine(Environment.CurrentDirectory, #"C:\Data_Warehouse\SVNRepository\CD.BNS.W5555.LT45555C.D180306.T113850.Z0101\", s)));
Bitmap bm = (Bitmap)Image.FromStream(mss);
int frameCount = bm.GetFrameCount(FrameDimension.Page);
for(int i=0;i<frameCount;i++){
bm.SelectActiveFrame(FrameDimension.Page, i);
pages.SaveAdd(bm, ep);
}
You may have to tweak it as I haven't tested it.
The given code works great to merge single-page TIFF files into a single multi-page TIFF, however, if there are multi-page TIFF files as sources, it will only merge their first page in the resulting TIFF file: the other ones will be discarded.
Since we couldn't find any working samples that could work around this issue, we ended up coding a small C# helper class, which later became a full-fledged multi-platform console application written in .NET Core 2 and C#. We called the project MergeTIFF and we released the whole source code on GitHub under GNU v3 license, so that everyone else can use it as well; we also released the binaries for Windows and Linux (32-bit and 64-bit).
Here's the relevant excerpt of the C# code:
using System;
using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
namespace MergeTiff.NET
{
/// <summary>
/// A small helper class to handle TIFF files
/// </summary>
public static class TiffHelper
{
/// <summary>
/// Merges multiple TIFF files (including multipage TIFFs) into a single multipage TIFF file.
/// </summary>
public static byte[] MergeTiff(params byte[][] tiffFiles)
{
byte[] tiffMerge = null;
using (var msMerge = new MemoryStream())
{
//get the codec for tiff files
ImageCodecInfo ici = null;
foreach (ImageCodecInfo i in ImageCodecInfo.GetImageEncoders())
if (i.MimeType == "image/tiff")
ici = i;
Encoder enc = Encoder.SaveFlag;
EncoderParameters ep = new EncoderParameters(1);
Bitmap pages = null;
int frame = 0;
foreach (var tiffFile in tiffFiles)
{
using (var imageStream = new MemoryStream(tiffFile))
{
using (Image tiffImage = Image.FromStream(imageStream))
{
foreach (Guid guid in tiffImage.FrameDimensionsList)
{
//create the frame dimension
FrameDimension dimension = new FrameDimension(guid);
//Gets the total number of frames in the .tiff file
int noOfPages = tiffImage.GetFrameCount(dimension);
for (int index = 0; index < noOfPages; index++)
{
FrameDimension currentFrame = new FrameDimension(guid);
tiffImage.SelectActiveFrame(currentFrame, index);
using (MemoryStream tempImg = new MemoryStream())
{
tiffImage.Save(tempImg, ImageFormat.Tiff);
{
if (frame == 0)
{
//save the first frame
pages = (Bitmap)Image.FromStream(tempImg);
ep.Param[0] = new EncoderParameter(enc, (long)EncoderValue.MultiFrame);
pages.Save(msMerge, ici, ep);
}
else
{
//save the intermediate frames
ep.Param[0] = new EncoderParameter(enc, (long)EncoderValue.FrameDimensionPage);
pages.SaveAdd((Bitmap)Image.FromStream(tempImg), ep);
}
}
frame++;
}
}
}
}
}
}
if (frame >0)
{
//flush and close.
ep.Param[0] = new EncoderParameter(enc, (long)EncoderValue.Flush);
pages.SaveAdd(ep);
}
msMerge.Position = 0;
tiffMerge = msMerge.ToArray();
}
return tiffMerge;
}
}
}
For additional info and/or to download it, you can take a look at the following resources that we published to better document the whole project:
MergeTIFF on GitHub
Specifications, dependencies and other info

Accessing Picturebox From Stream

How can I access picturebox1 from my ocr.Image = img bit of the code. I have it working if I load it by using
ocr.Image = ImageStream.FromFile("C:/Users/John/Pictures/3.jpg"); // Give the image to the library
but obviously thats not what I am tryng to achive.
Error is:
cannot implicitly convert type system.drawing.image to
apose.ocr.iimagestream
private void timer1_Tick(object sender, EventArgs e)
{
//SendKeys.Send("{PRTSC}");
Image img = Clipboard.GetImage();
pictureBox1.Image = img;
//ocr processing
ocr.Image = img; // Give the image to the library
if (ocr.Process()) // Start processing it
{
label1.Text = "Text: " + ocr.Text;
}
}
Try this:
if(img!=null)
{
var ms = new MemoryStream();
img.Save(ms, ImageFormat.Jpeg); // put here the image format
ms.Position = 0;
ocr.Image = ImageStream.FromStream(ms,ImageStreamFormat.Jpg);
..
..//all your processing stuff
}

Categories

Resources