Mozilla/mozilla/cmd/xfe/src/BrowserDrop.cpp
dmose%mozilla.org 83e38c06cc updated license boilerplate to xPL v1.1
git-svn-id: svn://10.0.0.236/trunk@52594 18797224-902f-48f8-a5cc-f745e15eee43
1999-11-02 22:43:10 +00:00

240 lines
6.6 KiB
C++

/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
*
* The contents of this file are subject to the Netscape Public
* License Version 1.1 (the "License"); you may not use this file
* except in compliance with the License. You may obtain a copy of
* the License at http://www.mozilla.org/NPL/
*
* Software distributed under the License is distributed on an "AS
* IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
* implied. See the License for the specific language governing
* rights and limitations under the License.
*
* The Original Code is mozilla.org code.
*
* The Initial Developer of the Original Code is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All
* Rights Reserved.
*
* Contributor(s):
*/
/*
BrowserDrop.cpp -- class definition for the browser drop class
Created: Alastair Gourlay <sgidev@netscape.com>, 1-Jan-96.
*/
#include "BrowserDrop.h"
#ifdef DEBUG_sgidev
#define XDEBUG(x) x
#else
#define XDEBUG(x)
#endif
//
// XFE_BrowserDrop class
//
// constructor
XFE_BrowserDrop::XFE_BrowserDrop(Widget parent,XFE_BrowserFrame *browserFrame)
: XFE_DropNetscape(parent)
{
_browserFrame=browserFrame;
_jsList=NULL;
_sameDragSource=False;
}
XFE_BrowserDrop::~XFE_BrowserDrop()
{
if (_jsList)
cleanupJsList();
}
void XFE_BrowserDrop::targets()
{
_numTargets=2;
_targets=new Atom[_numTargets];
_targets[0]=_XA_NETSCAPE_URL;
_targets[1]=XA_STRING;
acceptFileTargets();
}
void XFE_BrowserDrop::operations()
{
// always copy - move/link irrelevant
_operations=(unsigned int)XmDROP_COPY;
}
// wrapper for JavaScript event callback
void XFE_BrowserDrop::JsDropEventCb(MWContext*,LO_Element*,int32,void* closure, ETEventStatus status)
{
if (closure) {
XFE_BrowserDrop *bd=(XFE_BrowserDrop*)closure;
bd->jsDropEventCb(status);
}
}
int XFE_BrowserDrop::processTargets(Atom *targets,const char **data,int numItems)
{
int i;
XDEBUG(printf("XFE_BrowserDrop::processTargets()\n"));
_sameDragSource=False;
if (!targets || !data || numItems==0)
return FALSE;
// build list of dropped URLs for event JS dragdrop handler
// count # of items in list (need to expand multi-item NetscapeURL data)
int urlCount=0;
for (i=0;i<numItems;i++) {
if (targets[i]==None || data[i]==NULL || strlen(data[i])==0)
continue;
if (targets[i]==_XA_FILE_NAME) urlCount++;
else if (targets[i]==XA_STRING) urlCount++;
else if (targets[i]==_XA_NETSCAPE_URL) {
XFE_URLDesktopType urlData(data[i]);
urlCount+=urlData.numItems();
}
}
_jsList=new char*[urlCount+1];
int listSize=0;
for (i=0;i<numItems;i++) {
if (targets[i]==None || data[i]==NULL || strlen(data[i])==0)
continue;
XDEBUG(printf(" [%d] %s: \"%s\"\n",i,XmGetAtomName(XtDisplay(_widget),targets[i]),data[i]));
if (targets[i]==_XA_FILE_NAME) {
char *address=(char*)XP_ALLOC(5+strlen(data[i])+1); // "file:" + filename + \0
sprintf(address,"file:%s",data[i]);
_jsList[listSize++]=address;
}
if (targets[i]==_XA_NETSCAPE_URL) {
XFE_URLDesktopType urlData(data[i]);
for (int j=0;j<urlData.numItems();j++) {
_jsList[listSize++]=XP_STRDUP(urlData.url(j));
}
}
if (targets[i]==XA_STRING) {
_jsList[listSize++]=XP_STRDUP(data[i]);
}
}
_jsList[listSize]=NULL;
// bail if there are no valid URL's
if (listSize==0) {
cleanupJsList();
return FALSE;
}
// detect drag from the same browser window
if (XFE_DragBase::_activeDragShell) {
Widget shell=_widget;
while (!XtIsShell(shell)) shell=XtParent(shell);
if (shell==XFE_DragBase::_activeDragShell) {
_sameDragSource=True;
}
}
// build JavaScript DRAGDROP event struct
MWContext *context=_browserFrame->getContext();
if (context) {
JSEvent *jsEvent = XP_NEW_ZAP(JSEvent);
jsEvent->type = EVENT_DRAGDROP;
jsEvent->x=_dropEventX;
jsEvent->y=_dropEventY;
jsEvent->docx=_dropEventX + CONTEXT_DATA(context)->document_x;
jsEvent->docy=_dropEventY + CONTEXT_DATA(context)->document_y;
Position rootX=0;Position rootY=0;
XtTranslateCoords(_widget,_dropEventX,_dropEventY,&rootX,&rootY);
jsEvent->screenx=rootX;
jsEvent->screeny=rootY;
jsEvent->which=0; // Motif drag and drop doesn't give us the Button events
jsEvent->modifiers=0; // Motif drag and drop doesn't give us the Button events
jsEvent->data=_jsList;
jsEvent->dataSize=listSize;
ET_SendEvent(context, NULL, jsEvent, JsDropEventCb, (void*)this);
}
// URL's will be loaded by event handler, if approved by page's JavaScript handler.
return TRUE;
}
void XFE_BrowserDrop::jsDropEventCb(int status)
{
XDEBUG(printf("XFE_BrowserDrop::jsDropEventCb(%d)\n",status));
// Load URLs if no event handler present, or if event handler said ok.
// Note: We ignore the drop if it originated from the same browser window.
// (We let JavaScript have it, but if it's not interested then the default UI
// is to disallow it.)
if (_jsList && status==0 && !_sameDragSource) {
// open dropped URLs in browser
int i=0;
while (_jsList[i]) {
loadURL(_jsList[i], i!=0);
i++;
}
}
// free the drop data
cleanupJsList();
return;
}
// defined in mozilla.c - cancels timer which loads homepage after sploosh screen
extern "C" void plonk_cancel();
void XFE_BrowserDrop::loadURL(const char *url,int newFrame)
{
if (!url)
return;
// cancel initial sploosh-screen loader timeout
plonk_cancel();
URL_Struct *urlStruct = NET_CreateURLStruct (url,NET_DONT_RELOAD);
if (!newFrame
#ifdef MOZ_MAIL_NEWS
|| !MSG_RequiresBrowserWindow(urlStruct->address)
#endif
) {
_browserFrame->getURL(urlStruct);
fe_UserActivity(_browserFrame->getContext());
}
else {
XFE_BrowserFrame *newFrame=new XFE_BrowserFrame(XtParent(_browserFrame->getBaseWidget()), _browserFrame, (Chrome *)NULL);
newFrame->show();
newFrame->getURL(urlStruct);
fe_UserActivity(newFrame->getContext());
}
}
void XFE_BrowserDrop::cleanupJsList()
{
if (_jsList) {
int i=0;
while (_jsList[i])
XP_FREE(_jsList[i++]);
delete _jsList;
_jsList=NULL;
}
}