Ignore:
Timestamp:
Aug 12, 2002, 5:54:49 PM (23 years ago)
Author:
umoeller
Message:

Minor updates.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/helpers/textview.c

    r201 r206  
    594594
    595595    // current anchor
    596     PSZ             pszCurrentLink;
     596    PCSZ            pcszCurrentLinkTarget;
    597597                        // this is != NULL if we're currently in a link block
    598598                        // and points to an item in XFORMATDATA.llLinks
     
    731731        pWord->flChar = pflbuf->flChar;
    732732
    733         pWord->pszLinkTarget = pflbuf->pszCurrentLink; // 0 if none
     733        pWord->pcszLinkTarget = pflbuf->pcszCurrentLinkTarget; // 0 if none
    734734    }
    735735
     
    837837            if (pEnd = strchr((*ppCurrent) + 2, 0xFF))
    838838            {
    839                 pflbuf->pszCurrentLink = strhSubstr((*ppCurrent) + 2, pEnd);
     839                PSZ pszNewLink = strhSubstr((*ppCurrent) + 2, pEnd);
     840                lstAppendItem(&pxfd->llLinks,
     841                              pszNewLink);
     842
     843                pflbuf->pcszCurrentLinkTarget = pszNewLink;
     844
    840845                ulSkip = pEnd - *ppCurrent + 1;
    841 
    842                 lstAppendItem(&pxfd->llLinks,
    843                               pflbuf->pszCurrentLink);
    844846            }
    845847        }
     
    847849
    848850        case 7:     // /A HREF (end of link)
    849             pflbuf->pszCurrentLink = NULL;
     851            pflbuf->pcszCurrentLinkTarget = NULL;
    850852            ulSkip = 2;
    851853        break;
     
    974976            pEscapeWord->cEscapeCode = *(*ppCurrent + 1);
    975977            pEscapeWord->fPaintEscapeWord = fPaintEscapeWord;
    976             pEscapeWord->pszLinkTarget = pflbuf->pszCurrentLink;
     978            pEscapeWord->pcszLinkTarget = pflbuf->pcszCurrentLinkTarget;
    977979                    // V0.9.20 (2002-08-10) [umoeller]
    978980                    // NULL if none
     
    15011503 *      prcl2Paint.
    15021504 *
    1503  *      -- For WM_PAINT, set this to the
    1504  *         update rectangle, and set fPaintHalfLines
    1505  *         to TRUE.
    1506  *
    1507  *      -- For printing, set this to the page rectangle,
    1508  *         and set fPaintHalfLines to FALSE.
     1505 *      --  For WM_PAINT, set this to the
     1506 *          update rectangle, and set fPaintHalfLines
     1507 *          to TRUE.
     1508 *
     1509 *      --  For printing, set this to the page rectangle,
     1510 *          and set fPaintHalfLines to FALSE.
    15091511 *
    15101512 *      All coordinates are in world space (PU_PELS).
     
    16151617                ULONG flChar = pWordThis->flChar;
    16161618
    1617                 if (pWordThis->pszLinkTarget)       // V0.9.20 (2002-08-10) [umoeller]
     1619                if (pWordThis->pcszLinkTarget)       // V0.9.20 (2002-08-10) [umoeller]
    16181620                    flChar |= CHS_UNDERSCORE;
    16191621
     
    18841886    PLISTNODE   pWordNodeFirstInAnchor;  // points to first word which belongs to anchor
    18851887    // USHORT      usLastAnchorClicked;    // last anchor which was clicked (1-0xFFFF)
    1886     PSZ         pszLastLinkClicked;     // last link that was clicked (points into llLinks)
     1888    PCSZ        pcszLastLinkClicked;     // last link that was clicked (points into llLinks)
     1889                                         // V0.9.20 (2002-08-10) [umoeller]
    18871890
    18881891} TEXTVIEWWINDATA, *PTEXTVIEWWINDATA;
     
    22482251    rclLine.yTop = pLineRcl->rcl.yTop + ptxvd->ulViewYOfs;
    22492252
    2250     if (pWordThis->pszLinkTarget)
     2253    if (pWordThis->pcszLinkTarget)
    22512254        flChar |= CHS_UNDERSCORE;
    22522255
     
    22922295                          LONG lColor)
    22932296{
    2294     PLISTNODE pNode = ptxvd->pWordNodeFirstInAnchor;
    2295     PSZ     pszLinkTarget = NULL;
     2297    PLISTNODE   pNode = ptxvd->pWordNodeFirstInAnchor;
     2298    PCSZ        pcszLinkTarget = NULL;
    22962299    while (pNode)
    22972300    {
    22982301        PTXVWORD pWordThis = (PTXVWORD)pNode->pItemData;
    2299         if (!pszLinkTarget)
     2302        if (!pcszLinkTarget)
    23002303            // first loop:
    2301             pszLinkTarget = pWordThis->pszLinkTarget;
     2304            pcszLinkTarget = pWordThis->pcszLinkTarget;
    23022305        else
    2303             if (pWordThis->pszLinkTarget != pszLinkTarget)
     2306            if (pWordThis->pcszLinkTarget != pcszLinkTarget)
    23042307                // first word with different anchor:
    23052308                break;
     
    23102313        pNode = pNode->pNext;
    23112314    }
     2315}
     2316
     2317/*
     2318 *@@ ProcessCreate:
     2319 *      implementation for WM_CREATE in fnwpTextView.
     2320 *
     2321 *@@added V0.9.21 (2002-08-12) [umoeller]
     2322 */
     2323
     2324static MRESULT ProcessCreate(HWND hwndTextView, MPARAM mp1, MPARAM mp2)
     2325{
     2326    PXTEXTVIEWCDATA     pcd = (PXTEXTVIEWCDATA)mp1;
     2327                // can be NULL
     2328    PCREATESTRUCT       pcs = (PCREATESTRUCT)mp2;
     2329    SBCDATA             sbcd;
     2330
     2331    MRESULT             mrc = (MRESULT)TRUE;     // error
     2332    PTEXTVIEWWINDATA    ptxvd;
     2333
     2334    // allocate TEXTVIEWWINDATA for QWL_PRIVATE
     2335    if (ptxvd = (PTEXTVIEWWINDATA)malloc(sizeof(TEXTVIEWWINDATA)))
     2336    {
     2337        SIZEL   szlPage = {0, 0};
     2338        BOOL    fShow = FALSE;
     2339
     2340        // query message queue
     2341        HMQ hmq = WinQueryWindowULong(hwndTextView, QWL_HMQ);
     2342        // get codepage of message queue
     2343        ULONG ulCodepage = WinQueryCp(hmq);
     2344
     2345        memset(ptxvd, 0, sizeof(TEXTVIEWWINDATA));
     2346        WinSetWindowPtr(hwndTextView, QWL_PRIVATE, ptxvd);
     2347
     2348        ptxvd->hab = WinQueryAnchorBlock(hwndTextView);
     2349
     2350        ptxvd->hdc = WinOpenWindowDC(hwndTextView);
     2351        ptxvd->hps = GpiCreatePS(ptxvd->hab,
     2352                                 ptxvd->hdc,
     2353                                 &szlPage, // use same page size as device
     2354                                 PU_PELS | GPIT_MICRO | GPIA_ASSOC);
     2355
     2356        // copy window style flags V0.9.20 (2002-08-10) [umoeller]
     2357        ptxvd->flStyle = pcs->flStyle;
     2358
     2359        gpihSwitchToRGB(ptxvd->hps);
     2360
     2361        // set codepage; GPI defaults this to
     2362        // the process codepage
     2363        GpiSetCp(ptxvd->hps, ulCodepage);
     2364
     2365        txvInitFormat(&ptxvd->xfd);
     2366
     2367        // copy control data, if present
     2368        if (pcd)
     2369            memcpy(&ptxvd->cdata, pcd, pcd->cbData);
     2370
     2371        // check values which might cause null divisions
     2372        if (ptxvd->cdata.ulVScrollLineUnit == 0)
     2373            ptxvd->cdata.ulVScrollLineUnit = 15;
     2374        if (ptxvd->cdata.ulHScrollLineUnit == 0)
     2375            ptxvd->cdata.ulHScrollLineUnit = 15;
     2376
     2377        ptxvd->fAcceptsPresParamsNow = FALSE;
     2378
     2379        // copy window dimensions from CREATESTRUCT
     2380        ptxvd->rclViewReal.xLeft = 0;
     2381        ptxvd->rclViewReal.yBottom = 0;
     2382        ptxvd->rclViewReal.xRight = pcs->cx;
     2383        ptxvd->rclViewReal.yTop = pcs->cy;
     2384
     2385        sbcd.cb = sizeof(SBCDATA);
     2386        sbcd.sHilite = 0;
     2387        sbcd.posFirst = 0;
     2388        sbcd.posLast = 100;
     2389        sbcd.posThumb = 30;
     2390        sbcd.cVisible = 50;
     2391        sbcd.cTotal = 50;
     2392
     2393        ptxvd->hwndVScroll = WinCreateWindow(hwndTextView,
     2394                                             WC_SCROLLBAR,
     2395                                             "",
     2396                                             SBS_VERT | SBS_THUMBSIZE | WS_VISIBLE,
     2397                                             10, 10,
     2398                                             20, 100,
     2399                                             hwndTextView,     // owner
     2400                                             HWND_TOP,
     2401                                             ID_VSCROLL,
     2402                                             &sbcd,
     2403                                             0);
     2404        fShow = ((ptxvd->flStyle & XS_VSCROLL) != 0);
     2405        WinShowWindow(ptxvd->hwndVScroll, fShow);
     2406        ptxvd->fVScrollVisible = fShow;
     2407
     2408        ptxvd->hwndHScroll = WinCreateWindow(hwndTextView,
     2409                                             WC_SCROLLBAR,
     2410                                             "",
     2411                                             SBS_THUMBSIZE | WS_VISIBLE,
     2412                                             10, 10,
     2413                                             20, 100,
     2414                                             hwndTextView,     // owner
     2415                                             HWND_TOP,
     2416                                             ID_HSCROLL,
     2417                                             &sbcd,
     2418                                             0);
     2419        fShow = ((ptxvd->flStyle & XS_HSCROLL) != 0);
     2420        WinShowWindow(ptxvd->hwndHScroll, fShow);
     2421        ptxvd->fHScrollVisible = fShow;
     2422
     2423        if (ptxvd->flStyle & XS_WORDWRAP)
     2424            // word-wrapping should be enabled from the start:
     2425            // V0.9.20 (2002-08-10) [umoeller]
     2426            ptxvd->xfd.fmtpStandard.fWordWrap = TRUE;
     2427
     2428        // set "code" format
     2429        SetFormatFont(ptxvd->hps,
     2430                      &ptxvd->xfd.fmtcCode,
     2431                      6,
     2432                      "System VIO");
     2433
     2434        // get colors from presparams/syscolors
     2435        UpdateTextViewPresData(hwndTextView, ptxvd);
     2436
     2437        AdjustViewRects(hwndTextView,
     2438                        ptxvd);
     2439
     2440        if (ptxvd->flStyle & XS_HTML)
     2441        {
     2442            // if we're operating in HTML mode, set a
     2443            // different default paragraph format to
     2444            // make things prettier
     2445            // V0.9.20 (2002-08-10) [umoeller]
     2446            ptxvd->xfd.fmtpStandard.lSpaceBefore = 5;
     2447            ptxvd->xfd.fmtpStandard.lSpaceAfter = 5;
     2448        }
     2449
     2450        // setting the window text on window creation never
     2451        // worked V0.9.20 (2002-08-10) [umoeller]
     2452        if (pcs->pszText)
     2453            SetWindowText(hwndTextView,
     2454                          ptxvd,
     2455                          pcs->pszText);
     2456
     2457        mrc = (MRESULT)FALSE;        // OK
     2458    }
     2459
     2460    return mrc;
     2461}
     2462
     2463/*
     2464 *@@ ProcessPaint:
     2465 *      implementation for WM_PAINT in fnwpTextView.
     2466 *
     2467 *@@added V0.9.21 (2002-08-12) [umoeller]
     2468 */
     2469
     2470static VOID ProcessPaint(HWND hwndTextView)
     2471{
     2472    PTEXTVIEWWINDATA    ptxvd;
     2473    if (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     2474    {
     2475        HRGN    hrgnOldClip;
     2476        RECTL   rclClip;
     2477        RECTL   rcl2Update;
     2478
     2479        // get update rectangle
     2480        WinQueryUpdateRect(hwndTextView,
     2481                           &rcl2Update);
     2482        // since we're not using WinBeginPaint,
     2483        // we must validate the update region,
     2484        // or we'll get bombed with WM_PAINT msgs
     2485        WinValidateRect(hwndTextView,
     2486                        NULL,
     2487                        FALSE);
     2488
     2489        // reset clip region to "all"
     2490        GpiSetClipRegion(ptxvd->hps,
     2491                         NULLHANDLE,
     2492                         &hrgnOldClip);        // out: old clip region
     2493        // reduce clip region to update rectangle
     2494        GpiIntersectClipRectangle(ptxvd->hps,
     2495                                  &rcl2Update);     // exclusive
     2496
     2497        // draw little box at the bottom right
     2498        // (in between scroll bars) if we have
     2499        // both vertical and horizontal scroll bars
     2500        if (    (ptxvd->flStyle & (XS_VSCROLL | XS_HSCROLL))
     2501                == (XS_VSCROLL | XS_HSCROLL)
     2502             && (ptxvd->fVScrollVisible)
     2503             && (ptxvd->fHScrollVisible)
     2504           )
     2505        {
     2506            RECTL   rclBox;
     2507            rclBox.xLeft = ptxvd->rclViewPaint.xRight;
     2508            rclBox.yBottom = 0;
     2509            rclBox.xRight = rclBox.xLeft + WinQuerySysValue(HWND_DESKTOP, SV_CXVSCROLL);
     2510            rclBox.yTop = WinQuerySysValue(HWND_DESKTOP, SV_CYHSCROLL);
     2511            WinFillRect(ptxvd->hps,
     2512                        &rclBox,
     2513                        WinQuerySysColor(HWND_DESKTOP,
     2514                                         SYSCLR_DIALOGBACKGROUND,
     2515                                         0));
     2516        }
     2517
     2518        // paint "view paint" rectangle white;
     2519        // this can be larger than "view text"
     2520        WinFillRect(ptxvd->hps,
     2521                    &ptxvd->rclViewPaint,       // exclusive
     2522                    ptxvd->lBackColor);
     2523
     2524        // now reduce clipping rectangle to "view text" rectangle
     2525        rclClip.xLeft = ptxvd->rclViewText.xLeft;
     2526        rclClip.xRight = ptxvd->rclViewText.xRight - 1;
     2527        rclClip.yBottom = ptxvd->rclViewText.yBottom;
     2528        rclClip.yTop = ptxvd->rclViewText.yTop - 1;
     2529        GpiIntersectClipRectangle(ptxvd->hps,
     2530                                  &rclClip);    // exclusive
     2531        // finally, draw text lines in invalid rectangle;
     2532        // this subfunction is smart enough to redraw only
     2533        // the lines which intersect with rcl2Update
     2534        GpiSetColor(ptxvd->hps, ptxvd->lForeColor);
     2535        PaintViewText2Screen(ptxvd,
     2536                             &rcl2Update);
     2537
     2538        if (    (!(ptxvd->flStyle & XS_STATIC))
     2539                        // V0.9.20 (2002-08-10) [umoeller]
     2540             && (WinQueryFocus(HWND_DESKTOP) == hwndTextView)
     2541           )
     2542        {
     2543            // we have the focus:
     2544            // reset clip region to "all"
     2545            GpiSetClipRegion(ptxvd->hps,
     2546                             NULLHANDLE,
     2547                             &hrgnOldClip);        // out: old clip region
     2548            PaintViewFocus(ptxvd->hps,
     2549                           ptxvd,
     2550                           TRUE);
     2551        }
     2552
     2553        ptxvd->fAcceptsPresParamsNow = TRUE;
     2554    }
     2555}
     2556
     2557/*
     2558 *@@ ProcessPresParamChanged:
     2559 *      implementation for WM_PRESPARAMCHANGED in fnwpTextView.
     2560 *
     2561 *@@added V0.9.21 (2002-08-12) [umoeller]
     2562 */
     2563
     2564static VOID ProcessPresParamChanged(HWND hwndTextView, MPARAM mp1)
     2565{
     2566    PTEXTVIEWWINDATA    ptxvd;
     2567    if (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     2568    {
     2569        switch ((LONG)mp1)
     2570        {
     2571            case 0:     // layout palette thing dropped
     2572            case PP_BACKGROUNDCOLOR:
     2573            case PP_FOREGROUNDCOLOR:
     2574            case PP_FONTNAMESIZE:
     2575                // re-query our presparams
     2576                UpdateTextViewPresData(hwndTextView, ptxvd);
     2577        }
     2578
     2579        if (ptxvd->fAcceptsPresParamsNow)
     2580            FormatText2Screen(hwndTextView,
     2581                              ptxvd,
     2582                              FALSE,
     2583                              TRUE);    // full reformat
     2584    }
     2585}
     2586
     2587/*
     2588 *@@ ProcessSetFocus:
     2589 *      implementation for WM_SETFOCUS in fnwpTextView.
     2590 *
     2591 *@@added V0.9.21 (2002-08-12) [umoeller]
     2592 */
     2593
     2594static VOID ProcessSetFocus(HWND hwndTextView, MPARAM mp2)
     2595{
     2596    PTEXTVIEWWINDATA    ptxvd;
     2597    if (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     2598    {
     2599        if (ptxvd->flStyle & XS_STATIC)
     2600        {
     2601            if (mp2)
     2602            {
     2603                // we're receiving the focus, but shouldn't have it:
     2604                // then behave like the static control does, that is,
     2605                // give focus to the next window in the dialog
     2606                HWND    hwnd = hwndTextView,
     2607                        hwndStart = hwnd;
     2608
     2609                while (TRUE)
     2610                {
     2611                    ULONG flStyle;
     2612
     2613                    if (!(hwnd = WinQueryWindow(hwnd, QW_NEXT)))
     2614                        hwnd = WinQueryWindow(WinQueryWindow(hwndStart, QW_PARENT), QW_TOP);
     2615
     2616                    // avoid endless looping
     2617                    if (hwnd == hwndStart)
     2618                    {
     2619                        if (    (hwnd = WinQueryWindow(hwnd, QW_OWNER))
     2620                             && (hwnd == hwndStart)
     2621                           )
     2622                            hwnd = NULLHANDLE;
     2623
     2624                        break;
     2625                    }
     2626
     2627                    if (    (flStyle = WinQueryWindowULong(hwnd, QWL_STYLE))
     2628                         && (flStyle & (WS_DISABLED | WS_TABSTOP | WS_VISIBLE)
     2629                                == (WS_TABSTOP | WS_VISIBLE))
     2630                       )
     2631                    {
     2632                        WinSetFocus(HWND_DESKTOP, hwnd);
     2633                        break;
     2634                    }
     2635                };
     2636            }
     2637        }
     2638        else
     2639        {
     2640            HPS hps = WinGetPS(hwndTextView);
     2641            gpihSwitchToRGB(hps);
     2642            PaintViewFocus(hps,
     2643                           ptxvd,
     2644                           (mp2 != 0));
     2645            WinReleasePS(hps);
     2646        }
     2647    }
     2648}
     2649
     2650/*
     2651 *@@ ProcessButton1Down:
     2652 *      implementation for WM_BUTTON1DOWN in fnwpTextView.
     2653 *
     2654 *@@added V0.9.21 (2002-08-12) [umoeller]
     2655 */
     2656
     2657static MRESULT ProcessButton1Down(HWND hwndTextView, MPARAM mp1)
     2658{
     2659    MRESULT             mrc = 0;
     2660    PTEXTVIEWWINDATA    ptxvd;
     2661
     2662    if (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     2663    {
     2664        POINTL ptlPos;
     2665        PLISTNODE pWordNodeClicked;
     2666
     2667        ptlPos.x = SHORT1FROMMP(mp1) + ptxvd->ulViewXOfs;
     2668        ptlPos.y = SHORT2FROMMP(mp1) - ptxvd->ulViewYOfs;
     2669
     2670        if (    (!(ptxvd->flStyle & XS_STATIC))
     2671                        // V0.9.20 (2002-08-10) [umoeller]
     2672             && (hwndTextView != WinQueryFocus(HWND_DESKTOP))
     2673           )
     2674            WinSetFocus(HWND_DESKTOP, hwndTextView);
     2675
     2676        ptxvd->pcszLastLinkClicked = NULL;
     2677
     2678        if (pWordNodeClicked = txvFindWordFromPoint(&ptxvd->xfd,
     2679                                                    &ptlPos))
     2680        {
     2681            PTXVWORD pWordClicked = (PTXVWORD)pWordNodeClicked->pItemData;
     2682
     2683            // store link target (can be NULL)
     2684            if (ptxvd->pcszLastLinkClicked = pWordClicked->pcszLinkTarget)
     2685            {
     2686                // word has a link target:
     2687                PLISTNODE   pNode = pWordNodeClicked;
     2688
     2689                // reset first word of anchor
     2690                ptxvd->pWordNodeFirstInAnchor = NULL;
     2691
     2692                // go back to find the first word which has this anchor,
     2693                // because we need to repaint them all
     2694                while (pNode)
     2695                {
     2696                    PTXVWORD pWordThis = (PTXVWORD)pNode->pItemData;
     2697                    if (pWordThis->pcszLinkTarget == pWordClicked->pcszLinkTarget)
     2698                    {
     2699                        // still has same anchor:
     2700                        // go for previous
     2701                        ptxvd->pWordNodeFirstInAnchor = pNode;
     2702                        pNode = pNode->pPrevious;
     2703                    }
     2704                    else
     2705                        // different anchor:
     2706                        // pNodeFirst points to first node with same anchor now
     2707                        break;
     2708                }
     2709
     2710                RepaintAnchor(ptxvd,
     2711                              RGBCOL_RED);
     2712            }
     2713        }
     2714
     2715        WinSetCapture(HWND_DESKTOP, hwndTextView);
     2716        mrc = (MRESULT)TRUE;
     2717    }
     2718
     2719    return mrc;
     2720}
     2721
     2722/*
     2723 *@@ ProcessButton1Up:
     2724 *      implementation for WM_BUTTON1UP in fnwpTextView.
     2725 *
     2726 *@@added V0.9.21 (2002-08-12) [umoeller]
     2727 */
     2728
     2729static MRESULT ProcessButton1Up(HWND hwndTextView, MPARAM mp1)
     2730{
     2731    MRESULT             mrc = 0;
     2732    PTEXTVIEWWINDATA    ptxvd;
     2733
     2734    if (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     2735    {
     2736        POINTL      ptlPos;
     2737        HWND        hwndOwner = NULLHANDLE;
     2738
     2739        ptlPos.x = SHORT1FROMMP(mp1) + ptxvd->ulViewXOfs;
     2740        ptlPos.y = SHORT2FROMMP(mp1) - ptxvd->ulViewYOfs;
     2741        WinSetCapture(HWND_DESKTOP, NULLHANDLE);
     2742
     2743        if (ptxvd->pcszLastLinkClicked)
     2744        {
     2745            RepaintAnchor(ptxvd,
     2746                          ptxvd->lForeColor);
     2747
     2748            // nofify owner
     2749            if (hwndOwner = WinQueryWindow(hwndTextView, QW_OWNER))
     2750                WinPostMsg(hwndOwner,
     2751                           WM_CONTROL,
     2752                           MPFROM2SHORT(WinQueryWindowUShort(hwndTextView,
     2753                                                             QWS_ID),
     2754                                        TXVN_LINK),
     2755                           (MPARAM)(ULONG)(ptxvd->pcszLastLinkClicked));
     2756        }
     2757
     2758        mrc = (MRESULT)TRUE;
     2759    }
     2760
     2761    return mrc;
     2762}
     2763
     2764/*
     2765 *@@ ProcessChar:
     2766 *      implementation for WM_CHAR in fnwpTextView.
     2767 *
     2768 *@@added V0.9.21 (2002-08-12) [umoeller]
     2769 */
     2770
     2771static MRESULT ProcessChar(HWND hwndTextView, MPARAM mp1, MPARAM mp2)
     2772{
     2773    MRESULT             mrc = 0;
     2774    PTEXTVIEWWINDATA    ptxvd;
     2775
     2776    if (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     2777    {
     2778        BOOL    fDefProc = TRUE;
     2779        USHORT usFlags    = SHORT1FROMMP(mp1);
     2780        // USHORT usch       = SHORT1FROMMP(mp2);
     2781        USHORT usvk       = SHORT2FROMMP(mp2);
     2782
     2783        if (usFlags & KC_VIRTUALKEY)
     2784        {
     2785            ULONG   ulMsg = 0;
     2786            USHORT  usID = ID_VSCROLL;
     2787            SHORT   sPos = 0;
     2788            SHORT   usCmd = 0;
     2789            fDefProc = FALSE;
     2790
     2791            switch (usvk)
     2792            {
     2793                case VK_UP:
     2794                    ulMsg = WM_VSCROLL;
     2795                    usCmd = SB_LINEUP;
     2796                break;
     2797
     2798                case VK_DOWN:
     2799                    ulMsg = WM_VSCROLL;
     2800                    usCmd = SB_LINEDOWN;
     2801                break;
     2802
     2803                case VK_RIGHT:
     2804                    ulMsg = WM_HSCROLL;
     2805                    usCmd = SB_LINERIGHT;
     2806                break;
     2807
     2808                case VK_LEFT:
     2809                    ulMsg = WM_HSCROLL;
     2810                    usCmd = SB_LINELEFT;
     2811                break;
     2812
     2813                case VK_PAGEUP:
     2814                    ulMsg = WM_VSCROLL;
     2815                    if (usFlags & KC_CTRL)
     2816                    {
     2817                        sPos = 0;
     2818                        usCmd = SB_SLIDERPOSITION;
     2819                    }
     2820                    else
     2821                        usCmd = SB_PAGEUP;
     2822                break;
     2823
     2824                case VK_PAGEDOWN:
     2825                    ulMsg = WM_VSCROLL;
     2826                    if (usFlags & KC_CTRL)
     2827                    {
     2828                        sPos = ptxvd->xfd.szlWorkspace.cy;
     2829                        usCmd = SB_SLIDERPOSITION;
     2830                    }
     2831                    else
     2832                        usCmd = SB_PAGEDOWN;
     2833                break;
     2834
     2835                case VK_HOME:
     2836                    if (usFlags & KC_CTRL)
     2837                        // vertical:
     2838                        ulMsg = WM_VSCROLL;
     2839                    else
     2840                        ulMsg = WM_HSCROLL;
     2841
     2842                    sPos = 0;
     2843                    usCmd = SB_SLIDERPOSITION;
     2844                break;
     2845
     2846                case VK_END:
     2847                    if (usFlags & KC_CTRL)
     2848                    {
     2849                        // vertical:
     2850                        ulMsg = WM_VSCROLL;
     2851                        sPos = ptxvd->xfd.szlWorkspace.cy;
     2852                    }
     2853                    else
     2854                    {
     2855                        ulMsg = WM_HSCROLL;
     2856                        sPos = ptxvd->xfd.szlWorkspace.cx;
     2857                    }
     2858
     2859                    usCmd = SB_SLIDERPOSITION;
     2860                break;
     2861
     2862                default:
     2863                    // other:
     2864                    fDefProc = TRUE;
     2865            }
     2866
     2867            if (    ((usFlags & KC_KEYUP) == 0)
     2868                 && (ulMsg)
     2869               )
     2870                WinSendMsg(hwndTextView,
     2871                           ulMsg,
     2872                           MPFROMSHORT(usID),
     2873                           MPFROM2SHORT(sPos,
     2874                                        usCmd));
     2875        }
     2876
     2877        if (fDefProc)
     2878            mrc = WinDefWindowProc(hwndTextView, WM_CHAR, mp1, mp2);
     2879                    // sends to owner
     2880        else
     2881            mrc = (MPARAM)TRUE;
     2882    }
     2883
     2884    return mrc;
     2885}
     2886
     2887/*
     2888 *@@ ProcessJumpToAnchorName:
     2889 *      implementation for TXM_JUMPTOANCHORNAME in fnwpTextView.
     2890 *
     2891 *@@added V0.9.21 (2002-08-12) [umoeller]
     2892 */
     2893
     2894static MRESULT ProcessJumpToAnchorName(HWND hwndTextView, MPARAM mp1)
     2895{
     2896    MRESULT             mrc = 0;
     2897    PTEXTVIEWWINDATA    ptxvd;
     2898
     2899    if (    (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     2900         && (mp1)
     2901       )
     2902    {
     2903        PLISTNODE pWordNode;
     2904        PTXVWORD pWord;
     2905        if (    (pWordNode = txvFindWordFromAnchor(&ptxvd->xfd,
     2906                                                   (const char*)mp1))
     2907             && (pWord = (PTXVWORD)pWordNode->pItemData)
     2908           )
     2909        {
     2910            // found:
     2911            PTXVRECTANGLE pRect = pWord->pRectangle;
     2912            ULONG ulWinCY = (ptxvd->rclViewText.yTop - ptxvd->rclViewText.yBottom);
     2913
     2914            // now we need to scroll the window so that this rectangle is on top.
     2915            // Since rectangles start out with the height of the window (e.g. +768)
     2916            // and then have lower y coordinates down to way in the negatives,
     2917            // to get the y offset, we must...
     2918            ptxvd->ulViewYOfs = (-pRect->rcl.yTop) - ulWinCY;
     2919
     2920            if (ptxvd->ulViewYOfs < 0)
     2921                ptxvd->ulViewYOfs = 0;
     2922            if (ptxvd->ulViewYOfs > ((LONG)ptxvd->xfd.szlWorkspace.cy - ulWinCY))
     2923                ptxvd->ulViewYOfs = (LONG)ptxvd->xfd.szlWorkspace.cy - ulWinCY;
     2924
     2925            // vertical scroll bar enabled at all?
     2926            if (ptxvd->flStyle & XS_VSCROLL)
     2927            {
     2928                /* BOOL fEnabled = */ winhUpdateScrollBar(ptxvd->hwndVScroll,
     2929                                                    ulWinCY,
     2930                                                    ptxvd->xfd.szlWorkspace.cy,
     2931                                                    ptxvd->ulViewYOfs,
     2932                                                    (ptxvd->flStyle & XS_AUTOVHIDE));
     2933                WinInvalidateRect(hwndTextView, NULL, FALSE);
     2934            }
     2935
     2936            mrc = (MRESULT)TRUE;
     2937        }
     2938    }
     2939
     2940    return mrc;
     2941}
     2942
     2943/*
     2944 *@@ ProcessDestroy:
     2945 *      implementation for WM_DESTROY in fnwpTextView.
     2946 *
     2947 *@@added V0.9.21 (2002-08-12) [umoeller]
     2948 */
     2949
     2950static MRESULT ProcessDestroy(HWND hwndTextView, MPARAM mp1, MPARAM mp2)
     2951{
     2952    PTEXTVIEWWINDATA    ptxvd;
     2953
     2954    if (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     2955    {
     2956        xstrClear(&ptxvd->xfd.strViewText);
     2957        lstClear(&ptxvd->xfd.llRectangles);
     2958        lstClear(&ptxvd->xfd.llWords);
     2959        GpiDestroyPS(ptxvd->hps);
     2960        free(ptxvd);
     2961        WinSetWindowPtr(hwndTextView, QWL_PRIVATE, NULL);
     2962    }
     2963
     2964    return WinDefWindowProc(hwndTextView, WM_DESTROY, mp1, mp2);
    23122965}
    23132966
     
    23643017 *@@changed V0.9.20 (2002-08-10) [umoeller]: added TXN_ANCHORCLICKED owner notify for anchors
    23653018 *@@changed V0.9.20 (2002-08-10) [umoeller]: converted private style flags to XS_* window style flags
     3019 *@@changed V0.9.20 (2002-08-10) [umoeller]: added support for XS_STATIC
    23663020 *@@changed V0.9.20 (2002-08-10) [umoeller]: added support for formatting HTML and plain text automatically
     3021 *@@changed V0.9.21 (2002-08-12) [umoeller]: optimized locality by moving big chunks into subfuncs
    23673022 */
    23683023
    23693024static MRESULT EXPENTRY fnwpTextView(HWND hwndTextView, ULONG msg, MPARAM mp1, MPARAM mp2)
    23703025{
    2371     MRESULT mrc = 0;
    2372 
    2373     PTEXTVIEWWINDATA ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE);
     3026    MRESULT             mrc = 0;
     3027    PTEXTVIEWWINDATA    ptxvd;
    23743028
    23753029    switch (msg)
     
    23813035
    23823036        case WM_CREATE:
    2383         {
    2384             PXTEXTVIEWCDATA pcd = (PXTEXTVIEWCDATA)mp1;
    2385                         // can be NULL
    2386             PCREATESTRUCT pcs = (PCREATESTRUCT)mp2;
    2387             SBCDATA sbcd;
    2388 
    2389             mrc = (MPARAM)TRUE;     // error
    2390 
    2391             // allocate TEXTVIEWWINDATA for QWL_PRIVATE
    2392             if (ptxvd = (PTEXTVIEWWINDATA)malloc(sizeof(TEXTVIEWWINDATA)))
    2393             {
    2394                 SIZEL   szlPage = {0, 0};
    2395                 BOOL    fShow = FALSE;
    2396 
    2397                 // query message queue
    2398                 HMQ hmq = WinQueryWindowULong(hwndTextView, QWL_HMQ);
    2399                 // get codepage of message queue
    2400                 ULONG ulCodepage = WinQueryCp(hmq);
    2401 
    2402                 memset(ptxvd, 0, sizeof(TEXTVIEWWINDATA));
    2403                 WinSetWindowPtr(hwndTextView, QWL_PRIVATE, ptxvd);
    2404 
    2405                 ptxvd->hab = WinQueryAnchorBlock(hwndTextView);
    2406 
    2407                 ptxvd->hdc = WinOpenWindowDC(hwndTextView);
    2408                 ptxvd->hps = GpiCreatePS(ptxvd->hab,
    2409                                          ptxvd->hdc,
    2410                                          &szlPage, // use same page size as device
    2411                                          PU_PELS | GPIT_MICRO | GPIA_ASSOC);
    2412 
    2413                 // copy window style flags V0.9.20 (2002-08-10) [umoeller]
    2414                 ptxvd->flStyle = pcs->flStyle;
    2415 
    2416                 gpihSwitchToRGB(ptxvd->hps);
    2417 
    2418                 // set codepage; GPI defaults this to
    2419                 // the process codepage
    2420                 GpiSetCp(ptxvd->hps, ulCodepage);
    2421 
    2422                 txvInitFormat(&ptxvd->xfd);
    2423 
    2424                 // copy control data, if present
    2425                 if (pcd)
    2426                     memcpy(&ptxvd->cdata, pcd, pcd->cbData);
    2427 
    2428                 // check values which might cause null divisions
    2429                 if (ptxvd->cdata.ulVScrollLineUnit == 0)
    2430                     ptxvd->cdata.ulVScrollLineUnit = 15;
    2431                 if (ptxvd->cdata.ulHScrollLineUnit == 0)
    2432                     ptxvd->cdata.ulHScrollLineUnit = 15;
    2433 
    2434                 ptxvd->fAcceptsPresParamsNow = FALSE;
    2435 
    2436                 // copy window dimensions from CREATESTRUCT
    2437                 ptxvd->rclViewReal.xLeft = 0;
    2438                 ptxvd->rclViewReal.yBottom = 0;
    2439                 ptxvd->rclViewReal.xRight = pcs->cx;
    2440                 ptxvd->rclViewReal.yTop = pcs->cy;
    2441 
    2442                 sbcd.cb = sizeof(SBCDATA);
    2443                 sbcd.sHilite = 0;
    2444                 sbcd.posFirst = 0;
    2445                 sbcd.posLast = 100;
    2446                 sbcd.posThumb = 30;
    2447                 sbcd.cVisible = 50;
    2448                 sbcd.cTotal = 50;
    2449 
    2450                 ptxvd->hwndVScroll = WinCreateWindow(hwndTextView,
    2451                                                      WC_SCROLLBAR,
    2452                                                      "",
    2453                                                      SBS_VERT | SBS_THUMBSIZE | WS_VISIBLE,
    2454                                                      10, 10,
    2455                                                      20, 100,
    2456                                                      hwndTextView,     // owner
    2457                                                      HWND_TOP,
    2458                                                      ID_VSCROLL,
    2459                                                      &sbcd,
    2460                                                      0);
    2461                 fShow = ((ptxvd->flStyle & XS_VSCROLL) != 0);
    2462                 WinShowWindow(ptxvd->hwndVScroll, fShow);
    2463                 ptxvd->fVScrollVisible = fShow;
    2464 
    2465                 ptxvd->hwndHScroll = WinCreateWindow(hwndTextView,
    2466                                                      WC_SCROLLBAR,
    2467                                                      "",
    2468                                                      SBS_THUMBSIZE | WS_VISIBLE,
    2469                                                      10, 10,
    2470                                                      20, 100,
    2471                                                      hwndTextView,     // owner
    2472                                                      HWND_TOP,
    2473                                                      ID_HSCROLL,
    2474                                                      &sbcd,
    2475                                                      0);
    2476                 fShow = ((ptxvd->flStyle & XS_HSCROLL) != 0);
    2477                 WinShowWindow(ptxvd->hwndHScroll, fShow);
    2478                 ptxvd->fHScrollVisible = fShow;
    2479 
    2480                 if (ptxvd->flStyle & XS_WORDWRAP)
    2481                     // word-wrapping should be enabled from the start:
    2482                     // V0.9.20 (2002-08-10) [umoeller]
    2483                     ptxvd->xfd.fmtpStandard.fWordWrap = TRUE;
    2484 
    2485                 // set "code" format
    2486                 SetFormatFont(ptxvd->hps,
    2487                               &ptxvd->xfd.fmtcCode,
    2488                               6,
    2489                               "System VIO");
    2490 
    2491                 // get colors from presparams/syscolors
    2492                 UpdateTextViewPresData(hwndTextView, ptxvd);
    2493 
    2494                 AdjustViewRects(hwndTextView,
    2495                                 ptxvd);
    2496 
    2497                 if (ptxvd->flStyle & XS_HTML)
    2498                 {
    2499                     // if we're operating in HTML mode, set a
    2500                     // different default paragraph format to
    2501                     // make things prettier
    2502                     // V0.9.20 (2002-08-10) [umoeller]
    2503                     ptxvd->xfd.fmtpStandard.lSpaceBefore = 5;
    2504                     ptxvd->xfd.fmtpStandard.lSpaceAfter = 5;
    2505                 }
    2506 
    2507                 // setting the window text on window creation never
    2508                 // worked V0.9.20 (2002-08-10) [umoeller]
    2509                 if (pcs->pszText)
    2510                     SetWindowText(hwndTextView,
    2511                                   ptxvd,
    2512                                   pcs->pszText);
    2513 
    2514                 mrc = (MPARAM)FALSE;        // OK
    2515             }
    2516         }
     3037            mrc = ProcessCreate(hwndTextView, mp1, mp2);
     3038                    // extracted V0.9.21 (2002-08-12) [umoeller]
    25173039        break;
    25183040
     
    25263048
    25273049        case WM_SETWINDOWPARAMS:
    2528         {
    2529             WNDPARAMS *pwndParams;
    2530             if (    (pwndParams = (WNDPARAMS *)mp1)
    2531                  && (pwndParams->fsStatus & WPM_TEXT)
     3050            if (    (mp1)
     3051                 && (((PWNDPARAMS)mp1)->fsStatus & WPM_TEXT)
     3052                 && (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
    25323053               )
    25333054            {
    25343055                SetWindowText(hwndTextView,
    25353056                              ptxvd,
    2536                               pwndParams->pszText);
     3057                              ((PWNDPARAMS)mp1)->pszText);
    25373058                mrc = (MRESULT)TRUE;     // was missing V0.9.20 (2002-08-10) [umoeller]
    25383059            }
    2539         }
    25403060        break;
    25413061
     
    25463066
    25473067        case WM_WINDOWPOSCHANGED:
    2548         {
    2549             // this msg is passed two SWP structs:
    2550             // one for the old, one for the new data
    2551             // (from PM docs)
    2552             PSWP pswpNew = (PSWP)(mp1);
    2553             // PSWP pswpOld = pswpNew + 1;
    2554 
    25553068            // resizing?
    2556             if (pswpNew->fl & SWP_SIZE)
     3069            if (    (mp1)
     3070                 && (((PSWP)mp1)->fl & SWP_SIZE)
     3071                 && (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     3072               )
    25573073            {
    2558                 if (ptxvd)
    2559                 {
    2560                     WinQueryWindowRect(hwndTextView,
    2561                                        &ptxvd->rclViewReal);
    2562                     AdjustViewRects(hwndTextView,
    2563                                     ptxvd);
    2564                     FormatText2Screen(hwndTextView,
    2565                                       ptxvd,
    2566                                       FALSE,
    2567                                       FALSE);   // quick format
    2568                 }
     3074                WinQueryWindowRect(hwndTextView,
     3075                                   &ptxvd->rclViewReal);
     3076                AdjustViewRects(hwndTextView,
     3077                                ptxvd);
     3078                FormatText2Screen(hwndTextView,
     3079                                  ptxvd,
     3080                                  FALSE,
     3081                                  FALSE);   // quick format
    25693082            }
    2570         }
    25713083        break;
    25723084
     
    25773089
    25783090        case WM_PAINT:
    2579         {
    2580             HRGN    hrgnOldClip;
    2581 
    2582             /* HPS hps = WinBeginPaint(hwndTextView,
    2583                                     ptxvd->hps,
    2584                                     &rcl2Paint);  // store invalid rectangle here
    2585                */
    2586 
    2587             if (ptxvd)
    2588             {
    2589                 RECTL   rclClip;
    2590                 RECTL   rcl2Update;
    2591 
    2592                 // get update rectangle
    2593                 WinQueryUpdateRect(hwndTextView,
    2594                                    &rcl2Update);
    2595                 // since we're not using WinBeginPaint,
    2596                 // we must validate the update region,
    2597                 // or we'll get bombed with WM_PAINT msgs
    2598                 WinValidateRect(hwndTextView,
    2599                                 NULL,
    2600                                 FALSE);
    2601 
    2602                 // reset clip region to "all"
    2603                 GpiSetClipRegion(ptxvd->hps,
    2604                                  NULLHANDLE,
    2605                                  &hrgnOldClip);        // out: old clip region
    2606                 // reduce clip region to update rectangle
    2607                 GpiIntersectClipRectangle(ptxvd->hps,
    2608                                           &rcl2Update);     // exclusive
    2609 
    2610                 // draw little box at the bottom right
    2611                 // (in between scroll bars) if we have
    2612                 // both vertical and horizontal scroll bars
    2613                 if (    (ptxvd->flStyle & (XS_VSCROLL | XS_HSCROLL))
    2614                         == (XS_VSCROLL | XS_HSCROLL)
    2615                      && (ptxvd->fVScrollVisible)
    2616                      && (ptxvd->fHScrollVisible)
    2617                    )
    2618                 {
    2619                     RECTL   rclBox;
    2620                     rclBox.xLeft = ptxvd->rclViewPaint.xRight;
    2621                     rclBox.yBottom = 0;
    2622                     rclBox.xRight = rclBox.xLeft + WinQuerySysValue(HWND_DESKTOP, SV_CXVSCROLL);
    2623                     rclBox.yTop = WinQuerySysValue(HWND_DESKTOP, SV_CYHSCROLL);
    2624                     WinFillRect(ptxvd->hps,
    2625                                 &rclBox,
    2626                                 WinQuerySysColor(HWND_DESKTOP,
    2627                                                  SYSCLR_DIALOGBACKGROUND,
    2628                                                  0));
    2629                 }
    2630 
    2631                 // paint "view paint" rectangle white;
    2632                 // this can be larger than "view text"
    2633                 WinFillRect(ptxvd->hps,
    2634                             &ptxvd->rclViewPaint,       // exclusive
    2635                             ptxvd->lBackColor);
    2636 
    2637                 // now reduce clipping rectangle to "view text" rectangle
    2638                 rclClip.xLeft = ptxvd->rclViewText.xLeft;
    2639                 rclClip.xRight = ptxvd->rclViewText.xRight - 1;
    2640                 rclClip.yBottom = ptxvd->rclViewText.yBottom;
    2641                 rclClip.yTop = ptxvd->rclViewText.yTop - 1;
    2642                 GpiIntersectClipRectangle(ptxvd->hps,
    2643                                           &rclClip);    // exclusive
    2644                 // finally, draw text lines in invalid rectangle;
    2645                 // this subfunction is smart enough to redraw only
    2646                 // the lines which intersect with rcl2Update
    2647                 GpiSetColor(ptxvd->hps, ptxvd->lForeColor);
    2648                 PaintViewText2Screen(ptxvd,
    2649                                      &rcl2Update);
    2650 
    2651                 if (    (!(ptxvd->flStyle & XS_STATIC))
    2652                                 // V0.9.20 (2002-08-10) [umoeller]
    2653                      && (WinQueryFocus(HWND_DESKTOP) == hwndTextView)
    2654                    )
    2655                 {
    2656                     // we have the focus:
    2657                     // reset clip region to "all"
    2658                     GpiSetClipRegion(ptxvd->hps,
    2659                                      NULLHANDLE,
    2660                                      &hrgnOldClip);        // out: old clip region
    2661                     PaintViewFocus(ptxvd->hps,
    2662                                    ptxvd,
    2663                                    TRUE);
    2664                 }
    2665 
    2666                 ptxvd->fAcceptsPresParamsNow = TRUE;
    2667             }
    2668 
    2669             // WinEndPaint(hps);
    2670         }
     3091            ProcessPaint(hwndTextView);
     3092                    // extracted V0.9.21 (2002-08-12) [umoeller]
    26713093        break;
    26723094
     
    26803102
    26813103        case WM_PRESPARAMCHANGED:
    2682             mrc = WinDefWindowProc(hwndTextView, msg, mp1, mp2);
    2683             if (ptxvd)
    2684             {
    2685                 LONG    lPPIndex = (LONG)mp1;
    2686                 switch (lPPIndex)
    2687                 {
    2688                     case 0:     // layout palette thing dropped
    2689                     case PP_BACKGROUNDCOLOR:
    2690                     case PP_FOREGROUNDCOLOR:
    2691                     case PP_FONTNAMESIZE:
    2692                         // re-query our presparams
    2693                         UpdateTextViewPresData(hwndTextView, ptxvd);
    2694                 }
    2695 
    2696                 if (ptxvd->fAcceptsPresParamsNow)
    2697                     FormatText2Screen(hwndTextView,
    2698                                       ptxvd,
    2699                                       FALSE,
    2700                                       TRUE);    // full reformat
    2701             }
     3104            ProcessPresParamChanged(hwndTextView, mp1);
    27023105        break;
    27033106
     
    27083111
    27093112        case WM_VSCROLL:
    2710             if (ptxvd->fVScrollVisible)
     3113            if (    (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     3114                 && (ptxvd->fVScrollVisible)
     3115               )
    27113116            {
    27123117                winhHandleScrollMsg(hwndTextView,
     
    27273132
    27283133        case WM_HSCROLL:
    2729             if (ptxvd->fHScrollVisible)
     3134            if (    (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     3135                 && (ptxvd->fHScrollVisible)
     3136               )
    27303137            {
    27313138                winhHandleScrollMsg(hwndTextView,
     
    27463153
    27473154        case WM_SETFOCUS:
    2748         {
    2749             if (ptxvd->flStyle & XS_STATIC)
    2750             {
    2751                 if (mp2)
    2752                 {
    2753                     // we're receiving the focus, but shouldn't have it:
    2754                     // then behave like the static control does, that is,
    2755                     // give focus to the next window in the dialog
    2756                     HWND    hwnd = hwndTextView,
    2757                             hwndStart = hwnd;
    2758 
    2759                     while (TRUE)
    2760                     {
    2761                         ULONG flStyle;
    2762 
    2763                         if (!(hwnd = WinQueryWindow(hwnd, QW_NEXT)))
    2764                             hwnd = WinQueryWindow(WinQueryWindow(hwndStart, QW_PARENT), QW_TOP);
    2765 
    2766                         // avoid endless looping
    2767                         if (hwnd == hwndStart)
    2768                         {
    2769                             if (    (hwnd = WinQueryWindow(hwnd, QW_OWNER))
    2770                                  && (hwnd == hwndStart)
    2771                                )
    2772                                 hwnd = NULLHANDLE;
    2773 
    2774                             break;
    2775                         }
    2776 
    2777                         if (    (flStyle = WinQueryWindowULong(hwnd, QWL_STYLE))
    2778                              && (flStyle & (WS_DISABLED | WS_TABSTOP | WS_VISIBLE)
    2779                                     == (WS_TABSTOP | WS_VISIBLE))
    2780                            )
    2781                         {
    2782                             WinSetFocus(HWND_DESKTOP, hwnd);
    2783                             break;
    2784                         }
    2785                     };
    2786                 }
    2787             }
    2788             else
    2789             {
    2790                 HPS hps = WinGetPS(hwndTextView);
    2791                 gpihSwitchToRGB(hps);
    2792                 PaintViewFocus(hps,
    2793                                ptxvd,
    2794                                (mp2 != 0));
    2795                 WinReleasePS(hps);
    2796             }
    2797         }
     3155            ProcessSetFocus(hwndTextView, mp2);
    27983156        break;
    27993157
     
    28273185
    28283186        case WM_BUTTON1DOWN:
    2829         {
    2830             POINTL ptlPos;
    2831             PLISTNODE pWordNodeClicked;
    2832 
    2833             ptlPos.x = SHORT1FROMMP(mp1) + ptxvd->ulViewXOfs;
    2834             ptlPos.y = SHORT2FROMMP(mp1) - ptxvd->ulViewYOfs;
    2835 
    2836             if (    (!(ptxvd->flStyle & XS_STATIC))
    2837                             // V0.9.20 (2002-08-10) [umoeller]
    2838                  && (hwndTextView != WinQueryFocus(HWND_DESKTOP))
    2839                )
    2840                 WinSetFocus(HWND_DESKTOP, hwndTextView);
    2841 
    2842             ptxvd->pszLastLinkClicked = NULL;
    2843 
    2844             if (pWordNodeClicked = txvFindWordFromPoint(&ptxvd->xfd,
    2845                                                         &ptlPos))
    2846             {
    2847                 PTXVWORD pWordClicked = (PTXVWORD)pWordNodeClicked->pItemData;
    2848 
    2849                 // store link target (can be NULL)
    2850                 if (ptxvd->pszLastLinkClicked = pWordClicked->pszLinkTarget)
    2851                 {
    2852                     // word has a link target:
    2853                     PLISTNODE   pNode = pWordNodeClicked;
    2854 
    2855                     // reset first word of anchor
    2856                     ptxvd->pWordNodeFirstInAnchor = NULL;
    2857 
    2858                     // go back to find the first word which has this anchor,
    2859                     // because we need to repaint them all
    2860                     while (pNode)
    2861                     {
    2862                         PTXVWORD pWordThis = (PTXVWORD)pNode->pItemData;
    2863                         if (pWordThis->pszLinkTarget == pWordClicked->pszLinkTarget)
    2864                         {
    2865                             // still has same anchor:
    2866                             // go for previous
    2867                             ptxvd->pWordNodeFirstInAnchor = pNode;
    2868                             pNode = pNode->pPrevious;
    2869                         }
    2870                         else
    2871                             // different anchor:
    2872                             // pNodeFirst points to first node with same anchor now
    2873                             break;
    2874                     }
    2875 
    2876                     RepaintAnchor(ptxvd,
    2877                                   RGBCOL_RED);
    2878                 }
    2879             }
    2880 
    2881             WinSetCapture(HWND_DESKTOP, hwndTextView);
    2882             mrc = (MPARAM)TRUE;
    2883         }
     3187            mrc = ProcessButton1Down(hwndTextView, mp1);
    28843188        break;
    28853189
     
    28903194
    28913195        case WM_BUTTON1UP:
    2892         {
    2893             POINTL      ptlPos;
    2894             // PTXVWORD    pWordClicked = NULL;
    2895             HWND        hwndOwner = NULLHANDLE;
    2896 
    2897             ptlPos.x = SHORT1FROMMP(mp1) + ptxvd->ulViewXOfs;
    2898             ptlPos.y = SHORT2FROMMP(mp1) - ptxvd->ulViewYOfs;
    2899             WinSetCapture(HWND_DESKTOP, NULLHANDLE);
    2900 
    2901             if (ptxvd->pszLastLinkClicked)
    2902             {
    2903                 RepaintAnchor(ptxvd,
    2904                               ptxvd->lForeColor);
    2905 
    2906                 // nofify owner
    2907                 if (hwndOwner = WinQueryWindow(hwndTextView, QW_OWNER))
    2908                     WinPostMsg(hwndOwner,
    2909                                WM_CONTROL,
    2910                                MPFROM2SHORT(WinQueryWindowUShort(hwndTextView,
    2911                                                                  QWS_ID),
    2912                                             TXVN_LINK),
    2913                                (MPARAM)(ULONG)(ptxvd->pszLastLinkClicked));
    2914             }
    2915 
    2916             mrc = (MPARAM)TRUE;
    2917         }
     3196            mrc = ProcessButton1Up(hwndTextView, mp1);
    29183197        break;
    29193198
     
    29243203
    29253204        case WM_CHAR:
    2926         {
    2927             BOOL    fDefProc = TRUE;
    2928             USHORT usFlags    = SHORT1FROMMP(mp1);
    2929             // USHORT usch       = SHORT1FROMMP(mp2);
    2930             USHORT usvk       = SHORT2FROMMP(mp2);
    2931 
    2932             if (usFlags & KC_VIRTUALKEY)
    2933             {
    2934                 ULONG   ulMsg = 0;
    2935                 USHORT  usID = ID_VSCROLL;
    2936                 SHORT   sPos = 0;
    2937                 SHORT   usCmd = 0;
    2938                 fDefProc = FALSE;
    2939 
    2940                 switch (usvk)
    2941                 {
    2942                     case VK_UP:
    2943                         ulMsg = WM_VSCROLL;
    2944                         usCmd = SB_LINEUP;
    2945                     break;
    2946 
    2947                     case VK_DOWN:
    2948                         ulMsg = WM_VSCROLL;
    2949                         usCmd = SB_LINEDOWN;
    2950                     break;
    2951 
    2952                     case VK_RIGHT:
    2953                         ulMsg = WM_HSCROLL;
    2954                         usCmd = SB_LINERIGHT;
    2955                     break;
    2956 
    2957                     case VK_LEFT:
    2958                         ulMsg = WM_HSCROLL;
    2959                         usCmd = SB_LINELEFT;
    2960                     break;
    2961 
    2962                     case VK_PAGEUP:
    2963                         ulMsg = WM_VSCROLL;
    2964                         if (usFlags & KC_CTRL)
    2965                         {
    2966                             sPos = 0;
    2967                             usCmd = SB_SLIDERPOSITION;
    2968                         }
    2969                         else
    2970                             usCmd = SB_PAGEUP;
    2971                     break;
    2972 
    2973                     case VK_PAGEDOWN:
    2974                         ulMsg = WM_VSCROLL;
    2975                         if (usFlags & KC_CTRL)
    2976                         {
    2977                             sPos = ptxvd->xfd.szlWorkspace.cy;
    2978                             usCmd = SB_SLIDERPOSITION;
    2979                         }
    2980                         else
    2981                             usCmd = SB_PAGEDOWN;
    2982                     break;
    2983 
    2984                     case VK_HOME:
    2985                         if (usFlags & KC_CTRL)
    2986                             // vertical:
    2987                             ulMsg = WM_VSCROLL;
    2988                         else
    2989                             ulMsg = WM_HSCROLL;
    2990 
    2991                         sPos = 0;
    2992                         usCmd = SB_SLIDERPOSITION;
    2993                     break;
    2994 
    2995                     case VK_END:
    2996                         if (usFlags & KC_CTRL)
    2997                         {
    2998                             // vertical:
    2999                             ulMsg = WM_VSCROLL;
    3000                             sPos = ptxvd->xfd.szlWorkspace.cy;
    3001                         }
    3002                         else
    3003                         {
    3004                             ulMsg = WM_HSCROLL;
    3005                             sPos = ptxvd->xfd.szlWorkspace.cx;
    3006                         }
    3007 
    3008                         usCmd = SB_SLIDERPOSITION;
    3009                     break;
    3010 
    3011                     default:
    3012                         // other:
    3013                         fDefProc = TRUE;
    3014                 }
    3015 
    3016                 if (    ((usFlags & KC_KEYUP) == 0)
    3017                      && (ulMsg)
    3018                    )
    3019                     WinSendMsg(hwndTextView,
    3020                                ulMsg,
    3021                                MPFROMSHORT(usID),
    3022                                MPFROM2SHORT(sPos,
    3023                                             usCmd));
    3024             }
    3025 
    3026             if (fDefProc)
    3027                 mrc = WinDefWindowProc(hwndTextView, msg, mp1, mp2);
    3028                         // sends to owner
    3029             else
    3030                 mrc = (MPARAM)TRUE;
    3031         }
     3205            mrc = ProcessChar(hwndTextView, mp1, mp2);
    30323206        break;
    30333207
     
    30563230
    30573231        case TXM_QUERYPARFORMAT:
    3058         {
    3059             PXFMTPARAGRAPH pFmt = NULL; // source
    3060 
    3061             mrc = (MPARAM)FALSE;
    3062 
    3063             if (mp1 == 0)
    3064                 pFmt = &ptxvd->xfd.fmtpStandard;
    3065             /* else if ((ULONG)mp1 == 1)
    3066                 pFmt = &ptxvd->xfd.fmtpCode; */
    3067 
    3068             if ((pFmt) && (mp2))
     3232            if (    (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     3233                 && (!mp1)
     3234                 && (mp2)
     3235               )
    30693236            {
    3070                 memcpy(mp2, pFmt, sizeof(XFMTPARAGRAPH));
     3237                memcpy(mp2,
     3238                       &ptxvd->xfd.fmtpStandard,
     3239                       sizeof(XFMTPARAGRAPH));
    30713240                mrc = (MPARAM)TRUE;
    30723241            }
    3073         }
    30743242        break;
    30753243
     
    30993267
    31003268        case TXM_SETPARFORMAT:
    3101         {
    3102             PXFMTPARAGRAPH pFmt = NULL;     // target
    3103 
    3104             mrc = (MPARAM)FALSE;
    3105 
    3106             if (mp1 == 0)
    3107                 pFmt = &ptxvd->xfd.fmtpStandard;
    3108             /* else if ((ULONG)mp1 == 1)
    3109                 pFmt = &ptxvd->xfd.fmtpCode; */
    3110 
    3111             if (pFmt)
     3269            if (    (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     3270                 && (!mp1)
     3271               )
    31123272            {
    31133273                if (mp2)
    3114                     // copy
    3115                     memcpy(pFmt, mp2, sizeof(XFMTPARAGRAPH));
     3274                    // copy:
     3275                    memcpy(&ptxvd->xfd.fmtpStandard,
     3276                           mp2,
     3277                           sizeof(XFMTPARAGRAPH));
    31163278                else
    31173279                    // default:
    3118                     memset(pFmt, 0, sizeof(XFMTPARAGRAPH));
     3280                    memset(&ptxvd->xfd.fmtpStandard,
     3281                           0,
     3282                           sizeof(XFMTPARAGRAPH));
    31193283
    31203284                FormatText2Screen(hwndTextView,
     
    31253289                mrc = (MPARAM)TRUE;
    31263290            }
    3127         }
    31283291        break;
    31293292
     
    31413304
    31423305        case TXM_SETWORDWRAP:
    3143         {
    3144             BOOL    ulOldFlFormat = ptxvd->xfd.fmtpStandard.fWordWrap;
    3145             ptxvd->xfd.fmtpStandard.fWordWrap = (BOOL)mp1;
    3146             if (ptxvd->xfd.fmtpStandard.fWordWrap != ulOldFlFormat)
    3147                 FormatText2Screen(hwndTextView,
    3148                                   ptxvd,
    3149                                   FALSE,
    3150                                   FALSE);       // quick format
    3151         }
     3306            if (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     3307            {
     3308                BOOL    ulOldFlFormat = ptxvd->xfd.fmtpStandard.fWordWrap;
     3309                ptxvd->xfd.fmtpStandard.fWordWrap = (BOOL)mp1;
     3310                if (ptxvd->xfd.fmtpStandard.fWordWrap != ulOldFlFormat)
     3311                    FormatText2Screen(hwndTextView,
     3312                                      ptxvd,
     3313                                      FALSE,
     3314                                      FALSE);       // quick format
     3315            }
    31523316        break;
    31533317
     
    31653329         *          XTEXTVIEWCDATA.cbData.
    31663330         *
    3167          *      Returns: the bytes that were copied as
     3331         *      Returns the bytes that were copied as
    31683332         *      a ULONG.
    31693333         */
    31703334
    31713335        case TXM_QUERYCDATA:
    3172             if (mp1)
     3336            if (    (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     3337                 && (mp1)
     3338               )
    31733339            {
    31743340                PXTEXTVIEWCDATA pTarget = (PXTEXTVIEWCDATA)mp1;
     
    31883354         *
    31893355         *      Parameters:
     3356         *
    31903357         *      -- PXTEXTVIEWCDATA mp1: source buffer.
    31913358         *         Before calling this, you MUST specify
    31923359         *         XTEXTVIEWCDATA.cbData.
     3360         *
     3361         *      Returns the bytes that were copied as
     3362         *      a ULONG.
     3363         *
     3364         *@@changed V0.9.21 (2002-08-12) [umoeller]: now returning bytes
    31933365         */
    31943366
    31953367        case TXM_SETCDATA:
    3196             if (mp1)
     3368            if (    (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     3369                 && (mp1)
     3370               )
    31973371            {
    31983372                PXTEXTVIEWCDATA pSource = (PXTEXTVIEWCDATA)mp1;
    3199                 memcpy(&ptxvd->cdata, pSource, pSource->cbData);
     3373                mrc = (MRESULT)min(pSource->cbData, sizeof(XTEXTVIEWCDATA));
     3374                memcpy(&ptxvd->cdata,
     3375                       pSource,
     3376                       (ULONG)mrc);
    32003377            }
    32013378        break;
     
    32133390         *      -- PSZ mp1: anchor name (e.g. "anchor1").
    32143391         *
     3392         *      Returns TRUE if the jump was successful.
     3393         *
    32153394         *@@added V0.9.4 (2000-06-12) [umoeller]
    32163395         */
    32173396
    32183397        case TXM_JUMPTOANCHORNAME:
    3219             if (mp1)
    3220             {
    3221                 PLISTNODE pWordNode = txvFindWordFromAnchor(&ptxvd->xfd,
    3222                                                             (const char*)mp1);
    3223                 if (pWordNode)
    3224                 {
    3225                     // found:
    3226                     PTXVWORD pWord = (PTXVWORD)pWordNode->pItemData;
    3227                     if (pWord)
    3228                     {
    3229                         PTXVRECTANGLE pRect = pWord->pRectangle;
    3230                         ULONG ulWinCY = (ptxvd->rclViewText.yTop - ptxvd->rclViewText.yBottom);
    3231 
    3232                         // now we need to scroll the window so that this rectangle is on top.
    3233                         // Since rectangles start out with the height of the window (e.g. +768)
    3234                         // and then have lower y coordinates down to way in the negatives,
    3235                         // to get the y offset, we must...
    3236                         ptxvd->ulViewYOfs = (-pRect->rcl.yTop) - ulWinCY;
    3237 
    3238                         if (ptxvd->ulViewYOfs < 0)
    3239                             ptxvd->ulViewYOfs = 0;
    3240                         if (ptxvd->ulViewYOfs > ((LONG)ptxvd->xfd.szlWorkspace.cy - ulWinCY))
    3241                             ptxvd->ulViewYOfs = (LONG)ptxvd->xfd.szlWorkspace.cy - ulWinCY;
    3242 
    3243                         // vertical scroll bar enabled at all?
    3244                         if (ptxvd->flStyle & XS_VSCROLL)
    3245                         {
    3246                             /* BOOL fEnabled = */ winhUpdateScrollBar(ptxvd->hwndVScroll,
    3247                                                                 ulWinCY,
    3248                                                                 ptxvd->xfd.szlWorkspace.cy,
    3249                                                                 ptxvd->ulViewYOfs,
    3250                                                                 (ptxvd->flStyle & XS_AUTOVHIDE));
    3251                             WinInvalidateRect(hwndTextView, NULL, FALSE);
    3252                         }
    3253                     }
    3254                 }
    3255             }
     3398            mrc = ProcessJumpToAnchorName(hwndTextView, mp1);
    32563399        break;
    32573400
     
    32793422
    32803423        case TXM_QUERYTEXTEXTENT:
    3281             if (mp1)
     3424            if (    (mp1)
     3425                 && (ptxvd = (PTEXTVIEWWINDATA)WinQueryWindowPtr(hwndTextView, QWL_PRIVATE))
     3426               )
    32823427            {
    32833428                memcpy((PSIZEL)mp1,
     
    32943439
    32953440        case WM_DESTROY:
    3296             xstrClear(&ptxvd->xfd.strViewText);
    3297             lstClear(&ptxvd->xfd.llRectangles);
    3298             lstClear(&ptxvd->xfd.llWords);
    3299             GpiDestroyPS(ptxvd->hps);
    3300             free(ptxvd);
    3301             mrc = WinDefWindowProc(hwndTextView, msg, mp1, mp2);
     3441            mrc = ProcessDestroy(hwndTextView, mp1, mp2);
    33023442        break;
    33033443
Note: See TracChangeset for help on using the changeset viewer.