/*
 *  R : A Computer Language for Statistical Data Analysis
 *  file pager.c
 *  Copyright (C) 1998--2002  Guido Masarotto and Brian Ripley
 *  Copyright (C) 2004--8     The R Foundation
 *  Copyright (C) 2004--2020  The R Core Team
 *
 *  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.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program; if not, a copy is available at
 *  https://www.R-project.org/Licenses/
 */

#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include "win-nls.h"

#ifdef Win32
#define USE_MDI 1
#endif

#define WIN32_LEAN_AND_MEAN 1
#include <windows.h>
#include "graphapp/ga.h"
#ifdef USE_MDI
#include "graphapp/stdimg.h"
#endif
#include "console.h"
#include "consolestructs.h"
#include "rui.h"
#include <Startup.h> /* for CharacterMode */

#define CE_UTF8 1
extern size_t Rf_utf8towcs(wchar_t *wc, const char *s, size_t n);

#define PAGERMAXKEPT 12
#define PAGERMAXTITLE 128

static int pagerActualKept = 0, pagerActualShown;
static pager pagerInstance = NULL;
static menubar pagerBar = NULL;
static xbuf pagerXbuf[PAGERMAXKEPT];
static char pagerTitles[PAGERMAXKEPT][PAGERMAXTITLE+8];
static menuitem pagerMenus[PAGERMAXKEPT];
static int pagerRow[PAGERMAXKEPT];
static void pagerupdateview(void);

void menueditoropen(control m);
void menueditornew(control m);

/* from console.c */
extern int pagerMultiple, haveusedapager;


/*
   To be fixed: during creation, memory is allocated two times
   (faster for small files but a big waste otherwise)
*/
static xbuf file2xbuf(const char *name, int enc, int del)
{
    HANDLE f;
    DWORD rr, vv;
    char *p;
    xlong dim, cnt;
    xint  ms;
    xbuf  xb;
    wchar_t *wp, *q;

    if (enc == CE_UTF8) {
	wchar_t wfn[MAX_PATH+1];
	Rf_utf8towcs(wfn, name, MAX_PATH+1);
	f = CreateFileW(wfn, GENERIC_READ, FILE_SHARE_READ,
			NULL, OPEN_EXISTING, 0, NULL);
    } else
	f = CreateFile(name, GENERIC_READ, FILE_SHARE_READ,
		       NULL, OPEN_EXISTING, 0, NULL);
    if (f == INVALID_HANDLE_VALUE) {
	R_ShowMessage(G_("Error opening file"));
	return NULL;
    }
    vv = GetFileSize(f, NULL);
    p = (char *) malloc((size_t) vv + 1);
    if (!p) {
	CloseHandle(f);
	R_ShowMessage(G_("Insufficient memory to display file in internal pager"));
	return NULL;
    }
    ReadFile(f, p, vv, &rr, NULL);
    CloseHandle(f);
    if (del) DeleteFile(name);
    p[rr] = '\0';
    cnt = mbstowcs(NULL, p, 0);
    wp = (wchar_t *) malloc((cnt+1) * sizeof(wchar_t));
    mbstowcs(wp, p, cnt+1);
    for (q = wp, ms = 1, dim = cnt; *q; q++) {
	if (*q == '\t')
	    dim += TABSIZE;
	else if (*q == '\n') {
	    dim++;
	    ms++;
	}
    }
    free(p);
    if ((xb = newxbuf(dim + 1, ms + 1, 1)))
	for (q = wp, ms = 0; *q; q++) {
	    if (*q == L'\r') continue;
	    if (*q == L'\n') {
		ms++;
		xbufaddxc(xb, *q);
		/* next line interprets underlining in help files */
		if (q[1] ==  L'_' && q[2] == L'\b') xb->user[ms] = -2;
	    } else xbufaddxc(xb, *q);
	}
    free(wp);
    return xb;
}

static void delpager(control m)
{
    int i;

    ConsoleData p = getdata(m);
    if (!pagerMultiple) {
	for (i = 0; i < pagerActualKept; i++) xbufdel(pagerXbuf[i]);
	pagerActualKept = 0;
    }
    else
	xbufdel(p->lbuf);
    freeConsoleData(getdata(m));
}

void pagerbclose(control m)
{
    show(RConsole);
    if (!pagerMultiple) {
	hide(pagerInstance);
	del(pagerInstance);
	pagerInstance = pagerBar = NULL;
    }
    else {
	hide(m);
	del(m);
    }
}

static void pagerclose(control m)
{
    pagerbclose(getdata(m));
}

static void pagerprint(control m)
{
    consoleprint(getdata(m));
}

static void pagersavefile(control m)
{
    consolesavefile(getdata(m), 1);
}

static void pagercopy(control m)
{
    control c = getdata(m);

    if (consolecancopy(c)) consolecopy(c);
    else R_ShowMessage(G_("No selection"));
}

static void pagerpaste(control m)
{
    control c = getdata(m);

    if (CharacterMode != RGui) {
	R_ShowMessage(G_("No RGui console to paste to"));
	return;
    }
    if (!consolecancopy(c)) {
	R_ShowMessage(G_("No selection"));
	return;
    } else {
	consolecopy(c);
    }
    if (consolecanpaste(RConsole)) {
	consolepaste(RConsole);
	show(RConsole);
    }
}

static void pagerpastecmds(control m)
{
    control c = getdata(m);

    if (CharacterMode != RGui) {
	R_ShowMessage(G_("No RGui console to paste to"));
	return;
    }
    if (!consolecancopy(c)) {
	R_ShowMessage(G_("No selection"));
	return;
    } else {
	consolecopy(c);
    }
    if (consolecanpaste(RConsole)) {
	consolepastecmds(RConsole);
	show(RConsole);
    }
}

static void pagerselectall(control m)
{
    control c = getdata(m);

    consoleselectall(c);
}

static void pagerstayontop(control m)
{
    control c = getdata(m);

    BringToTop(c, 2);
}

static void pagerconsole(control m)
{
    show(RConsole);
}

static void pagerchangeview(control m)
{
    ConsoleData p = getdata(pagerInstance);
    int i = getvalue(m);

    if (i >= pagerActualKept) return;
    uncheck(pagerMenus[pagerActualShown]);
    /* save position of middle line of pager display */
    pagerRow[pagerActualShown] = FV + ROWS/2;
    pagerActualShown = i;
    check(pagerMenus[i]);
    pagerupdateview();
}

static void pagerupdateview(void)
{
    control c = pagerInstance;
    ConsoleData p = getdata(c);

    settext(pagerInstance, &pagerTitles[pagerActualShown][4]);
    p->lbuf = pagerXbuf[pagerActualShown];
    setfirstvisible(c, pagerRow[pagerActualShown] - ROWS/2);
    setfirstcol(c, 0);
    show(c);
}

static int pageraddfile(const char *wtitle,
			const char *filename, int enc,
			int deleteonexit)
{
    ConsoleData p = getdata(pagerInstance);
    int i;
    xbuf nxbuf = file2xbuf(filename, enc, deleteonexit);

    if (!nxbuf) {
	/* R_ShowMessage("File not found or memory insufficient"); */
	return 0;
    }
    if (pagerActualKept == PAGERMAXKEPT) {
	pagerActualKept -= 1;
	xbufdel(pagerXbuf[pagerActualKept]);
    }
    if(pagerActualKept > 0)
	pagerRow[0] = FV;
    for (i = pagerActualKept; i > 0; i--) {
	pagerXbuf[i] = pagerXbuf[i - 1];
	pagerRow[i] = pagerRow[i - 1];
	strcpy(&pagerTitles[i][4], &pagerTitles[i - 1][4]);
    }
    pagerXbuf[0] = nxbuf;
    pagerRow[0] = 0;
    strcpy(&pagerTitles[0][4], wtitle);
    pagerActualKept += 1;
    for (i = 0; i < pagerActualKept; i++) {
	enable(pagerMenus[i]);
	settext(pagerMenus[i], pagerTitles[i]);
    }
    for (i = pagerActualKept; i < PAGERMAXKEPT; i++)
	disable(pagerMenus[i]);
    uncheck(pagerMenus[pagerActualShown]);
    pagerActualShown = 0;
    check(pagerMenus[pagerActualShown]);
    return 1;
}

static MenuItem PagerPopup[] = {		   /* Numbers used below */
    {GN_("Copy"), pagercopy, 'C', 0},			   /* 0 */
    {GN_("Paste to console"), pagerpaste, 'V', 0},	   /* 1 */
    {GN_("Paste commands to console"), pagerpastecmds, 0, 0},   /* 2 */
    {GN_("Select all"), pagerselectall, 'A', 0},		   /* 3 */
    {"-", 0, 0, 0},
    {GN_("Stay on top"), pagerstayontop, 0, 0},		   /* 5 */
    {"-", 0, 0, 0},
    {GN_("Close"), pagerclose, 0, 0},			   /* 7 */
    LASTMENUITEM
};

static void pagermenuact(control m)
{
    control c = getdata(m);
    ConsoleData p = getdata(c);
    if (consolecancopy(c)) {
	enable(p->mcopy);
	enable(p->mpopcopy);
	if (CharacterMode == RGui) {
	    enable(p->mpaste);
	    enable(p->mpastecmds);
	    enable(p->mpoppaste);
	    enable(p->mpoppastecmds);
	}
    } else {
	disable(p->mcopy);
	disable(p->mpopcopy);
	disable(p->mpaste);
	disable(p->mpastecmds);
	disable(p->mpoppaste);
	disable(p->mpoppastecmds);
    }
    if (ismdi())
	disable(PagerPopup[5].m);
    else {
	enable(PagerPopup[5].m);
	if (isTopmost(c))
	    check(PagerPopup[5].m);
	else
	    uncheck(PagerPopup[5].m);
    }
}


#define MCHECK(a) if (!(a)) {freeConsoleData(p);del(c);return NULL;}
RECT *RgetMDIsize(void); /* in rui.c */

static pager pagercreate(void)
{
    ConsoleData p;
    int w, h, i, x, y, w0, h0;
    pager c;
    menuitem m;

    p = newconsoledata((consolefn) ? consolefn : FixedFont,
		       pagerrow, pagercol, 0, 0,
		       guiColors,
		       PAGER, 0, 0);
    if (!p) return NULL;

/*    if (ismdi()) {
      x = y = w = h = 0;
      }
      else {
      w = WIDTH ;
      h = HEIGHT;
      x = (devicewidth(NULL) - w) / 2;
      y = (deviceheight(NULL) - h) / 2 ;
      } */
    w = WIDTH ;
    h = HEIGHT;
    /* centre a single pager, randomly place each of multiple pagers */
#ifdef USE_MDI
    if(ismdi()) {
	RECT *pR = RgetMDIsize();
	w0 = pR->right;
	h0 = pR->bottom;
    } else {
#endif
	w0 = devicewidth(NULL);
	h0 = deviceheight(NULL);
#ifdef USE_MDI
    }
#endif
    x = (w0 - w) / 2; x = x > 20 ? x:20;
    y = (h0 - h) / 2; y = y > 20 ? y:20;
    if(pagerMultiple) {
#ifdef Win32
	DWORD rand = GetTickCount();
#else
	int rand = 0;
#endif
	int w0 = 0.4*x, h0 = 0.4*y;
	w0 = w0 > 20 ? w0 : 20;
	h0 = h0 > 20 ? h0 : 20;
	x += (rand % w0) - w0/2;
	y += ((rand/w0) % h0) - h0/2;
    }
    c = (pager) newwindow("PAGER", rect(x, y, w, h),
			  Document | StandardWindow | Menubar |
			  VScrollbar | HScrollbar | TrackMouse);
    if (!c) {
	freeConsoleData(p);
	return NULL;
    }
    setdata(c, p);
    if(h == 0) HEIGHT = getheight(c);
    if(w == 0) WIDTH  = getwidth(c);
    COLS = WIDTH / FW - 1;
    ROWS = HEIGHT / FH - 1;
    BORDERX = (WIDTH - COLS*FW) / 2;
    BORDERY = (HEIGHT - ROWS*FH) / 2;
    gsetcursor(c, ArrowCursor);
    gchangescrollbar(c, VWINSB, 0, 0, ROWS, 0);
    gchangescrollbar(c, HWINSB, 0, COLS-1, COLS, 1);
    setbackground(c, guiColors[pagerbg]);
#ifdef USE_MDI
    if (ismdi()) {
	int btsize = 24;
	rect r = rect(2, 2, btsize, btsize);
	control tb, bt;
	addto(c);
	MCHECK(tb = newtoolbar(btsize + 4));
	gsetcursor(tb, ArrowCursor);
	addto(tb);
	MCHECK(bt = newtoolbutton(open_image, r, menueditoropen));
	MCHECK(addtooltip(bt, G_("Open script")));
	gsetcursor(bt, ArrowCursor);
	/* wants NULL as data, not the pager */
	r.x += (btsize + 6) ;
	MCHECK(bt = newtoolbutton(copy1_image, r, pagerpaste));
	MCHECK(addtooltip(bt, G_("Paste to console")));
	gsetcursor(bt, ArrowCursor);
	setdata(bt, (void *) c);
	r.x += (btsize + 6) ;
	MCHECK(bt = newtoolbutton(copy1_image, r, pagerpastecmds));
	MCHECK(addtooltip(bt, G_("Paste commands to console")));
	gsetcursor(bt, ArrowCursor);
	setdata(bt, (void *) c);
	r.x += (btsize + 6) ;
	MCHECK(bt = newtoolbutton(print_image, r, pagerprint));
	MCHECK(addtooltip(bt, G_("Print")));
	gsetcursor(bt, ArrowCursor);
	setdata(bt, (void *) c);
	r.x += (btsize + 6) ;
	MCHECK(bt = newtoolbutton(console_image, r, pagerconsole));
	MCHECK(addtooltip(bt, G_("Return focus to Console")));
	gsetcursor(bt, ArrowCursor);
	setdata(bt, (void *) c);
    }
#endif
    addto(c);
    MCHECK(m = gpopup(pagermenuact, PagerPopup));
    setdata(m, c);
    setdata(p->mpopcopy = PagerPopup[0].m, c);
    setdata(p->mpoppaste = PagerPopup[1].m, c);
    setdata(p->mpoppastecmds = PagerPopup[2].m, c);
    setdata(PagerPopup[3].m, c);
    setdata(PagerPopup[5].m, c);
    setdata(PagerPopup[7].m, c);
    MCHECK(m = newmenubar(pagermenuact));
    setdata(m, c);
    MCHECK(newmenu(G_("File")));
    MCHECK(m = newmenuitem(G_("New script"), 'N', menueditornew));
    MCHECK(m = newmenuitem(G_("Open script..."), 'O', menueditoropen));
    MCHECK(m = newmenuitem(G_("Print..."), 'P', pagerprint));
    setdata(m, c);
    MCHECK(m = newmenuitem(G_("Save to File..."), 'S', pagersavefile));
    setdata(m, c);
    MCHECK(m = newmenuitem("-", 0, NULL));
    MCHECK(m = newmenuitem(G_("Close"), 0, pagerclose));
    setdata(m, c);
    MCHECK(newmenu(G_("Edit")));
    MCHECK(p->mcopy = newmenuitem(G_("Copy"), 'C', pagercopy));
    setdata(p->mcopy, c);
    MCHECK(p->mpaste = newmenuitem(G_("Paste to console"), 'V', pagerpaste));
    setdata(p->mpaste, c);
    MCHECK(p->mpastecmds = newmenuitem(G_("Paste commands to console"), 0, pagerpastecmds));
    setdata(p->mpastecmds, c);
    MCHECK(m = newmenuitem(G_("Select all"), 'A', pagerselectall));
    setdata(m, c);
    if (!pagerMultiple) {
	MCHECK(newmenu(G_("View")));
	for (i = 0; i < PAGERMAXKEPT; i++) {
	    snprintf(pagerTitles[i], PAGERMAXTITLE+8, "&%c.  ", 'A' + i);
	    MCHECK(pagerMenus[i] = newmenuitem(&pagerTitles[i][1], 0,
					       pagerchangeview));
	    setvalue(pagerMenus[i], i);
	}
    }
#ifdef USE_MDI
    if (ismdi()) newmdimenu();
    if (ismdi() && !(RguiMDI & RW_TOOLBAR)) toolbar_hide();
#endif
    MCHECK(BM = newbitmap(WIDTH, HEIGHT, 2));
    setdata(c, p);
    sethit(c, console_sbf);
    setresize(c, consoleresize);
    setredraw(c, drawconsole);
    setdel(c, delpager);
    setclose(c, pagerbclose);
    setkeyaction(c, console_ctrlkeyin);
    setkeydown(c, console_normalkeyin);
    setmousedrag(c, console_mousedrag);
    setmouserepeat(c, console_mouserep);
    setmousedown(c, console_mousedown);
    return(c);
}

static pager newpager1win(const char *wtitle,
			  const char *filename, int enc,
			  int deleteonexit)
{
    if (!pagerInstance && !(pagerInstance = pagercreate())) {
	R_ShowMessage(G_("Unable to create pager window"));
	return NULL;
    }
    if (!pageraddfile(wtitle, filename, enc, deleteonexit)) return NULL;
    pagerupdateview();
    return pagerInstance;
}

static pager newpagerNwin(const char *wtitle,
			  const char *filename, int enc,
			  int deleteonexit)
{
    pager c = pagercreate();
    ConsoleData p;

    if (!c) return NULL;
    settext(c, wtitle);
    p = getdata(c);
    if (!(p->lbuf = file2xbuf(filename, enc, deleteonexit))) {
	del(c);
	return NULL;
    }
    if (c) {
	gchangescrollbar(c, VWINSB, 0, NUMLINES - 1 , ROWS, 0);
	show(c);
    }
    return c;
}

pager newpager(const char *title,
	       const char *filename, int enc,
	       const char *header, int deleteonexit)
{
    char wtitle[PAGERMAXTITLE+1];
    pager c;

    /*    if (ismdi()) pagerMultiple = 1;*/
    strncpy(wtitle, title, PAGERMAXTITLE);
    wtitle[PAGERMAXTITLE] = '\0';
    if(strlen(header) &&
       ((strlen(header) + strlen(wtitle) + 4) < PAGERMAXTITLE)) {
	if(strlen(wtitle)) strcat(wtitle, " - ");
	strcat(wtitle, header);
    }
    if (!pagerMultiple)
	c = newpager1win(wtitle, filename, enc, deleteonexit);
    else
	c = newpagerNwin(wtitle, filename, enc, deleteonexit);
    if (c) {
	haveusedapager++;
	BringToTop(c, 0);
    }
    return c;
}
