Logo Search packages:      
Sourcecode: kazehakase version File versions

kz-mozwrapper.cpp

// -*- Mode: C++; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*-
//
//  Copyright (C) 2003 Takuro Ashie
//
//  This program is free software; you can redistribute it and/or modify
//  it under the terms of the GNU General Public License as published by
//  the Free Software Foundation; either version 2, or (at your option)
//  any later version.
//
//  This program is distributed in the hope that it will be useful,
//  but WITHOUT ANY WARRANTY; without even the implied warranty of
//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
//  GNU General Public License for more details.
//
//  You should have received a copy of the GNU General Public License
//  along with this program; if not, write to the Free Software
//  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
//

// Some codes are taken from Epiphany 0.8.2
// Copyright (C) 2000-2003 Marco Pesenti Gritti

// samples of nsISelection are:
//   content/base/src/nsDocumentViewer.cpp
//   layout/base/src/nsCaret.cpp


#include <kz-mozwrapper.h>
#include <gtkmozembed_internal.h>

#include <stdlib.h>
#include <nsIInterfaceRequestorUtils.h>
#include <nsILocalFile.h>
#include <nsIDocShell.h>
#include <nsIDocShellTreeItem.h>
#include <nsIDocShellTreeOwner.h>
#include <nsIContentViewer.h>
#include <nsIDOMHTMLDocument.h>
#include <nsIDOMHTMLElement.h>
#include <nsIDOMHTMLImageElement.h>
#include <nsIDOMNSHTMLElement.h>  
#include <nsIDOMDocumentRange.h>
#include <nsIDOMNamedNodeMap.h>
#include <nsIDOMText.h>
#include <nsIDOMNodeList.h>
#include <nsIDOMNode.h>
#include <nsIClipboardCommands.h>
#define MOZILLA_STRICT_API
#include <nsEmbedString.h>
#undef MOZILLA_STRICT_API
#include <nsIDOMElement.h>
#include <nsIDOMDocumentType.h>
#include <nsIURI.h>
#include <nsIWebBrowserFocus.h>
#include <nsIWebPageDescriptor.h>
#include <nsIMarkupDocumentViewer.h>
#include <nsIDOMWindowInternal.h>
#include <nsIDOMWindowCollection.h>
#include <nsIDocShellHistory.h>
#include <nsIDocShellTreeNode.h>
#include <nsIScriptGlobalObject.h>
#include <nsISHistoryInternal.h>
#include <nsIHistoryEntry.h>
#include <nsICacheService.h>
#include <nsICacheSession.h>
#include <nsNetCID.h>
#include <nsIServiceManager.h>
#include <nsIOutputStream.h>
#include <nsIWebBrowserPrint.h>
#include <nsIPrintSettingsService.h>
#include <nsIPrintSettings.h>
#include <nsISupportsPrimitives.h>
#include <nsIDOM3Document.h>
#include <nsIDocCharset.h>
#include "kz-mozprogresslistener.h"
#include "kz-mozutils.h"
#include "utils.h"
#include "MozillaPrivate.h"

#ifdef HAVE_CONFIG_H
#     include "config.h"
#endif /* HAVE_CONFIG_H */

KzMozWrapper::KzMozWrapper () :
      mWebBrowser (nsnull),
      mEventTarget (nsnull),
      mKzMozEmbed (nsnull),
      mKzMozEventListener (nsnull),
      mKzMozSelectionListener (nsnull),
      mSelectionWasCollapsed (PR_TRUE)
{
}


KzMozWrapper::~KzMozWrapper ()
{
}


nsresult
KzMozWrapper::Init (KzMozEmbed *kzembed)
{
      nsresult rv;
      
      mKzMozEmbed = kzembed;
      gtk_moz_embed_get_nsIWebBrowser(GTK_MOZ_EMBED(mKzMozEmbed),
                              getter_AddRefs(mWebBrowser));
      if (!mWebBrowser) return NS_ERROR_FAILURE;

      mWebBrowser->GetContentDOMWindow (getter_AddRefs (mDOMWindow));

      /* this codes was taken from Galeon-1.3.17 */
      /* This will instantiate an about:blank doc if necessary, but don't
       * initialize for mozilla XUL dialogs, it breaks them */
      /* 
       * 2004-09-19: removed the following codes 
       *  because of inactivity of the gestures.
       */ 
/*
      if (!(gtk_moz_embed_get_chrome_mask(GTK_MOZ_EMBED(kzembed)) &
          GTK_MOZ_EMBED_FLAG_OPENASCHROME))
      {
            nsCOMPtr<nsIDOMDocument> domDocument;
            rv = mDOMWindow->GetDocument (getter_AddRefs(domDocument));
            if (NS_FAILED(rv)) return NS_ERROR_FAILURE;
      }
*/

      mKzMozEventListener = new KzMozEventListener();
      rv = mKzMozEventListener->Init(kzembed);
      if (NS_FAILED (rv)) return NS_ERROR_FAILURE;
      GetListener();
      AttachListeners();
#if 0
      mKzMozSelectionListener = new KzMozSelectionListener;
      mKzMozSelectionListener->Init(kzembed);

      mKzMozHistoryListener = new KzMozHistoryListener();
      mKzMozHistoryListener->Init(kzembed);
      nsCOMPtr<nsIDocShell> DocShell;
      rv = GetDocShell (getter_AddRefs(DocShell));
      if (NS_FAILED(rv) || !DocShell) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIWebNavigation> ContentNav = do_QueryInterface (DocShell,
                                                   &rv);
      if (!ContentNav) return NS_ERROR_FAILURE;

      nsCOMPtr<nsISHistory> SessionHistory;
      rv = ContentNav->GetSessionHistory(getter_AddRefs (SessionHistory));
      if (!SessionHistory) return NS_ERROR_FAILURE;
      rv = SessionHistory->AddSHistoryListener(mKzMozHistoryListener);

      //nsCOMPtr<nsIWeakReference> listener(do_GetWeakReference(NS_STATIC_CAST(nsISHistoryListener*, mKzMozHistoryListener)));
      //rv = mWebBrowser->AddWebBrowserListener(listener, NS_GET_IID(nsISHistoryListener));

      if (NS_FAILED (rv)) g_warning("failed to add a history listener");
#endif
      return NS_OK;
}


nsresult
KzMozWrapper::GetListener (void)
{
      if (mEventTarget) return NS_ERROR_FAILURE;
      
      nsCOMPtr<nsIDOMWindow> domWindowExternal;
      mWebBrowser->GetContentDOMWindow(getter_AddRefs(domWindowExternal));
  
      nsCOMPtr<nsIDOMWindow2> domWindow;
        domWindow = do_QueryInterface(domWindowExternal);
      if (!domWindow) return NS_ERROR_FAILURE;

      domWindow->GetWindowRoot(getter_AddRefs(mEventTarget));

      if (!mEventTarget) return NS_ERROR_FAILURE;

      return NS_OK;
}


nsresult
KzMozWrapper::AttachListeners(void)
{
      if (!mEventTarget) return NS_ERROR_FAILURE;

      const PRUnichar domLiteral[] = { 'D', 'O', 'M', 'L', 'i', 'n', 'k',
                               'A', 'd', 'd', 'e', 'd', '\0' };
      return mEventTarget->AddEventListener(nsEmbedString(domLiteral),
                                    mKzMozEventListener, PR_FALSE);
}


nsresult
KzMozWrapper::DetachListeners(void)
{
      if (!mEventTarget) return NS_ERROR_FAILURE;
      
      const PRUnichar domLiteral[] = { 'D', 'O', 'M', 'L', 'i', 'n', 'k',
                               'A', 'd', 'd', 'e', 'd', '\0' };
      return mEventTarget->RemoveEventListener(nsEmbedString(domLiteral),
                                       mKzMozEventListener, PR_FALSE);
}


void
KzMozWrapper::Destroy (void)
{
      DetachListeners ();
      mKzMozEmbed = nsnull;
      mEventTarget = nsnull;
      mWebBrowser = nsnull;
}


//
// Our own methods
//

nsresult
KzMozWrapper::GetDocShell (nsIDocShell **aDocShell)
{
        if (!mWebBrowser) return NS_ERROR_FAILURE;

        nsCOMPtr<nsIDocShellTreeItem> browserAsItem;
        browserAsItem = do_QueryInterface(mWebBrowser);
        if (!browserAsItem) return NS_ERROR_FAILURE;

        // get the owner for that item
        nsCOMPtr<nsIDocShellTreeOwner> treeOwner;
        browserAsItem->GetTreeOwner(getter_AddRefs(treeOwner));
        if (!treeOwner) return NS_ERROR_FAILURE;

        // get the primary content shell as an item
        nsCOMPtr<nsIDocShellTreeItem> contentItem;
        treeOwner->GetPrimaryContentShell(getter_AddRefs(contentItem));
        if (!contentItem) return NS_ERROR_FAILURE;

        // QI that back to a docshell
        nsCOMPtr<nsIDocShell> DocShell;
        DocShell = do_QueryInterface(contentItem);
        if (!DocShell) return NS_ERROR_FAILURE;

        *aDocShell = DocShell.get();
        NS_IF_ADDREF(*aDocShell);

        return NS_OK;
}


nsresult
KzMozWrapper::GetDocument (nsIDOMDocument **aDOMDocument)
{
      nsCOMPtr<nsIDOMDocument> domDocument;
      
      return mDOMWindow->GetDocument (aDOMDocument);
}


nsresult
KzMozWrapper::GetMainDomDocument (nsIDOMDocument **aDOMDocument)
{
        nsresult rv;

        nsCOMPtr<nsIDocShell> DocShell;
        rv = GetDocShell(getter_AddRefs(DocShell));
        if (NS_FAILED(rv) || !DocShell) return NS_ERROR_FAILURE;

        nsCOMPtr<nsIContentViewer> contentViewer;
        rv = DocShell->GetContentViewer(getter_AddRefs(contentViewer));
        if (!NS_SUCCEEDED(rv) || !contentViewer) return NS_ERROR_FAILURE;

        return contentViewer->GetDOMDocument(aDOMDocument);
}


nsresult
KzMozWrapper::GetDOMWindow (nsIDOMWindow **aDOMWindow)
{
      nsresult rv;
      
      rv = mWebBrowser->GetContentDOMWindow (aDOMWindow);
      
      return rv;
}


nsresult
KzMozWrapper::GetContentViewer (nsIContentViewer **aViewer)
{
        g_return_val_if_fail(mWebBrowser, NS_ERROR_FAILURE);

        nsCOMPtr<nsIDocShell> ourDocShell(do_GetInterface(mWebBrowser));
        NS_ENSURE_TRUE(ourDocShell, NS_ERROR_FAILURE);
        return ourDocShell->GetContentViewer(aViewer);
}


/* this function picked from galeon-1.3.11a. */
nsresult
KzMozWrapper::GetSHistory (nsISHistory **aSHistory)
{
      nsresult rv;

      nsCOMPtr<nsIDocShell> DocShell;
      rv = GetDocShell (getter_AddRefs(DocShell));
      if (NS_FAILED(rv) || !DocShell) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIWebNavigation> ContentNav = do_QueryInterface (DocShell,
                                                   &rv);
      if (!ContentNav) return NS_ERROR_FAILURE;

      nsCOMPtr<nsISHistory> SessionHistory;
      rv = ContentNav->GetSessionHistory (getter_AddRefs (SessionHistory));
      if (!SessionHistory) return NS_ERROR_FAILURE;

      *aSHistory = SessionHistory.get();
      NS_IF_ADDREF (*aSHistory);

      return NS_OK;
}


nsresult
KzMozWrapper::GetSelection (nsISelection **selection)
{
      nsCOMPtr<nsIDOMWindow> domWindow;

      nsresult rv = GetFocusedDOMWindow (getter_AddRefs(domWindow));
      if (NS_FAILED(rv)) return NS_ERROR_FAILURE;

      return domWindow->GetSelection(selection);
}


nsresult
KzMozWrapper::GetHtmlWithContents (nsISelection *selection, 
                           const gchar *storedir,
                           nsAString &string)
{
      nsCOMPtr<nsIDOMRange> range;
      selection->GetRangeAt(0, getter_AddRefs(range));
      if (!range) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMDocument> domDoc;

      nsresult rv = GetMainDomDocument(getter_AddRefs(domDoc));
        if (NS_FAILED(rv) || !domDoc) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMNode> bodyNode;
      GetBodyNode(getter_AddRefs(bodyNode));
      
      SetHTMLHeadSource(domDoc, storedir, string);

      HTMLSourceFromNode(domDoc, bodyNode, selection, range, storedir, string);

      const PRUnichar end[] = { '\n', '<', '/', 'h', 't', 'm', 'l', '>', '\0' };
      string.Append(end);

      return NS_OK;
}


nsresult
KzMozWrapper::GetBodyString (nsAString &string)
{
      nsresult rv;
      nsCOMPtr<nsIDOMDocument> domDoc;
        rv = GetMainDomDocument(getter_AddRefs(domDoc));
        if (NS_FAILED(rv) || !domDoc) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMDocumentRange> docRange = do_QueryInterface(domDoc);
      if (!docRange)
            return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMRange> range;
      docRange->CreateRange(getter_AddRefs(range));
      if (!range)
            return NS_ERROR_FAILURE;

      MozillaPrivate::GetRootRange(domDoc, range);
      range->ToString(string);

      return NS_OK;
}


nsresult
KzMozWrapper::GetStringSelection (nsAString &string, gboolean backward)
{
      nsresult rv;
      nsCOMPtr<nsIDOMDocument> domDoc;
        rv = GetMainDomDocument(getter_AddRefs(domDoc));
        if (NS_FAILED(rv) || !domDoc) return NS_ERROR_FAILURE;
      
      nsCOMPtr<nsIDOMDocumentRange> docRange = do_QueryInterface(domDoc);
      if (!docRange)
            return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMRange> range;
      docRange->CreateRange(getter_AddRefs(range));
      if (!range)
            return NS_ERROR_FAILURE;

      nsCOMPtr<nsISelection> selection;

      mDOMWindow->GetSelection(getter_AddRefs(selection));

      MozillaPrivate::GetSelectedRange(domDoc, range, selection, backward);

      range->ToString(string);

      return NS_OK;
}


nsresult
KzMozWrapper::CanCutSelection (PRBool *result)
{
      nsCOMPtr<nsIClipboardCommands> clipboard(do_GetInterface(mWebBrowser));
      return clipboard->CanCutSelection(result);
}


nsresult 
KzMozWrapper::CanCopySelection (PRBool *result)
{
      nsCOMPtr<nsIClipboardCommands> clipboard(do_GetInterface(mWebBrowser));
      return clipboard->CanCopySelection(result);
}


nsresult
KzMozWrapper::CanPaste (PRBool *result)
{
      nsCOMPtr<nsIClipboardCommands> clipboard(do_GetInterface(mWebBrowser));
      return clipboard->CanPaste(result);
}


nsresult
KzMozWrapper::CutSelection (void)
{
      nsCOMPtr<nsIClipboardCommands> clipboard(do_GetInterface(mWebBrowser));
      return clipboard->CutSelection();
}


nsresult
KzMozWrapper::CopySelection (void)
{
      nsCOMPtr<nsIClipboardCommands> clipboard(do_GetInterface(mWebBrowser));
      return clipboard->CopySelection();
}


nsresult
KzMozWrapper::Paste (void)
{
      nsCOMPtr<nsIClipboardCommands> clipboard(do_GetInterface(mWebBrowser));
      return clipboard->Paste();
}


nsresult
KzMozWrapper::SelectAll (void)
{
      nsCOMPtr<nsIClipboardCommands> clipboard(do_GetInterface(mWebBrowser));
      
      return clipboard->SelectAll();
}


/* this function picked from galeon-1.3.11a. */
nsresult
KzMozWrapper::GetFocusedDOMWindow (nsIDOMWindow **aDOMWindow)
{
      nsresult rv;
      
      g_return_val_if_fail (mWebBrowser, NS_ERROR_FAILURE);

      nsCOMPtr<nsIWebBrowserFocus> focus = do_GetInterface(mWebBrowser, &rv);
      if (NS_FAILED(rv) || !focus) return NS_ERROR_FAILURE;

      rv = focus->GetFocusedWindow (aDOMWindow);
      if (NS_FAILED(rv))
            rv = mWebBrowser->GetContentDOMWindow (aDOMWindow);
      return rv;
}


/* this function picked from galeon-1.3.11a. */
nsresult
KzMozWrapper::GetWebNavigation (nsIWebNavigation **aWebNavigation)
{
      nsresult rv;

      nsCOMPtr<nsIDOMWindow> DOMWindow;
      rv = GetFocusedDOMWindow (getter_AddRefs(DOMWindow));
      if (NS_FAILED(rv) || !DOMWindow) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIScriptGlobalObject> scriptGlobal = do_QueryInterface(DOMWindow);
      if (!scriptGlobal) return NS_ERROR_FAILURE;

      nsIDocShell *docshell = scriptGlobal->GetDocShell();
      if (!docshell)
            return NS_ERROR_FAILURE;
      
      nsCOMPtr<nsIWebNavigation> wn = do_QueryInterface (docshell, &rv);
      if (!wn || !NS_SUCCEEDED (rv)) return NS_ERROR_FAILURE;

      NS_IF_ADDREF(*aWebNavigation = wn);
      return NS_OK;
}


/* this function picked from galeon-1.3.11a. */
nsresult
KzMozWrapper::LoadDocument (nsISupports *aPageDescriptor,
                      PRUint32 aDisplayType)
{
      nsresult rv;

      nsCOMPtr<nsIWebNavigation> wn;
      rv = GetWebNavigation(getter_AddRefs(wn));
      if (!wn || !NS_SUCCEEDED(rv)) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIWebPageDescriptor> wpd = do_QueryInterface(wn, &rv);
      if (!wpd || !NS_SUCCEEDED(rv)) return NS_ERROR_FAILURE;

      return wpd->LoadPage(aPageDescriptor, aDisplayType);
}


/* this function picked from galeon-1.3.11a. */
nsresult
KzMozWrapper::GetPageDescriptor (nsISupports **aPageDescriptor)
{
      nsresult rv;

      nsCOMPtr<nsIWebNavigation> wn;
      rv = GetWebNavigation(getter_AddRefs(wn));
      if (!wn || !NS_SUCCEEDED(rv)) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIWebPageDescriptor> wpd = do_QueryInterface(wn, &rv);
      if (!wpd || !NS_SUCCEEDED(rv)) return NS_ERROR_FAILURE;

      return wpd->GetCurrentDescriptor(aPageDescriptor);
}


/* this function picked from galeon-1.3.11a. */
nsresult
KzMozWrapper::CopyHistoryTo (KzMozWrapper *dest, 
                       PRBool back_history, 
                       PRBool forward_history, 
                       PRBool set_current)
{
      nsresult rv;
      PRInt32 count, index;
      
      nsCOMPtr<nsISHistory> h_src;
      rv = GetSHistory (getter_AddRefs(h_src));
      if (NS_FAILED(rv) || !h_src) return NS_ERROR_FAILURE;

      h_src->GetCount (&count);
      h_src->GetIndex (&index);

      nsCOMPtr<nsISHistory> h_dest;
      rv = dest->GetSHistory (getter_AddRefs (h_dest));
      if (!NS_SUCCEEDED (rv) || (!h_dest)) return NS_ERROR_FAILURE;

      nsCOMPtr<nsISHistoryInternal> hi_dest = do_QueryInterface (h_dest);
      if (!hi_dest) return NS_ERROR_FAILURE;

      if (count) {
            nsCOMPtr<nsIHistoryEntry> he;
            nsCOMPtr<nsISHEntry> she;

            for (PRInt32 i = (back_history ? 0 : index + 1); 
                 i < (forward_history ? count : index + 1);
                 i++) 
            {

                  rv = h_src->GetEntryAtIndex (i, PR_FALSE,
                                           getter_AddRefs (he));
                  if (!NS_SUCCEEDED(rv) || (!he))
                        return NS_ERROR_FAILURE;

                  she = do_QueryInterface (he);
                  if (!she) return NS_ERROR_FAILURE;

                  rv = hi_dest->AddEntry (she, PR_TRUE);
                  if (!NS_SUCCEEDED(rv) || (!she))
                        return NS_ERROR_FAILURE;
            }
            
            if (set_current)
            {
                  nsCOMPtr<nsIDocShell> destDocShell;
                  rv = dest->GetDocShell (getter_AddRefs(destDocShell));
                  if (NS_FAILED(rv) || !destDocShell) return NS_ERROR_FAILURE;
            
                  nsCOMPtr<nsIWebNavigation> wn_dest = do_QueryInterface (destDocShell, &rv);
                  
                  rv = wn_dest->GotoIndex(index);
                  if (!NS_SUCCEEDED(rv)) return NS_ERROR_FAILURE;
            }
      }

      return NS_OK;
}


// picked from galeon-1.3.11a 
nsresult
KzMozWrapper::GetSHInfo (PRInt32 *count, PRInt32 *index)
{
      nsresult rv;

      nsCOMPtr<nsISHistory> SessionHistory;
      rv = GetSHistory (getter_AddRefs(SessionHistory));
      if (NS_FAILED(rv) || ! SessionHistory) return NS_ERROR_FAILURE;

      SessionHistory->GetCount (count);
      SessionHistory->GetIndex (index);   

      return NS_OK;
}


// picked from galeon-1.3.11a 
nsresult
KzMozWrapper::GetSHUrlAtIndex (PRInt32 index, nsACString &url)
{
      nsresult rv;

      nsCOMPtr<nsISHistory> SessionHistory;
      rv = GetSHistory (getter_AddRefs(SessionHistory));
      if (NS_FAILED(rv) || ! SessionHistory) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIHistoryEntry> he;
      rv = SessionHistory->GetEntryAtIndex (index, PR_FALSE,
                                    getter_AddRefs (he));
      if (NS_FAILED(rv) || (!he)) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIURI> uri;
      rv = he->GetURI (getter_AddRefs(uri));
      if (NS_FAILED(rv) || (!uri)) return NS_ERROR_FAILURE;

      rv = uri->GetSpec(url);
      if (NS_FAILED(rv) || !url.Length()) return NS_ERROR_FAILURE;

      return NS_OK;
}

// picked from galeon-1.3.11a 
nsresult
KzMozWrapper::GetSHTitleAtIndex (PRInt32 index, PRUnichar **title)
{
      nsresult rv;

      nsCOMPtr<nsISHistory> SessionHistory;
      rv = GetSHistory (getter_AddRefs(SessionHistory));
      if (NS_FAILED(rv) || ! SessionHistory) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIHistoryEntry> he;
      rv = SessionHistory->GetEntryAtIndex (index, PR_FALSE,
                                      getter_AddRefs (he));
      if (!NS_SUCCEEDED(rv) || (!he)) return NS_ERROR_FAILURE;

      rv = he->GetTitle (title);
      if (!NS_SUCCEEDED(rv) || (!title)) return NS_ERROR_FAILURE;

      return NS_OK;
}


nsresult
KzMozWrapper::GetHistoryEntry (PRInt32 index, nsIHistoryEntry **he)
{
      nsresult rv;

      nsCOMPtr<nsISHistory> SessionHistory;
      rv = GetSHistory (getter_AddRefs(SessionHistory));
      if (NS_FAILED(rv) || ! SessionHistory) return NS_ERROR_FAILURE;

      rv = SessionHistory->GetEntryAtIndex (index, PR_FALSE,
                                    he);
      return rv;
}


nsresult 
KzMozWrapper::GoHistoryIndex (gint index)
{
      nsCOMPtr<nsIWebNavigation> nav = do_QueryInterface (mWebBrowser);
      if (!nav) return NS_ERROR_FAILURE;

      return nav->GotoIndex (index);
}


nsresult
KzMozWrapper::GetDocumentUrl (nsACString &url)
{
      nsresult rv;
      nsCOMPtr<nsIDOMWindow> domWindow;
      nsCOMPtr<nsIDOMDocument> DOMDocument;

      mWebBrowser->GetContentDOMWindow(getter_AddRefs(domWindow));

      rv = domWindow->GetDocument(getter_AddRefs(DOMDocument));
      if (NS_FAILED(rv) || !DOMDocument) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOM3Document> doc = do_QueryInterface(DOMDocument);

      if(!doc) return NS_ERROR_FAILURE;

      nsEmbedString URI;
      doc->GetDocumentURI(URI);

      NS_UTF16ToCString(URI,
                    NS_CSTRING_ENCODING_UTF8, url);

      return NS_OK;
}


nsresult
KzMozWrapper::ForceEncoding (const char *encoding)
{
        nsresult rv;

        nsCOMPtr<nsIContentViewer> contentViewer;
        rv = GetContentViewer(getter_AddRefs(contentViewer));
        if (!NS_SUCCEEDED(rv) || !contentViewer) return NS_ERROR_FAILURE;

        nsCOMPtr<nsIMarkupDocumentViewer> mdv = do_QueryInterface(contentViewer);
        if (!mdv) return NS_ERROR_FAILURE;

      rv = mdv->SetForceCharacterSet(nsEmbedCString(encoding));

        return rv;
}

/*
 * This function is derived from galeon-1.3.12(mozilla/GaleonWrapper.cpp).
 *  Copyright (C) 2000 Marco Pesenti Gritti
 */

nsresult 
KzMozWrapper::GetEncoding (char **encoding, PRBool &forced)
{
      nsCOMPtr<nsIDocCharset> docChar = do_GetInterface(mWebBrowser);
      char *charset;
      docChar->GetCharset(&charset);
      encoding = &charset;

      return NS_OK;
}


nsresult
KzMozWrapper::ResolveURI (nsIDOMDocument *domDoc,
                    const nsACString &origURI,
                    nsACString &URI)
{
        nsresult rv;

      nsCOMPtr<nsIDOM3Node> domnode = do_QueryInterface(domDoc);
      if(!domnode) return NS_ERROR_FAILURE;
      
      nsEmbedString spec;
      domnode->GetBaseURI(spec);

      nsEmbedCString cSpec;
      NS_UTF16ToCString(spec,
                    NS_CSTRING_ENCODING_UTF8, cSpec);

      nsCOMPtr<nsIURI> baseURI;
      NewURI(getter_AddRefs(baseURI), cSpec.get());
      
      rv = baseURI->Resolve(origURI, URI);

      return rv;
}


void 
KzMozWrapper::SetAttributes (nsIDOMNode *node, 
                       nsIDOMDocument *domDoc,
                       nsAString &aString)
{
      const PRUnichar eq[] = { '=', '\0' };
      const PRUnichar dq[] = { '"', '\0' };
      const PRUnichar sp[] = { ' ', '\0' };
      
      nsCOMPtr<nsIDOMNamedNodeMap> attrs;
      node->GetAttributes(getter_AddRefs(attrs));
      if (!attrs) return;

      PRUint32 index, length;
      attrs->GetLength(&length);
      
      for (index = 0; index < length; index++)
      {
            nsCOMPtr<nsIDOMNode> attr;
            attrs->Item(index, getter_AddRefs(attr));
            nsEmbedString name, value;
            attr->GetNodeName(name);
            attr->GetNodeValue(value);
            value.Assign(nsEscapeHTML2(value.get(),
                                 value.Length()));
                  
            aString += sp;
            aString += name;
            aString += eq;
            aString += dq;
            aString += value;
            aString += dq;
      }
}

void
KzMozWrapper::SetStartTag (const nsAString &tag,
                     nsIDOMDocument *domDoc,
                     nsAString &aString)
{
      const PRUnichar lt[] = { '<', '\0' };
      const PRUnichar gt[] = { '>', '\0' };
      const PRUnichar cr[] = { '\n', '\0' };

      nsCOMPtr<nsIDOMNodeList> nodeList;
      domDoc->GetElementsByTagName(tag, getter_AddRefs(nodeList));
      
      if (!nodeList) return;

      PRUint32 index, length;
      nodeList->GetLength(&length);
      for (index = 0; index < length; index++)
      {
            nsCOMPtr<nsIDOMNode> child;
            nodeList->Item(index, getter_AddRefs(child));

            nsCOMPtr<nsIDOMElement> element;
            element = do_QueryInterface(child);
            if (!element) continue;
                  
            nsEmbedString name;
            element->GetTagName(name);
            ToLowerCase(name);
            aString += lt;
            aString += name;
            SetAttributes(child, domDoc, aString);
            aString += gt;
            aString += cr;
      }
}

void
KzMozWrapper::SetHTMLHeadSource (nsIDOMDocument *domDocument,
                         const gchar *storedir,
                           nsAString &aSource)
{
      const PRUnichar dq[] = { '"', '\0' };
      const PRUnichar sp[] = { ' ', '\0' };
      const PRUnichar sl[] = { '/', '\0' };
      const PRUnichar lt[] = { '<', '\0' };
      const PRUnichar gt[] = { '>', '\0' };
      const PRUnichar cr[] = { '\n', '\0' };
      const PRUnichar dt[] = { '!', 'D', 'O', 'C', 'T', 'Y', 'P', 'E', '\0' };
      const PRUnichar head_c[] = {'h', 'e', 'a', 'd', '\0'};
      const PRUnichar htmlLiteral[] = {'h', 't', 'm', 'l', '\0'};
      
      nsCOMPtr<nsIDOMNode> domNode;
      domNode = do_QueryInterface(domDocument);

      // <!DOCTYPE name PUBLIC "PiblicId" "SystemId">
      nsCOMPtr<nsIDOMDocumentType> docType;
      domDocument->GetDoctype(getter_AddRefs(docType));
      
      if (docType)
      {
            nsEmbedString name, pubID, sysID;
            docType->GetName(name);
            docType->GetPublicId(pubID);
            docType->GetSystemId(sysID);
            aSource += lt;
            aSource += dt;
            aSource += sp;
            aSource += name;
            aSource += sp;
            aSource += sp;
            aSource += dq;
            aSource += pubID;
            aSource += dq;
            aSource += sp;
            aSource += dq;
            aSource += sysID;
            aSource += dq;
            aSource += gt;
            aSource += cr;
      }              

      // html node <html ...>
      SetStartTag(nsEmbedString(htmlLiteral), domDocument, aSource);

      nsCOMPtr<nsIDOMNodeList> headList;
      domDocument->GetElementsByTagName(nsEmbedString(head_c),
                                getter_AddRefs(headList));
      if (!headList) return;

      PRUint32 length;
      headList->GetLength(&length);
      if (!length) return;

      nsCOMPtr<nsIDOMNode> head;
      headList->Item(0, getter_AddRefs(head));

      HTMLSourceFromNode(domDocument, head, nsnull, nsnull,
                     storedir, aSource);
}

void
KzMozWrapper::HTMLSourceFromNode(nsIDOMDocument *domDoc,
                         nsIDOMNode *node,
                         nsISelection *selection,
                         nsIDOMRange *range,
                         const gchar *storedir, 
                         nsAString &string)
{
      nsEmbedString tagname;
      nsEmbedCString cTagname;
      const PRUnichar dq[] = { '"', '\0' };
      const PRUnichar sp[] = { ' ', '\0' };
      const PRUnichar sl[] = { '/', '\0' };
      const PRUnichar lt[] = { '<', '\0' };
      const PRUnichar gt[] = { '>', '\0' };
      const PRUnichar eq[] = { '=', '\0' };

      PRBool contains;
      if (selection)
      {
            selection->ContainsNode(node, PR_TRUE, &contains);
            // if node is not contained in seletion, ignore.
            if(!contains)
                  return;
      }

      nsCOMPtr<nsIDOMElement> element = do_QueryInterface(node);
      if (element)
      {
            element->GetTagName(tagname);
            NS_UTF16ToCString(tagname,
                          NS_CSTRING_ENCODING_UTF8, cTagname);
            ToLowerCase(tagname);
            string += lt;
            string += tagname;
      
            char *relattr =  NULL;
            GetAttributeFromNode(node, "rel", &relattr);
                        
            nsCOMPtr<nsIDOMNamedNodeMap> attrs;
            node->GetAttributes(getter_AddRefs(attrs));
            if (attrs)
            {
                  PRUint32 index, length;
                  attrs->GetLength(&length);
                  for (index = 0; index < length; index++)
                  {
                        nsCOMPtr<nsIDOMNode> attr;
                        attrs->Item(index, getter_AddRefs(attr));
                        nsEmbedString name, value;
                        attr->GetNodeName(name);
                        attr->GetNodeValue(value);
                  
                        nsEmbedCString cName;
                        NS_UTF16ToCString(name,
                                      NS_CSTRING_ENCODING_UTF8,
                                      cName);
                        value.Assign(nsEscapeHTML2(value.get(),
                                             value.Length()));
                        
                        nsEmbedCString cValue;
                        NS_UTF16ToCString(value,
                                      NS_CSTRING_ENCODING_UTF8,
                                      cValue);
                        string += sp;
                        string += name;
                        string += eq;

                        // convert img src address to local file name
                        if ((!g_ascii_strcasecmp(cTagname.get(), "img") && 
                             !g_ascii_strcasecmp(cName.get(), "src")) ||
                            (!g_ascii_strcasecmp(cName.get(), "background")))
                        {
                              nsEmbedCString curi; 
                              nsEmbedString localfile;
                              ResolveURI(domDoc, cValue, curi);

                              GetFileToLocal(curi, storedir,
                                           "images", localfile);
                              
                              string += dq;
                              string += localfile;
                              string += dq;
                        }
                        else if (!g_ascii_strcasecmp(cTagname.get(), "link") && 
                                 !g_ascii_strcasecmp(cName.get(), "href") &&
                               relattr && 
                               !strcasecmp(relattr, "stylesheet"))
                        {
                              nsEmbedCString curi; 
                              nsEmbedString localfile;
                              ResolveURI(domDoc, cValue, curi);
                              
                              GetFileToLocal(curi, storedir,
                                           "css", localfile);
                              
                              string += dq;
                              string += localfile;
                              string += dq;
                        }
                        else if (!g_ascii_strcasecmp(cTagname.get(), "a") && 
                               !g_ascii_strcasecmp(cName.get(), "href"))
                        {
                              nsEmbedCString curi;
                              ResolveURI(domDoc, cValue, curi);

                              nsEmbedString uri;
                              NS_CStringToUTF16(curi,
                                            NS_CSTRING_ENCODING_UTF8,
                                            uri);
                              string += dq;
                              string += uri;
                              string += dq;
                        }
                        else if (!g_ascii_strcasecmp(cTagname.get(), "meta") && 
                               !g_ascii_strcasecmp(cName.get(), "content"))
                        {
                              // change the encoding
                              gchar *find, *start, *end;
                              gchar *str = g_strdup(cValue.get());

                              find = strstr(str, "charset=");

                              if (find)
                              {
                                    gint len;
                                    start = find + 8;
                                    end = strchr(start, ';');

                                    if (!end)
                                          len = strlen(start);
                                    else
                                          len = end - start;
                                    gchar *charset;
                                    charset = g_strndup(start, len);
                                    cValue.Assign(str, start - str);
                                    cValue.Append(charset);
                                    cValue.Append("UTF-8");
                                    if (end)
                                          cValue.Append(end);
                                    g_free(charset);
                              }
                              g_free(str);
                              
                              NS_CStringToUTF16(cValue,
                                            NS_CSTRING_ENCODING_UTF8,
                                            value);
                              string += dq;
                              string += value;
                              string += dq;
                        }
                        else
                        {
                              string += dq;
                              string += value;
                              string += dq;
                        }

                  }
            }
            if (relattr) 
                  g_free(relattr);
            // img,hr,br,input -> <img .. />,<hr />, <br />, <input .. /> 
            if (!g_ascii_strcasecmp(cTagname.get(), "img") ||
                !g_ascii_strcasecmp(cTagname.get(), "hr") ||
                !g_ascii_strcasecmp(cTagname.get(), "br") ||
                !g_ascii_strcasecmp(cTagname.get(), "meta") ||
                !g_ascii_strcasecmp(cTagname.get(), "link") ||
                !g_ascii_strcasecmp(cTagname.get(), "input"))
            {
                  string += sp;
                  string += sl;
                  string += gt;
            }
            else
                  string += gt;
      }

      nsEmbedString text;
      nsCOMPtr<nsIDOMText> textNode = do_QueryInterface(node);
      if (textNode) // if it's a text node, get the text
      {
            nsCOMPtr<nsIDOMNode> startNode;
            nsCOMPtr<nsIDOMNode> endNode;
            
            if (range)
            {
                  range->GetStartContainer(getter_AddRefs(startNode));
                  range->GetEndContainer(getter_AddRefs(endNode));
            
                  if (node == startNode && node == endNode)
                  {
                        PRInt32 startOffset, endOffset;
                        range->GetStartOffset(&startOffset);
                        range->GetEndOffset(&endOffset);
                        textNode->SubstringData(startOffset,
                                          endOffset-startOffset,
                                          text);
                  }
                  else if (node == startNode)
                  {
                        PRInt32 startOffset;
                        PRUint32 strLength;
                        textNode->GetLength(&strLength);
                        range->GetStartOffset(&startOffset);
                        textNode->SubstringData(startOffset,
                                          strLength-startOffset,
                                          text);
                  }
                  else if (node == endNode)
                  {
                        PRInt32 endOffset;
                        range->GetEndOffset(&endOffset);
                        textNode->SubstringData(0,
                                          endOffset,
                                          text);
                  }
                  else 
                  {
                        textNode->GetData(text);
                  }
            }
            else 
            {
                  textNode->GetData(text);
            }
            text.Assign(nsEscapeHTML2(text.get(),
                                text.Length()));
                        
            string += text;
      }

      nsCOMPtr<nsIDOMNodeList> childNodeList;
      node->GetChildNodes(getter_AddRefs(childNodeList));
      if (childNodeList)
      {
            PRUint32 index, length;
            childNodeList->GetLength(&length);
            for (index = 0; index < length; index++)
            {
                  nsCOMPtr<nsIDOMNode> child;
                  childNodeList->Item(index, getter_AddRefs(child));
                  
                  if (selection)
                        selection->ContainsNode(child, PR_TRUE, &contains);
                  else 
                        contains = PR_TRUE;
                  if (contains)
                  {
                        HTMLSourceFromNode(domDoc,
                                       child, 
                                       selection,
                                       range,
                                       storedir, 
                                       string);
                  }
            }
      }

      if (element)
      {
            if (g_ascii_strcasecmp(cTagname.get(), "br") &&
                g_ascii_strcasecmp(cTagname.get(), "hr") &&
                g_ascii_strcasecmp(cTagname.get(), "input") &&
                g_ascii_strcasecmp(cTagname.get(), "img") &&
                g_ascii_strcasecmp(cTagname.get(), "meta") &&
                g_ascii_strcasecmp(cTagname.get(), "link"))
            {
                  string += lt;
                  string += sl;
                  string += tagname;
                  string += gt;
            }
      }
}


// this function is picked from galeon-1.3.13
nsresult
KzMozWrapper::GetCacheEntryDescriptor(const nsACString &aKey,
                              nsICacheEntryDescriptor **aCacheEntryDescriptor)
{
      nsresult rv;

      nsCOMPtr<nsICacheService> cacheService =
            do_GetService(NS_CACHESERVICE_CONTRACTID, &rv);
      if (NS_FAILED(rv) || !cacheService) return NS_ERROR_FAILURE;


      nsCOMPtr<nsICacheSession> cacheSession;
      rv = cacheService->CreateSession("HTTP",
                               nsICache::STORE_ANYWHERE,
                               nsICache::STREAM_BASED,
                               getter_AddRefs(cacheSession));
      if(NS_FAILED(rv) || !cacheSession) return NS_ERROR_FAILURE;

      cacheSession->SetDoomEntriesIfExpired(PR_FALSE);
            
      nsCOMPtr<nsICacheEntryDescriptor> cacheEntryDescriptor;
#ifdef MOZ_NSICACHESESSION_NSACSTRING_
      rv = cacheSession->OpenCacheEntry(aKey,
                                nsICache::ACCESS_READ,
                                nsICache::NON_BLOCKING,
                                aCacheEntryDescriptor);
#else
      nsEmbedCString cKey(aKey);
      rv = cacheSession->OpenCacheEntry(cKey.get(),
                                nsICache::ACCESS_READ,
                                nsICache::NON_BLOCKING,
                                aCacheEntryDescriptor);
#endif

      if (NS_FAILED(rv) || !aCacheEntryDescriptor)
      {
            rv = cacheService->CreateSession("FTP",
                                     nsICache::STORE_ANYWHERE,
                                     nsICache::STREAM_BASED,
                                     getter_AddRefs(cacheSession));
            if(NS_FAILED(rv) || !cacheSession) return NS_ERROR_FAILURE;

            cacheSession->SetDoomEntriesIfExpired (PR_FALSE);
#ifdef MOZ_NSICACHESESSION_NSACSTRING_
            return cacheSession->OpenCacheEntry(aKey,
                                nsICache::ACCESS_READ,
                                nsICache::NON_BLOCKING,
                                aCacheEntryDescriptor);
#else
            nsEmbedCString cKey(aKey);
            return cacheSession->OpenCacheEntry(cKey.get(),
                                nsICache::ACCESS_READ,
                                nsICache::NON_BLOCKING,
                                aCacheEntryDescriptor);
#endif
      }

      return NS_OK;
}


void
KzMozWrapper::GetFileToLocal (const nsACString &URI,
                        const gchar *storedir,
                        const gchar *type, 
                        nsAString &LocalFile)
{
      nsresult rv;
      nsEmbedCString sl("/");

      nsCOMPtr<nsICacheEntryDescriptor> cacheEntryDescriptor;
      rv = GetCacheEntryDescriptor(URI,
                             getter_AddRefs(cacheEntryDescriptor));

      if (NS_SUCCEEDED(rv) && cacheEntryDescriptor)
      {
            PRUint32 dataSize = 0;
            nsCOMPtr<nsIInputStream> inStream;

            gchar *dir, *buf;
            const gchar *uri;
            NS_CStringGetData(URI, &uri);
            gchar *filename = create_filename_from_uri(uri);

            dir = g_build_filename(g_get_home_dir(),
                               ".", PACKAGE,
                               storedir,
                               type, /* images or css */ 
                               filename,
                               NULL);

            cacheEntryDescriptor->GetDataSize(&dataSize);
            cacheEntryDescriptor->OpenInputStream(0, getter_AddRefs(inStream));

            buf = g_new0(gchar, dataSize);

            inStream->Read(buf, dataSize, &rv);
            inStream->Close();
            
            nsEmbedCString cLocalFile;
            cLocalFile.Assign(type);
            cLocalFile += sl;
            cLocalFile.Append(filename);
            NS_CStringToUTF16(cLocalFile, 
                          NS_CSTRING_ENCODING_UTF8, LocalFile);

            nsCOMPtr<nsILocalFile> imageFile = do_CreateInstance(NS_LOCAL_FILE_CONTRACTID);
            imageFile->InitWithNativePath(nsEmbedCString(dir));
            imageFile->Create(nsIFile::NORMAL_FILE_TYPE, 0600);
            nsCOMPtr<nsIOutputStream> outStream;

            NS_NewLocalFileOutputStream(getter_AddRefs(outStream),
                                  imageFile,
                                  -1,
                                  0600);
            outStream->Write(buf, dataSize, &rv);
            outStream->Close();

            g_free(filename);
            g_free(dir);
            g_free(buf);
      }
}


nsresult
KzMozWrapper::Print (void)
{
      nsresult rv;
        nsCOMPtr<nsIPrintSettings> options;

      g_return_val_if_fail (mWebBrowser, NS_ERROR_FAILURE);

      nsCOMPtr<nsIWebBrowserPrint> print(do_GetInterface(mWebBrowser, &rv));
      if (NS_FAILED(rv) || !print) return NS_ERROR_FAILURE;

      print->GetGlobalPrintSettings(getter_AddRefs(options));
      options->SetPaperSize(nsIPrintSettings::kPaperSizeNativeData);
      options->SetPrintSilent(PR_FALSE);
      
//    KzMozProgressListener *aProgress = new KzMozProgressListener();
      rv = print->Print(options, nsnull);

      return rv;
}

nsresult
KzMozWrapper::PrintPreview (void)
{
      nsresult rv;
        nsCOMPtr<nsIPrintSettings> options;

      g_return_val_if_fail (mWebBrowser, NS_ERROR_FAILURE);

      nsCOMPtr<nsIWebBrowserPrint> print(do_GetInterface(mWebBrowser, &rv));
      if (NS_FAILED(rv) || !print) return NS_ERROR_FAILURE;

      print->GetGlobalPrintSettings(getter_AddRefs(options));
      options->SetPaperSize(nsIPrintSettings::kPaperSizeNativeData);
      rv = print->PrintPreview(options, mDOMWindow, nsnull);

      return rv;
}


nsresult
KzMozWrapper::GetPrinterList (GList **list)
{
      *list = MozillaPrivate::GetPrinterList();
      return NS_OK;
}

// these functions were picked from Galeon-1.3.17.

nsresult
KzMozWrapper::SetZoom (float aZoom, PRBool reflow)
{
      nsresult result;

      nsCOMPtr<nsIDocShell> DocShell;
      result = GetDocShell (getter_AddRefs(DocShell));
      if (NS_FAILED(result) || !DocShell) return NS_ERROR_FAILURE;

      if (reflow)
      {
            nsCOMPtr<nsIContentViewer> contentViewer; 
            result = DocShell->GetContentViewer (getter_AddRefs(contentViewer));
            if (!NS_SUCCEEDED (result) || !contentViewer) return NS_ERROR_FAILURE;

            nsCOMPtr<nsIMarkupDocumentViewer> mdv = do_QueryInterface(contentViewer,
                                                  &result);
            if (NS_FAILED(result) || !mdv) return NS_ERROR_FAILURE;

            return mdv->SetTextZoom (aZoom);
      }
      else
      {
            SetZoomOnDocshell (aZoom, DocShell);

            nsCOMPtr<nsIDocShellTreeNode> docShellNode(do_QueryInterface(DocShell));
            if (docShellNode)
            {
                  PRInt32 i;
                  PRInt32 n;
                  docShellNode->GetChildCount(&n);
                  for (i=0; i < n; i++) 
                  {
                        nsCOMPtr<nsIDocShellTreeItem> child;
                        docShellNode->GetChildAt(i, getter_AddRefs(child));
                        nsCOMPtr<nsIDocShell> childAsShell(do_QueryInterface(child));
                        if (childAsShell) 
                        {
                              return SetZoomOnDocshell (aZoom, childAsShell);
                        }
                  }
            }
      }

      return NS_OK;
}

nsresult
KzMozWrapper::SetZoomOnDocshell (float aZoom, nsIDocShell *DocShell)
{
      gboolean ret = MozillaPrivate::SetZoomOnDocShell(aZoom, DocShell);

      if (!ret) return NS_ERROR_FAILURE;

      return NS_OK;
}

nsresult
KzMozWrapper::GetZoom (float *aZoom)
{
      nsresult result;

      nsCOMPtr<nsIDocShell> DocShell;
      result = GetDocShell (getter_AddRefs(DocShell));
      if (NS_FAILED(result) || !DocShell) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIContentViewer> contentViewer; 
      result = DocShell->GetContentViewer (getter_AddRefs(contentViewer));
      if (!NS_SUCCEEDED (result) || !contentViewer) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIMarkupDocumentViewer> mdv = do_QueryInterface(contentViewer,
                                                  &result);
      if (NS_FAILED(result) || !mdv) return NS_ERROR_FAILURE;

      return mdv->GetTextZoom (aZoom);
}

nsresult
KzMozWrapper::SetImageZoom (float aZoom)
{
      const PRUnichar imgLiteral[] = { 'i', 'm', 'g', '\0' };
      const PRUnichar styleLiteral[] = { 's', 't', 'y', 'l', 'e', '\0' };
      
      nsresult rv;
      nsCOMPtr<nsIDOMDocument> domDoc;
        rv = GetMainDomDocument(getter_AddRefs(domDoc));
        if (NS_FAILED(rv) || !domDoc) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMNodeList> nodeList;
      rv = domDoc->GetElementsByTagName(nsEmbedString(imgLiteral),
                                getter_AddRefs(nodeList));
        if (NS_FAILED(rv) || !domDoc) return NS_ERROR_FAILURE;

      PRUint32 num;
      rv = nodeList->GetLength(&num);
      if (NS_FAILED(rv) || num < 1) return NS_ERROR_FAILURE;

      for (PRUint32 i = 0; i < num; i++)
      {
            nsCOMPtr<nsIDOMNode> node;
            rv = nodeList->Item(i, getter_AddRefs(node));
            if (NS_FAILED(rv) || !node) continue;
            nsCOMPtr<nsIDOMHTMLImageElement> img;
            img = do_QueryInterface(node);
            PRInt32 width = 0, height = 0;

            char *width_str =  NULL;
            GetAttributeFromNode(node, "width",
                             &width_str);
            if (!width_str) continue;

            if (str_isdigit(width_str))
                  width = atoi(width_str);
            g_free(width_str);
            
            char *height_str =  NULL;
            GetAttributeFromNode(node, "height",
                             &height_str);
            if (!height_str) continue;
      
            if (str_isdigit(height_str))
                  height = atoi(height_str);
            g_free(height_str);

            if (width == 0 || height == 0)
                  continue;

            width = (PRInt32)(width * aZoom);
            height = (PRInt32)(height * aZoom);
            nsCOMPtr<nsIDOMElement> elm;
            elm = do_QueryInterface(node);
            nsEmbedString style_value;
            gchar *v;
            v = g_strdup_printf("width: %dpx; height: %dpx;",
                            width, height);
            nsEmbedCString cValue(v);
            NS_CStringToUTF16(cValue, NS_CSTRING_ENCODING_UTF8, style_value);
            elm->SetAttribute(nsEmbedString(styleLiteral), style_value);
            g_free(v);
      }
      
      return NS_OK;
}

nsresult
KzMozWrapper::GetLinksFromWindow (nsIDOMWindow *domWindow,
                          GList **list,
                          nsISelection *selection, 
                          gboolean selected_only)
{
      nsresult rv;
      PRUint32 num = 0;
      gboolean flag = FALSE;
      const PRUnichar aLiteral[] = { 'a', '\0' };

        // get frame window
        nsCOMPtr<nsIDOMWindowCollection> frames;
        domWindow->GetFrames(getter_AddRefs(frames));

        if (frames)
      {
            frames->GetLength(&num);
      }

      if (num != 0)
      {
            for (PRUint32 i = 0; i < num; i++)
            {
                  nsCOMPtr<nsIDOMWindow> childWindow;
                      frames->Item(i, getter_AddRefs(childWindow));
                      rv = GetLinksFromWindow(childWindow, list,
                                      selection, selected_only);
                  if (NS_SUCCEEDED(rv))
                        flag |= TRUE;
            }
      }
      else
      {
            nsCOMPtr<nsIDOMDocument> domDoc;
            domWindow->GetDocument(getter_AddRefs(domDoc));

            nsCOMPtr<nsIDOMNodeList> nodeList;
            rv = domDoc->GetElementsByTagName(nsEmbedString(aLiteral),
                                      getter_AddRefs(nodeList));
              if (NS_FAILED(rv) || !nodeList) return NS_ERROR_FAILURE;

            PRUint32 num;
            rv = nodeList->GetLength(&num);
            if (NS_FAILED(rv) || num < 1) return NS_ERROR_FAILURE;

            // store links to GList
            nsCOMPtr<nsIDOMNode> node;
            for (PRUint32 i = 0; i < num; i++)
            {
                  rv = nodeList->Item(i, getter_AddRefs(node));
                  if (NS_FAILED(rv) || !node) continue;

                  // check whether the selection contains these nodes or not.
                  if (selected_only)
                  {
                        PRBool contains;
                        selection->ContainsNode(node, PR_TRUE, &contains);
                        if (!contains) continue;
                  }
                  gchar *uri = NULL, *title = NULL;
                  GetLinkAndTitleFromNode(domDoc, node,
                                      &uri, &title);
                  if (uri && *uri)
                  {
                        KzBookmark *link;
                        link = kz_bookmark_new_with_attrs(title, uri, NULL);
                        *list = g_list_append(*list, link);
                  }
                  g_free(uri);
                  g_free(title);
                  flag |= TRUE;
            }
      }

      return flag ? NS_OK : NS_ERROR_FAILURE;
}

nsresult 
KzMozWrapper::GetAttributeFromNode (nsIDOMNode *node, const char *attr, char **value)
{
      nsresult result;

      nsCOMPtr<nsIDOMNamedNodeMap> attributes;
      result = node->GetAttributes(getter_AddRefs(attributes));
      if (!NS_SUCCEEDED (result) || !attributes) return NS_ERROR_FAILURE;

      nsEmbedString Attr;
      NS_CStringToUTF16(nsEmbedCString(attr), NS_CSTRING_ENCODING_UTF8, Attr);
      nsCOMPtr<nsIDOMNode> attrNode;
      result = attributes->GetNamedItem (Attr, getter_AddRefs(attrNode));
      if (!NS_SUCCEEDED(result) || !attrNode)  return NS_ERROR_FAILURE;

      nsEmbedString nodeValue;

      result = attrNode->GetNodeValue(nodeValue);
      if (!NS_SUCCEEDED(result))  return NS_ERROR_FAILURE;

      nsEmbedCString cNodeValue;
      NS_UTF16ToCString(nodeValue,
                    NS_CSTRING_ENCODING_UTF8, cNodeValue);
      *value = g_strdup(cNodeValue.get());
      return NS_OK;
}

nsresult
KzMozWrapper::GetLinkFromNode (nsIDOMDocument *domDoc, nsIDOMNode *node,
                           gchar **url)
{
      if (url) *url = NULL;

      // get url
      char *hrefattr =  NULL;
      GetAttributeFromNode(node, "href", &hrefattr);
      if (!hrefattr) return NS_ERROR_FAILURE;   


      nsEmbedCString hrefc,linkc;
      hrefc.Assign(hrefattr);

      nsCOMPtr<nsIDOM3Node> domnode = do_QueryInterface(domDoc);
      if(!domnode) return NS_ERROR_FAILURE;
      
      nsEmbedString spec;
      domnode->GetBaseURI(spec);

      nsEmbedCString cSpec;
      NS_UTF16ToCString(spec,
                    NS_CSTRING_ENCODING_UTF8, cSpec);

      nsCOMPtr<nsIURI> baseURI;
      NewURI(getter_AddRefs(baseURI), cSpec.get());
      
      nsresult rv = baseURI->Resolve(hrefc,linkc);

      *url = g_strdup(linkc.get());

      g_free(hrefattr);

      return NS_OK;
}

nsresult
KzMozWrapper::GetLinkAndTitleFromNode (nsIDOMDocument *domDoc, nsIDOMNode *node,
                                 gchar **url, gchar **title)
{
      nsresult rv;
      const PRUnichar hrefLiteral[] = { 'h', 'r', 'e', 'f', '\0'};
      
      if (title) *title = NULL;
      if (url) *url = NULL;

      // get url
      GetLinkFromNode(domDoc, node, url);

      // get title
      nsCOMPtr<nsIDOMNamedNodeMap> attributes;
      node->GetAttributes(getter_AddRefs(attributes));

      nsCOMPtr<nsIDOMNode> hrefNode;
      attributes->GetNamedItem(nsEmbedString(hrefLiteral), getter_AddRefs(hrefNode));
      if (!hrefNode) return NS_ERROR_FAILURE;

      nsEmbedString linkhtml;
      nsCOMPtr<nsIDOMNSHTMLElement> nsElement;

      nsElement = do_QueryInterface(node);
      if (!nsElement) return NS_ERROR_FAILURE;

      rv = nsElement->GetInnerHTML(linkhtml);
      if (NS_SUCCEEDED(rv) && linkhtml.Length()) 
      {
            nsEmbedCString cLinkhtml;
            NS_UTF16ToCString(linkhtml,
                          NS_CSTRING_ENCODING_UTF8, cLinkhtml);
            *title = g_strdup(cLinkhtml.get());
      }

      return NS_OK;
}

nsresult
KzMozWrapper::GetPostData (nsIHistoryEntry *he, nsAString &postData)
{
      nsresult rv;

      nsCOMPtr<nsISHEntry> she = do_QueryInterface (he);

      nsCOMPtr<nsIInputStream> iStream;

      rv = she->GetPostData(getter_AddRefs(iStream));

      if (!iStream || NS_FAILED(rv)) return NS_ERROR_FAILURE;

      char *aBuf;
      PRUint32 aCount;
      PRUint32 ret;

      rv = iStream->Read(aBuf, 1024, &ret);

      g_warning("%s", aBuf);  

      return rv;
}     

nsresult
KzMozWrapper::SetPostData (nsIHistoryEntry *he, const nsAString &postData)
{
      nsresult rv;
#if 0
      nsCOMPtr<nsISHEntry> she = do_QueryInterface (he);

      nsCOMPtr<nsIInputStream> iStream;

      rv = NS_NewStringInputStream (getter_AddRefs(iStream), postData);
      if (!iStream || NS_FAILED(rv)) return NS_ERROR_FAILURE;

      rv = she->SetPostData(iStream);
#endif
      return rv;
}

// this function is picked from galeon-1.3.18
nsresult 
KzMozWrapper::FineScroll (int horiz, int vert)
{
      nsCOMPtr<nsIDOMWindow> DOMWindow;
      GetFocusedDOMWindow (getter_AddRefs(DOMWindow));
      NS_ENSURE_TRUE (DOMWindow, NS_ERROR_FAILURE);

      return DOMWindow->ScrollBy(horiz, vert);
}

nsresult 
KzMozWrapper::PageUp (void)
{
      nsCOMPtr<nsIDOMWindow> DOMWindow;
      GetFocusedDOMWindow (getter_AddRefs(DOMWindow));
      NS_ENSURE_TRUE (DOMWindow, NS_ERROR_FAILURE);

      return DOMWindow->ScrollByPages(-1);
}

nsresult 
KzMozWrapper::PageDown (void)
{
      nsCOMPtr<nsIDOMWindow> DOMWindow;
      GetFocusedDOMWindow (getter_AddRefs(DOMWindow));
      NS_ENSURE_TRUE (DOMWindow, NS_ERROR_FAILURE);

      return DOMWindow->ScrollByPages(1);
}

nsresult 
KzMozWrapper::AddSelectionListener (void)
{
      if (!mKzMozSelectionListener) return NS_ERROR_FAILURE;
      return mKzMozSelectionListener->AddSelectionListener();
}


nsresult 
KzMozWrapper::RemoveSelectionListener (void)
{
      if (!mKzMozSelectionListener) return NS_ERROR_FAILURE;
      return mKzMozSelectionListener->RemoveSelectionListener();
}


nsresult
KzMozWrapper::GetBodyNode (nsIDOMNode **bodyNode)
{
      nsCOMPtr<nsIDOMDocument> domDoc;
        nsresult rv = GetMainDomDocument(getter_AddRefs(domDoc));
        if (NS_FAILED(rv) || !domDoc) return NS_ERROR_FAILURE;
      
      nsCOMPtr<nsIDOMHTMLDocument> htmlDoc = do_QueryInterface(domDoc);
      if (!htmlDoc) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMHTMLElement> bodyElement;
      htmlDoc->GetBody(getter_AddRefs(bodyElement));

      if (!bodyElement) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMNode> node;
      node = do_QueryInterface(bodyElement);

      NS_IF_ADDREF(*bodyNode = node);
      return NS_OK;
}

nsresult
KzMozWrapper::SetHighlightRange (nsIDOMRange **aSearchRange,
                         nsIDOMRange **aStartRange,
                         nsIDOMRange **aEndRange)
{
      nsCOMPtr<nsIDOMDocument> domDoc;
        nsresult rv = GetMainDomDocument(getter_AddRefs(domDoc));
        if (NS_FAILED(rv) || !domDoc) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMNode> bodyNode;
      rv = GetBodyNode(getter_AddRefs(bodyNode));
        if (NS_FAILED(rv) || !bodyNode) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMNodeList> domNodeList;
      bodyNode->GetChildNodes(getter_AddRefs(domNodeList));
      if (!domNodeList) return NS_ERROR_FAILURE;

      PRUint32 length;
      domNodeList->GetLength(&length);
      
      nsCOMPtr<nsIDOMDocumentRange> docRange = do_QueryInterface(domDoc);
      if (!docRange) return NS_ERROR_FAILURE;

      nsCOMPtr<nsIDOMRange>searchRange;
      nsCOMPtr<nsIDOMRange>startRange;
      nsCOMPtr<nsIDOMRange>endRange;

      docRange->CreateRange(getter_AddRefs(searchRange));
      docRange->CreateRange(getter_AddRefs(startRange));
      docRange->CreateRange(getter_AddRefs(endRange));

      searchRange->SetStart(bodyNode, 0);
      searchRange->SetEnd(bodyNode, length);

      startRange->SetStart(bodyNode, 0);
      startRange->SetEnd(bodyNode, 0);

      endRange->SetStart(bodyNode, length);
      endRange->SetEnd(bodyNode, length);

      NS_IF_ADDREF(*aSearchRange = searchRange);
      NS_IF_ADDREF(*aStartRange = startRange);
      NS_IF_ADDREF(*aEndRange = endRange);
      return NS_OK;
}

nsresult
KzMozWrapper::GetAllowJavascript (PRBool *aAllow)
{
      nsresult result;

      nsCOMPtr<nsIDocShell> DocShell;
      result = GetDocShell (getter_AddRefs(DocShell));
      if (NS_FAILED(result) || !DocShell) return NS_ERROR_FAILURE;

      return DocShell->GetAllowJavascript(aAllow);
}

nsresult
KzMozWrapper::SetAllowJavascript (PRBool aAllow)
{
      nsresult result;

      nsCOMPtr<nsIDocShell> DocShell;
      result = GetDocShell (getter_AddRefs(DocShell));
      if (NS_FAILED(result) || !DocShell) return NS_ERROR_FAILURE;

      return DocShell->SetAllowJavascript(aAllow);
}

nsresult
KzMozWrapper::GetAllowImages (PRBool *aAllow)
{
      nsresult result;

      nsCOMPtr<nsIDocShell> DocShell;
      result = GetDocShell (getter_AddRefs(DocShell));
      if (NS_FAILED(result) || !DocShell) return NS_ERROR_FAILURE;

      return DocShell->GetAllowImages(aAllow);
}

nsresult
KzMozWrapper::SetAllowImages (PRBool aAllow)
{
      nsresult result;

      nsCOMPtr<nsIDocShell> DocShell;
      result = GetDocShell (getter_AddRefs(DocShell));
      if (NS_FAILED(result) || !DocShell) return NS_ERROR_FAILURE;

      return DocShell->SetAllowImages(aAllow);
}


Generated by  Doxygen 1.6.0   Back to index