如何将Youtube视频(Flash播放器?)连接到减速播放?

17

我所知道的唯一一款能够在任何浏览器中减速和加速播放YouTube视频的好软件,而且不需要先下载(因为那样会很麻烦)的是Enounce MySpeed

不幸的是,这个软件不是免费的,我的试用版已经过期了。我在调试它的注册表设置时注意到了一些键:

ProgramsToHook: iexplore.exe;firefox.exe;plugin-container.exe;chrome.exe;safari.exe;opera.exe;maxthon.exe;feeddemon.exe;realplay.exe;flvplayer.exe;flv player.exe;flock.exe;adobe media player.exe
UseFlashAdapter: 1
LLModules: ole32.dll;nspr4.dll;chrome.exe;realplay.exe;objb3201.dll;oleaut32.dll;rpflashplayer.dll
ModulesToIntercept: flash10*;flash9*;npswf32.dll;gcswf32.dll;fldbg10*;flashplayer.3.1.1k.ocx;adobe media player.exe

基于这些注册表键的名称和值,我猜测MySpeed软件钩取了列出模块中的某些函数(但是模块和DLL是否相同?...)并为ProgramsToHook中列出的每个进程执行此操作。这就是我不理解的地方。MySpeed软件的概念是什么?显然它正在钩取某些东西,但我对Windows钩子的复杂性并不太熟悉,因此我来请教您这些专家。我认为,如果我能理解这个钩取过程的工作原理,我就可以使用EasyHook创建自己版本的软件,它是一个非常棒的.NET库,可执行用户模式和内核模式的钩子。

我认为Windows用户模式挂钩大致是这样的。您选择一个DLL中的一个函数,并在您想要的一个进程中拦截该函数(也称为钩子)。如果您想在多个进程中钩取DLL,则只需为每个进程重复该过程。

然后,内核模式挂钩只是选择一个DLL中的一个函数,并在调用它的每个进程中拦截该函数(因此是内核模式)。但是肯定有许多方法可以进行钩取;我不太确定这两种钩子和DLL注入之间的区别。

因此,关键是我想知道MySpeed的工作原理。他们的钩取概念是什么?如果我能知道这一点,那么我就可以在.NET中制作这样的软件!

提前感谢。


2
+1 - 很好的问题;这对于提高可用性(第二语言,听力/视力障碍)以及从音乐视频中学习乐器部分非常有帮助。 - Tim M.
是的。除了Enounce的MySpeed之外,实际上没有其他软件可以减慢或加速YouTube视频播放速度,这真是令人惊讶。 - Jason
4个回答

3
加速或减速视频的关键是让多媒体播放器认为你的计算机比实际上更慢或更快。这可以通过挂接timeGetTime()来实现。
以下是一个非常简单的C#代码来实现它:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using Nektra.Deviare2;


namespace DeviareTest
{
    public partial class Form1 : Form
    {
        private int nSpeed;
        private uint nTime;

        private NktSpyMgr _spyMgr;

        public Form1()
        {
            InitializeComponent();

            _spyMgr = new NktSpyMgr();
            _spyMgr.Initialize();
            _spyMgr.OnFunctionCalled += new DNktSpyMgrEvents_OnFunctionCalledEventHandler(OnFunctionCalled);
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            NktHook hook = _spyMgr.CreateHook("WINMM.dll!timeGetTime", (int)(eNktHookFlags.flgOnlyPostCall));
            hook.Hook(true);

            bool bProcessFound = false;
            NktProcessesEnum enumProcess = _spyMgr.Processes();
            NktProcess tempProcess = enumProcess.First();
            while (tempProcess != null)
            {
                if (tempProcess.Name.Equals("iexplore.exe", StringComparison.InvariantCultureIgnoreCase) && tempProcess.PlatformBits == 32)
                {
                    hook.Attach(tempProcess, true);
                    bProcessFound = true;
                }
                tempProcess = enumProcess.Next();
            } 

            if(!bProcessFound)
            {
                MessageBox.Show("Please run \"iexplore.exe\" before!", "Error");
                Environment.Exit(0);
            }
        }

        private void OnFunctionCalled(NktHook hook, NktProcess process, NktHookCallInfo hookCallInfo)
        {
            nTime++;

            if (nSpeed==-2)
                hookCallInfo.Result().LongVal = hookCallInfo.Result().LongVal - (int)(nTime * 0.2);
            else if(nSpeed==2)
                hookCallInfo.Result().LongVal = hookCallInfo.Result().LongVal + (int)(nTime * 3);
        }

        private void SlowButton_CheckedChanged(object sender, EventArgs e)
        {
            nSpeed = -2;
        }
        private void FastButton_CheckedChanged(object sender, EventArgs e)
        {
            nSpeed = 2;
        }
    }
}

我刚刚发表了一篇文章,其中包含一个使用Deviare hooking引擎实现此功能的代码示例。样例代码仅适用于视频部分(不适用于音频),您可以在这里获得。


我刚从Github编译了代码,但应用程序崩溃了。我找不到Deviare包中的清单文件。也许这就是原因? - Mark
请发送崩溃的详细信息。主要有两种情况:您需要下载最新的Deviare版本,因为它已经更新了,或者代码现在不起作用,因为Flash或YouTube工作方式发生了一些变化。 - sw.
应用程序在启动时崩溃,并显示“Deviare测试已停止工作”的消息。我注意到指南需要一个名为Devicom.x.manifest的文件。我在我认为是最新版本的DeviareV2文件夹中找不到它。 - Mark
我已经成功运行了SpeedTube应用程序,但它并没有对视频速度产生影响。也许Flash播放器已经改变了对timeGetTime的使用方式?只是好奇,你是如何发现Flash播放器使用timeGetTime的呢?是通过试错法吗? - Mark
@Mark 是的,我们认为YouTube/Flash改变了内部行为。解决方案基于我们的直觉。如果将来有时间,我们会尝试对更新版本做同样的处理。 - sw.
嗨sw。即使Flash改变了其内部行为,我想任何媒体播放器,包括Flash,都需要知道何时在特定时间显示特定帧。因此,它必须需要某种参考点,无论是计时器、垂直同步还是我不知道的其他东西。你认为Flash是否只是切换到了不同的时间函数,还是有一种方法可以以固定速率显示帧而不为人所知? - Mark

3
我无法给出准确的解释,因为我不知道API调用或功能,但大致如下: 您的应用程序搜索iexplore.exe,拦截对某些模块的调用。该模块主要是Flash Player。Flash支持慢速播放视频,因此您可以修改来自iexplore.exe(网页上的JavaScript播放按钮)的调用或进行附加调用以设置播放速度。
你需要做的:
- 使用这个工具检查实际发生的情况:http://www.nektra.com/products/deviare-api-hook-windows/ - 学习如何要求Flash Player减慢视频的速度(可能在Flash API文档中)。一个简单的方法是使用Deviare API挂钩工具查看MySpeed实际上在做什么。 - 编写一个复制此过程的程序。它涉及拦截从一个句柄(iexplore.exe)发送到另一个句柄(flash.dll)的消息。这不能在外部完成,必须在内部完成,因此这可能会有所帮助:http://www.codeproject.com/KB/threads/winspy.aspx

关于钩子: http://msdn.microsoft.com/zh-cn/library/ms644960.aspx

我认为在C#中做这个的人不多,所以它可能会带来一些挑战。如果你有一个博客或者其他分享经验的地方,我会很感兴趣了解进展(障碍)。 :)

编辑:Deviare API Hook软件不仅可以监视调用,还可以让您拦截它们。因此,它是满足您需求的一站式解决方案。 :)
编辑2:相关问题:如何拦截发送到窗口的消息?


感谢Deviare,也许它是EasyHook的一个有趣替代品。第二个链接对于进入新的学习领域非常有用。真的很感谢你在回答这个老问题方面的努力,所以我将把它标记为答案。 - Jason

2

现在Youtube已经拥有一个带有播放速度控制的html5播放器。

你只需要在这里启用html5 http://www.youtube.com/html5。不过,目前仅有部分视频支持html5播放器。

希望这能帮到你。


0
加快或减慢视频的关键是让多媒体播放器相信你的计算机比实际更慢或更快。
操纵系统时间是非常危险和愚蠢的事情 - 不仅会破坏用户模式线程片段,从而对系统性能产生严重影响,而且还会破坏许多日志记录功能甚至控制KM驱动程序的用户模式反射器... 这可能会导致系统崩溃并造成物理伤害!因为现代硬件可以编程,只要给出正确(当然是专有的)函数调用集合等。我强烈建议不要复制这个行为,即使一些AV应用程序也会拦截它,因为它具有危险性。
但你有点幸运:内核使用自己的时间与硬件同步,因此Windows本身可以保持稳定一段有限的时间。
我认为你应该返回草稿板,操纵操作系统的基本结构肯定不是实现目标的正确方式。

1
他提到了Enounce MySpeed,他们确实做到了,所以在那个问题的背景下这是一个合适的答案。你会惊讶于在Windows上运行的软件为完成某些任务而执行的很多“愚蠢”的事情。它们甚至被称为黑客技术! - sw.
无法进行操作,需要账户和大约999999999999个互联网点数。 - name
这根本没有任何意义。 - name

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接