Mercurial > projects > mde
comparison mde/gui/widget/layout.d @ 139:29a524e7c858
Fixed a resizing issue and added a popup menu for all content.
author | Diggory Hardy <diggory.hardy@gmail.com> |
---|---|
date | Sun, 08 Feb 2009 11:55:36 +0000 |
parents | 3468e9bfded1 |
children | c94ec5594449 |
comparison
equal
deleted
inserted
replaced
138:3468e9bfded1 | 139:29a524e7c858 |
---|---|
625 return i; | 625 return i; |
626 } | 626 } |
627 | 627 |
628 /** Adjust total size with direction dir. | 628 /** Adjust total size with direction dir. |
629 * | 629 * |
630 * nw should be at least the minimal width. */ | 630 * nw should be at least the minimal width. |
631 * | |
632 * Returns: the final width */ | |
631 wdim resizeWidth (wdim nw, int dir) { | 633 wdim resizeWidth (wdim nw, int dir) { |
632 debug assert (width, "AlignColumns not initialized when resizeWidth called (code error)"); | 634 debug assert (width, "AlignColumns not initialized when resizeWidth called (code error)"); |
633 if (nw < mw) { | 635 debug if (nw < mw) { |
634 debug logger.warn ("Widget dimension set below minimal"); | 636 logger.warn ("Widget dimension set below minimal (code error)"); |
635 nw = mw; | 637 return w; |
636 } | 638 } |
637 if (nw == w) return w; | 639 if (nw == w) return w; |
638 | 640 |
639 wdim diff = nw - w; | 641 wdim diff = nw - w; |
640 if (firstSizable == -1) | 642 if (firstSizable == -1) |
704 wdim nd = 0; // negative diff to keep overall size constant if possible | 706 wdim nd = 0; // negative diff to keep overall size constant if possible |
705 wdim omw = minWidth[col]; // to check if mw actually changes | 707 wdim omw = minWidth[col]; // to check if mw actually changes |
706 if (minWidth[col] < nmw) { // increase minimal | 708 if (minWidth[col] < nmw) { // increase minimal |
707 minWidth[col] = nmw; | 709 minWidth[col] = nmw; |
708 nd = width[col] - nmw; // negative diff | 710 nd = width[col] - nmw; // negative diff |
711 if (nd > 0) | |
712 nd = 0; // don't decrease our width! | |
709 } else if (minWidth[col] > nmw) { // potentially decrease minimal | 713 } else if (minWidth[col] > nmw) { // potentially decrease minimal |
710 nmw = 0; | 714 nmw = 0; // set nmw to max of all cell min widths |
711 for (size_t r = 0; r < rows; ++r) { | 715 for (size_t r = 0; r < rows; ++r) { |
712 wdim mcw = minCellWidths[col+r*cols]; | 716 wdim mcw = minCellWidths[col+r*cols]; |
713 if (nmw < mcw) | 717 if (nmw < mcw) |
714 nmw = mcw; | 718 nmw = mcw; |
715 } | 719 } |
716 minWidth[col] = nmw; | 720 minWidth[col] = nmw; |
717 if (!sizable[col]) | 721 if (!sizable[col] && lastSizable >= 0) |
718 nd = width[col] - nmw; | 722 nd = width[col] - nmw; // Not resizable but another column is |
719 } else | 723 } else |
720 return false; | 724 return false; |
721 | 725 |
722 mw = spacing * cast(wdim)(cols - 1); | 726 mw = spacing * cast(wdim)(cols - 1); |
723 foreach (imw; minWidth) | 727 foreach (imw; minWidth) |
725 | 729 |
726 if (nd != 0) { // needs enlarging or shrinking | 730 if (nd != 0) { // needs enlarging or shrinking |
727 width[col] = nmw; | 731 width[col] = nmw; |
728 foreach (cb; cbs) | 732 foreach (cb; cbs) |
729 cb.setWidth (col, nmw, -1); | 733 cb.setWidth (col, nmw, -1); |
730 if (lastSizable >= 0) | 734 if (lastSizable >= 0) { |
731 adjustCellSizes (nd, lastSizable, -1); // doesn't necessarily resize exactly | 735 if (nd != adjustCellSizes (nd, lastSizable, -1)) |
736 logger.error ("New minimal size not applied correctly (code error): minWidth: {}, nmw: {}, col: {}, nd: {}", minWidth, nmw, col, nd); | |
737 } | |
732 genPositions; | 738 genPositions; |
733 } | 739 } |
734 | 740 |
735 bool mwChange = nmw != omw; // size only changes if true, presuming old size is valid | 741 bool mwChange = nmw != omw; // size only changes if true, presuming old size is valid |
736 foreach (cb; cbs) | 742 foreach (cb; cbs) |
757 * incr = direction to resize in (added to index each step). Must be either -1 or +1. | 763 * incr = direction to resize in (added to index each step). Must be either -1 or +1. |
758 * | 764 * |
759 * Returns: | 765 * Returns: |
760 * The amount adjusted. This may be larger than diff, since cellD is clamped by cellDMin. | 766 * The amount adjusted. This may be larger than diff, since cellD is clamped by cellDMin. |
761 * | 767 * |
762 * Doesn't touch non-sizable columns (except start which is only assumed sizable). | 768 * Will shrink non-sizable columns if they're over minimal size. |
769 * Will increase column start, since it's assumed sizable. | |
763 * | 770 * |
764 * Note: Check variable used for start is valid before calling! If a non-sizable column's | 771 * Note: Check variable used for start is valid before calling! If a non- |
765 * index is passed, this should get increased (if diff > 0) but not decreased. | 772 * sizable column's index is passed, this should get increased (if diff > 0) |
766 */ | 773 * but not decreased. */ |
767 private wdim adjustCellSizes (wdim diff, ptrdiff_t start, int incr) | 774 private wdim adjustCellSizes (wdim diff, ptrdiff_t start, int incr) |
768 in { | 775 in { |
769 assert (width.length == cols, "CellAlign.adjustCellSizes: width is invalid (code error)"); | 776 assert (width.length == cols, "CellAlign.adjustCellSizes: width is invalid (code error)"); |
770 // Most likely if passed negative when sizing is disabled: | 777 // Most likely if passed negative when sizing is disabled: |
771 assert (start >= 0 && start < cols, "adjustCellSizes: invalid start"); | 778 assert (start >= 0 && start < cols, "adjustCellSizes: invalid start"); |
778 foreach (cb; cbs) | 785 foreach (cb; cbs) |
779 cb.setWidth (i, width[i], incr); | 786 cb.setWidth (i, width[i], incr); |
780 } | 787 } |
781 else if (diff < 0) { // decrease | 788 else if (diff < 0) { // decrease |
782 wdim rd = diff; // running diff | 789 wdim rd = diff; // running diff |
783 aCSwhile: | 790 while (i >= 0 && i < cols) { |
784 while (true) { | 791 if (width[i] > minWidth[i]) { |
785 width[i] += rd; // decrease this cell's size (but may be too much) | 792 width[i] += rd; // decrease this cell's size (but may be too much) |
786 rd = width[i] - minWidth[i]; | 793 rd = width[i] - minWidth[i]; |
787 if (rd >= 0) { // OK; we're done | 794 if (rd >= 0) { // OK; we're done |
795 foreach (cb; cbs) | |
796 cb.setWidth (i, width[i], incr); | |
797 break; // we hit the mark exactly: diff is correct | |
798 } | |
799 | |
800 // else we decreased it too much! | |
801 width[i] = minWidth[i]; | |
788 foreach (cb; cbs) | 802 foreach (cb; cbs) |
789 cb.setWidth (i, width[i], incr); | 803 cb.setWidth (i, width[i], incr); |
790 break; // we hit the mark exactly: diff is correct | 804 // rd is remainder to decrease by |
791 } | 805 } |
792 | 806 |
793 // else we decreased it too much! | 807 i += incr; |
794 width[i] = minWidth[i]; | 808 } |
795 foreach (cb; cbs) | 809 diff -= rd; // still had rd left to decrease (may be 0) |
796 cb.setWidth (i, width[i], incr); | |
797 // rd is remainder to decrease by | |
798 | |
799 do { | |
800 i += incr; | |
801 if (i < 0 || i >= cols) { // run out of next cells | |
802 diff -= rd; // still had rd left to decrease | |
803 break aCSwhile; // exception: Array index out of bounds | |
804 } | |
805 } while (!sizable[i]) // iterate again if row/col isn't resizable | |
806 } | |
807 } | 810 } |
808 // else no adjustment needed (diff == 0) | 811 // else no adjustment needed (diff == 0) |
809 | 812 |
810 return diff; | 813 return diff; |
811 } | 814 } |