📄 readpart.c
字号:
/* * $Id: ReadPart.C,v 1.3 2000/05/07 12:26:12 fnevgeny Exp $ * * Copyright (c) 1994 HAL Computer Systems International, Ltd. * * HAL COMPUTER SYSTEMS INTERNATIONAL, LTD. * 1315 Dell Avenue * Campbell, CA 95008 * * Author: Greg Hilton * Contributors: Tom Lang, Frank Bieser, and others * * 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 * of the License, 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. * * http://www.gnu.org/copyleft/gpl.html * * 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. */#include <config.h>#include "ReadWinC.h"#include "ReadWinP.h"#include "ReadIconC.h"#include "MsgPartC.h"#include "LoginWinC.h"#include "ParamC.h"#include "Mailcap.h"#include "LocalTextWinC.h"#include "MsgC.h"#include "Query.h"#include "Misc.h"#include "Fork.h"#include "FileMsgC.h"#include "FileChooserWinC.h"#include "FileMisc.h"#include "IshAppC.h"#include "AppPrefC.h"#include <hgl/WXmString.h>#include <hgl/PtrListC.h>#include <hgl/WArgList.h>#include <hgl/HalAppC.h>#include <hgl/rsrc.h>#include <hgl/SysErr.h>#include <hgl/PixmapC.h>#include <hgl/StringListC.h>#include <hgl/TextMisc.h>#include <Xm/RowColumn.h> // For XmMenuPosition#include <Xm/MessageB.h>#include <Xm/PushB.h>#include <Xm/Protocols.h>#include <Xm/AtomMgr.h>#include <unistd.h>#include <errno.h>#include <signal.h>extern int debuglev;/*----------------------------------------------------------------------- * Handle display of mime popup menu */voidReadWinP::PostPartMenu(ReadIconC *icon, ReadWinP *This){ MsgPartC *part = icon->part; MailcapC *mcap = MailcapEntry(part); Boolean getting = (This->FetchData(part) != NULL); Boolean showing = (This->DisplayData(icon) != NULL); Boolean showOk = (!showing && !getting && !icon->textWin && !icon->msgWin); Boolean hideOk = (showing || icon->textWin || icon->msgWin); Boolean fetchOk = (part->IsExternal() && !getting && !showing && !part->IsLocal()); Boolean printOk = (!getting && (part->IsText() || part->IsPostScript() || part->Is822() || (mcap && mcap->print.size() > 0)) ); XtSetSensitive(This->mimePUShowPB, showOk); XtSetSensitive(This->mimePUHidePB, hideOk); XtSetSensitive(This->mimePUPrintPB, printOk); XtSetSensitive(This->mimePUFetchPB, fetchOk); WXmString wstr = (char *)icon->showStr; XtVaSetValues(This->mimePUShowPB, XmNlabelString, (XmString)wstr, NULL); wstr = (char *)icon->hideStr; XtVaSetValues(This->mimePUHidePB, XmNlabelString, (XmString)wstr, NULL);//// Display parameters// StringC desc; ParamC *param = part->conParams; while ( param ) { if ( desc.size() > 0 ) desc += '\n'; desc += param->full; param = param->next; } param = part->accParams; while ( param ) { if ( desc.size() > 0 ) desc += '\n'; desc += param->full; param = param->next; } wstr = (char *)desc; XtVaSetValues(This->mimePULabel, XmNlabelString, (XmString)wstr, NULL); This->popupIcon = icon; XmMenuPosition(This->mimePU, icon->lastEvent); XtManageChild(This->mimePU);} // End PostPartMenu/*----------------------------------------------------------------------- * Handle double-click on mime part */voidReadWinP::HandleDoubleClick(ReadIconC *icon, ReadWinP *This){ This->popupIcon = icon; if ( icon->Highlighted() ) DoHidePart(NULL, This, NULL); else DoShowPart(NULL, This, NULL);}/*----------------------------------------------------------------------- * Callback request for display of mime attachment */voidReadWinP::DoShowPart(Widget, ReadWinP *This, XtPointer){ This->ShowIcon(This->popupIcon);//// If this part is in a parallel multipart, show siblings.// MsgPartC *part = This->popupIcon->part; if ( part->parent && part->parent->IsParallel() ) { MsgPartC *child = part->parent->child; while ( child ) {//// Display the child if it's not the original one and it's not already// displayed// ReadIconC *icon = This->IconWithPart(child); if ( child != part && !icon->Highlighted() ) This->ShowIcon(icon); child = child->next; } } // End if part in parallel} // End DoShowPart/*----------------------------------------------------------------------- * Method to display an attachment */voidReadWinP::ShowIcon(ReadIconC *icon){ if ( icon->Highlighted() ) { if ( icon->textWin ) icon->textWin->Show(); if ( icon->msgWin ) icon->msgWin->Show(); return; } MsgPartC *part = icon->part; icon->Highlight();//// See if this part needs to be retrieved first// if ( part->NeedFetch() ) {//// Ask the user if they want to retrieve it// if ( !OkToGet(part, "getString") ) { icon->Unhighlight(); return; }//// Execute the retrieval. Finish the display when the fetch completes// FetchPart(icon, NULL, (CallbackFn*)FinishShowPart); } // End if retrieval is needed else FinishShowPart(icon, this);} // End ShowPart/*----------------------------------------------------------------------- * Finish request for display of MIME attachment. This one is called * after we know the file is present. */voidReadWinP::FinishShowPart(ReadIconC *icon, ReadWinP *This){ This->pub->BusyCursor(True); MsgPartC *part = icon->part; Boolean internalDisplay = False;//// Get the mailcap entry// MailcapC *mcap = MailcapEntry(part); if ( !mcap ) { if ( part->IsText() || part->Is822() ) internalDisplay = True; else { This->NoMailcap(icon); This->pub->BusyCursor(False); return; } } else if ( mcap->present.size() == 0 || mcap->present.Equals("ishmail", IGNORE_CASE) ) internalDisplay = True; This->LoadDisplayPixmaps(icon); icon->Animate(displayPixmaps);//// See if we are to display the text internally// if ( internalDisplay ) { if ( part->Is822() ) This->Show822(icon); else This->ShowText(icon); } else This->ShowExternal(icon, mcap); This->pub->BusyCursor(False);} // End FinishShowPart/*--------------------------------------------------------------- * Method to display a text mime body part internally */voidReadWinP::ShowText(ReadIconC *icon){ MsgPartC *part = icon->part;//// Create a text window// icon->textWin = GetTextWindow(); StringC label; part->GetLabel(label); icon->textWin->SetTitle(label);//// Display the text// StringC body; if ( !part->GetData(body) ) { HideIcon(icon); return; } MsgC *msg = part->parentMsg; icon->textWin->CheckFroms(msg->HasSafeFroms()); if ( part->IsRichText() ) icon->textWin->SetRichString(body); else if ( part->IsEnriched() ) icon->textWin->SetEnrichedString(body); else icon->textWin->SetString(body); icon->textWin->CheckFroms(False); icon->textWin->Show();} // End ShowText/*----------------------------------------------------------------------- * Method to get the next available text window from the text window list. */LocalTextWinC*ReadWinP::GetTextWindow(){ LocalTextWinC *tw = NULL; u_int count = textWinList.size(); Boolean found = False; for (int i=0; !found && i<count; i++) { tw = (LocalTextWinC*)*textWinList[i]; if ( !tw->IsShown() ) found = True; } if ( !found ) { tw = new LocalTextWinC(*pub); tw->AddHideCallback((CallbackFn*)HideTextWin, this); void *tmp = (void*)tw; textWinList.add(tmp); } tw->SetWrap(pub->Wrapping()); tw->SetSize(msgBodyText->RowCount(), msgBodyText->ColumnCount()); return tw;} // End GetTextWindow/*--------------------------------------------------------------- * Method to display an RFC822 mime body part internally */voidReadWinP::Show822(ReadIconC *icon){ MsgPartC *part = icon->part;//// Create a message window// icon->msgWin = GetMsgWindow();//// Display the message// FileMsgC *msg = part->ChildMsg(); icon->msgWin->SetMessage(msg); icon->msgWin->Show();} // End Show822/*----------------------------------------------------------------------- * Method to get the next available message window from the message * window list. */ReadWinC*ReadWinP::GetMsgWindow(){ ReadWinC *rw = NULL; u_int count = msgWinList.size(); Boolean found = False; for (int i=0; !found && i<count; i++) { rw = (ReadWinC*)*msgWinList[i]; if ( !rw->IsShown() ) found = True; } if ( !found ) { rw = new ReadWinC("readWin", *pub, pub); rw->AddHideCallback((CallbackFn*)HideMsgWin, this); void *tmp = (void*)rw; msgWinList.add(tmp); } rw->SetWrap(pub->Wrapping()); rw->SetViewType(pub->ViewType()); rw->SetSize(msgHeadText->RowCount(), msgBodyText->RowCount(), msgBodyText->ColumnCount()); return rw;} // End GetMsgWindow/*--------------------------------------------------------------- * Method to display a mime body part externally */voidReadWinP::ShowExternal(ReadIconC *icon, MailcapC *mcap){ MsgPartC *part = icon->part;//// Make sure there is a data file// if ( !part->CreateDataFile() ) { HideIcon(icon); return; }//// Double check that the file exists and is readable// if ( access(part->dataFile, R_OK) != 0 ) { StringC errmsg = "Could not display file: \""; errmsg += part->dataFile; errmsg += "\".\n"; errmsg += SystemErrorMessage(errno); pub->PopupMessage(errmsg); HideIcon(icon); return; }//// Build a data record to store info about this display// DisplayDataT *data = new DisplayDataT; data->win = this; data->icon = icon;//// Build the command for display.// data->cmdStr = BuildCommand(mcap->present, part, part->dataFile); data->pid = -1; CallbackC doneCb((CallbackFn*)DisplayDone, data); data->pid = ForkIt(data->cmdStr, &doneCb);//// If the pid is < 0, an error occurred// if ( data->pid < 0 ) { pub->PopupMessage(ForkStatusMsg(data->cmdStr, (int)data->pid)); icon->Unhighlight(); delete data; }//// Add this process to the list of running processes// else { void *tmp = (void*)data; displayDataList.add(tmp); }} // End ShowExternal/*--------------------------------------------------------------- * Callback called when external display process stops */voidReadWinP::DisplayDone(int, DisplayDataT *data){ ReadWinP *This = data->win;//// Remove this process from the list of running processes// void *tmp = (void*)data; This->displayDataList.remove(tmp);//// Make sure the icon is still around// ReadIconC *icon = data->icon; PtrListC& list = This->msgBodyText->GraphicList(); u_int count = list.size(); Boolean found = False; for (int i=0; !found && i<count; i++) { ReadIconC *ip = (ReadIconC*)*list[i]; found = (ip == icon); } if ( found ) { if ( debuglev > 0 ) { MsgPartC *part = icon->part; cout <<"DisplayDone for part: " <<part->partNum <<endl; }//// Turn off the display animation// icon->AnimationOff(); icon->Unhighlight();#if 0//// Report status if reading window is longer visible and the process failed// if ( This->pub->IsShown() && This->pub->msg == part->parentMsg && status != 0 ) { StringC statmsg("Part \""); statmsg += name; statmsg += "\" could not be displayed.\n"; statmsg += ForkStatusMsg(data->cmdStr, status, data->pid); This->pub->PopupMessage(statmsg); } // End if display failed#endif } // End if icon still exists delete data; return;} // End DisplayDone/*--------------------------------------------------------------- * Callback to handle press of DONE button in local text window */voidReadWinP::HideTextWin(LocalTextWinC *win, ReadWinP *This){//// Loop through the list of icons and see which one corresponds to this// window// PtrListC& list = This->msgBodyText->GraphicList(); u_int count = list.size(); for (int i=0; i<count; i++) { ReadIconC *icon = (ReadIconC*)*list[i]; if ( icon->textWin == win ) { icon->textWin = NULL; // So it doesn't get hidden again This->HideIcon(icon); return; } }} // End HideTextWin/*--------------------------------------------------------------- * Callback to handle press of close button in message window */voidReadWinP::HideMsgWin(ReadWinC *win, ReadWinP *This)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -