簡體   English   中英

如何在Tapiex ActiveX v3.6中每行多路通話?

[英]how can i get multi calls per line in tapiex activex v3.6?

我用tapiex activex v3.6編寫了一個IVR程序,我希望每行多路通話,但是在我的程序中,當程序正在通話時,我想同時調用它,很忙! 我該怎么辦? 我應該保持已接通的呼叫嗎? 如果是,當我必須這樣做時? 當程序正在調用並且有人嘗試同時調用它時,是否會觸發事件? 如果是,哪個事件? 我的程序應該是多線程的嗎? 我試圖使其成為多線程,但發生了此錯誤!

“不能使用已與其基礎RCW分開的COM對象。”

StartIvr();
//UiGlobal.ThreadManager.StartThread(o => StartIvr());

這是我的startIvr方法

private void StartIvr()
        {
            UI.Class.IVR.EventHandler eventHandler = new Class.IVR.EventHandler();
            eventHandler.InitPhone();
            eventHandler.OpenLine(null);
            UiGlobal.eventHandler = eventHandler;
        }

這是我的事件處理程序類

class EventHandler
{
    public List<string> linesName { get; set; }
    public AxTAPIEXLib.AxTAPIExCtl Tapiex_com { get; set; }
    public bool IsOutputCall = false;
    CallHandler callHandler;


    public EventHandler()
    {
        linesName = new List<string>();
        Tapiex_com = new AxTAPIEXLib.AxTAPIExCtl();

    }

    public EventHandler(AxTAPIEXLib.AxTAPIExCtl Tapiex_com)
    {
        linesName = new List<string>();
        this.Tapiex_com = Tapiex_com;
    }

    public ITAPILine Find_line(string LineName)
    {
        ITAPILine line = null;
        for (int i = 0; i < Tapiex_com.Lines.Count; i++)
            if (Tapiex_com.Lines.Item(i).Name == LineName)
            {
                line = Tapiex_com.Lines.Item(i);
                break;
            }
        return line;

    }
    protected void Dispose(bool disposing)
    {
        if (disposing && (Tapiex_com != null))
        {
            Tapiex_com.Dispose();
        }
    }
    public bool InitPhone()
    {
        Tapiex_com.CreateControl();
        Tapiex_com.OnRing += new AxTAPIEXLib._ITAPIExEvents_OnRingEventHandler(this.Tapiex_com_OnRing);
        Tapiex_com.OnDTMF += new AxTAPIEXLib._ITAPIExEvents_OnDTMFEventHandler(this.Tapiex_com_OnDTMF);
        Tapiex_com.OnConnected += new AxTAPIEXLib._ITAPIExEvents_OnConnectedEventHandler(this.Tapiex_com_OnConnected);
        Tapiex_com.OnDisConnected += new AxTAPIEXLib._ITAPIExEvents_OnDisConnectedEventHandler(this.Tapiex_com_OnDisConnected);
        Tapiex_com.OnCallerID += new AxTAPIEXLib._ITAPIExEvents_OnCallerIDEventHandler(this.Tapiex_com_OnCallerID);
        Tapiex_com.OnNewCall += new AxTAPIEXLib._ITAPIExEvents_OnNewCallEventHandler(this.Tapiex_com_OnNewCall);
        bool init = Tapiex_com.initialize();

        foreach (ITAPILine tmpline in Tapiex_com.Lines)
            if ((tmpline.Caps.Media_Modes & LINEMEDIAMODE.MEDIAMODE_INTERACTIVEVOICE) > 0 ||
                (tmpline.Caps.Media_Modes & LINEMEDIAMODE.MEDIAMODE_AUTOMATEDVOICE) > 0)
                linesName.Add(tmpline.Name);
        return init;
    }

    public bool OpenLine(string lineName)
    {
        if (lineName == null)
        {
            foreach (string item in linesName)
            {
                var line = Find_line(item);
                if (!line.Opened)
                    line.Open();
            }
            return true;
        }
        else
        {
            var line = Find_line(lineName);
            if (line != null)
            {
                if (!line.Opened)
                    line.Open();
                return true;
            }
            else return false;
        }

    }
    private void Tapiex_com_OnDTMF(object sender, _ITAPIExEvents_OnDTMFEvent e)
    {
        if (!IsOutputCall)
        {
            isInDTMFMethod = true;
            callHandler.DTMF(e);
            isInDTMFMethod = false;
        }
    }
    private void Tapiex_com_OnNewCall(object sender, _ITAPIExEvents_OnNewCallEvent e)
    {
        callHandler = new CallHandler();
    }

    private void Tapiex_com_OnRing(object sender, AxTAPIEXLib._ITAPIExEvents_OnRingEvent e)
    {
        if (e.ringCount > 1) e.m_Call.Answer();
    }

    private void Tapiex_com_OnConnected(object sender, AxTAPIEXLib._ITAPIExEvents_OnConnectedEvent e)
    {
        callHandler.Connected(e, IsOutputCall);

    }

    private void Tapiex_com_OnDisConnected(object sender, AxTAPIEXLib._ITAPIExEvents_OnDisConnectedEvent e)
    {
        callHandler.HangUp(e.m_Call);
        IsOutputCall = false;
    }

    private void Tapiex_com_OnCallerID(object sender, AxTAPIEXLib._ITAPIExEvents_OnCallerIDEvent e)
    {
        callHandler.GetCallerID(e);
    }

好的,一個帖子中有很多問題。 如果這沒有一個“實用”的答案,我深表歉意,但是我將需要幾頁內容來介紹您的所有內容。 因此,我將在此處進行一些一般性的觀察,希望它可以幫助您縮小范圍。

1)設備上的多行不是“正常”或“平均”行為,這也不是TAPI可以決定的事情,這完全取決於PBX系統。 大多數只允許在一個分機上撥打電話,一些2和一些例外將允許使用特殊配置設置進行更多呼叫。 TAPI在大多數情況下都可以理解為一種設備,它代表一種物理電話設備。 IVR通常使用的是“中繼線”,但是許多PBX不會通過TAPI發布/公開這些線。

2)ActiveX和COM在多線程環境中需要以不同的方式處理:不同的啟動和停止功能。 您可能想先尋找有關多線程COM編程的教程或書籍。

3)TAPI的主要重點是監視和控制擴展,它實際上並不適合支持IVR。 我並不是說這是不可能的,但這絕對是“艱難的道路”。 在呼叫中心環境中,TAPI通常用於在離開IVR后監視呼叫,而不是IVR本身。 您可能需要考慮在SIP,H323或中間件堆棧上構建IVR。

4)如果您確定要執行TAPI,建議不要使用TAPI 3。 TAPI 3是將TAPI引入現代世界(1999年)的嘗試,並沒有采取一切措施,因此存在很多遺漏之處。 到目前為止,所使用的技術本身已過時或已過時。 如果您認真構建與商業IVR系統一樣復雜的內容,則不妨使用基於TAPI 2的系統,以獲得更完整和穩定的界面(如果您不熟悉本機,則可以使用一些.NET包裝器。 C / C ++編碼)。 這是反直觀的,但在這種情況下2比3更好更好。 尤其是因為您需要使用諸如音頻處理(很少有PBX支持!)之類的更多“特殊”部件來制作IVR。

首先,語音調制解調器是最糟糕的電話設備。 您將永遠無法以所需的方式運行它。 是的,您可以使用連接到模擬線路的“掛機閃光”來使用呼叫等待或三方呼叫,但是您無法控制或報告呼叫。 您將不知道它是否有效以及您真正打過什么電話。 請參見: http : //www.exceletel.com/products/TeleTools/Help/Working_With_Modems.htm 解決方案:獲得用於模擬或更好的VoIP提供商的Way2Call Hi-Phone,並使用SIP Communications Server軟件將SIP中繼線連接到TAPI(安裝2分鍾)。 最后,您可以安裝“免費” PBX(例如3CX或Asterisk)並將其連接到模擬線路或SIP中繼,並在您的計算機上安裝PBX的TSP來控制它。

第一個答案充滿了很多錯誤信息(抱歉,Kris)。 首先,TAPI並非旨在“代表物理電話設備”。 TAPI可以控制“線路設備”,“電話設備”,“終端設備”以及對wave,傳真和其他設備的訪問。 它最常用於控制“行”。 它完全控制設備制造商提供的任何功能。 TAPI當然可以支持多線IVR。 這是英特爾和微軟設計其工作的一部分。 上面的項目3完全不正確。 這是僅使用幾行代碼和TAPI控件的四行IVR程序的示例: http : //www.exceletel.com/products/TeleTools/SamplePrograms/etIVR4Line/Index.htm 您將需要一台可以暴露多條線的設備,以便您一次測試多條線。

如果您查看該代碼,則可以將其翻譯為使用TAPI控件,因為它們從TeleTools控件復制了許多功能。 通常,您必須通過所謂的“第三方” TSP通過設備的TSP暴露多條線路,而不僅僅是“第一方” TSP(否則,您將只能控制每台計算機上的一條線路(但對於每條線路,例如轉接和會議,可能會超過一個呼叫)。

例如,一個Dialogic 4端口卡將為您提供4條模擬線路。 一張T1卡可以讓您訪問24。PBX可以通過其TSP(電話服務提供商驅動程序軟件)向您公開線路,也可以通過SIP中繼向您提供上述公司的SIP通信服務器軟件,以進行訪問。連接到它。 使用SIP DOES可以在電話的更多方面進行建模,但是對於硬件有限的TAPI支持或SIP安裝更加簡單或消除PBX許可費用(某些功能額外收費)的人們來說,這是一個選擇。

例如,安裝了呼叫管理器的Cisco PBX可以向TAPI應用程序公開多條線路。 Avaya及其IP Office軟件也是如此。 您不需要線程化任何東西。 您只需要多個控件。 每個控件都會初始化一條線(如IVR 4 Line示例中所示)。 如果您使用了TeleScope或Julmar Phone之類的實用程序,或者甚至是上面的IVR程序的EXE版本,則在下拉列表中會看到系統上找到的所有設備。 因此,如果看到“ Analog Line1”和“ Analog Line2”,那么您將創建2個線路控件,並將每個控件指向一個不同的線路設備。 然后,您可以為每行Line1_OnConnected,Line2_Onconnected設置多個事件處理程序,或者更有效地創建自己的“ OnConnected”事件處理程序並將所有控件指向該事件處理程序,並使用控件或事件處理程序中的sender / object屬性,以分析在哪一行觸發了事件處理程序的控件。 同樣,該IVR示例頁面上有一些開發環境的示例。

您可以使用上面提到的實用程序之一來查詢設備報告的“設備功能”。 它會告訴您每條線路可以處理的呼叫數量,以及它支持的TAPI功能,例如保持呼叫,支持盲轉,受監督的轉接,會議等。如果每條線路呼叫不超過一個,那么您顯然無法撥打其他電話。 每條線路有2個呼叫,您可以將第一個呼叫置於保留狀態(參考其呼叫句柄),然后撥打另一個呼叫,或者設置轉接或會議(最少需要3個呼叫)。 無論如何,除非您參加會議,否則您最多只能有幾個通話,並且一次只能管理一個通話。 每行使用一個控件,您可以有多個彼此完全獨立的調用。 希望能使您更進一步!

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM