diff options
author | Taru Karttunen <taruti@taruti.net> | 2011-03-30 15:46:40 +0300 |
---|---|---|
committer | Taru Karttunen <taruti@taruti.net> | 2011-03-30 15:46:40 +0300 |
commit | e5888a1ffdae813d7575f5fb02275c6bb07e5199 (patch) | |
tree | d8d51eac403f07814b9e936eed0c9a79195e2450 /sys/src/cmd/aux/antiword/saveas.c |
Import sources from 2011-03-30 iso image
Diffstat (limited to 'sys/src/cmd/aux/antiword/saveas.c')
-rwxr-xr-x | sys/src/cmd/aux/antiword/saveas.c | 387 |
1 files changed, 387 insertions, 0 deletions
diff --git a/sys/src/cmd/aux/antiword/saveas.c b/sys/src/cmd/aux/antiword/saveas.c new file mode 100755 index 000000000..678ff045d --- /dev/null +++ b/sys/src/cmd/aux/antiword/saveas.c @@ -0,0 +1,387 @@ +/* + * saveas.c + * Copyright (C) 1998-2001 A.J. van Os; Released under GPL + * + * Description: + * Functions to save the results as a textfile or a drawfile + */ + +#include <stdio.h> +#include <string.h> +#include "DeskLib:Menu.h" +#include "DeskLib:Save.h" +#include "DeskLib:Template.h" +#include "DeskLib:Window.h" +#include "drawfile.h" +#include "antiword.h" + +/* The window handle of the save window */ +static window_handle tSaveWindow = 0; + +/* Xfer_send box fields */ +#define DRAG_SPRITE 3 +#define OK_BUTTON 0 +#define CANCEL_BUTTON (-1) +#define FILENAME_ICON 2 + + +/* + * saveas - a wrapper around Save_InitSaveWindowhandler + */ +static void +saveas(int iFileType, char *szOutfile, size_t tEstSize, + save_filesaver save_function, void *pvReference) +{ + TRACE_MSG("saveas"); + + if (tSaveWindow == 0) { + tSaveWindow = Window_Create("xfer_send", template_TITLEMIN); + } + Icon_SetText(tSaveWindow, FILENAME_ICON, szOutfile); + Window_Show(tSaveWindow, open_UNDERPOINTER); + (void)Save_InitSaveWindowHandler(tSaveWindow, FALSE, TRUE, TRUE, + DRAG_SPRITE, OK_BUTTON, CANCEL_BUTTON, FILENAME_ICON, + save_function, NULL, NULL, tEstSize, iFileType, pvReference); +} /* end of saveas */ + +static BOOL +bWrite2File(void *pvBytes, size_t tSize, FILE *pFile, const char *szFilename) +{ + if (fwrite(pvBytes, sizeof(char), tSize, pFile) != tSize) { + werr(0, "I can't write to '%s'", szFilename); + return FALSE; + } + return TRUE; +} /* end of bWrite2File */ + +/* + * bText2File - Save the generated draw file to a Text file + */ +static BOOL +bText2File(char *szFilename, void *pvHandle) +{ + FILE *pFile; + diagram_type *pDiag; + drawfile_object *pObj; + drawfile_text *pText; + const char *pcTmp; + int iToGo, iX, iYtopPrev, iHeight, iLines; + BOOL bFirst, bIndent, bSuccess; + + TRACE_MSG("bText2File"); + + fail(szFilename == NULL || szFilename[0] == '\0'); + fail(pvHandle == NULL); + + DBG_MSG(szFilename); + + pDiag = (diagram_type *)pvHandle; + pFile = fopen(szFilename, "w"); + if (pFile == NULL) { + werr(0, "I can't open '%s' for writing", szFilename); + return FALSE; + } + bFirst = TRUE; + iYtopPrev = 0; + iHeight = (int)lWord2DrawUnits20(DEFAULT_FONT_SIZE); + bSuccess = TRUE; + fail(pDiag->tInfo.length < offsetof(drawfile_diagram, objects)); + iToGo = pDiag->tInfo.length - offsetof(drawfile_diagram, objects); + DBG_DEC(iToGo); + pcTmp = (const char *)pDiag->tInfo.data + + offsetof(drawfile_diagram, objects); + while (iToGo > 0 && bSuccess) { + pObj = (drawfile_object *)pcTmp; + switch (pObj->type) { + case drawfile_TYPE_TEXT: + pText = &pObj->data.text; + /* Compute the number of lines */ + iLines = (iYtopPrev - pText->bbox.max.y + + iHeight / 2) / iHeight; + DBG_DEC_C(iLines < 0, iYtopPrev); + DBG_DEC_C(iLines < 0, pText->bbox.max.y); + fail(iLines < 0); + bIndent = iLines > 0 || bFirst; + bFirst = FALSE; + /* Print the newlines */ + while (iLines > 0 && bSuccess) { + bSuccess = bWrite2File("\n", + 1, pFile, szFilename); + iLines--; + } + /* Print the indentation */ + if (bIndent && bSuccess) { + for (iX = Drawfile_ScreenToDraw(8); + iX <= pText->bbox.min.x && bSuccess; + iX += Drawfile_ScreenToDraw(16)) { + bSuccess = bWrite2File(" ", + 1, pFile, szFilename); + } + } + if (!bSuccess) { + break; + } + /* Print the text object */ + bSuccess = bWrite2File(pText->text, + strlen(pText->text), pFile, szFilename); + /* Setup for the next object */ + iYtopPrev = pText->bbox.max.y; + iHeight = pText->bbox.max.y - pText->bbox.min.y; + break; + case drawfile_TYPE_FONT_TABLE: + case drawfile_TYPE_PATH: + case drawfile_TYPE_SPRITE: + case drawfile_TYPE_JPEG: + /* These are not relevant in a textfile */ + break; + default: + DBG_DEC(pObj->type); + bSuccess = FALSE; + break; + } + pcTmp += pObj->size; + iToGo -= pObj->size; + } + DBG_DEC_C(iToGo != 0, iToGo); + if (bSuccess) { + bSuccess = bWrite2File("\n", 1, pFile, szFilename); + } + (void)fclose(pFile); + if (bSuccess) { + vSetFiletype(szFilename, FILETYPE_TEXT); + } else { + (void)remove(szFilename); + werr(0, "Unable to save textfile '%s'", szFilename); + } + return bSuccess; +} /* end of bText2File */ + +/* + * bSaveTextfile - save the diagram as a text file + */ +BOOL +bSaveTextfile(event_pollblock *pEvent, void *pvReference) +{ + diagram_type *pDiag; + size_t tRecLen, tNbrRecs, tEstSize; + + TRACE_MSG("bSaveTextfile"); + + fail(pEvent == NULL); + fail(pvReference == NULL); + + pDiag = (diagram_type *)pvReference; + + switch (pEvent->type) { + case event_SEND: /* From a menu */ + fail(pEvent->data.message.header.action != message_MENUWARN); + if (menu_currentopen != pDiag->pSaveMenu || + pEvent->data.message.data.menuwarn.selection[0] != + SAVEMENU_SAVETEXT) { + return FALSE; + } + break; + case event_KEY: /* From a key short cut */ + if (pEvent->data.key.caret.window != pDiag->tMainWindow) { + return FALSE; + } + break; + default: + DBG_DEC(pEvent->type); + return FALSE; + } + + tRecLen = sizeof(drawfile_text) + DEFAULT_SCREEN_WIDTH * 2 / 3; + tNbrRecs = pDiag->tInfo.length / tRecLen + 1; + tEstSize = tNbrRecs * DEFAULT_SCREEN_WIDTH * 2 / 3; + DBG_DEC(tEstSize); + + saveas(FILETYPE_TEXT, "WordText", tEstSize, bText2File, pDiag); + return TRUE; +} /* end of bSaveTextfile */ + +/* + * bDraw2File - Save the generated draw file to a Draw file + * + * Remark: This is not a simple copy action. The origin of the + * coordinates (0,0) must move from the top-left corner to the + * bottom-left corner. + */ +static BOOL +bDraw2File(char *szFilename, void *pvHandle) +{ + FILE *pFile; + diagram_type *pDiagram; + wimp_box *pBbox; + drawfile_object *pObj; + drawfile_text *pText; + drawfile_path *pPath; + drawfile_sprite *pSprite; + drawfile_jpeg *pJpeg; + int *piPath; + char *pcTmp; + int iYadd, iToGo, iSize; + BOOL bSuccess; + + TRACE_MSG("bDraw2File"); + + fail(szFilename == NULL || szFilename[0] == '\0'); + fail(pvHandle == NULL); + + NO_DBG_MSG(szFilename); + + pDiagram = (diagram_type *)pvHandle; + pFile = fopen(szFilename, "wb"); + if (pFile == NULL) { + werr(0, "I can't open '%s' for writing", szFilename); + return FALSE; + } + iToGo = pDiagram->tInfo.length; + DBG_DEC(iToGo); + pcTmp = pDiagram->tInfo.data; + bSuccess = bWrite2File(pcTmp, + offsetof(drawfile_diagram, bbox), pFile, szFilename); + if (bSuccess) { + pcTmp += offsetof(drawfile_diagram, bbox); + iToGo -= offsetof(drawfile_diagram, bbox); + pBbox = (wimp_box *)pcTmp; + iYadd = -pBbox->min.y; + pBbox->min.y += iYadd; + pBbox->max.y += iYadd; + bSuccess = bWrite2File(pcTmp, + sizeof(*pBbox), pFile, szFilename); + iToGo -= sizeof(*pBbox); + DBG_DEC(iToGo); + pcTmp += sizeof(*pBbox); + } else { + iYadd = 0; + } + while (iToGo > 0 && bSuccess) { + pObj = (drawfile_object *)pcTmp; + iSize = pObj->size; + switch (pObj->type) { + case drawfile_TYPE_FONT_TABLE: + bSuccess = bWrite2File(pcTmp, + iSize, pFile, szFilename); + pcTmp += iSize; + iToGo -= iSize; + break; + case drawfile_TYPE_TEXT: + pText = &pObj->data.text; + /* First correct the coordinates */ + pText->bbox.min.y += iYadd; + pText->bbox.max.y += iYadd; + pText->base.y += iYadd; + /* Now write the information to file */ + bSuccess = bWrite2File(pcTmp, + iSize, pFile, szFilename); + pcTmp += pObj->size; + iToGo -= pObj->size; + break; + case drawfile_TYPE_PATH: + pPath = &pObj->data.path; + /* First correct the coordinates */ + pPath->bbox.min.y += iYadd; + pPath->bbox.max.y += iYadd; + /* Now write the information to file */ + bSuccess = bWrite2File(pPath, + sizeof(*pPath), pFile, szFilename); + pcTmp += sizeof(*pPath); + iSize = pObj->size - sizeof(*pPath); + fail(iSize < 14 * sizeof(int)); + /* Second correct the path coordinates */ + piPath = xmalloc(iSize); + memcpy(piPath, pcTmp, iSize); + piPath[ 2] += iYadd; + piPath[ 5] += iYadd; + piPath[ 8] += iYadd; + piPath[11] += iYadd; + if (bSuccess) { + bSuccess = bWrite2File(piPath, + iSize, pFile, szFilename); + pcTmp += iSize; + } + piPath = xfree(piPath); + iToGo -= pObj->size; + break; + case drawfile_TYPE_SPRITE: + pSprite = &pObj->data.sprite; + /* First correct the coordinates */ + pSprite->bbox.min.y += iYadd; + pSprite->bbox.max.y += iYadd; + /* Now write the information to file */ + bSuccess = bWrite2File(pcTmp, + iSize, pFile, szFilename); + pcTmp += pObj->size; + iToGo -= pObj->size; + break; + case drawfile_TYPE_JPEG: + pJpeg = &pObj->data.jpeg; + /* First correct the coordinates */ + pJpeg->bbox.min.y += iYadd; + pJpeg->bbox.max.y += iYadd; + pJpeg->trfm.entries[2][1] += iYadd; + /* Now write the information to file */ + bSuccess = bWrite2File(pcTmp, + iSize, pFile, szFilename); + pcTmp += pObj->size; + iToGo -= pObj->size; + break; + default: + DBG_DEC(pObj->type); + bSuccess = FALSE; + break; + } + } + DBG_DEC_C(iToGo != 0, iToGo); + (void)fclose(pFile); + if (bSuccess) { + vSetFiletype(szFilename, FILETYPE_DRAW); + } else { + (void)remove(szFilename); + werr(0, "Unable to save drawfile '%s'", szFilename); + } + return bSuccess; +} /* end of bDraw2File */ + +/* + * bSaveDrawfile - save the diagram as a draw file + */ +BOOL +bSaveDrawfile(event_pollblock *pEvent, void *pvReference) +{ + diagram_type *pDiag; + size_t tEstSize; + + TRACE_MSG("bSaveDrawfile"); + + fail(pEvent == NULL); + fail(pvReference == NULL); + + pDiag = (diagram_type *)pvReference; + + switch (pEvent->type) { + case event_SEND: /* From a menu */ + fail(pEvent->data.message.header.action != message_MENUWARN); + if (menu_currentopen != pDiag->pSaveMenu || + pEvent->data.message.data.menuwarn.selection[0] != + SAVEMENU_SAVEDRAW) { + return FALSE; + } + break; + case event_KEY: /* From a key short cut */ + if (pEvent->data.key.caret.window != pDiag->tMainWindow) { + return FALSE; + } + break; + default: + DBG_DEC(pEvent->type); + return FALSE; + } + + tEstSize = pDiag->tInfo.length; + DBG_DEC(tEstSize); + + saveas(FILETYPE_DRAW, "WordDraw", tEstSize, bDraw2File, pDiag); + return TRUE; +} /* end of bSaveDrawfile */ |