Initial community commit

This commit is contained in:
Jef 2024-09-24 14:54:57 +02:00
parent 537bcbc862
commit fc06254474
16440 changed files with 4239995 additions and 2 deletions

View file

@ -0,0 +1,661 @@
#include <precomp.h>
#include "alphamgr.h"
#include <api/wndmgr/layout.h>
#include <api/skin/skinparse.h>
#ifdef _WIN32
#include <tataki/blending/blending.h>
#endif
#include <bfc/util/profiler.h>
#include <bfc/wasabi_std_wnd.h>
#ifndef PI
#define PI 3.1415926536
#endif
#define ALPHAMGR_HOVERCHECK 100
#define ALPHAMGR_UPDATEALPHA 200
AlphaMgr::AlphaMgr() {
overlayout = NULL;
timerclient_setTimer(ALPHAMGR_HOVERCHECK, 200);
alllinked = 0;
autoopacify = 0;
fast_timer_on = 0;
big_curtransparency = 0;
big_status = STATUS_UNKNOWN;
big_startalpha = 0;
big_lasttimein = 0;
extend_px = 0;
global_alpha = 0;
big_enterleave_time = 0;
fadein_ms = 1;
fadeout_ms = 1;
holdtime_ms = 1;
}
AlphaMgr::~AlphaMgr()
{
timerclient_killTimer(ALPHAMGR_HOVERCHECK);
}
void AlphaMgr::addLayout(Layout *l)
{
checkTimer();
if (layouts.findItem((const wchar_t *)l))
return;
layouts.addItem(new AlphaMgrEntry(l));
}
void AlphaMgr::removeLayout(Layout *l) {
int p=-1;
AlphaMgrEntry *e = layouts.findItem((const wchar_t *)l, &p);
if (p != -1) {
if (e->getStatus() == STATUS_IN_FADINGON || e->getStatus() == STATUS_IN_ON) {
updateInList(e, 0);
checkTimer();
}
layouts.removeByPos(p);
in_layouts.removeItem(e);
delete e;
checkTimer();
}
}
// gets the currently needed transparency, according to layout overrides and global link, and then applies this
// transparency to the layout, it does not change anything in any data structure, this is only a visual update function
void AlphaMgr::updateTransparency(Layout *l) {
if (!l) return;
if (l->isInited()) {
if (l->isTransparencySafe()) {
int a = l->getTransparencyOverride();
if (a == -1) {
if (l->getNoParent()!=1) {
if (a == -1 && hasAutoOpacity(l))
a = getTransparency(l);
else if (a == -1 && getAllLinked())
a = getGlobalAlpha();
}
if (a == -1) {
/* why the hell would it care if it's alllinked if it's an independent window ?? (noparent=1)
if (getAllLinked())
a = getGlobalAlpha();
else
*/
a = l->getPaintingAlpha();
}
}
l->setTransparency(a);
} else {
l->setTransparency(255);
}
}
}
// returns the alpha value for this slot, that's not necessarily the transparency that should be applied to the layout
// since overrides & calculations in updateTransparency and getTransparency should apply.
int AlphaMgr::getAlpha(AlphaMgrEntry *e) {
if (alllinked && e->getLayout()->getNoParent() != 1) return getGlobalAlpha();
return e->getLayout()->getAlpha();
}
int AlphaMgr::getAlpha(Layout *l) {
int p=-1;
AlphaMgrEntry *e = layouts.findItem((const wchar_t *)l, &p);
if (p != -1) return getAlpha(e);
return l->getAlpha();
}
int AlphaMgr::getGlobalAlpha() {
return global_alpha;
}
void AlphaMgr::updateAllTransparency() {
foreach(layouts)
updateTransparency(layouts.getfor()->getLayout());
endfor;
}
void AlphaMgr::setGlobalAlpha(int a) {
global_alpha = a;
updateAllTransparency();
}
int AlphaMgr::getCurve(AlphaMgrEntry *e) {
int n;
int status = e ? e->getStatus() : getBigStatus();
if (e == NULL) {
n = MulDiv(Wasabi::Std::getTickCount()-getBigEnterLeaveTime(),256,status == STATUS_IN_FADINGON ? fadein_ms : fadeout_ms);
if (n > 255) n = 255; if (n < 0) n = 0;
} else {
if (e->getEnterLeaveTime() == -1) return -1;
n = MulDiv(Wasabi::Std::getTickCount()-e->getEnterLeaveTime(),256,status == STATUS_IN_FADINGON ? fadein_ms : fadeout_ms);
if (n > 255) n = 255; if (n < 0) n = 0;
}
return n;
}
// returns the value of the transparency if no override applies, you still need to check overrides (see updatetransparency)
int AlphaMgr::getTransparency(Layout *l) {
if (getAutoOpacify())
l = NULL;
if (l == NULL) {
if (getBigStatus() == STATUS_UNKNOWN) {
setBigStatus(STATUS_OUT_OFF);
Layout *main = SkinParser::getMainLayout();
if (main)
big_curtransparency = main->getTransparency();
else
big_curtransparency = 255;
}
}
AlphaMgrEntry *e = NULL;
if (l) e = layouts.findItem((const wchar_t *)l);
int s = e ? e->getStatus() : getBigStatus();
if (e && s == STATUS_UNKNOWN) {
initStatus(e);
s = e->getStatus();
}
switch (s) {
case STATUS_IN_OFF: return e ? getAlpha(e) : getGlobalAlpha();
case STATUS_OUT_OFF: return e ? getAlpha(e) : getGlobalAlpha();
case STATUS_IN_ON: return 255;
case STATUS_OUT_FADINGOUT: {
int n = e ? getCurve(e) : getCurve(NULL);
float sintrans = (float)(sin(((float)n/255)*PI-PI/2)/2+0.5);
int na;
if (e)
na = (int)(((float)(getAlpha(e) - e->getStartAlpha()) * sintrans) + e->getStartAlpha());
else
na = (int)(((float)(getGlobalAlpha() - getBigStartAlpha()) * sintrans) + getBigStartAlpha());
return na;
}
case STATUS_IN_FADINGON: {
int n = e ? getCurve(e) : getCurve(NULL);
float sintrans = (float)(sin(((float)n/255)*PI-PI/2)/2+0.5);
int na;
if (e)
na = (int)(((float)(255 - e->getStartAlpha()) * sintrans) + e->getStartAlpha());
else
na = (int)(((float)(255 - getBigStartAlpha()) * sintrans) + getBigStartAlpha());
return na;
}
default: return e ? getAlpha(e) : getGlobalAlpha();
}
}
int AlphaMgr::hasAutoOpacityOnHover(Layout *l) {
AlphaMgrEntry *e = layouts.findItem((const wchar_t *)l);
if (e) return hasAutoOpacityOnHover(e);
return 0;
}
int AlphaMgr::hasAutoOpacity(Layout *l) {
AlphaMgrEntry *e = layouts.findItem((const wchar_t *)l);
if (e) return hasAutoOpacity(e);
return 0;
}
int AlphaMgr::hasAutoOpacityOnFocus(Layout *l) {
AlphaMgrEntry *e = layouts.findItem((const wchar_t *)l);
if (e) return hasAutoOpacityOnFocus(e);
return 0;
}
int AlphaMgr::hasAutoOpacityOnFocus(AlphaMgrEntry *e) {
if (alllinked) return autoopacify == 2;
return e->getLayout()->getAutoOpacify() == 2 && e->getLayout()->getNoParent() != 1;
}
int AlphaMgr::hasAutoOpacityOnHover(AlphaMgrEntry *e) {
if (alllinked) return autoopacify == 1;
return e->getLayout()->getAutoOpacify() == 1 && e->getLayout()->getNoParent() != 1;
}
int AlphaMgr::hasAutoOpacity(AlphaMgrEntry *e) {
if (alllinked) return autoopacify;
return e->getLayout()->getAutoOpacify() && e->getLayout()->getNoParent() != 1;
}
// we got a new layout to manage, and its status flags is not set, we should init it to something safe
void AlphaMgr::initStatus(AlphaMgrEntry *l, int applytransparency) {
if (isMouseInLayout(l->getLayout())) {
l->setEnterLeaveTime((uint32_t)-1);
if (hasAutoOpacity(l)) {
l->setStatus(STATUS_IN_FADINGON);
l->onEnterLeave();
l->setStartAlpha(l->getLayout()->getTransparency());
checkTimer();
} else {
l->setStatus(STATUS_IN_OFF);
}
l->getLayout()->onMouseEnterLayout();
} else {
if (hasAutoOpacityOnHover(l)) {
l->setStartAlpha(l->getLayout()->getTransparency());
l->onEnterLeave();
l->setStatus(STATUS_OUT_FADINGOUT);
checkTimer();
} else {
l->setStatus(STATUS_OUT_OFF);
}
l->getLayout()->onMouseLeaveLayout();
}
if (applytransparency) updateTransparency(l->getLayout());
}
int AlphaMgr::isPointInLayout(Layout *l, int x, int y, api_region **rgn)
{
api_region *rg = NULL;
if (!l) return 0;
if (!l->isVisible()) return 0;
RECT r,r2;
l->getClientRect(&r);
if (l->renderRatioActive()) l->multRatio(&r);
l->getWindowRect(&r2);
Wasabi::Std::offsetRect(&r, r2.left, r2.top);
// OffsetRect(&r, r2.left, r2.top);
if (x < r.left || x > r.right || y < r.top || y > r.bottom) return 0;
if (rgn) {
if (!*rgn) {
rg = l->getComposedRegion();
*rgn = rg;
} else {
rg = *rgn;
}
} else {
rg = l->getComposedRegion();
}
if (!rgn) return 1;
x -= r.left; y -= r.top;
POINT pt={x,y};
if (l->renderRatioActive()) l->divRatio((int*)&pt.x, (int*)&pt.y);
if (l->getComposedRegion()->ptInRegion(&pt)) return 1;
return 0;
}
int AlphaMgr::isFocusInLayout(Layout *l) {
if (l->gotFocus()) return 1;
OSWINDOWHANDLE fw = Wasabi::Std::Wnd::getFocus();
while (fw)
{
if (fw == l->gethWnd()) return 1;
fw = Wasabi::Std::Wnd::getParent(fw);
}
return 0;
}
int AlphaMgr::isMouseInLayout(Layout *l) {
int isin = 0;
if (hasAutoOpacityOnFocus(l)) {
return isFocusInLayout(l);
} else {
int x, y;
api_region *r = NULL;
Wasabi::Std::getMousePos(&x, &y);
isin = isPointInLayout(l, x, y, &r);
int ext = getExtendAutoOpacity();
if (!isin && ext > 0) {
isin = isPointInLayout(l, x-ext, y, &r);
if (!isin) isin = isPointInLayout(l, x-ext, y-ext, &r);
if (!isin) isin = isPointInLayout(l, x, y-ext, &r);
if (!isin) isin = isPointInLayout(l, x+ext, y-ext, &r);
if (!isin) isin = isPointInLayout(l, x+ext, y, &r);
if (!isin) isin = isPointInLayout(l, x+ext, y+ext, &r);
if (!isin) isin = isPointInLayout(l, x, y+ext, &r);
if (!isin) isin = isPointInLayout(l, x-ext, y+ext, &r);
if (!isin) isin = isPointInLayout(l, x-ext, y, &r);
}
}
return isin;
}
int AlphaMgr::needForcedTransparencyFlag(Layout *l) {
if (!l->isTransparencySafe()) return 0;
if (l->isAlphaForced()) return 1;
if (l->getTransparencyOverride() > 0) return 1; // should not be testing for < 255 here
AlphaMgrEntry *e = layouts.findItem((const wchar_t *)l);
if (hasAutoOpacity(e) && getAlpha(e) < 255) return 1;
return 0;
}
void AlphaMgr::checkTimer() {
int fading = 0;
foreach(layouts)
AlphaMgrEntry *e = layouts.getfor();
if (e->getStatus() == STATUS_IN_FADINGON || e->getStatus() == STATUS_OUT_FADINGOUT) { fading++; break; }
endfor;
if (getAutoOpacify() && getBigStatus() == STATUS_IN_FADINGON || getBigStatus() == STATUS_OUT_FADINGOUT)
fading++;
if (fading && !fast_timer_on) {
timerclient_setTimer(ALPHAMGR_UPDATEALPHA, 20);
fast_timer_on = 1;
} else if (!fading && fast_timer_on) {
timerclient_killTimer(ALPHAMGR_UPDATEALPHA);
fast_timer_on = 0;
}
}
void AlphaMgr::doEndCheck(AlphaMgrEntry *e) {
if (getCurve(e) == 255) {
switch (e ? e->getStatus() : getBigStatus()) {
case STATUS_IN_FADINGON:
if (e) e->setStatus(STATUS_IN_ON); else setBigStatus(STATUS_IN_ON);
break;
case STATUS_OUT_FADINGOUT:
if (e) e->setStatus(STATUS_OUT_OFF); else setBigStatus(STATUS_OUT_OFF);
break;
}
checkTimer();
}
}
void AlphaMgr::updateInList(AlphaMgrEntry *e, int isin) {
if (isin) {
if (in_layouts.searchItem(e) == -1)
in_layouts.addItem(e);
} else {
in_layouts.removeItem(e);
}
int big_isin = in_layouts.getNumItems() > 0;
if (getAutoOpacify()) {
if (big_isin) {
// mouse is in a layout, autoopacity is on
switch (getBigStatus()) {
case STATUS_OUT_OFF:
case STATUS_OUT_FADINGOUT:
case STATUS_IN_OFF: {
setBigStartAlpha(e->getLayout()->getTransparency());
onBigEnterLeave();
setBigStatus(STATUS_IN_FADINGON);
checkTimer();
break;
}
case STATUS_IN_FADINGON:
doEndCheck(NULL);
break;
}
} else {
// mouse out of all layouts, autoopacity is on
switch (getBigStatus()) {
case STATUS_IN_FADINGON:
case STATUS_IN_ON: {
setBigStartAlpha(getTransparency(NULL));
onBigEnterLeave();
setBigStatus(STATUS_OUT_FADINGOUT);
checkTimer();
break;
}
case STATUS_OUT_FADINGOUT:
doEndCheck(NULL);
break;
}
}
} else {
if (big_isin) {
// mouse is in a layout, no autoopacity
setBigStatus(STATUS_IN_OFF);
} else {
// mouse is out of all layouts, no autoopacity
setBigStatus(STATUS_OUT_OFF);
}
}
}
int AlphaMgr::isFocusingExternalWindow()
{
OSWINDOWHANDLE fw = Wasabi::Std::Wnd::getFocus();
if (isOurExternalWindow(fw)) return 1;
return 0;
}
int AlphaMgr::isOverExternalWindow()
{
int x, y;
Wasabi::Std::getMousePos(&x, &y);
int ext = getExtendAutoOpacity();
POINT pt;
pt.x = x; pt.y = y;
OSWINDOWHANDLE w = Wasabi::Std::Wnd::getWindowFromPoint(pt);
if (isOurExternalWindow(w)) return 1;
pt.x = x-ext; pt.y = y-ext;
w = Wasabi::Std::Wnd::getWindowFromPoint(pt);
if (isOurExternalWindow(w)) return 1;
pt.x = x; pt.y = y-ext;
w = Wasabi::Std::Wnd::getWindowFromPoint(pt);
if (isOurExternalWindow(w)) return 1;
pt.x = x+ext; pt.y = y-ext;
w = Wasabi::Std::Wnd::getWindowFromPoint(pt);
if (isOurExternalWindow(w)) return 1;
pt.x = x+ext; pt.y = y;
w = Wasabi::Std::Wnd::getWindowFromPoint(pt);
if (isOurExternalWindow(w)) return 1;
pt.x = x+ext; pt.y = y+ext;
w = Wasabi::Std::Wnd::getWindowFromPoint(pt);
if (isOurExternalWindow(w)) return 1;
pt.x = x; pt.y = y+ext;
w = Wasabi::Std::Wnd::getWindowFromPoint(pt);
if (isOurExternalWindow(w)) return 1;
pt.x = x-ext; pt.y = y+ext;
w = Wasabi::Std::Wnd::getWindowFromPoint(pt);
if (isOurExternalWindow(w)) return 1;
pt.x = x-ext; pt.y = y;
w = Wasabi::Std::Wnd::getWindowFromPoint(pt);
if (isOurExternalWindow(w)) return 1;
return 0;
}
int AlphaMgr::isWasabiWindow(OSWINDOWHANDLE w)
{
#ifdef _WIN32
wchar_t classname[256]=L"";
GetClassNameW(w, classname, 255);
return (w == WASABI_API_WND->main_getRootWnd()->gethWnd() || !wcscmp(classname, BASEWNDCLASSNAME));
#else
#warning port me
return 1;
#endif
}
int AlphaMgr::isMenuWindow(OSWINDOWHANDLE w)
{
#ifdef _WIN32
char classname[256]="";
GetClassNameA(w, classname, 255);
return STRCASEEQL(classname, "#32768");
#else
return 0;
#warning port me
#endif
}
int AlphaMgr::isOurExternalWindow(OSWINDOWHANDLE w)
{
OSWINDOWHANDLE wnd = w;
if (isWasabiWindow(w))
return 0;
if (isMenuWindow(wnd)) {
wnd = Wasabi::Std::Wnd::getFocus();
if (isWasabiWindow(wnd) || isOurExternalWindow(wnd))
return 1;
}
while (wnd)
{
if (Wasabi::Std::Wnd::isPopup(wnd))
{
if (isWasabiWindow(wnd))
return 0;
OSWINDOWHANDLE _w = Wasabi::Std::Wnd::getParent(wnd);
#ifdef _WIN32
if (!_w) _w = GetWindow(wnd, GW_OWNER);
#else
#warning port me
#endif
if (!wnd) _w = wnd;
return (_w == WASABI_API_WND->main_getRootWnd()->gethWnd() || isWasabiWindow(_w) || isOurExternalWindow(_w));
}
wnd = Wasabi::Std::Wnd::getParent(wnd);
}
return 0;
}
void AlphaMgr::preHoverCheck(AlphaMgrEntry *e) {
int isin = isMouseInLayout(e->getLayout());
uint32_t last = e->getLastTimeIn();
uint32_t lastbig = getBigLastTimeIn();
if (isin) { e->onLastIn(); onBigLastIn(); }
if (!getAutoOpacify()) {
if (!isin && last != 0 && (last > Wasabi::Std::getTickCount() - holdtime_ms))
isin = 1;
} else {
if (!isin && lastbig != 0 && (lastbig > Wasabi::Std::getTickCount() - holdtime_ms))
isin = 1;
}
if (!isin) {
if (hasAutoOpacityOnFocus(e)) {
if (isFocusingExternalWindow()) isin = 1;
} else {
if (isOverExternalWindow()) isin = 1;
}
}
e->setNextIn(isin);
updateInList(e, isin);
}
void AlphaMgr::hoverCheck(Layout *l) {
AlphaMgrEntry *e = layouts.findItem((const wchar_t *)l);
if (e) hoverCheck(e);
}
void AlphaMgr::hoverCheck(AlphaMgrEntry *e, int applytransparency) {
if (e->getStatus() == STATUS_UNKNOWN)
initStatus(e);
int isin = e->getNextIn();
if (getAutoOpacify()) {
isin = big_status == STATUS_IN_FADINGON || big_status == STATUS_IN_ON || big_status == STATUS_IN_OFF;
}
if (hasAutoOpacity(e)) {
if (isin) {
// mouse is in, autoopacity is on
switch (e->getStatus()) {
case STATUS_OUT_OFF:
case STATUS_OUT_FADINGOUT:
case STATUS_IN_OFF:
e->setStartAlpha(e->getLayout()->getTransparency());
e->onEnterLeave();
e->setStatus(STATUS_IN_FADINGON);
checkTimer();
e->getLayout()->onMouseEnterLayout();
break;
case STATUS_IN_FADINGON:
doEndCheck(e);
break;
}
} else {
// mouse is out, autoopacity is on
switch (e->getStatus()) {
case STATUS_IN_FADINGON:
case STATUS_IN_ON:
e->setStartAlpha(e->getLayout()->getTransparency());
e->onEnterLeave();
e->setStatus(STATUS_OUT_FADINGOUT);
checkTimer();
e->getLayout()->onMouseLeaveLayout();
break;
case STATUS_OUT_FADINGOUT:
doEndCheck(e);
break;
}
}
} else {
if (isin) {
// mouse is in, no autoopacity
e->setStatus(STATUS_IN_OFF);
} else {
// mouse is out, no autoopacity
e->setStatus(STATUS_OUT_OFF);
}
}
// if (applytransparency) updateTransparency(e->getLayout());
}
void AlphaMgr::timerclient_timerCallback(int id) {
switch(id) {
case ALPHAMGR_HOVERCHECK: {
foreach(layouts)
AlphaMgrEntry *e = layouts.getfor();
preHoverCheck(e);
endfor;
foreach(layouts)
AlphaMgrEntry *e = layouts.getfor();
hoverCheck(e);
endfor;
}
break;
case ALPHAMGR_UPDATEALPHA: {
foreach(layouts)
AlphaMgrEntry *e = layouts.getfor();
if (e->getStatus() == STATUS_IN_FADINGON || e->getStatus() == STATUS_OUT_FADINGOUT) updateTransparency(e->getLayout());
endfor;
}
break;
}
}
int AlphaMgr::getBigCurTransparency() {
switch (getBigStatus()) {
case STATUS_IN_FADINGON:
case STATUS_OUT_FADINGOUT:
return getTransparency(NULL);
case STATUS_IN_ON:
return 255;
case STATUS_IN_OFF:
case STATUS_OUT_OFF:
return getGlobalAlpha();
default: return getTransparency(NULL);
}
}
void AlphaMgr::setBigStartAlpha(int a) {
big_startalpha = a;
}
void AlphaMgr::setBigStatus(int s) {
big_status = s;
}
void AlphaMgr::onBigEnterLeave() {
big_enterleave_time = Wasabi::Std::getTickCount();
}
uint32_t AlphaMgr::getBigEnterLeaveTime() {
return big_enterleave_time;
}
void AlphaMgr::setAutoOpacify(int l) {
autoopacify = l;
resetTimer();
if (l == 0) {
foreach(layouts)
if (layouts.getfor()->getStatus() == STATUS_IN_FADINGON) layouts.getfor()->setStatus(STATUS_IN_OFF);
if (layouts.getfor()->getStatus() == STATUS_OUT_FADINGOUT) layouts.getfor()->setStatus(STATUS_OUT_OFF);
endfor;
}
updateAllTransparency();
}
void AlphaMgr::resetTimer() {
timerclient_killTimer(ALPHAMGR_HOVERCHECK);
if (autoopacify == 1 && alllinked)
timerclient_setTimer(ALPHAMGR_HOVERCHECK, 99);
else
timerclient_setTimer(ALPHAMGR_HOVERCHECK, 300);
}

View file

@ -0,0 +1,136 @@
#ifndef _ALPHAMGR_H
#define _ALPHAMGR_H
#include <api/timer/timerclient.h>
class Layout;
#define STATUS_UNKNOWN -1
#define STATUS_OUT_OFF 0
#define STATUS_IN_ON 1
#define STATUS_OUT_FADINGOUT 2
#define STATUS_IN_FADINGON 3
#define STATUS_IN_OFF 4 // when no autoopacity
class AlphaMgrEntry {
public:
AlphaMgrEntry(Layout *l) : layout(l), status(STATUS_UNKNOWN), fade_val(-1), startalpha(-1), lasttime_in(0), next_in(-1) {}
virtual ~AlphaMgrEntry() { }
Layout *getLayout() { return layout; }
int getStatus() { return status; }
void onEnterLeave() { enterleave_time = Wasabi::Std::getTickCount(); }
int getEnterLeaveTime() { return enterleave_time; }
void setEnterLeaveTime(uint32_t t) { enterleave_time = t; }
void setStatus(int s) { status = s; }
int getStartAlpha() { return startalpha; }
void setStartAlpha(int s) { startalpha = s; }
uint32_t getLastTimeIn() { return lasttime_in; }
void onLastIn() { lasttime_in = Wasabi::Std::getTickCount(); }
void setNextIn(int i) { next_in = i; }
int getNextIn() { return next_in; }
private:
Layout *layout;
int status;
int fade_val;
uint32_t enterleave_time;
int startalpha;
uint32_t lasttime_in;
int next_in;
};
class AlphaMgrEntryComparator {
public:
static int compareItem(AlphaMgrEntry *p1, AlphaMgrEntry* p2) {
return CMP3((void*)p1->getLayout(), (void *)p2->getLayout());
}
static int compareAttrib(const wchar_t *attrib, AlphaMgrEntry *item) {
return CMP3((void *)attrib, (void *)item->getLayout());
}
};
class AlphaMgr : public TimerClientDI {
public:
AlphaMgr();
virtual ~AlphaMgr();
void addLayout(Layout *l);
void removeLayout(Layout *l);
virtual void timerclient_timerCallback(int id);
void updateTransparency(Layout *l);
int getTransparency(Layout *l);
int getGlobalAlpha();
void setGlobalAlpha(int a);
int isFocusInLayout(Layout *l);
int isMouseInLayout(Layout *l);
int isPointInLayout(Layout *l, int x, int y, api_region **rgn=NULL);
int needForcedTransparencyFlag(Layout *l);
int hasAutoOpacity(Layout *l);
int hasAutoOpacityOnHover(Layout *l);
int hasAutoOpacityOnFocus(Layout *l);
void setAllLinked(int l) { alllinked = l; resetTimer(); updateAllTransparency(); }
void setAutoOpacify(int l);
int getAllLinked() { return alllinked; }
int getAutoOpacify() { return (autoopacify && alllinked) ? autoopacify : 0; }
void setExtendAutoOpacity(int n) { extend_px = n; }
int getExtendAutoOpacity() { return extend_px; }
int getBigCurTransparency();
void setFadeInTime(int ms) { fadein_ms = MAX(ms, 1); }
void setFadeOutTime(int ms) { fadeout_ms = MAX(ms, 1); }
void setHoldTime(int ms) { holdtime_ms = ms; }
void hoverCheck(Layout *l);
int getAlpha(Layout *l);
private:
void updateAllTransparency();
void updateInList(AlphaMgrEntry *e, int isin);
void setBigStartAlpha(int a);
int getBigStartAlpha() { return big_startalpha; }
void onBigEnterLeave();
uint32_t getBigEnterLeaveTime();
void setBigStatus(int s);
int getBigStatus() { return big_status; }
void initStatus(AlphaMgrEntry *e, int applytransparency=0);
int getAlpha(AlphaMgrEntry *e);
int hasAutoOpacityOnHover(AlphaMgrEntry *e);
int hasAutoOpacityOnFocus(AlphaMgrEntry *e);
int hasAutoOpacity(AlphaMgrEntry *e);
void checkTimer();
void hoverCheck(AlphaMgrEntry *e, int applytransparency=1);
void preHoverCheck(AlphaMgrEntry *e);
int getCurve(AlphaMgrEntry *e);
void doEndCheck(AlphaMgrEntry *e);
void onBigLastIn() { big_lasttimein = Wasabi::Std::getTickCount(); }
uint32_t getBigLastTimeIn() { return big_lasttimein; }
int isFocusingExternalWindow();
int isOverExternalWindow();
int isOurExternalWindow(OSWINDOWHANDLE w);
int isWasabiWindow(OSWINDOWHANDLE w);
int isMenuWindow(OSWINDOWHANDLE w);
void resetTimer();
PtrListQuickSorted<AlphaMgrEntry, AlphaMgrEntryComparator> layouts;
PtrListQuickSortedByPtrVal<AlphaMgrEntry> in_layouts;
Layout *overlayout;
int alllinked;
int autoopacify;
int global_alpha;
int fast_timer_on;
int big_status;
int big_curtransparency;
int big_startalpha;
uint32_t big_enterleave_time;
int big_lasttimein;
int fadein_ms;
int fadeout_ms;
int holdtime_ms;
int extend_px;
};
#endif

View file

@ -0,0 +1,96 @@
#include <precomp.h>
#include <wasabicfg.h>
#include "animate.h"
#include <api/config/items/cfgitem.h>
//---------------------------------------------------------------------------
void AnimatedRects::draw(const RECT *source, const RECT *dest, int steps)
{
#ifdef WASABI_COMPILE_CONFIG
// {280876CF-48C0-40bc-8E86-73CE6BB462E5}
const GUID options_guid =
{ 0x280876cf, 0x48c0, 0x40bc, { 0x8e, 0x86, 0x73, 0xce, 0x6b, 0xb4, 0x62, 0xe5 } };
if (!_intVal(WASABI_API_CONFIG->config_getCfgItemByGuid(options_guid), L"Animated rects")) return;
#else
if (!WASABI_WNDMGR_ANIMATEDRECTS) return;
#endif
//FG> Not anymore, old code, old bugs
//BU you're so cool, Francis
//FG> thank you, you're not too bad either :)
int sizex=source->right-source->left-(dest->right-dest->left);
int sizey=source->bottom-source->top-(dest->bottom-dest->top);
int diffx=source->left-dest->left;
int diffy=(source->top)-dest->top;
#ifdef WIN32
HDC dc;
dc=GetDC(0);
HBRUSH brush = CreateSolidBrush(0xFFFFFF);
HPEN pen = CreatePen(PS_SOLID,0,0xFFFFFF);
HBRUSH obrush = (HBRUSH)SelectObject(dc, brush);
HPEN open = (HPEN)SelectObject(dc, pen);
int oldrop = SetROP2(dc,R2_XORPEN);
#endif
#ifdef LINUX
HDC dc = (HDC)MALLOC( sizeof( hdc_typ ) );
XGCValues gcv;
gcv.foreground = 0xffffff;
gcv.function = GXxor;
gcv.subwindow_mode = IncludeInferiors;
dc->gc = XCreateGC( Linux::getDisplay(), Linux::RootWin(), GCForeground | GCFunction | GCSubwindowMode, &gcv );
#endif
//PORTME
for(int i=0;i<steps;i++) {
int x=dest->left+diffx-((diffx*i)/steps);
int y=dest->top+diffy-((diffy*i)/steps);
int maxx=(source->right-source->left)-((sizex*i)/steps);
int maxy=(source->bottom-source->top)-((sizey*i)/steps);
#ifdef WIN32
int p1x=x,p1y=y;
int p2x=x+maxx,p2y=y;
int p3x=x+maxx,p3y=y+maxy;
int p4x=x,p4y=y+maxy;
MoveToEx(dc,p1x,p1y,NULL);
LineTo(dc,p2x,p2y);
LineTo(dc,p3x,p3y);
LineTo(dc,p4x,p4y);
LineTo(dc,p1x,p1y);
#endif
#ifdef LINUX
XDrawRectangle( Linux::getDisplay(), Linux::RootWin(), dc->gc,
x, y, maxx, maxy );
#endif
//PORTME
Wasabi::Std::usleep(5);
#ifdef WIN32
MoveToEx(dc,p1x,p1y,NULL);
LineTo(dc,p2x,p2y);
LineTo(dc,p3x,p3y);
LineTo(dc,p4x,p4y);
LineTo(dc,p1x,p1y);
#endif
#ifdef LINUX
XDrawRectangle( Linux::getDisplay(), Linux::RootWin(), dc->gc,
x, y, maxx, maxy );
#endif
//PORTME
}
#ifdef WIN32
SetROP2(dc, oldrop);
SelectObject(dc, open);
SelectObject(dc, obrush);
DeleteObject(brush);
DeleteObject(pen);
ReleaseDC(0,dc);
#endif
#ifdef LINUX
XFreeGC( Linux::getDisplay(), dc->gc );
FREE( dc );
#endif
//PORTME
}

View file

@ -0,0 +1,11 @@
#ifndef _ANIMATE_H
#define _ANIMATE_H
#include <bfc/wasabi_std.h>
class AnimatedRects {
public:
static void draw(const RECT *src, const RECT *dst, int nsteps=5);
};
#endif

View file

@ -0,0 +1,47 @@
#include <precomp.h>
#include "api_wndmgr.h"
#ifdef CBCLASS
#undef CBCLASS
#endif
#define CBCLASS wndmgr_apiI
START_DISPATCH;
VCB(WNDMGR_API_WNDTRACKADD, wndTrackAdd);
VCB(WNDMGR_API_WNDTRACKREMOVE, wndTrackRemove);
CB(WNDMGR_API_WNDTRACKDOCK, wndTrackDock);
CB(WNDMGR_API_WNDTRACKDOCK2, wndTrackDock2);
VCB(WNDMGR_API_WNDTRACKSTARTCOOPERATIVE, wndTrackStartCooperative);
VCB(WNDMGR_API_WNDTRACKENDCOOPERATIVE, wndTrackEndCooperative);
CB(WNDMGR_API_WNDTRACKWASCOOPERATIVE, wndTrackWasCooperative);
VCB(WNDMGR_API_WNDTRACKINVALIDATEALL, wndTrackInvalidateAll);
CB(WNDMGR_API_SKINWND_TOGGLEBYGUID, skinwnd_toggleByGuid);
CB(WNDMGR_API_SKINWND_TOGGLEBYGROUPID, skinwnd_toggleByGroupId);
CB(WNDMGR_API_SKINWND_CREATEBYGUID, skinwnd_createByGuid);
CB(WNDMGR_API_SKINWND_CREATEBYGROUPID, skinwnd_createByGroupId);
VCB(WNDMGR_API_SKINWND_DESTROY, skinwnd_destroy);
CB(WNDMGR_API_SKINWND_GETNUMBYGUID, skinwnd_getNumByGuid);
CB(WNDMGR_API_SKINWND_ENUMBYGUID, skinwnd_enumByGuid);
CB(WNDMGR_API_SKINWND_GETNUMBYGROUPID, skinwnd_getNumByGroupId);
CB(WNDMGR_API_SKINWND_ENUMBYGROUPID, skinwnd_enumByGroupId);
VCB(WNDMGR_API_SKINWND_ATTACHTOSKIN, skinwnd_attachToSkin);
//CB(WNDMGR_API_SKIN_GETCONTAINER, skin_getContainer);
//CB(WNDMGR_API_SKIN_GETLAYOUT, skin_getLayout);
VCB(WNDMGR_API_WNDHOLDER_REGISTER, wndholder_register);
VCB(WNDMGR_API_WNDHOLDER_UNREGISTER, wndholder_unregister);
CB(WNDMGR_API_MESSAGEBOX, messageBox);
CB(WNDMGR_API_GETMODALWND, getModalWnd);
VCB(WNDMGR_API_PUSHMODALWND, pushModalWnd);
VCB(WNDMGR_API_POPMODALWND, popModalWnd);
VCB(WNDMGR_API_DRAWANIMATEDRECTS, drawAnimatedRects);
CB(WNDMGR_API_AUTOPOPUP_REGISTERGUID, autopopup_registerGuid);
CB(WNDMGR_API_AUTOPOPUP_REGISTERGROUPID, autopopup_registerGroupId);
VCB(WNDMGR_API_AUTOPOPUP_UNREGISTER, autopopup_unregister);
CB(WNDMGR_API_AUTOPOPUP_GETNUMGUIDS, autopopup_getNumGuids);
CB(WNDMGR_API_AUTOPOPUP_ENUMGUID, autopopup_enumGuid);
CB(WNDMGR_API_AUTOPOPUP_GETNUMGROUPS, autopopup_getNumGroups);
CB(WNDMGR_API_AUTOPOPUP_ENUMGROUPS, autopopup_enumGroup);
CB(WNDMGR_API_AUTOPOPUP_ENUMGUIDDESC, autopopup_enumGuidDescription);
CB(WNDMGR_API_AUTOPOPUP_ENUMGROUPDESC, autopopup_enumGroupDescription);
CB(WNDMGR_API_VARMGR_TRANSLATE, varmgr_translate);
CB(WNDMGR_API_NEWDYNAMICCONTAINER, newDynamicContainer);
END_DISPATCH;

View file

@ -0,0 +1,305 @@
#ifndef __WNDMGR_API_H
#define __WNDMGR_API_H
#include <bfc/dispatch.h>
#include <bfc/nsguid.h>
class ifc_window;
class WindowHolder;
class Container;
class ScriptObject;
#ifndef MODALWND_DEF
#define MODALWND_DEF
ifc_window *const MODALWND_NOWND = reinterpret_cast<ifc_window*>(-1);
#endif
class wndmgr_api : public Dispatchable {
public:
void wndTrackAdd(ifc_window *wnd);
void wndTrackRemove(ifc_window *wnd);
bool wndTrackDock(ifc_window *wnd, RECT *r, int mask);
bool wndTrackDock(ifc_window *wnd, RECT *r, RECT *orig_r, int mask);
void wndTrackStartCooperative(ifc_window *wnd);
void wndTrackEndCooperative();
int wndTrackWasCooperative();
void wndTrackInvalidateAll();
int skinwnd_toggleByGuid(GUID g, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0);
int skinwnd_toggleByGroupId(const wchar_t *groupid, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0);
ifc_window *skinwnd_createByGuid(GUID g, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0, int starthidden = 0, int *isnew = NULL);
ifc_window *skinwnd_createByGroupId(const wchar_t *groupid, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0, int starthidden = 0, int *isnew = NULL);
void skinwnd_destroy(ifc_window *w, RECT *destanimrect = NULL);
int skinwnd_getNumByGuid(GUID g);
ifc_window *skinwnd_enumByGuid(GUID g, int n);
int skinwnd_getNumByGroupId(const wchar_t *groupid);
ifc_window *skinwnd_enumByGroupId(const wchar_t *groupid, int n);
void skinwnd_attachToSkin(ifc_window *w, int side, int size);
//ScriptObject *skin_getContainer(const wchar_t *container_name);
//ScriptObject *skin_getLayout(ScriptObject *container, const wchar_t *layout_name);
void wndholder_register(WindowHolder *wh);
void wndholder_unregister(WindowHolder *wh);
int messageBox(const wchar_t *txt, const wchar_t *title, int flags, const wchar_t *not_anymore_identifier, ifc_window *parenwnt);
ifc_window *getModalWnd();
void pushModalWnd(ifc_window *w = MODALWND_NOWND);
void popModalWnd(ifc_window *w = MODALWND_NOWND);
void drawAnimatedRects(const RECT *r1, const RECT *r2);
int autopopup_registerGuid(GUID g, const wchar_t *desc, const wchar_t *prefered_container = NULL, int container_flag = 0);
int autopopup_registerGroupId(const wchar_t *groupid, const wchar_t *desc, const wchar_t *prefered_container = NULL, int container_flag = 0);
void autopopup_unregister(int id);
int autopopup_getNumGuids();
GUID autopopup_enumGuid(int n);
int autopopup_getNumGroups();
const wchar_t *autopopup_enumGroup(int n);
const wchar_t *autopopup_enumGuidDescription(int n);
const wchar_t *autopopup_enumGroupDescription(int n);
const wchar_t *varmgr_translate(const wchar_t *str);
//Container *newDynamicContainer(const wchar_t *containername, int transcient = 1);
enum {
WNDMGR_API_WNDTRACKADD = 0,
WNDMGR_API_WNDTRACKREMOVE = 10,
WNDMGR_API_WNDTRACKDOCK = 20,
WNDMGR_API_WNDTRACKDOCK2 = 30,
WNDMGR_API_WNDTRACKSTARTCOOPERATIVE = 40,
WNDMGR_API_WNDTRACKENDCOOPERATIVE = 50,
WNDMGR_API_WNDTRACKWASCOOPERATIVE = 60,
WNDMGR_API_WNDTRACKINVALIDATEALL = 70,
WNDMGR_API_SKINWND_TOGGLEBYGUID = 80,
WNDMGR_API_SKINWND_TOGGLEBYGROUPID = 90,
WNDMGR_API_SKINWND_CREATEBYGUID = 100,
WNDMGR_API_SKINWND_CREATEBYGROUPID = 110,
WNDMGR_API_SKINWND_DESTROY = 120,
WNDMGR_API_SKINWND_GETNUMBYGUID = 130,
WNDMGR_API_SKINWND_ENUMBYGUID = 140,
WNDMGR_API_SKINWND_GETNUMBYGROUPID = 150,
WNDMGR_API_SKINWND_ENUMBYGROUPID = 160,
WNDMGR_API_SKINWND_ATTACHTOSKIN = 170,
//WNDMGR_API_SKIN_GETCONTAINER = 180,
WNDMGR_API_SKIN_GETLAYOUT = 190,
WNDMGR_API_WNDHOLDER_REGISTER = 200,
WNDMGR_API_WNDHOLDER_UNREGISTER = 210,
WNDMGR_API_MESSAGEBOX = 220,
WNDMGR_API_GETMODALWND = 230,
WNDMGR_API_PUSHMODALWND = 240,
WNDMGR_API_POPMODALWND = 250,
WNDMGR_API_DRAWANIMATEDRECTS = 260,
WNDMGR_API_AUTOPOPUP_REGISTERGUID = 270,
WNDMGR_API_AUTOPOPUP_REGISTERGROUPID = 280,
WNDMGR_API_AUTOPOPUP_UNREGISTER = 290,
WNDMGR_API_VARMGR_TRANSLATE = 300,
WNDMGR_API_NEWDYNAMICCONTAINER = 310,
WNDMGR_API_AUTOPOPUP_GETNUMGUIDS = 320,
WNDMGR_API_AUTOPOPUP_ENUMGUID = 330,
WNDMGR_API_AUTOPOPUP_GETNUMGROUPS = 340,
WNDMGR_API_AUTOPOPUP_ENUMGROUPS = 350,
WNDMGR_API_AUTOPOPUP_ENUMGUIDDESC = 360,
WNDMGR_API_AUTOPOPUP_ENUMGROUPDESC = 370,
};
};
inline void wndmgr_api::wndTrackAdd(ifc_window *wnd) {
_voidcall(WNDMGR_API_WNDTRACKADD, wnd);
}
inline void wndmgr_api::wndTrackRemove(ifc_window *wnd) {
_voidcall(WNDMGR_API_WNDTRACKREMOVE, wnd);
}
inline bool wndmgr_api::wndTrackDock(ifc_window *wnd, RECT *r, int mask) {
return _call(WNDMGR_API_WNDTRACKDOCK, (bool)FALSE, wnd, r, mask);
}
inline bool wndmgr_api::wndTrackDock(ifc_window *wnd, RECT *r, RECT *orig_r, int mask) {
return _call(WNDMGR_API_WNDTRACKDOCK2, (bool)FALSE, wnd, r, orig_r, mask);
}
inline void wndmgr_api::wndTrackStartCooperative(ifc_window *wnd) {
_voidcall(WNDMGR_API_WNDTRACKSTARTCOOPERATIVE, wnd);
}
inline void wndmgr_api::wndTrackEndCooperative() {
_voidcall(WNDMGR_API_WNDTRACKENDCOOPERATIVE);
}
inline int wndmgr_api::wndTrackWasCooperative() {
return _call(WNDMGR_API_WNDTRACKWASCOOPERATIVE, (int)0);
}
inline void wndmgr_api::wndTrackInvalidateAll() {
_voidcall(WNDMGR_API_WNDTRACKINVALIDATEALL);
}
inline int wndmgr_api::skinwnd_toggleByGuid(GUID g, const wchar_t *prefered_container, int container_flag, RECT *sourceanimrect, int transcient) {
return _call(WNDMGR_API_SKINWND_TOGGLEBYGUID, (int)0, g, prefered_container, container_flag, sourceanimrect, transcient);
}
inline int wndmgr_api::skinwnd_toggleByGroupId(const wchar_t *groupid, const wchar_t *prefered_container, int container_flag, RECT *sourceanimrect, int transcient) {
return _call(WNDMGR_API_SKINWND_TOGGLEBYGROUPID, (int)0, groupid, prefered_container, container_flag, sourceanimrect, transcient);
}
inline ifc_window *wndmgr_api::skinwnd_createByGuid(GUID g, const wchar_t *prefered_container, int container_flag, RECT *sourceanimrect, int transcient, int starthidden, int *isnew) {
return _call(WNDMGR_API_SKINWND_CREATEBYGUID, (ifc_window *)NULL, g, prefered_container, container_flag, sourceanimrect, transcient, starthidden, isnew);
}
inline ifc_window *wndmgr_api::skinwnd_createByGroupId(const wchar_t *groupid, const wchar_t *prefered_container, int container_flag, RECT *sourceanimrect, int transcient, int starthidden, int *isnew) {
return _call(WNDMGR_API_SKINWND_CREATEBYGROUPID, (ifc_window *)NULL, groupid, prefered_container, container_flag, sourceanimrect, transcient, starthidden, isnew);
}
inline void wndmgr_api::skinwnd_destroy(ifc_window *w, RECT *destanimrect) {
_voidcall(WNDMGR_API_SKINWND_DESTROY, w, destanimrect);
}
inline int wndmgr_api::skinwnd_getNumByGuid(GUID g) {
return _call(WNDMGR_API_SKINWND_GETNUMBYGUID, (int)0, g);
}
inline ifc_window *wndmgr_api::skinwnd_enumByGuid(GUID g, int n) {
return _call(WNDMGR_API_SKINWND_ENUMBYGUID, (ifc_window *)NULL, g, n);
}
inline int wndmgr_api::skinwnd_getNumByGroupId(const wchar_t *groupid) {
return _call(WNDMGR_API_SKINWND_GETNUMBYGROUPID, (int)0, groupid);
}
inline ifc_window *wndmgr_api::skinwnd_enumByGroupId(const wchar_t *groupid, int n) {
return _call(WNDMGR_API_SKINWND_ENUMBYGROUPID, (ifc_window *)NULL, groupid, n);
}
inline void wndmgr_api::skinwnd_attachToSkin(ifc_window *w, int side, int size) {
_voidcall(WNDMGR_API_SKINWND_ATTACHTOSKIN, w, side, size);
}
/*
inline ScriptObject *wndmgr_api::skin_getContainer(const wchar_t *container_name) {
return _call(WNDMGR_API_SKIN_GETCONTAINER, (ScriptObject *)NULL, container_name);
}
*/
/*
inline ScriptObject *wndmgr_api::skin_getLayout(ScriptObject *container, const wchar_t *layout_name) {
return _call(WNDMGR_API_SKIN_GETLAYOUT, (ScriptObject *)NULL, container, layout_name);
}
*/
inline void wndmgr_api::wndholder_register(WindowHolder *wh) {
_voidcall(WNDMGR_API_WNDHOLDER_REGISTER, wh);
}
inline void wndmgr_api::wndholder_unregister(WindowHolder *wh) {
_voidcall(WNDMGR_API_WNDHOLDER_UNREGISTER, wh);
}
inline int wndmgr_api::messageBox(const wchar_t *txt, const wchar_t *title, int flags, const wchar_t *not_anymore_identifier, ifc_window *parenwnt) {
return _call(WNDMGR_API_MESSAGEBOX, (int)0, txt, title, flags, not_anymore_identifier, parenwnt);
}
inline ifc_window *wndmgr_api::getModalWnd() {
return _call(WNDMGR_API_GETMODALWND, (ifc_window *)NULL);
}
inline void wndmgr_api::pushModalWnd(ifc_window *w) {
_voidcall(WNDMGR_API_PUSHMODALWND, w);
}
inline void wndmgr_api::popModalWnd(ifc_window *w) {
_voidcall(WNDMGR_API_POPMODALWND, w);
}
inline void wndmgr_api::drawAnimatedRects(const RECT *r1, const RECT *r2) {
_voidcall(WNDMGR_API_DRAWANIMATEDRECTS, r1, r2);
}
inline int wndmgr_api::autopopup_registerGuid(GUID g, const wchar_t *desc, const wchar_t *prefered_container, int container_flag) {
return _call(WNDMGR_API_AUTOPOPUP_REGISTERGUID, (int)0, g, desc, prefered_container, container_flag);
}
inline int wndmgr_api::autopopup_registerGroupId(const wchar_t *groupid, const wchar_t *desc, const wchar_t *prefered_container, int container_flag) {
return _call(WNDMGR_API_AUTOPOPUP_REGISTERGROUPID, (int)0, groupid, desc, prefered_container, container_flag);
}
inline void wndmgr_api::autopopup_unregister(int id) {
_voidcall(WNDMGR_API_AUTOPOPUP_UNREGISTER, id);
}
inline const wchar_t *wndmgr_api::varmgr_translate(const wchar_t *str) {
return _call(WNDMGR_API_VARMGR_TRANSLATE, (const wchar_t *)0, str);
}
/*
inline Container *wndmgr_api::newDynamicContainer(const wchar_t *containername, int transcient) {
return _call(WNDMGR_API_NEWDYNAMICCONTAINER, (Container *)NULL, containername, transcient);
}
*/
inline int wndmgr_api::autopopup_getNumGuids() {
return _call(WNDMGR_API_AUTOPOPUP_GETNUMGUIDS, 0);
}
inline GUID wndmgr_api::autopopup_enumGuid(int n) {
return _call(WNDMGR_API_AUTOPOPUP_ENUMGUID, INVALID_GUID, n);
}
inline int wndmgr_api::autopopup_getNumGroups() {
return _call(WNDMGR_API_AUTOPOPUP_GETNUMGROUPS, 0);
}
inline const wchar_t *wndmgr_api::autopopup_enumGroup(int n) {
return _call(WNDMGR_API_AUTOPOPUP_ENUMGROUPS, (const wchar_t*)NULL, n);
}
inline const wchar_t *wndmgr_api::autopopup_enumGuidDescription(int n) {
return _call(WNDMGR_API_AUTOPOPUP_ENUMGUIDDESC, (const wchar_t *)NULL, n);
}
inline const wchar_t *wndmgr_api::autopopup_enumGroupDescription(int n) {
return _call(WNDMGR_API_AUTOPOPUP_ENUMGROUPDESC, (const wchar_t *)NULL, n);
}
class wndmgr_apiI : public wndmgr_api {
public:
virtual void wndTrackAdd(ifc_window *wnd)=0;
virtual void wndTrackRemove(ifc_window *wnd)=0;
virtual bool wndTrackDock(ifc_window *wnd, RECT *r, int mask)=0;
virtual bool wndTrackDock2(ifc_window *wnd, RECT *r, RECT *orig_r, int mask)=0;
virtual void wndTrackStartCooperative(ifc_window *wnd)=0;
virtual void wndTrackEndCooperative()=0;
virtual int wndTrackWasCooperative()=0;
virtual void wndTrackInvalidateAll()=0;
virtual int skinwnd_toggleByGuid(GUID g, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0)=0;
virtual int skinwnd_toggleByGroupId(const wchar_t *groupid, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0)=0;
virtual ifc_window *skinwnd_createByGuid(GUID g, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0, int starthidden = 0, int *isnew=NULL)=0;
virtual ifc_window *skinwnd_createByGroupId(const wchar_t *groupid, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0, int starthidden = 0, int *isnew=NULL)=0;
virtual void skinwnd_destroy(ifc_window *w, RECT *destanimrect = NULL)=0;
virtual int skinwnd_getNumByGuid(GUID g)=0;
virtual ifc_window *skinwnd_enumByGuid(GUID g, int n)=0;
virtual int skinwnd_getNumByGroupId(const wchar_t *groupid)=0;
virtual ifc_window *skinwnd_enumByGroupId(const wchar_t *groupid, int n)=0;
virtual void skinwnd_attachToSkin(ifc_window *w, int side, int size)=0;
virtual ScriptObject *skin_getContainer(const wchar_t *container_name)=0;
virtual ScriptObject *skin_getLayout(ScriptObject *container, const wchar_t *layout_name)=0;
virtual void wndholder_register(WindowHolder *wh)=0;
virtual void wndholder_unregister(WindowHolder *wh)=0;
virtual int messageBox(const wchar_t *txt, const wchar_t *title, int flags, const wchar_t *not_anymore_identifier, ifc_window *parenwnt)=0;
virtual ifc_window *getModalWnd()=0;
virtual void pushModalWnd(ifc_window *w = MODALWND_NOWND)=0;
virtual void popModalWnd(ifc_window *w = MODALWND_NOWND)=0;
virtual void drawAnimatedRects(const RECT *r1, const RECT *r2)=0;
virtual int autopopup_registerGuid(GUID g, const wchar_t *desc, const wchar_t *prefered_container = NULL, int container_flag = 0)=0;
virtual int autopopup_registerGroupId(const wchar_t *groupid, const wchar_t *desc, const wchar_t *prefered_container = NULL, int container_flag = 0)=0;
virtual void autopopup_unregister(int id)=0;
virtual int autopopup_getNumGuids()=0;
virtual GUID autopopup_enumGuid(int n)=0;
virtual int autopopup_getNumGroups()=0;
virtual const wchar_t *autopopup_enumGroup(int n)=0;
virtual const wchar_t *varmgr_translate(const wchar_t *str)=0;
virtual Container *newDynamicContainer(const wchar_t *containername, int transcient = 1)=0;
virtual const wchar_t *autopopup_enumGuidDescription(int n)=0;
virtual const wchar_t *autopopup_enumGroupDescription(int n)=0;
protected:
RECVS_DISPATCH;
};
// {038A3567-1530-4062-BA87-CCB4F01DA3E9}
static const GUID wndMgrApiServiceGuid =
{ 0x38a3567, 0x1530, 0x4062, { 0xba, 0x87, 0xcc, 0xb4, 0xf0, 0x1d, 0xa3, 0xe9 } };
extern wndmgr_api *wndManagerApi;
#endif //wndmgr_api_h

View file

@ -0,0 +1,61 @@
#include <precomp.h>
#include "appcmds.h"
#define CBCLASS AppCmdsI
START_DISPATCH;
CB(APPCMDS_GETNUMCMDS, appcmds_getNumCmds);
CB(APPCMDS_ENUMCMD, appcmds_enumCmd);
VCB(APPCMDS_ONCOMMAND, appcmds_onCommand);
END_DISPATCH;
#undef CBCLASS
AppCmdsI::~AppCmdsI()
{
foreach(cmds)
if (cmds.getfor()->autodelete)
delete cmds.getfor();
endfor
}
void AppCmdsI::appcmds_addCmd(CmdRec *cmdrec)
{
cmds.addItem(cmdrec);
}
void AppCmdsI::appcmds_addCmd(const wchar_t *name, int id, int side)
{
cmds.addItem(new CmdRec(name, id, side, TRUE));
}
void AppCmdsI::appcmds_deleteAll()
{
foreach(cmds)
if (cmds.getfor()->autodelete) delete cmds.getfor();
endfor
cmds.removeAll();
}
int AppCmdsI::appcmds_getNumCmds()
{
return cmds.getNumItems();
}
const wchar_t *AppCmdsI::appcmds_enumCmd(int n, int *side, int *id)
{
CmdRec *cr = cmds[n];
if (cr == NULL) return NULL;
if (side != NULL) *side = cr->side;
if (id != NULL) *id = cr->id;
return cr->cmdname;
}
void AppCmdsI::appcmds_onCommand(int id, const RECT *buttonRect, int which_button)
{
foreach(cmds)
if (cmds.getfor()->id == id)
{
cmds.getfor()->onCommand(buttonRect, which_button);
break;
}
endfor
}

View file

@ -0,0 +1,89 @@
#ifndef _APPCMDS_H
#define _APPCMDS_H
#include <bfc/dispatch.h>
#include <bfc/depend.h>
#include <bfc/common.h>
#include <bfc/string/StringW.h>
#include <bfc/ptrlist.h>
class DragItem;
// this will be fully dispatched later on
class AppCmds : public Dispatchable
{
public:
int appcmds_getNumCmds();
const wchar_t *appcmds_enumCmd(int n, int *side, int *id);
enum {
SIDE_LEFT = 0, SIDE_RIGHT = 1
};
enum {
LEFT_CLICK = 0,
RIGHT_CLICK = 1,
};
void appcmds_onCommand(int id, const RECT *buttonRect, int which_button); //onscreen coords
enum {
APPCMDS_GETNUMCMDS = 100,
APPCMDS_ENUMCMD = 200,
APPCMDS_ONCOMMAND = 300,
};
};
inline int AppCmds::appcmds_getNumCmds()
{
return _call(APPCMDS_GETNUMCMDS, 0);
}
inline const wchar_t *AppCmds::appcmds_enumCmd(int n, int *side, int *id)
{
return _call(APPCMDS_ENUMCMD, (const wchar_t *)NULL, n, side, id);
}
inline void AppCmds::appcmds_onCommand(int id, const RECT *buttonRect, int which_button)
{
_voidcall(APPCMDS_ONCOMMAND, id, buttonRect, which_button);
}
class CmdRec
{
public:
CmdRec(const wchar_t *name, int _id, int _side, int _autodelete = 0) : cmdname(name), id(_id), side(_side), autodelete(_autodelete) {}
virtual ~CmdRec() {}
StringW cmdname;
int id, side;
int autodelete;
virtual void onCommand(const RECT *buttonRect, int which_button) {}}
;
class AppCmdsI : public AppCmds
{
public:
AppCmdsI() { }
virtual ~AppCmdsI();
protected:
void appcmds_addCmd(CmdRec *cmdrec);
void appcmds_addCmd(const wchar_t *name, int id, int side = SIDE_LEFT);
void appcmds_deleteAll(); //calls delete on each one
public:
virtual int appcmds_getNumCmds();
virtual const wchar_t *appcmds_enumCmd(int n, int *side, int *id);
// override this and catch your commands, otherwise it'll call the CmdRec
virtual void appcmds_onCommand(int id, const RECT *buttonRect, int which_button);
protected:
RECVS_DISPATCH;
PtrList<CmdRec> cmds;
};
#endif

View file

@ -0,0 +1,157 @@
#include <precomp.h>
#include "autopopup.h"
static PtrListQuickSorted<AutoPopupEntry, AutoPopupEntrySort> entries;
static int nid=0;
int AutoPopup::registerGuid(int skinpartid, GUID g, const wchar_t *desc, const wchar_t *prefered_container, int required)
{
if (desc == NULL || !*desc) desc = L"[????]";
AutoPopupEntry *ape = new AutoPopupEntry(skinpartid, g, NULL, desc, prefered_container, required);
entries.addItem(ape);
return ape->getNid();
}
int AutoPopup::registerGroupId(int skinpartid, const wchar_t *groupid, const wchar_t *desc, const wchar_t *prefered_container, int required) {
if (desc == NULL || !*desc) desc = L"[????]";
AutoPopupEntry *ape = new AutoPopupEntry(skinpartid, INVALID_GUID, groupid, desc, prefered_container, required);
entries.addItem(ape);
return ape->getNid();
}
int AutoPopup::getNumItems() { return entries.getNumItems(); }
AutoPopupEntry *AutoPopup::enumItem(int n) { return entries.enumItem(n); }
int AutoPopup::getNumGroups() {
int n = 0;
foreach(entries)
AutoPopupEntry *e = entries.getfor();
if (e->getGroupId() != NULL && e->getGuid() == INVALID_GUID) n++;
endfor;
return n;
}
int AutoPopup::getNumGuids() {
int n = 0;
foreach(entries)
AutoPopupEntry *e = entries.getfor();
if (e->getGroupId() == NULL && e->getGuid() != INVALID_GUID) n++;
endfor;
return n;
}
const wchar_t *AutoPopup::enumGroup(int n) {
int c = 0;
foreach(entries)
AutoPopupEntry *e = entries.getfor();
if (e->getGroupId() != NULL && e->getGuid() == INVALID_GUID) {
if (c == n) return e->getGroupId();
c++;
}
endfor;
return NULL;
}
GUID AutoPopup::enumGuid(int n) {
int c = 0;
foreach(entries)
AutoPopupEntry *e = entries.getfor();
if (e->getGroupId() == NULL && e->getGuid() != INVALID_GUID) {
if (c == n) return e->getGuid();
c++;
}
endfor;
return INVALID_GUID;
}
const wchar_t *AutoPopup::enumGroupDescription(int n) {
int c = 0;
foreach(entries)
AutoPopupEntry *e = entries.getfor();
if (e->getGroupId() != NULL && e->getGuid() == INVALID_GUID) {
if (c == n) return e->getDescription();
c++;
}
endfor;
return NULL;
}
const wchar_t *AutoPopup::enumGuidDescription(int n) {
int c = 0;
foreach(entries)
AutoPopupEntry *e = entries.getfor();
if (e->getGroupId() == NULL && e->getGuid() != INVALID_GUID) {
if (c == n) return e->getDescription();
c++;
}
endfor;
return NULL;
}
AutoPopupEntry *AutoPopup::getByDesc(const wchar_t *desc) {
foreach(entries)
if (!WCSICMP(desc, entries.getfor()->getDescription()))
return entries.getfor();
endfor;
return NULL;
}
void AutoPopup::reset() { entries.deleteAll(); nid = 0; }
const wchar_t *AutoPopup::getDefaultContainerParams(const wchar_t *groupid, GUID g, int *flag) {
if (groupid == NULL) { // guid
for (int i=entries.getNumItems()-1;i>=0;i--) {
if (entries.enumItem(i)->getGuid() == g) {
if (flag != NULL) *flag = entries.enumItem(i)->getContainerHow();
return entries.enumItem(i)->getPreferedContainer();
}
}
} else { // groupid
for (int i=entries.getNumItems()-1;i>=0;i--)
{
if (WCSCASEEQLSAFE(entries.enumItem(i)->getGroupId(), groupid))
{
if (flag != NULL) *flag = entries.enumItem(i)->getContainerHow();
return entries.enumItem(i)->getPreferedContainer();
}
}
}
return NULL;
}
void AutoPopup::unregister(int id) {
for (int i=0;i<entries.getNumItems();i++) {
AutoPopupEntry *ape = entries.enumItem(i);
if (ape->getNid() == id) {
delete ape;
entries.removeByPos(i);
i--;
continue;
}
}
}
void AutoPopup::removeSkinPart(int id) {
for (int i=0;i<entries.getNumItems();i++) {
AutoPopupEntry *ape = entries.enumItem(i);
if (ape->getSkinpart() == id) {
delete ape;
entries.removeByPos(i);
i--;
}
}
}
int AutoPopup::allocNid() { return nid++; }
void AutoPopup::removeAllAddons() {
for (int i=0;i<entries.getNumItems();i++) {
AutoPopupEntry *ape = entries.enumItem(i);
if (ape->getSkinpart() != SKINPARTID_NONE) {
delete ape;
entries.removeByPos(i);
i--;
}
}
}

View file

@ -0,0 +1,76 @@
#ifndef __AUTOPOPUP_H
#define __AUTOPOPUP_H
#include <bfc/ptrlist.h>
#include <bfc/string/StringW.h>
class AutoPopupEntry;
class AutoPopupEntrySort;
#define SKINPARTID_NONE -1
class AutoPopup {
public:
static int registerGuid(int skinpartid/*SKINPARTID_NONE*/, GUID g, const wchar_t *desc, const wchar_t *prefered_container=NULL, int required=FALSE);
static int registerGroupId(int skinpartid/*SKINPARTID_NONE*/, const wchar_t *groupid, const wchar_t *desc, const wchar_t *prefered_container=NULL, int required=FALSE);
static void unregister(int id);
static int getNumItems();
static AutoPopupEntry *enumItem(int n);
static AutoPopupEntry *getByDesc(const wchar_t *desc);
static void reset();
static void removeSkinPart(int id);
static int allocNid();
static void removeAllAddons();
static int getNumGuids();
static GUID enumGuid(int n);
static int getNumGroups();
static const wchar_t *enumGroup(int n);
static const wchar_t *enumGuidDescription(int n);
static const wchar_t *enumGroupDescription(int n);
static const wchar_t *getDefaultContainerParams(const wchar_t *groupid, GUID g, int *flag);
};
class AutoPopupEntry {
public:
AutoPopupEntry(int skinpartid, GUID g, const wchar_t *grpid, const wchar_t *description, const wchar_t *prefered_container=NULL, int required=TRUE) : guid(g), groupid(grpid), desc(description), container(prefered_container), container_how(required), skinpart(skinpartid) { nid = AutoPopup::allocNid(); }
virtual ~AutoPopupEntry() { }
GUID getGuid() { return guid; }
const wchar_t *getGroupId() { return groupid; }
const wchar_t *getDescription() { return desc; }
int getNid() { return nid; }
const wchar_t *getPreferedContainer() { return container; }
int getContainerHow() { return container_how; }
int getSkinpart() { return skinpart; }
private:
GUID guid;
StringW groupid;
StringW desc;
int nid;
StringW container;
int container_how;
int skinpart;
};
class AutoPopupEntrySort {
public:
static int compareItem(AutoPopupEntry *p1, AutoPopupEntry *p2) {
return WCSICMP(p1->getDescription(), p2->getDescription());
}
static int compareAttrib(const wchar_t *attrib, AutoPopupEntry *item) {
return WCSICMP(attrib, item->getDescription());
}
};
#endif

View file

@ -0,0 +1,919 @@
#include <precomp.h>
#include "wasabicfg.h"
#include <api/wndmgr/container.h>
#include <api/script/script.h>
#include <api/script/scriptmgr.h>
#include <api/config/items/attrbool.h>
#include <api/config/items/cfgitem.h>
#include <api/skin/skinparse.h>
#include <api/wac/compon.h>
#include <api/wnd/wndtrack.h>
#include <api/skin/skin.h>
#include <api/wndmgr/skinembed.h>
#include <api/syscb/callbacks/wndcb.h>
#include <bfc/string/stringdict.h>
#include <api/skin/widgets/xuiwndholder.h> // TODO: cut, but we need XuiWindowHolder::parseGUID for now
#include <bfc/platform/guid.h>
#ifdef WIN32
#include "resource.h"
#include "../Agave/Language/api_language.h"
#endif
BEGIN_STRINGDICTIONARY(_containerparams)
SDI(L"name", CONTAINERPARAM_NAME);
SDI(L"id", CONTAINERPARAM_ID);
SDI(L"dynamic", CONTAINERPARAM_DYNAMIC);
SDI(L"default_x", CONTAINERPARAM_DEFAULTX);
SDI(L"default_y", CONTAINERPARAM_DEFAULTY);
SDI(L"default_visible", CONTAINERPARAM_DEFAULTVISIBLE);
SDI(L"canclose", CONTAINERPARAM_CANCLOSE);
SDI(L"nomenu", CONTAINERPARAM_NOMENU);
SDI(L"nofocusapponclose", CONTAINERPARAM_NOFOCUSAPPONCLOSE);
SDI(L"primarycomponent", CONTAINERPARAM_CONTENT);
END_STRINGDICTIONARY(_containerparams, containerparams);
Container::Container(int script_id)
{
getScriptObject()->vcpu_setInterface(containerGuid, (void *)static_cast<Container *>(this));
getScriptObject()->vcpu_setClassName(L"Container");
getScriptObject()->vcpu_setController(containerController);
scriptid = script_id;
currentLayout = -1;
default_visible = TRUE;
loaded_default_visible = TRUE;
dynamic = 0;
MEMCPY(&myGUID, &INVALID_GUID, sizeof(GUID));
lastLayout = -1;
refocusapponclose = 1;
canclose = 1;
inited = 0;
deleting = 0;
transcient = 0;
switching_layout = 0;
nomenu = 0;
prevent_save_visibility = 0;
contentGuid = INVALID_GUID;
hasContentGuid=false;
}
void Container::setName(const wchar_t *name)
{
#ifdef ON_TWEAK_CONTAINER_NAMEW
ON_TWEAK_CONTAINER_NAMEW(name);
#endif
containerName = name ? name : CONTAINER_UNDEFINED_NAME;
foreach(layouts)
Layout *l = layouts.getfor();
if (l->getRootWndName() == NULL)
{
l->setOSWndName(name);
}
endfor;
updateDefaultVisible();
dependent_sendEvent(Container::depend_getClassGuid(), Event_NAMECHANGE, 0, this);
}
void Container::resetLayouts()
{
updateDefaultVisible();
foreach(layouts)
layouts.getfor()->loadSavedState();
endfor;
}
void Container::setId(const wchar_t *id)
{
containerId = id ? id : L"undefined";
ismain = !WCSICMP(id, L"main");
}
int Container::setXmlParam(const wchar_t *paramname, const wchar_t *strvalue)
{
switch (containerparams.getId(paramname))
{
case CONTAINERPARAM_NAME:
setName(strvalue);
return 1;
case CONTAINERPARAM_ID:
setId(strvalue);
return 1;
case CONTAINERPARAM_DYNAMIC:
setDynamic(WTOI(strvalue));
return 1;
case CONTAINERPARAM_DEFAULTX:
default_x = WTOI(strvalue);
return 1;
case CONTAINERPARAM_DEFAULTY:
default_y = WTOI(strvalue);
return 1;
case CONTAINERPARAM_DEFAULTVISIBLE:
default_visible = WTOI(strvalue);
updateDefaultVisible();
return 1;
case CONTAINERPARAM_CANCLOSE:
canclose = WTOI(strvalue);
return 1;
case CONTAINERPARAM_NOMENU:
nomenu = WTOI(strvalue);
return 1;
case CONTAINERPARAM_NOFOCUSAPPONCLOSE:
refocusapponclose = !WTOI(strvalue);
break;
case CONTAINERPARAM_CONTENT:
{
// TODO: move this out of XuiWindowHolder
GUID *g = XuiWindowHolder::parseGUID(strvalue);
contentGuid = *g;
hasContentGuid=true;
break;
}
}
return 0;
}
Container::~Container()
{
containerCallback(CONT_CB_HIDDEN);
layouts.deleteAll();
contents.deleteAll();
SkinParser::containers.removeItem(this);
}
void Container::getWindowRect(RECT *r)
{
Layout *l = getCurrentLayout();
if (l)
l->getWindowRect(r);
}
void Container::addLayout(Layout *layout)
{
layouts.addItem(layout);
}
const wchar_t *Container::getName()
{
return containerName;
}
const wchar_t *Container::getId()
{
return containerId;
}
int Container::getDefaultPositionX(void)
{
return default_x;
}
int Container::getDefaultPositionY(void)
{
return default_y;
}
void Container::onInit(int noshow)
{
if (inited) return ;
inited++;
loadFromDefaults(noshow);
}
void Container::loadFromDefaults(int noshow)
{
#ifdef WASABI_COMPILE_CONFIG
if (last_layout.isempty())
{
StringPrintfW tmp(L"container_%s|active", getName());
wchar_t c[512] = {0};
WASABI_API_CONFIG->getStringPrivate(tmp, c, 511, L"");
c[510] = 0;
last_layout = c;
}
#endif
if (loaded_default_visible)
{
showDefaultLayout(noshow);
}
}
void Container::setDefaultLayout(const wchar_t *name)
{
last_layout = name;
}
void Container::showDefaultLayout(int noshow)
{
Layout *l = getLayout(last_layout);
if (!l)
l = layouts.enumItem(0);
if (l)
{
currentLayout = layouts.searchItem(l);
if (!noshow)
l->setVisible(1);
containerCallback(CONT_CB_VISIBLE); // since we set currentLayout prior to showing the layout, the callback will not be processed in onChildSetLayoutVisible
}
}
void Container::setVisible(int sh)
{
if (!sh && !canclose)
return ;
int is = isVisible();
if (!!sh == !!is)
return ;
Layout *l = getCurrentLayout();
if (!l && lastLayout != -1)
l = layouts[lastLayout];
if (sh)
{
if (!l)
showDefaultLayout();
else
{
l->setVisible(1);
}
}
else
{
if (l)
l->setVisible(0);
}
}
int Container::isVisible()
{
if (switching_layout) return 1;
Layout *l = getCurrentLayout();
if (!l) return 0;
return l->isVisible();
}
void Container::onChildSetLayoutVisible(Layout *l, int v)
{
for (int i = 0;i < layouts.getNumItems();i++)
{
if (layouts[i] == l)
{
if (v)
{
if (currentLayout != i)
{
Layout *l = NULL;
if (currentLayout >= 0)
l = layouts[currentLayout];
if (l) l->setVisible(0);
containerCallback(CONT_CB_VISIBLE);
currentLayout = i;
l = layouts[currentLayout];
#ifdef WASABI_COMPILE_CONFIG
if (!isTranscient() && !prevent_save_visibility)
WASABI_API_CONFIG->setStringPrivate(StringPrintfW(L"container_%s|active", getName()), l->getGuiObject()->guiobject_getId());
#endif
#ifdef WA3COMPATIBILITY
l->setForwardMsgWnd(WASABI_API_WND->main_getRootWnd()->gethWnd());
#endif
if (l->wantActivation())
{
l->bringToFront();
l->setFocus();
}
l->invalidate();
}
#ifdef WASABI_COMPILE_CONFIG
if (!isTranscient() && !isDynamic() && !prevent_save_visibility)
WASABI_API_CONFIG->setIntPrivate(StringPrintfW(L"activated/%s", getName()), v);
WASABI_API_CONFIG->setIntPrivate(StringPrintfW(L"everloaded/%s", getName()), 1);
#endif
}
else
{
if (i == currentLayout)
{
if (!isDeleting() && !isTranscient() && !isDynamic())
{
#ifdef WASABI_COMPILE_CONFIG
WASABI_API_CONFIG->setIntPrivate(StringPrintfW(L"activated/%s", getName()), v);
#endif
lastLayout = currentLayout;
currentLayout = -1;
}
containerCallback(CONT_CB_HIDDEN);
}
}
return ;
}
}
}
void Container::containerCallback(int msg)
{
switch (msg)
{
case CONT_CB_VISIBLE:
{
foreach(contents)
ContentEntry *e = contents.getfor();
WndInfo i;
i.groupid = e->groupid;
i.guid = e->guid;
i.c = this;
WASABI_API_SYSCB->syscb_issueCallback(SysCallback::WINDOW, WndCallback::SHOWWINDOW, reinterpret_cast<intptr_t>(&i));
endfor
WndInfo i;
i.groupid = getId();
i.guid = INVALID_GUID;
i.c = this;
WASABI_API_SYSCB->syscb_issueCallback(SysCallback::WINDOW, WndCallback::SHOWWINDOW, reinterpret_cast<intptr_t>(&i));
}
break;
case CONT_CB_HIDDEN:
{
foreach(contents)
ContentEntry *e = contents.getfor();
WndInfo i;
i.groupid = e->groupid;
i.guid = e->guid;
i.c = this;
WASABI_API_SYSCB->syscb_issueCallback(SysCallback::WINDOW, WndCallback::HIDEWINDOW, reinterpret_cast<intptr_t>(&i));
endfor
WndInfo i;
i.groupid = getId();
i.guid = INVALID_GUID;
i.c = this;
WASABI_API_SYSCB->syscb_issueCallback(SysCallback::WINDOW, WndCallback::HIDEWINDOW, reinterpret_cast<intptr_t>(&i));
}
break;
}
}
void Container::close()
{
int norefocs = !wantRefocusApp();
if (norefocs) WASABI_API_WND->appdeactivation_push_disallow(NULL);
if (!canclose) return ;
if (isDynamic())
{
setVisible(0);
skinEmbedder->destroyContainer(this); // deferred
}
else
setVisible(0);
if (norefocs) WASABI_API_WND->appdeactivation_pop_disallow(NULL);
}
void Container::toggle()
{
if (isVisible()) close(); else setVisible(1); // close has special function hide/destroy depending on dynamic status
}
void Container::switchToLayout(const wchar_t *name, int moveit)
{
int l = -1;
getLayout(name, &l);
if (l == -1)
{
// Layout not found, reverting to first in the list
if (layouts.getNumItems() > 0) l = 0;
else
return ; // none found, abort
}
switching_layout = 1;
if (l != currentLayout)
{
int old = currentLayout;
RECT r = {0};
Layout *oldlayout = old >= 0 ? layouts[old] : NULL;
Layout *newlayout = layouts[l];
onBeforeSwitchToLayout(oldlayout, newlayout);
if (oldlayout)
{
oldlayout->getWindowRect(&r);
oldlayout->endCapture();
}
int unlinked = layouts[l]->isUnlinked();
unlinked |= oldlayout ? oldlayout->isUnlinked() : 0;
if (moveit && !unlinked && oldlayout)
layouts[l]->move(r.left, r.top);
#ifdef WASABI_COMPILE_CONFIG
// {9149C445-3C30-4e04-8433-5A518ED0FDDE}
const GUID uioptions_guid =
{ 0x9149c445, 0x3c30, 0x4e04, { 0x84, 0x33, 0x5a, 0x51, 0x8e, 0xd0, 0xfd, 0xde } };
if (_intVal(WASABI_API_CONFIG->config_getCfgItemByGuid(uioptions_guid), L"Link layouts scale"))
{
#else
if (WASABI_WNDMGR_LINKLAYOUTSCALES)
{
#endif
if (oldlayout)
{
double _r = oldlayout->getRenderRatio();
newlayout->setRenderRatio(_r);
}
}
#ifdef WASABI_COMPILE_CONFIG
if (_intVal(WASABI_API_CONFIG->config_getCfgItemByGuid(uioptions_guid), L"Link layouts alpha"))
{
#else
if (WASABI_WNDMGR_LINKLAYOUTSALPHA)
{
#endif
if (oldlayout)
{
int a = layouts[old]->getAlpha();
newlayout->setAlpha(a);
int autoopacify = layouts[old]->getAutoOpacify();
newlayout->setAutoOpacify(autoopacify);
}
}
WindowTracker::layoutChanged(oldlayout, newlayout);
#ifdef ON_LAYOUT_CHANGED
ON_LAYOUT_CHANGED;
#endif
layouts[l]->setVisible(1);
foreach(SkinParser::containers)
SkinParser::containers.getfor()->savePositions();
endfor
onSwitchToLayout(newlayout);
}
switching_layout = 0;
}
void Container::savePositions()
{
foreach (layouts)
layouts.getfor()->savePosition();
endfor
}
Layout *Container::getLayout(const wchar_t *name, int *pos)
{
for ( int i = 0; i < getNumLayouts(); i++ )
{
if ( WCSCASEEQLSAFE( enumLayout( i )->getGuiObject()->guiobject_getId(), name ) )
{
if (pos)
{
*pos = i;
}
return enumLayout( i );
}
}
return NULL;
}
Layout *Container::getCurrentLayout()
{
if (currentLayout < 0)
return NULL;
return layouts.enumItem(currentLayout);
}
void Container::otherContainerToggled(const wchar_t *id, int visible)
{
for (int i = 0;i < layouts.getNumItems();i++)
layouts[i]->containerToggled(id, visible);
}
void Container::componentToggled(GUID *g, int visible)
{
for (int i = 0;i < layouts.getNumItems();i++)
layouts[i]->componentToggled(g, visible);
}
void Container::sendNotifyToAllLayouts(int notifymsg, int param1, int param2)
{
for (int i = 0;i < layouts.getNumItems();i++)
layouts[i]->sendNotifyToAllChildren(notifymsg, param1, param2);
}
int Container::isMainContainer()
{
return ismain;
}
void Container::sysMenu()
{
POINT p;
Wasabi::Std::getMousePos(&p);
layouts.enumItem(currentLayout)->onRightButtonDown(p.x, p.y);
}
void Container::setDynamic(int i)
{
dynamic = i;
if (!containerId.isempty())
setId(containerId);
}
int Container::isDynamic()
{
return dynamic;
}
void Container::onSwitchToLayout(Layout *l)
{
ScriptObject *ls = l ? l->getGuiObject()->guiobject_getScriptObject() : NULL;
script_onSwitchToLayout(SCRIPT_CALL, getScriptObject(), MAKE_SCRIPT_OBJECT(ls));
}
void Container::onBeforeSwitchToLayout(Layout *oldl, Layout *newl)
{
ScriptObject *olds = oldl ? oldl->getGuiObject()->guiobject_getScriptObject() : NULL;
ScriptObject *news = newl ? newl->getGuiObject()->guiobject_getScriptObject() : NULL;
script_onBeforeSwitchToLayout(SCRIPT_CALL, getScriptObject(), MAKE_SCRIPT_OBJECT(olds), MAKE_SCRIPT_OBJECT(news));
}
void Container::onHideLayout(Layout *l)
{
script_onHideLayout(SCRIPT_CALL, getScriptObject(), MAKE_SCRIPT_OBJECT(l->getGuiObject()->guiobject_getScriptObject()));
}
void Container::onShowLayout(Layout *l)
{
script_onShowLayout(SCRIPT_CALL, getScriptObject(), MAKE_SCRIPT_OBJECT(l->getGuiObject()->guiobject_getScriptObject()));
}
int Container::getNumLayouts()
{
return layouts.getNumItems();
}
Layout *Container::enumLayout(int n)
{
return layouts.enumItem(n);
}
const wchar_t *Container::getDescriptor()
{
static wchar_t d[256];
// if we've tweaked the container names then when saving out we can see and attempt to 'untweak'
// so that things like Winamp Modern's ML will be correctly positioned irrespective of language
int untweak = 0;
wchar_t tweaked[96] = {0};
// Martin> We need to check the containerName against null - dunno why some skins cause this string to be null
if(containerName.v() != NULL && !_wcsicmp(containerName.v(), WASABI_API_LNGSTRINGW_BUF(IDS_MEDIA_LIBRARY,tweaked,96))){
untweak = 1;
}
WCSNPRINTF(d, 256,L"%s/%s", getId(), (!untweak ? containerName.v() : L"Media Library"));
return d;
}
void Container::updateDefaultVisible()
{
if (!canclose)
{
loaded_default_visible = 1;
return ;
}
#ifdef WASABI_COMPILE_CONFIG
loaded_default_visible = WASABI_API_CONFIG->getIntPrivate(StringPrintfW(L"activated/%s", getName()), default_visible);
#else
loaded_default_visible = default_visible;
#endif
}
int Container::getScriptId()
{
return scriptid;
}
void Container::notifyAddContent(ifc_window *w, const wchar_t *id, GUID g)
{
contents.addItem(new ContentEntry(id, g, w));
ScriptObject *_w = w ? w->getGuiObject()->guiobject_getScriptObject() : NULL;
wchar_t guidstr[256] = {0};
nsGUID::toCharW(g, guidstr);
script_onAddContent(SCRIPT_CALL, getScriptObject(), MAKE_SCRIPT_OBJECT(_w), MAKE_SCRIPT_STRING(id), MAKE_SCRIPT_STRING(guidstr));
}
void Container::notifyRemoveContent(ifc_window *w)
{
foreach(contents)
ContentEntry *e = contents.getfor();
if (e->wnd == w)
{
contents.removeItem(e);
delete e;
return ;
}
endfor;
}
int Container::hasContent(GUID g)
{
foreach(contents)
ContentEntry *e = contents.getfor();
if (e->guid == g)
{
return 1;
}
endfor;
return 0;
}
GUID Container::getDefaultContent()
{
if (hasContentGuid)
return contentGuid;
if (contents.getNumItems() > 0) return contents.enumItem(0)->guid;
return INVALID_GUID;
}
ContainerScriptController _containerController;
ContainerScriptController *containerController = &_containerController;
// -- Functions table -------------------------------------
function_descriptor_struct ContainerScriptController::exportedFunction[] = {
{L"onSwitchToLayout", 1, (void*)Container::script_onSwitchToLayout },
{L"onBeforeSwitchToLayout", 2, (void*)Container::script_onBeforeSwitchToLayout },
{L"onHideLayout", 1, (void*)Container::script_onHideLayout },
{L"onShowLayout", 1, (void*)Container::script_onShowLayout },
{L"getLayout", 1, (void*)Container::script_getLayout },
{L"getNumLayouts", 0, (void*)Container::script_getNumLayouts },
{L"enumLayout", 1, (void*)Container::script_enumLayout },
{L"getCurLayout", 0, (void*)Container::script_getCurrentLayout},
{L"switchToLayout", 1, (void*)Container::script_switchToLayout },
{L"isDynamic", 0, (void*)Container::script_isDynamic },
{L"show", 0, (void*)Container::script_show },
{L"hide", 0, (void*)Container::script_hide },
{L"close", 0, (void*)Container::script_close},
{L"toggle", 0, (void*)Container::script_toggle },
{L"setName", 1, (void*)Container::script_setName },
{L"getName", 0, (void*)Container::script_getName },
{L"getGuid", 0, (void*)Container::script_getGuid },
{L"setXmlParam", 2, (void*)Container::script_setXmlParam},
{L"onAddContent", 3, (void*)Container::script_onAddContent},
};
// --------------------------------------------------------
/*SET_HIERARCHY(Container, SCRIPT_CONTAINER);
SET_HIERARCHY2(Container, SCRIPT_CONTAINER, CONTAINER_SCRIPTPARENT);*/
const wchar_t *ContainerScriptController::getClassName()
{
return L"Container";
}
const wchar_t *ContainerScriptController::getAncestorClassName()
{
return L"Object";
}
ScriptObjectController *ContainerScriptController::getAncestorController()
{
return rootScriptObjectController;
}
int ContainerScriptController::getInstantiable()
{
return 1;
}
ScriptObject *ContainerScriptController::instantiate()
{
Container *c = new Container;
return c->getScriptObject();
}
void ContainerScriptController::destroy(ScriptObject *o)
{
//ASSERTALWAYS("be nice, don't do that");
Container *c = (Container *)o->vcpu_getInterface(containerGuid);
delete c;
}
void *ContainerScriptController::encapsulate(ScriptObject *o)
{
return NULL;
}
void ContainerScriptController::deencapsulate(void *o)
{}
int ContainerScriptController::getNumFunctions()
{
return sizeof(exportedFunction) / sizeof(function_descriptor_struct);
}
const function_descriptor_struct *ContainerScriptController::getExportedFunctions()
{
return exportedFunction;
}
GUID ContainerScriptController::getClassGuid()
{
return containerGuid;
}
//-----------------------------------------------------------------------
scriptVar Container::script_onSwitchToLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar l)
{
SCRIPT_FUNCTION_INIT;
PROCESS_HOOKS1(o, containerController, l);
SCRIPT_FUNCTION_CHECKABORTEVENT;
SCRIPT_EXEC_EVENT1(o, l);
}
scriptVar Container::script_onBeforeSwitchToLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar oldl, scriptVar newl)
{
SCRIPT_FUNCTION_INIT;
PROCESS_HOOKS2(o, containerController, oldl, newl);
SCRIPT_FUNCTION_CHECKABORTEVENT;
SCRIPT_EXEC_EVENT2(o, oldl, newl);
}
scriptVar Container::script_onHideLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar l)
{
SCRIPT_FUNCTION_INIT;
PROCESS_HOOKS1(o, containerController, l);
SCRIPT_FUNCTION_CHECKABORTEVENT;
SCRIPT_EXEC_EVENT1(o, l);
}
scriptVar Container::script_onShowLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar l)
{
SCRIPT_FUNCTION_INIT;
PROCESS_HOOKS1(o, containerController, l);
SCRIPT_FUNCTION_CHECKABORTEVENT;
SCRIPT_EXEC_EVENT1(o, l);
}
// Get an layout from its ID
scriptVar Container::script_getLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar obj)
{
SCRIPT_FUNCTION_INIT
ASSERT(obj.type == SCRIPT_STRING); // compiler discarded
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c)
{
for (int i = 0;i < c->layouts.getNumItems();i++)
if (!WCSICMP(obj.data.sdata, c->layouts.enumItem(i)->getGuiObject()->guiobject_getId()))
{
return MAKE_SCRIPT_OBJECT(c->layouts.enumItem(i)->getGuiObject()->guiobject_getScriptObject());
}
}
RETURN_SCRIPT_ZERO;
}
scriptVar Container::script_show(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c) c->setVisible(1);
RETURN_SCRIPT_VOID;
}
scriptVar Container::script_hide(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c) c->setVisible(0);
RETURN_SCRIPT_VOID;
}
scriptVar Container::script_close(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c) c->close();
RETURN_SCRIPT_VOID;
}
scriptVar Container::script_toggle(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c) c->toggle();
RETURN_SCRIPT_VOID;
}
// Switch to another layout
scriptVar Container::script_switchToLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar l)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c)
c->switchToLayout(GET_SCRIPT_STRING(l));
RETURN_SCRIPT_VOID;
}
scriptVar Container::script_getNumLayouts(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c) return MAKE_SCRIPT_INT(c->getNumLayouts());
RETURN_SCRIPT_ZERO;
}
scriptVar Container::script_enumLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar n)
{
SCRIPT_FUNCTION_INIT
ASSERT(SOM::isNumeric(&n)); // compiler discarded
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
Layout *l = NULL;
if (c) l = c->enumLayout(SOM::makeInt(&n));
return MAKE_SCRIPT_OBJECT(l ? l->getScriptObject() : NULL);
}
scriptVar Container::script_getCurrentLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
Layout *l = c->getCurrentLayout();
return MAKE_SCRIPT_OBJECT(l ? l->getScriptObject() : NULL);
}
// Switch to another layout
scriptVar Container::script_vcpu_getId(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c)
return MAKE_SCRIPT_STRING(c->getId());
return MAKE_SCRIPT_STRING(L"");
}
scriptVar Container::script_isDynamic(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c) return MAKE_SCRIPT_INT(c->isDynamic());
RETURN_SCRIPT_ZERO;
}
scriptVar Container::script_setName(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar name)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c) c->setName(GET_SCRIPT_STRING(name));
RETURN_SCRIPT_VOID;
}
scriptVar Container::script_getName(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c) return MAKE_SCRIPT_STRING(c->getName());
return MAKE_SCRIPT_STRING(L"");
}
scriptVar Container::script_getGuid(SCRIPT_FUNCTION_PARAMS, ScriptObject *o)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c)
{
static wchar_t guidstr[256];
nsGUID::toCharW(c->getGUID(), guidstr);
return MAKE_SCRIPT_STRING(guidstr);
}
return MAKE_SCRIPT_STRING(L"");
}
scriptVar Container::script_setXmlParam(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar p, scriptVar v)
{
SCRIPT_FUNCTION_INIT
Container *c = static_cast<Container *>(o->vcpu_getInterface(containerGuid));
if (c) c->setXmlParam(GET_SCRIPT_STRING(p), GET_SCRIPT_STRING(v));
RETURN_SCRIPT_VOID;
}
//void Container::notifyAddContent(ifc_window *w, const wchar_t *id, GUID g)
scriptVar Container::script_onAddContent(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar window, scriptVar id, scriptVar g)
{
SCRIPT_FUNCTION_INIT;
PROCESS_HOOKS3(o, containerController, window, id, g);
SCRIPT_FUNCTION_CHECKABORTEVENT;
SCRIPT_EXEC_EVENT3(o, window, id, g);
}

View file

@ -0,0 +1,231 @@
#ifdef WASABI_COMPILE_WNDMGR
#ifndef __CONTAINER_H
#define __CONTAINER_H
class Container;
class Layout;
#include <bfc/ptrlist.h>
#include <api/skin/xmlobject.h>
#ifdef WASABI_WIDGETS_GUIOBJECT
#include <api/script/objects/guiobj.h>
#endif
#include <api/script/script.h>
#include <api/script/scriptobj.h>
#include <api/script/objcontroller.h>
#include <api/script/objects/rootobj.h>
#define CONTAINER_UNDEFINED_NAME L"undefined container name"
enum {
CONTAINERPARAM_NAME = 0,
CONTAINERPARAM_ID,
CONTAINERPARAM_DYNAMIC,
CONTAINERPARAM_DEFAULTX,
CONTAINERPARAM_DEFAULTY,
CONTAINERPARAM_DEFAULTVISIBLE,
CONTAINERPARAM_CANCLOSE,
CONTAINERPARAM_NOMENU,
CONTAINERPARAM_NOFOCUSAPPONCLOSE,
CONTAINERPARAM_CONTENT,
};
class ContainerScriptController: public ScriptObjectControllerI
{
public:
virtual const wchar_t *getClassName();
virtual const wchar_t *getAncestorClassName();
virtual ScriptObjectController *getAncestorController();
virtual int getNumFunctions();
virtual const function_descriptor_struct *getExportedFunctions();
virtual GUID getClassGuid();
virtual ScriptObject *instantiate();
virtual void destroy(ScriptObject *o);
virtual void *encapsulate(ScriptObject *o);
virtual void deencapsulate(void *o);
virtual int getInstantiable();
private:
static function_descriptor_struct exportedFunction[];
};
class ContentEntry
{
public:
ContentEntry(const wchar_t *gid, GUID g, ifc_window *w) : groupid(gid), guid(g), wnd(w) { }
GUID guid;
StringW groupid;
ifc_window *wnd;
};
extern ContainerScriptController *containerController;
#define CONTAINER_SCRIPTPARENT RootObjectInstance
class Container : public CONTAINER_SCRIPTPARENT, public XmlObjectI, public DependentI
{
public:
Container(int scriptid = -1);
virtual ~Container();
virtual void setName(const wchar_t *name);
virtual void setId(const wchar_t *id);
virtual const wchar_t *getName();
virtual const wchar_t *getId();
virtual int setXmlParam(const wchar_t *p, const wchar_t *v);
virtual void onInit(int noshow = 0);
virtual void addLayout(Layout *layout);
virtual void resetLayouts();
virtual void setVisible(int sh);
virtual int isVisible();
virtual void switchToLayout(const wchar_t *name, int moveit = 1);
virtual void toggle();
virtual void close();
virtual void sysMenu();
virtual int getNumLayouts();
virtual Layout *enumLayout(int n);
virtual Layout *getLayout(const wchar_t *name, int *pos = NULL);
virtual int getScriptId();
virtual void savePositions();
void setDefaultLayout(const wchar_t *name);
void loadFromDefaults(int noshow = 0);
int isTranscient() { return transcient; }
void setTranscient(int is) { transcient = is; }
// player callbacks to notify that container/component
// has been set visible/invisible
virtual void otherContainerToggled(const wchar_t *id, int visible);
virtual void componentToggled(GUID *g, int visible);
virtual int isMainContainer();
virtual int isDynamic();
virtual void onSwitchToLayout(Layout *l);
virtual void onBeforeSwitchToLayout(Layout *oldl, Layout *newl);
virtual void onHideLayout(Layout *l);
virtual void onShowLayout(Layout *l);
virtual Layout *getCurrentLayout();
virtual int getDefaultPositionX(void);
virtual int getDefaultPositionY(void);
virtual void onChildSetLayoutVisible(Layout *l, int v);
virtual void notifyAddContent(ifc_window *w, const wchar_t *groupid, GUID guid = INVALID_GUID);
virtual void notifyRemoveContent(ifc_window *w);
virtual int hasContent(GUID g);
virtual GUID getDefaultContent();
const wchar_t *getDescriptor(void);
virtual void getWindowRect(RECT *r);
virtual void sendNotifyToAllLayouts(int notifymsg, int param1, int param2);
void setDynamic(int i);
void updateDefaultVisible();
void setDeleting() { deleting = 1; }
int isDeleting() { return deleting; }
int isInited() { return inited; }
int canClose() { return canclose; }
void setCanClose(int c) { canclose = c; }
GUID getGUID() { return myGUID; }
int getNoMenu() { return nomenu; }
void setPreventSaveVisibility(int p) { prevent_save_visibility = p; }
int wantRefocusApp() { return refocusapponclose; }
void setWantRefocusApp(int rf) { refocusapponclose = rf; }
public:
// ifc_dependent stuff
static const GUID *depend_getClassGuid() {
// {C439D9F4-34F5-453c-B947-448ED20203FC}
static const GUID ret =
{ 0xc439d9f4, 0x34f5, 0x453c, { 0xb9, 0x47, 0x44, 0x8e, 0xd2, 0x2, 0x3, 0xfc } };
return &ret;
}
enum
{
Event_NAMECHANGE = 0,
};
private:
void containerCallback(int msg);
StringW containerName;
StringW containerId;
PtrList<Layout> layouts;
int currentLayout;
StringW last_layout;
int canclose;
int lastLayout;
int default_visible, loaded_default_visible;
int ismain;
int dynamic;
int default_x = -1;
int default_y = -1;
int default_w = -1;
int default_h = -1;
int scriptid;
int inited;
int deleting;
int transcient;
PtrList<ContentEntry> contents;
int switching_layout;
int nomenu;
int prevent_save_visibility;
int refocusapponclose;
GUID contentGuid;
bool hasContentGuid;
private:
GUID myGUID;
void showDefaultLayout(int noshow = 0);
public:
static scriptVar script_vcpu_getId(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_onSwitchToLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar l);
static scriptVar script_onBeforeSwitchToLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar oldl, scriptVar newl);
static scriptVar script_onHideLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar l);
static scriptVar script_onShowLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar l);
static scriptVar script_getLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar obj);
static scriptVar script_switchToLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar s);
static scriptVar script_getCurrentLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_show(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_hide(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_close(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_toggle(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_getNumLayouts(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_enumLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar n);
static scriptVar script_isDynamic(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_setName(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar name);
static scriptVar script_getName(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_getGuid(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_setXmlParam(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar p, scriptVar v);
static scriptVar script_onAddContent(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar window, scriptVar id, scriptVar g);
};
enum {
CONT_CB_NONE,
CONT_CB_VISIBLE,
CONT_CB_HIDDEN
};
#endif
#endif

View file

@ -0,0 +1,24 @@
#include <precomp.h>
#include "gc.h"
GarbageCollector *garbageCollector=NULL;
GarbageCollector::GarbageCollector() {
last = 0;
WASABI_API_SYSCB->syscb_registerCallback(this);
}
GarbageCollector::~GarbageCollector() {
WASABI_API_SYSCB->syscb_deregisterCallback(this);
}
int GarbageCollector::gccb_onGarbageCollect() {
uint32_t tc = Wasabi::Std::getTickCount();
if (tc < last + 10000) return 0;
last = tc;
#ifdef WIN32
//SetProcessWorkingSetSize(GetCurrentProcess(), -1, -1);
#endif
return 0;
}

View file

@ -0,0 +1,19 @@
#ifndef __GARBAGECOLLECT_H
#define __GARBAGECOLLECT_H
#include <api/syscb/callbacks/gccb.h>
class GarbageCollector : public GarbageCollectCallbackI {
public:
GarbageCollector();
virtual ~GarbageCollector();
virtual int gccb_onGarbageCollect();
private:
uint32_t last;
};
extern GarbageCollector *garbageCollector;
#endif

View file

@ -0,0 +1,15 @@
#include <precomp.h>
#include "guistatuscb.h"
#define CBCLASS GuiStatusCallbackI
START_DISPATCH;
CB(STATUS_GETDEP, status_getDependencyPtr);
VCB(STATUS_ONSETTEXT, onSetStatusText);
VCB(STATUS_ADDCTXTCMDS, onAddAppCmds);
VCB(STATUS_REMCTXTCMDS, onRemoveAppCmds);
VCB(STATUS_PUSHCOMPLETED, pushCompleted);
VCB(STATUS_INCCOMPLETED, incCompleted);
VCB(STATUS_SETCOMPLETED, setCompleted);
VCB(STATUS_POPCOMPLETED, popCompleted);
END_DISPATCH;
#undef CBCLASS

View file

@ -0,0 +1,83 @@
#ifndef _GUISTATUSCB_H
#define _GUISTATUSCB_H
#include <bfc/dispatch.h>
class AppCmds;
class ifc_dependent;
class GuiStatusCallback : public Dispatchable {
public:
void onSetStatusText(const wchar_t *text, int overlay);
void onAddAppCmds(AppCmds *commands);
void onRemoveAppCmds(AppCmds *commands);
void pushCompleted(int max=100);
void incCompleted(int add=1);
void setCompleted(int pos);
void popCompleted();
api_dependent *status_getDependencyPtr();
enum {
STATUS_ONSETTEXT = 101,
STATUS_GETDEP = 200,
STATUS_ADDCTXTCMDS = 300,
STATUS_REMCTXTCMDS = 400,
STATUS_PUSHCOMPLETED = 500,
STATUS_INCCOMPLETED = 600,
STATUS_SETCOMPLETED = 700,
STATUS_POPCOMPLETED = 800,
};
};
inline void GuiStatusCallback ::onSetStatusText(const wchar_t *text, int overlay) {
_voidcall(STATUS_ONSETTEXT, text, overlay);
}
inline api_dependent *GuiStatusCallback ::status_getDependencyPtr() {
return _call(STATUS_GETDEP, (api_dependent *)NULL);
}
inline void GuiStatusCallback ::onAddAppCmds(AppCmds *commands) {
_voidcall(STATUS_ADDCTXTCMDS, commands);
}
inline void GuiStatusCallback ::onRemoveAppCmds(AppCmds *commands) {
_voidcall(STATUS_REMCTXTCMDS, commands);
}
inline
void GuiStatusCallback::pushCompleted(int max) {
_voidcall(STATUS_PUSHCOMPLETED, max);
}
inline
void GuiStatusCallback::incCompleted(int add) {
_voidcall(STATUS_INCCOMPLETED, add);
}
inline
void GuiStatusCallback::setCompleted(int pos) {
_voidcall(STATUS_SETCOMPLETED, pos);
}
inline
void GuiStatusCallback::popCompleted() {
_voidcall(STATUS_POPCOMPLETED);
}
class GuiStatusCallbackI : public GuiStatusCallback {
public:
virtual void onSetStatusText(const wchar_t *text, int overlay)=0;
virtual api_dependent *status_getDependencyPtr()=0;
virtual void onAddAppCmds(AppCmds *commands)=0;
virtual void onRemoveAppCmds(AppCmds *commands)=0;
virtual void pushCompleted(int max=100)=0;
virtual void incCompleted(int add=1)=0;
virtual void setCompleted(int pos)=0;
virtual void popCompleted()=0;
protected:
RECVS_DISPATCH;
};
#endif

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,465 @@
#ifndef __LAYOUT_H
#define __LAYOUT_H
class Layout;
class Group;
class Container;
class Layer;
#include <bfc/tlist.h>
#include <bfc/depend.h>
#include <tataki/bitmap/bitmap.h>
#include <api/wnd/wndclass/buttwnd.h>
#include <tataki/region/region.h>
#include <api/wndmgr/container.h>
#include <api/skin/group.h>
#include <api/skin/widgets/layer.h>
#include <api/wndmgr/guistatuscb.h>
#include <api/script/script.h>
#include <api/script/scriptobj.h>
#ifdef WASABI_WIDGETS_GUIOBJECT
#include <api/script/objects/guiobj.h>
#endif
#include <api/wnd/accessible.h>
#include <api/wndmgr/alphamgr.h>
#include <api/wnd/resizable.h>
class XmlObject;
class Layout;
extern AlphaMgr *alphaMgr;
class LayoutScriptController : public GroupScriptController {
public:
virtual const wchar_t *getClassName();
virtual const wchar_t *getAncestorClassName();
virtual ScriptObjectController *getAncestorController() { return groupController; }
virtual int getNumFunctions();
virtual const function_descriptor_struct *getExportedFunctions();
virtual GUID getClassGuid();
virtual ScriptObject *instantiate();
virtual int getInstantiable();
virtual void destroy(ScriptObject *o);
virtual void *encapsulate(ScriptObject *o);
virtual void deencapsulate(void *o);
private:
static function_descriptor_struct exportedFunction[];
};
extern LayoutScriptController *layoutController;
#ifndef _NOSTUDIO
class AutoOpacityLinker;
#define LAYOUT_PARENT Group
#define LAYOUT_SCRIPTPARENT Group
class Layout : public LAYOUT_SCRIPTPARENT, public DependentViewerI, public GuiResizable
{
public:
Layout();
virtual ~Layout();
#ifdef _WIN32
virtual LRESULT wndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
#else
virtual OSStatus eventHandler(EventHandlerCallRef inHandlerCallRef, EventRef inEvent, void *inUserData);
#endif
// int onPaint(Canvas *canvas);
virtual int onInit();
virtual int init(OSMODULEHANDLE inst, OSWINDOWHANDLE parent, int nochild);
virtual int reinit(OSMODULEHANDLE inst, OSWINDOWHANDLE parent, int nochild);
virtual int childNotify(ifc_window *child, int msg, intptr_t param1=0, intptr_t param2=0);
virtual int onActionNotify(int action, intptr_t param=0);
virtual void resize(int x, int y, int w, int h, int wantcb=1);
virtual void move(int x, int y);
// virtual int onRightButtonDown(int x, int y);
// virtual int onLeftButtonDown(int x, int y);
// virtual int onMouseMove(int x, int y);
// virtual int onLeftButtonUp(int x, int y);
virtual int onResize();
virtual int onPostedMove();
virtual int onPaint(Canvas *canvas);
virtual void onSetDesktopAlpha(int a);
virtual int isLayout();
virtual void setAlphaBackground(const wchar_t *txture);
virtual SkinBitmap *getBaseTexture();
virtual void onGuiObjectSetVisible(GuiObject *o, int status); // called whenever a child shows/hide
virtual ifc_window *getCustomOwner();
virtual void addLockedLayout(Layout *l);
virtual void removeLockedLayout(Layout *l);
virtual int getNumLockedLayouts();
virtual Layout *enumLockedLayout(int n);
virtual int isLocked();
virtual void lockTo(Layout *l);
virtual Layout *getLockedTo();
void updateLockedLayouts();
virtual int onGetFocus();
virtual int onKillFocus();
virtual void snapAdjust(int left, int right, int top, int bottom);
virtual void onShow(void);
virtual void onHide(void);
virtual void center();
virtual int wantDesktopAlpha();
virtual void setWantDesktopAlpha(int want);
virtual int handleDesktopAlpha();
virtual int setXuiParam(int _xuihandle, int attribid, const wchar_t *paramname, const wchar_t *strvalue);
void setWindowRegion(api_region *reg);
virtual int allowResize() {
return !isLocked()
#ifdef USEAPPBAR
&& !appbar_isDocked()
#endif
;
}
// container/component callbacks to get notified that a container
// has been set visible/invisible
void containerToggled(const wchar_t *id,int visible);
void componentToggled(GUID *guid, int visible);
void setParentContainer(Container *c);
virtual Container *getParentContainer();
virtual int isClickThrough();
void onSetVisible(int show);
virtual void cancelCapture();
virtual int onActivate();
virtual int onDeactivate();
virtual int forceTransparencyFlag();
int x, y;
#ifdef _WIN32
void setForwardMsgWnd(HWND wnd) { forwardMsgWnd = wnd; }
LPARAM wndHolder_getParentParam(int i=0);
#endif
void scaleTo(int s);
virtual void setRenderRatio(double s);
virtual void beginMove();
virtual void beginScale();
virtual void beginResize();
virtual void endMove();
virtual void endScale();
virtual void endResize();
virtual void setEndMoveResize(int w, int h) {
m_w = w;
m_h = h;
m_endmovesize = 1;
};
virtual ifc_window *guiresizable_getRootWnd() { return (this); }
virtual void lockScale(int locked);
virtual int isScaleLocked() { return scalelocked; }
virtual void onMove();
virtual int isDesktopAlphaSafe();
void addSubRegionLayer(Layer *l);
void removeSubRegionLayer(Layer *l);
virtual void setInDesktop(int a);
virtual int getInDesktop();
virtual void setAlpha(int a);
virtual int getAlpha();
virtual int getPaintingAlpha();
virtual void timerCallback(int id);
virtual void setLinkWidth(const wchar_t *layoutid);
virtual void setLinkHeight(const wchar_t *layoutid);
virtual void setBaseTexture(const wchar_t *b, int regis=1);
virtual void setPaintingAlpha(int activealpha, int inactivealpha=-1);
static void onGlobalEnableDesktopAlpha(int enabled);
void savePosition();
#ifdef USEAPPBAR
void saveAppBarPosition();
#endif
virtual void setStatusText(const wchar_t *txt, int overlay=0);
virtual void addAppCmds(AppCmds *commands);
virtual void removeAppCmds(AppCmds *commands);
void pushCompleted(int max=100);
void incCompleted(int add=1);
void setCompleted(int pos);
void popCompleted();
virtual void registerStatusCallback(GuiStatusCallback *lcb);
virtual int viewer_onItemDeleted(api_dependent *item);
virtual int wantActivation() { return wantactiv && LAYOUT_PARENT::wantActivation(); }
void loadSavedState();
virtual void updateOnTop();
virtual int runAction(int actionid, const wchar_t *param=NULL);
virtual void getSnapAdjust(RECT *r);
virtual void updateTransparency();
virtual int onDeferredCallback(intptr_t p1, intptr_t p2);
virtual int wantRedrawOnResize() { return wantredrawonresize; }
virtual void setWantRedrawOnResize(int v);
#ifdef USEAPPBAR
virtual int appbar_wantAutoHide() { return getAppBarAutoHide(); }
virtual int appbar_wantAlwaysOnTop() { return getAppBarAlwaysOnTop(); }
virtual int getAppBarAutoHide();
virtual void setAppBarAutoHide(int ah);
virtual int getAppBarAlwaysOnTop();
virtual void setAppBarAlwaysOnTop(int aot);
#endif
virtual void pushForceUnlink() { m_forceunlink++; }
virtual void popForceUnlink() { m_forceunlink--; }
virtual int isUnlinked() {
#ifdef USEAPPBAR
return unlinked || appbar_isDocked() || m_forceunlink;
#else
return unlinked || m_forceunlink;
#endif
}
void setAutoOpacify(int a);
int getAutoOpacify() { return autoopacify; }
void offscreenCheck();
int isOffscreen(ifc_window *w);
int getResizable();
int getScalable();
void setTransparencyOverride(int v);
int getTransparencyOverride() { return transparencyoverride; }
enum {
LAYOUT_SETDESKTOPALPHA=0,
LAYOUT_SETINDESKTOP,
LAYOUT_SETALPHA,
LAYOUT_SETLINKWIDTH,
LAYOUT_SETLINKHEIGHT,
LAYOUT_SETOWNER,
LAYOUT_SETLOCKTO,
LAYOUT_SETOSFRAME,
LAYOUT_SETALPHABACKGROUND,
LAYOUT_SETNOACTIVATION,
LAYOUT_SETONTOP,
LAYOUT_SNAPADJUSTLEFT,
LAYOUT_SNAPADJUSTTOP,
LAYOUT_SNAPADJUSTRIGHT,
LAYOUT_SNAPADJUSTBOTTOM,
LAYOUT_UNLINKED,
LAYOUT_NOPARENT,
LAYOUT_FORCEALPHA,
LAYOUT_NODOCK,
LAYOUT_NOOFFSCREENCHECK,
LAYOUT_RESIZABLE,
LAYOUT_SCALABLE,
};
void onMouseEnterLayout();
void onMouseLeaveLayout();
int getNoParent() { return noparent; }
void setNoParent(int np) { noparent = np; }
int isAlphaForced() { return forcealpha; }
AlphaMgr *getAlphaMgr() { return alphaMgr; }
int getNoDock() { return nodock; }
void setNoDock(int nd) { nodock = nd; }
int isTransparencyForcedOff() { return transparency_autooff; }
void controlMenu();
void setNoOffscreenCheck(int nocheck);
#ifdef USEAPPBAR
void onDock(int side);
void onUnDock();
virtual void appbar_onDock(int side);
virtual void appbar_onUnDock();
virtual void appbar_onSlide();
#endif
protected:
/*static */void CreateXMLParameters(int master_handle);
/* virtual int dragEnter(ifc_window *sourceWnd);
virtual int dragOver(int x, int y, ifc_window *sourceWnd);
virtual int dragDrop(ifc_window *sourceWnd, int x, int y);
virtual int acceptExternalDrops() { return 1; }*/
virtual int wantClickWndAutoInvalidate() { return 0; }
private:
StringW MakePrefix();
static XMLParamPair params[];
void fixPosition();
void saveAllPositions();
void activateChildren(int act);
#ifdef _WIN32
void getExplorerWindows(HWND *parent, HWND *listview, HWND *webserver);
#endif
void desktopAlpha_autoTurnOn();
void desktopAlpha_autoTurnOff();
void transparency_autoTurnOn();
void transparency_autoTurnOff();
void globalEnableDesktopAlpha(int enabled);
#ifdef _WIN32
HWND forwardMsgWnd;
#endif
int resizing;
int wantactiv;
int size_w,size_h;
int cX,cY;
int captured;
POINT mousepos;
#ifdef _WIN32
HWND webserver;
HWND listview;
#endif
int alphagoingon;
int alphagoingoff;
int scalelocked;
int wantredrawonresize;
int xuihandle;
RegionI *reg;
//PtrList<Layer> *subregionlayers;
Container *p_container;
StringW alphabackgroundstr;
ifc_window *wndholders;
int abortSaving();
int transparencyoverride;
int default_x;
int default_y;
int moving;
int scaling;
int mover;
int indesktop;
int alpha;
StringW linkedheight, linkedwidth;
int inlinkwidth, inlinkheight;
AutoSkinBitmap alphabackground;
int wantdesktopalpha;
int galphadisabled;
static PtrList<Layout> alllayouts;
StringW owner;
PtrList<Layout> locked;
StringW lockto;
Layout *lockedto;
int inpostedmove;
int osframe;
PtrList<GuiStatusCallback> statuscbs;
int initontop;
// GarbageCollector gc;
PtrList<AppCmds> appcmds;
int inresize;
int unlinked;
int snap_adjust_left;
int snap_adjust_top;
int snap_adjust_right;
int snap_adjust_bottom;
int disable_auto_alpha;
int autoopacify;
int noparent;
int forcealpha;
redock_struct redock;
static int broadcasting;
int nodock;
uint32_t transparency_reenabled_at;
int transparency_autooff;
int nooffscreencheck;
int resizable;
int scalable;
int m_w, m_h;
int m_endmovesize;
int m_allowsavedock;
int m_forceunlink;
#ifdef USEAPPBAR
int appbar_want_autohide;
int appbar_want_alwaysontop;
#endif
// FG>
// -- SCRIPT -----------------------------------------------------
public:
static scriptVar script_vcpu_onDock(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar side);
static scriptVar script_vcpu_onUndock(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_getScale(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_setScale(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar s);
static scriptVar script_vcpu_onScale(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar s);
static scriptVar script_vcpu_setDesktopAlpha(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar s);
static scriptVar script_vcpu_getDesktopAlpha(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_isTransparencySafe(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_isLayoutAnimationSafe(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_getContainer(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_center(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_onMove(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_onEndMove(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_onUserResize(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar x, scriptVar y, scriptVar w, scriptVar h);
static scriptVar script_vcpu_snapAdjust(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar left, scriptVar top, scriptVar right, scriptVar bottom);
static scriptVar script_vcpu_setRedrawOnResize(SCRIPT_FUNCTION_PARAMS, ScriptObject *o, scriptVar v);
static scriptVar script_vcpu_beforeRedock(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_redock(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_getSnapAdjustTop(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_getSnapAdjustLeft(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_getSnapAdjustRight(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_getSnapAdjustBottom(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_onMouseEnterLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_onMouseLeaveLayout(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
static scriptVar script_vcpu_onSnapAdjustChanged(SCRIPT_FUNCTION_PARAMS, ScriptObject *o);
#else
class Layout : public LAYOUT_SCRIPTPARENT {
public:
#endif
// INSERT_SCRIPT_OBJECT_CONTROL
};
// END SCRIPT
#endif

View file

@ -0,0 +1,251 @@
#include <precomp.h>
#include "msgbox.h"
#include <api/wndmgr/skinwnd.h>
#include <api/wnd/wndclass/guiobjwnd.h>
#include <api/script/scriptguid.h>
#include <api/script/objects/c_script/c_container.h>
#include <api/script/objects/c_script/c_text.h>
#include <api/script/objects/c_script/c_button.h>
_btnstruct msgboxbtns[] =
{
{ L"<<", MSGBOX_PREVIOUS },
{ L"OK", MSGBOX_OK },
{ L"Yes", MSGBOX_YES },
{ L"All", MSGBOX_ALL },
{ L"No", MSGBOX_NO },
{ L">>", MSGBOX_NEXT },
{ L"Cancel", MSGBOX_CANCEL },
};
MsgBox::MsgBox(const wchar_t *_text, const wchar_t *_title, int _flags, const wchar_t *notanymore)
{
text = _text;
title = _title;
flags = _flags;
#ifdef WIN32
#ifdef _DEBUG
DebugStringW(L"msgbox: %s: %s", title, text.getValue());
#endif
#endif
notanymore_id = notanymore;
sw = NULL;
if (flags == 0) flags = MSGBOX_OK;
}
MsgBox::~MsgBox()
{
foreach(buttons)
WASABI_API_SKIN->xui_delete(buttons.getfor());
endfor
}
int MsgBox::run()
{
int _r = -1;
#ifdef WASABI_COMPILE_CONFIG
if (!notanymore_id.isempty())
{
StringPrintfW txt(L"msgbox_defaultvalue_%s", notanymore_id);
if ((GetKeyState(VK_SHIFT) & 0x8000))
WASABI_API_CONFIG->setIntPublic(txt, -1);
_r = WASABI_API_CONFIG->getIntPublic(txt, -1);
}
#endif
if (_r == -1)
{
sw = new SkinWnd(L"msgbox.custom.group", L"modal", FALSE, NULL, 1, 1);
if (!sw->getWindow()) return -1;
ifc_window *grp = sw->getWindow();
ifc_window *l = grp->getDesktopParent();
GuiObject *_p = sw->findObject(L"msgbox.custom.group");
//CUT: api_window *p = _p->guiobject_getRootWnd();
C_Container cont(sw->getContainer());
cont.setName(title);
createButtons();
int min_w = reposButtons();
GuiObject *go_txt = sw->findObject(L"msgbox.text");
if (go_txt != NULL)
{
GuiObject *to = go_txt->guiobject_findObject(L"wasabi.text");
GuiObject *gto = sw->findObject(L"text");
if (to != NULL && gto != NULL)
{
go_txt->guiobject_setXmlParam(L"text", text);
C_GuiObject t(*go_txt);
int _w = t.getAutoWidth();
int _h = t.getAutoHeight();
to->guiobject_setXmlParam(L"w", StringPrintfW(_w));
to->guiobject_setXmlParam(L"h", StringPrintfW(_h));
to->guiobject_setXmlParam(L"relatw", L"0");
to->guiobject_setXmlParam(L"relath", L"0");
int x, rx, w, rw;
int y, ry, h, rh;
int gtow, gtoh;
go_txt->guiobject_getGuiPosition(&x, &y, &w, &h, &rx, &ry, &rw, &rh);
if (rw == 1)
_w += -w;
else
_w += x * 2;
if (rh == 1)
_h += -h;
else
_h += y * 2;
gtow = _w;
gtoh = _h;
GuiObject *grpo = grp->getGuiObject();
ASSERT(grpo != NULL);
gto->guiobject_getGuiPosition(&x, &y, &w, &h, &rx, &ry, &rw, &rh);
if (rw == 1)
_w += -w;
else
_w += x * 2;
if (rh == 1)
_h += -h;
else
_h += y * 2;
gto->guiobject_setXmlParam(L"w", StringPrintfW(gtow));
gto->guiobject_setXmlParam(L"h", StringPrintfW(gtoh));
grpo->guiobject_setXmlParam(L"w", StringPrintfW(_w));
grpo->guiobject_setXmlParam(L"h", StringPrintfW(_h));
grpo->guiobject_setXmlParam(L"lockminmax", L"1");
grpo->guiobject_setXmlParam(L"propagatesize", L"1");
XmlObject *xl = static_cast<XmlObject *>(l->getInterface(xmlObjectGuid));
xl->setXmlParam(L"minimum_h", StringPrintfW(L"%d", _h));
xl->setXmlParam(L"minimum_w", StringPrintfW(L"%d", (_w < min_w) ? min_w : _w));
}
}
if (!notanymore_id.isempty())
{
GuiObject *o = WASABI_API_SKIN->xui_new(L"Wasabi:CheckBox"); // that'll be deleted automatically when our parent group destroys
if (o != NULL)
{
ifc_window *w = o->guiobject_getRootWnd();
C_GuiObject go(*o);
go.init(_p->guiobject_getScriptObject());
o->guiobject_setXmlParam(L"text", L"Do not show this message anymore");
o->guiobject_setXmlParam(L"y", L"-50");
o->guiobject_setXmlParam(L"relaty", L"1");
o->guiobject_setXmlParam(L"x", L"12");
o->guiobject_setXmlParam(L"relatx", L"0");
o->guiobject_setXmlParam(L"w", L"-24");
o->guiobject_setXmlParam(L"relatw", L"1");
min_w = MAX(w->getPreferences(SUGGESTED_W), min_w);
}
}
sw->notifyMinMaxChanged();
reposButtons();
_r = sw->runModal(1);
}
#ifdef WASABI_COMPILE_CONFIG
if (!notanymore_id.isempty() && _r != -1 && sw != NULL)
{
GuiObject *o = sw->findObject(L"checkbox.toggle");
if (o != NULL)
{
C_Button b(*o);
if (b.getActivated())
{
StringPrintfW txt(L"msgbox_defaultvalue_%s", notanymore_id);
WASABI_API_CONFIG->setIntPublic(txt, _r);
}
}
}
#endif
if (sw) sw->destroy(); sw = NULL;
return _r;
}
void MsgBox::addButton(const wchar_t *text, int retcode)
{
GuiObject *o = WASABI_API_SKIN->xui_new(L"Wasabi:Button"); // that wil NOT be deleted automatically when our parent group destroys because we did not init with guiobject
if (o != NULL)
{
o->guiobject_setXmlParam(L"action", L"endmodal");
o->guiobject_setXmlParam(L"retcode", StringPrintfW(retcode));
o->guiobject_setXmlParam(L"text", text);
buttons.addItem(o);
}
}
void MsgBox::createButtons()
{
GuiObject *_p = sw->findObject(L"msgbox.custom.group");
if (!_p) return ;
ASSERT(buttons.getNumItems() == 0);
buttons.deleteAll();
for (int i = 0;i < sizeof(msgboxbtns) / sizeof(_btnstruct);i++)
{
if (flags & msgboxbtns[i].id)
{
addButton(msgboxbtns[i].txt, msgboxbtns[i].id);
}
}
ifc_window *p = _p->guiobject_getRootWnd();
foreach(buttons)
ifc_window *wnd = buttons.getfor()->guiobject_getRootWnd();
if (wnd != NULL)
{
wnd->setStartHidden(1);
wnd->setParent(p);
wnd->init(p);
}
endfor;
}
int MsgBox::reposButtons()
{
RECT r;
GuiObject *_p = sw->findObject(L"msgbox.custom.group");
ifc_window *p = _p->guiobject_getRootWnd();
p->getClientRect(&r);
int shift = 0;
//CUT: int _w = 0;
//CUT: int _h = 0;
for (int i = buttons.getNumItems() - 1;i >= 0;i--)
{
ifc_window *wnd = buttons.enumItem(i)->guiobject_getRootWnd();
if (wnd != NULL)
{
int _w = wnd->getPreferences(SUGGESTED_W);
int _h = wnd->getPreferences(SUGGESTED_H);
if (_w == AUTOWH) _w = -1;
int w = MAX(_w, 64);
wnd->resize(r.right - w - 16 - shift, r.bottom - 8 - _h, w, _h);
_w = MAX(w, _w);
_h = MAX(_h, _h);
shift += w + 4;
}
}
foreach(buttons)
ifc_window *wnd = buttons.getfor()->guiobject_getRootWnd();
if (wnd != NULL)
wnd->setVisible(1);
endfor;
return shift;
}

View file

@ -0,0 +1,49 @@
#ifndef __MESSAGEBOX_H
#define __MESSAGEBOX_H
#include <bfc/string/bfcstring.h>
#include <bfc/string/StringW.h>
#include <bfc/ptrlist.h>
#define MSGBOX_ABORTED 0 // NOT a flag, only a return code
#define MSGBOX_OK 1
#define MSGBOX_CANCEL 2
#define MSGBOX_YES 4
#define MSGBOX_NO 8
#define MSGBOX_ALL 16
#define MSGBOX_NEXT 32
#define MSGBOX_PREVIOUS 64
class GuiObject;
class SkinWnd;
typedef struct {
wchar_t *txt;
int id;
} _btnstruct;
class MsgBox {
public:
MsgBox(const wchar_t *text, const wchar_t *title=L"Alert", int flags=MSGBOX_OK, const wchar_t *notanymore=NULL);
virtual ~MsgBox();
virtual int run();
private:
void createButtons();
int reposButtons();
void addButton(const wchar_t *text, int retcode);
StringW text, title;
int flags;
PtrList<GuiObject> buttons;
GuiObject *checkbox;
SkinWnd *sw;
StringW notanymore_id;
};
#endif

View file

@ -0,0 +1,383 @@
#include <precomp.h>
#ifdef WIN32
#include <windows.h>
#endif
#include <bfc/assert.h>
#include <api/wndmgr/resize.h>
#include <api/wnd/wndtrack.h>
#include <api/wnd/basewnd.h>
#include <api/wndmgr/layout.h>
#define tag L"wa3_resizerclass"
extern HINSTANCE hInstance;
//----------------------------------------------------------------------
resizeClass::resizeClass(ifc_window *wnd, int minx, int miny, int maxx, int maxy, int sugx, int sugy)
{
screenWidth = Wasabi::Std::getScreenWidth();
screenHeight = Wasabi::Std::getScreenHeight();
#if defined (_WIN32) || defined(_WIN64)
WNDCLASSW wc;
if (!GetClassInfoW(hInstance, tag, &wc))
{
MEMSET(&wc, 0, sizeof(wc));
wc.lpfnWndProc = resizeWndProc;
wc.hInstance = hInstance; // hInstance of DLL
wc.lpszClassName = tag; // our window class name
wc.style = 0;
int _r = RegisterClassW(&wc);
ASSERTPR(_r, "cannot create resizer wndclass");
}
hWnd = CreateWindowExW(0, tag, L"", 0, 0, 0, 1, 1, NULL, NULL, hInstance, NULL);
ASSERT(hWnd);
SetWindowLongPtrW(hWnd, GWLP_USERDATA, (LONG_PTR)this);
if (minx > maxx && maxx != -1) minx = maxx;
if (miny > maxy && maxy != -1) miny = maxy;
#endif
minWinWidth = minx;
minWinHeight = miny;
maxWinWidth = maxx;
maxWinHeight = maxy;
sugWinWidth = sugx;
sugWinHeight = sugy;
if (wnd->getInterface(layoutGuid))
{
static_cast<Layout *>(wnd)->getSnapAdjust(&snapAdjust);
if (minWinWidth != -1) minWinWidth -= snapAdjust.left + snapAdjust.right;
if (minWinHeight != -1) minWinHeight -= snapAdjust.bottom + snapAdjust.top;
if (maxWinWidth != -1) maxWinWidth -= snapAdjust.left + snapAdjust.right;
if (maxWinHeight != -1) maxWinHeight -= snapAdjust.bottom + snapAdjust.top;
if (sugWinWidth != -1) sugWinWidth -= snapAdjust.left + snapAdjust.right;
if (sugWinHeight != -1) sugWinHeight -= snapAdjust.bottom + snapAdjust.top;
}
dc = NULL;
#ifdef WIN32
oldB = NULL;
brush = NULL;
oldP = NULL;
pen = NULL;
#endif
}
//----------------------------------------------------------------------
resizeClass::~resizeClass()
{
#ifdef WIN32
if (dc)
{
SelectObject(dc, oldB);
SelectObject(dc, oldP);
SetROP2(dc, mix);
DeleteObject(pen);
DeleteObject(brush);
ReleaseDC(NULL, dc);
}
if (IsWindow(hWnd))
DestroyWindow(hWnd);
//BU win98 sucks UnregisterClass(tag, Main::gethInstance());
#else
if (dc)
{
XFreeGC(Linux::getDisplay(), dc->gc);
FREE(dc);
}
#endif
}
//----------------------------------------------------------------------
BOOL CALLBACK invalidateChildren(HWND hwnd, LPARAM lParam)
{
InvalidateRect(hwnd, NULL, FALSE);
return TRUE;
}
//----------------------------------------------------------------------
BOOL CALLBACK invalidateAll(HWND hwnd, LPARAM lParam)
{
EnumChildWindows(hwnd, invalidateChildren, 0);
InvalidateRect(hwnd, NULL, FALSE);
return TRUE;
}
//----------------------------------------------------------------------
int resizeClass::resizeWindow(ifc_window *wnd, int way)
{
// paintHookStart();
wnd->getWindowRect(&originalRect);
snapAdjust.left = 0;
snapAdjust.top = 0;
snapAdjust.right = 0;
snapAdjust.bottom = 0;
if (wnd->getInterface(layoutGuid))
{
static_cast<Layout *>(wnd)->getSnapAdjust(&snapAdjust);
if (wnd->getRenderRatio() != 1.0)
{
double rr = wnd->getRenderRatio();
snapAdjust.left = (int)((double)(snapAdjust.left) * rr);
snapAdjust.top = (int)((double)(snapAdjust.top) * rr);
snapAdjust.right = (int)((double)(snapAdjust.right) * rr);
snapAdjust.bottom = (int)((double)(snapAdjust.bottom) * rr);
}
originalRect.left += snapAdjust.left;
originalRect.top += snapAdjust.top;
originalRect.right -= snapAdjust.right;
originalRect.bottom -= snapAdjust.bottom;
}
curRect = originalRect;
resizeWay = way;
resizedWindow = wnd->gethWnd();
resizedWindowR = wnd;
POINT pt;
Wasabi::Std::getMousePos(&pt);
cX = pt.x;
cY = pt.y;
#ifdef WIN32
SetCapture(hWnd);
#endif
SetTimer(hWnd, 1, 100, NULL); // this timer will make sure that we never get interlock
drawFrame();
MSG msg;
cancelit = 1;
while (GetCapture() == hWnd && GetMessage( &msg, hWnd, 0, 0 ))
{
TranslateMessage( &msg );
#ifdef LINUX
if ( msg.message == WM_LBUTTONUP || msg.message == WM_MOUSEMOVE )
wndProc( msg.hwnd, msg.message, msg.wParam, msg.lParam );
else
#endif
DispatchMessage( &msg );
}
drawFrame();
// paintHookStop();
if (GetCapture() == hWnd) ReleaseCapture();
KillTimer(hWnd, 1);
if (!cancelit)
{
curRect.left -= snapAdjust.left;
curRect.top -= snapAdjust.top;
curRect.right += snapAdjust.right;
curRect.bottom += snapAdjust.bottom;
}
else
{
curRect = originalRect;
// evil, but less evil than InvalidateRect(NULL, NULL, FALSE);
EnumWindows(invalidateAll, 0);
}
return !cancelit;
}
//----------------------------------------------------------------------
RECT resizeClass::getRect(void)
{
return curRect;
}
//#define nifty
//----------------------------------------------------------------------
void resizeClass::drawFrame(void)
{
RECT outRect;
#ifdef WIN32
if (!dc)
{
dc = GetDC(NULL);
brush = CreateSolidBrush(0xFFFFFF);
pen = CreatePen(PS_SOLID, 0, 0xFFFFFF);
oldB = (HBRUSH)SelectObject(dc, brush);
oldP = (HPEN)SelectObject(dc, pen);
mix = SetROP2(dc, R2_XORPEN);
}
outRect = curRect;
#ifndef nifty
DrawFocusRect(dc, &outRect);
#else
RECT inRect;
inRect = outRect;
inRect.left += 10;
inRect.right -= 10;
inRect.top += 24;
inRect.bottom -= 10;
MoveToEx(dc, inRect.left, inRect.top, NULL);
LineTo(dc, inRect.right, inRect.top);
LineTo(dc, inRect.right, inRect.bottom);
LineTo(dc, inRect.left, inRect.bottom);
LineTo(dc, inRect.left, inRect.top);
MoveToEx(dc, outRect.left, 0, NULL);
LineTo(dc, outRect.left, screenHeight);
MoveToEx(dc, outRect.right, 0, NULL);
LineTo(dc, outRect.right, screenHeight);
MoveToEx(dc, 0, outRect.top, NULL);
LineTo(dc, screenWidth, outRect.top);
MoveToEx(dc, 0, outRect.bottom, NULL);
LineTo(dc, screenWidth, outRect.bottom);
#endif
#endif//WIN32
#ifdef LINUX
outRect = curRect;
if ( ! dc )
{
dc = (HDC)MALLOC( sizeof( hdc_typ ) );
XGCValues gcv;
gcv.function = GXxor;
gcv.subwindow_mode = IncludeInferiors;
gcv.foreground = 0xffffff;
gcv.line_style = LineOnOffDash;
gcv.dashes = 1;
dc->gc = XCreateGC( Linux::getDisplay(), Linux::RootWin(), GCFunction | GCForeground | GCSubwindowMode, &gcv );
}
XDrawRectangle( Linux::getDisplay(), Linux::RootWin(), dc->gc,
outRect.left, outRect.top, outRect.right - outRect.left,
outRect.bottom - outRect.top );
#endif
//PORTME
}
LRESULT resizeClass::wndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
switch (uMsg)
{
case WM_LBUTTONUP:
cancelit = 0;
ReleaseCapture();
return 0;
case WM_MOUSEMOVE:
{
POINT pt;
int iX, iY;
Wasabi::Std::getMousePos(&pt);
iX = pt.x - cX;
iY = pt.y - cY;
drawFrame();
if (resizeWay & TOP)
curRect.top = originalRect.top + iY;
if (resizeWay & BOTTOM)
curRect.bottom = originalRect.bottom + iY;
if (resizeWay & LEFT)
curRect.left = originalRect.left + iX;
if (resizeWay & RIGHT)
curRect.right = originalRect.right + iX;
if (abs((curRect.right - curRect.left) - sugWinWidth) < 10)
if (resizeWay & RIGHT)
curRect.right = curRect.left + sugWinWidth;
else if (resizeWay & LEFT)
curRect.left = curRect.right - sugWinWidth;
if (abs((curRect.bottom - curRect.top) - sugWinHeight) < 10)
if (resizeWay & BOTTOM)
curRect.bottom = curRect.top + sugWinHeight;
else if (resizeWay & TOP)
curRect.top = curRect.bottom - sugWinHeight;
curRect.left -= snapAdjust.left;
curRect.top -= snapAdjust.top;
curRect.right += snapAdjust.right;
curRect.bottom += snapAdjust.bottom;
windowTracker->autoDock(resizedWindowR, &curRect, resizeWay);
curRect.left += snapAdjust.left;
curRect.top += snapAdjust.top;
curRect.right -= snapAdjust.right;
curRect.bottom -= snapAdjust.bottom;
if ((curRect.right - curRect.left) < minWinWidth)
if (resizeWay & RIGHT)
curRect.right = curRect.left + minWinWidth;
else if (resizeWay & LEFT)
curRect.left = curRect.right - minWinWidth;
if ((curRect.bottom - curRect.top) < minWinHeight)
if (resizeWay & BOTTOM)
curRect.bottom = curRect.top + minWinHeight;
else if (resizeWay & TOP)
curRect.top = curRect.bottom - minWinHeight;
if (maxWinWidth != -1 && (curRect.right - curRect.left) > maxWinWidth)
if (resizeWay & RIGHT)
curRect.right = curRect.left + maxWinWidth;
else if (resizeWay & LEFT)
curRect.left = curRect.right - maxWinWidth;
if (maxWinHeight != -1 && (curRect.bottom - curRect.top) > maxWinHeight)
if (resizeWay & BOTTOM)
curRect.bottom = curRect.top + maxWinHeight;
else if (resizeWay & TOP)
curRect.top = curRect.bottom - maxWinHeight;
drawFrame();
}
return 0;
}
#ifdef WIN32
return DefWindowProcW(hwnd, uMsg, wParam, lParam);
#else
return 0;
#endif
}
// Window Procedure
//
LRESULT CALLBACK resizeWndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
#ifdef WIN32
resizeClass *gThis = (resizeClass *)GetWindowLongPtrW(hwnd, GWLP_USERDATA);
if (!gThis)
return DefWindowProcW(hwnd, uMsg, wParam, lParam);
else
return gThis->wndProc(hwnd, uMsg, wParam, lParam);
#else
return 0;
#endif
}
void resizeClass::setResizeCursor(int action)
{}

View file

@ -0,0 +1,48 @@
#ifndef __RESIZE_H
#define __RESIZE_H
#ifdef _WIN32
LRESULT CALLBACK resizeWndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
#endif
class resizeClass
{
#ifdef _WIN32
friend LRESULT CALLBACK resizeWndProc(HWND wnd, UINT uMsg, WPARAM wParam, LPARAM lParam); // heh, i really need this one ;)
#endif
private:
void drawFrame(void);
void setResizeCursor(int action);
int orientation(int a, int action);
OSWINDOWHANDLE hWnd;
OSWINDOWHANDLE resizedWindow;
ifc_window *resizedWindowR;
int resizeWay;
RECT curRect;
RECT originalRect;
int cX, cY;
int minWinWidth, minWinHeight;
int maxWinWidth, maxWinHeight;
int sugWinWidth, sugWinHeight;
int screenHeight, screenWidth;
bool cancelit;
RECT snapAdjust;
#ifdef WIN32
HBRUSH oldB, brush;
HPEN oldP, pen;
#endif
HDC dc;
int mix;
public:
resizeClass(ifc_window *wnd, int minx, int miny, int maxx, int maxy, int sugx, int sugy);
~resizeClass();
int resizeWindow(ifc_window *wnd, int way);
#ifdef _WIN32
LRESULT wndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
#endif
RECT getRect(void);
};
#endif

View file

@ -0,0 +1,733 @@
#include <precomp.h>
#include "skinembed.h"
#include <api/wndmgr/layout.h>
#include <api/wnd/wndclass/wndholder.h>
#include <api/skin/skinparse.h>
#include <api/wnd/wndtrack.h>
#include <api/config/items/cfgitemi.h>
#include <api/config/items/attrint.h>
#include <bfc/named.h>
#include <api/wndmgr/autopopup.h>
#include <api/syscb/callbacks/wndcb.h>
#include <api/wndmgr/skinwnd.h>
#include <api/script/scriptmgr.h>
#include <bfc/critsec.h>
CriticalSection skinembed_cs;
SkinEmbedder *skinEmbedder = NULL;
SkinEmbedder::SkinEmbedder()
{
ASSERTPR(skinEmbedder == NULL, "only one skin embedder please!");
skinEmbedder = this;
}
SkinEmbedder::~SkinEmbedder()
{
inserted.deleteAll();
allofthem.deleteAll();
}
int SkinEmbedder::toggle(GUID g, const wchar_t *prefered_container, int container_flag, RECT *r, int transcient)
{
ifc_window *w = enumItem(g, 0);
if (w != NULL)
{
destroy(w, r);
return 0;
}
ifc_window *wnd = create(g, NULL, prefered_container, container_flag, r, transcient);
if (wnd == NULL)
{
#ifdef ON_CREATE_EXTERNAL_WINDOW_GUID
int y;
ON_CREATE_EXTERNAL_WINDOW_GUID(g, y);
#endif
}
return 1;
}
int SkinEmbedder::toggle(const wchar_t *groupid, const wchar_t *prefered_container, int container_flag, RECT *r, int transcient)
{
ifc_window *w = enumItem(groupid, 0);
if (w != NULL)
{
destroy(w, r);
return 0;
}
create(INVALID_GUID, groupid, prefered_container, container_flag, r, transcient);
return 1;
}
ifc_window *SkinEmbedder::create(GUID g, const wchar_t *prefered_container, int container_flag, RECT *r, int transcient, int starthidden, int *isnew)
{
return create(g, NULL, prefered_container, container_flag, r, transcient, starthidden, isnew);
}
ifc_window *SkinEmbedder::create(const wchar_t *groupid, const wchar_t *prefered_container, int container_flag, RECT *r, int transcient, int starthidden, int *isnew)
{
return create(INVALID_GUID, groupid, prefered_container, container_flag, r, transcient, starthidden, isnew);
}
WindowHolder *SkinEmbedder::getSuitableWindowHolder(GUID g, const wchar_t *group_id, Container *cont, Layout *lay, int _visible, int _dynamic, int _empty, int _hasself, int _autoavail)
{
foreach(wndholders)
WindowHolder *h = wndholders.getfor();
ifc_window *w = h->getRootWndPtr()->getDesktopParent();
int dyn = 1;
int visible = 0;
int hasself = 0;
int empty = 0;
int autoavail = h->wndholder_isAutoAvailable();
Layout *l = (NULL != w) ? static_cast<Layout *>(w->getInterface(layoutGuid)) : NULL;
Container *c = NULL;
if (l)
{
c = l->getParentContainer();
if (c)
{
dyn = c->isDynamic();
}
}
if (NULL == w || !w->isInited()) visible = -1;
else
{
if (_visible == 1)
{
if (h->getRootWndPtr()->isVisible()) visible = 1;
}
else if (_visible == 0)
{
if (w->isVisible()) visible = 1;
}
}
if (!h->getCurRootWnd()) empty = 1;
if (g != INVALID_GUID)
{
if (g == h->getCurGuid())
hasself = 1;
}
else if (group_id && h->getCurGroupId())
{
if (!WCSICMP(group_id, h->getCurGroupId()))
hasself = 1;
}
if (_visible != -1)
{
if (visible != _visible) continue;
}
if (_dynamic != -1)
{
if (_dynamic != dyn) continue;
}
if (_empty != -1)
{
if (empty != _empty) continue;
}
if (_hasself != -1)
{
if (hasself != _hasself) continue;
}
if (_autoavail != -1)
{
if (autoavail != _autoavail) continue;
}
if (cont != NULL)
{
if (c != cont) continue;
}
if (lay != NULL)
{
if (l != lay) continue;
}
if (g != INVALID_GUID)
{
if (h->wantGuid(g)) return h;
}
else if (group_id)
{
if (h->wantGroup(group_id)) return h;
}
endfor;
return NULL;
}
ifc_window *SkinEmbedder::create(GUID g, const wchar_t *groupid, const wchar_t *prefered_container, int container_flag, RECT *r, int transcient, int starthidden, int *isnew)
{
// InCriticalSection in_cs(&skinembed_cs);
foreach(in_deferred_callback)
SkinEmbedEntry *e = in_deferred_callback.getfor();
if ((e->guid != INVALID_GUID && e->guid == g) || WCSCASEEQLSAFE(groupid, e->groupid))
{
#ifdef _DEBUG
DebugStringW(L"trying to show a window that is being destroyed, hm, try again later\n");
#endif
// too soon! try later dude
return NULL;
}
endfor;
RECT destrect = {0};
if (isnew) *isnew = 0;
WindowHolder *wh = NULL;
// todo: get from c++ callback
if (SOM::checkAbortShowHideWindow(g, 1))
return NULL;
if (g != INVALID_GUID)
wh = SOM::getSuitableWindowHolderFromScript(g);
if (!wh) wh = getSuitableWindowHolder(g, groupid, NULL, NULL, 1 /*visible*/, 0 /*static*/, 1 /*empty*/, -1 /*donttest*/, -1 /*donttest*/);
if (!wh) wh = getSuitableWindowHolder(g, groupid, NULL, NULL, 0 /*hidden*/, 0 /*static*/, 0 /*notempty*/, 1 /*hasself*/, -1 /*donttest*/);
if (!wh) wh = getSuitableWindowHolder(g, groupid, NULL, NULL, 0 /*hidden*/, 0 /*static*/, 1 /*empty*/, -1 /*donttest*/, 1 /*autoavail*/);
if (!wh) wh = getSuitableWindowHolder(g, groupid, NULL, NULL, 1 /*visible*/, 1 /*dynamic*/, 1 /*empty*/, -1 /*donttest*/, -1 /*donttest*/);
ifc_window *whrw = wh ? wh->getRootWndPtr() : NULL;
Container *cont = NULL;
Layout *lay = NULL;
ifc_window *wnd = NULL;
int newcont = 0;
if (!wh)
{ // no hidden static container, so lets create a dynamic one
if (isnew) *isnew = 1;
if (container_flag == 0 && (prefered_container == NULL || !*prefered_container))
{
prefered_container = AutoPopup::getDefaultContainerParams(groupid, g, &container_flag);
}
if (container_flag == 0 && (prefered_container == NULL || !*prefered_container))
{
prefered_container = WASABI_DEFAULT_STDCONTAINER;
}
cont = SkinParser::loadContainerForWindowHolder(groupid, g, 0, transcient, prefered_container, container_flag);
if (cont)
{
cont->setTranscient(transcient);
newcont = 1;
lay = cont->enumLayout(0);
/* if (prefered_layout) { // find its target layout
cont->setDefaultLayout(prefered_layout);
lay = cont->getLayout(prefered_layout);
if (!lay) {
if (!layout_flag) // see if we can fallback
lay = cont->enumLayout(0);
else {
destroyContainer(cont); // deferred
api->console_outputString(9, StringPrintf("could not find the requested layout (%s) to host the window", prefered_container));
return NULL;
}
}*/
}
else
{
DebugStringW(L"no container found to hold the window... not even a default one :/\n");
}
wh = getSuitableWindowHolder(g, groupid, cont, lay, -1 /*donttest*/, -1 /*donttest*/, 0 /*notempty*/, 1 /*hasself*/, -1 /*donttest*/);
if (!wh) wh = getSuitableWindowHolder(g, groupid, cont, lay, -1 /*donttest*/, -1 /*donttest*/, 1 /*empty*/, -1 /*donttest*/, -1 /*donttest*/);
whrw = wh ? wh->getRootWndPtr() : NULL;
}
if (wh)
{
GuiObject *o = static_cast<GuiObject *>(whrw->getInterface(guiObjectGuid));
ASSERT(o != NULL);
if (o)
{
lay = o->guiobject_getParentLayout();
if (lay)
cont = lay->getParentContainer();
}
if ((g != INVALID_GUID && (g == wh->getCurGuid())) || (groupid && (wh->getCurGroupId() == groupid)))
wnd = wh->getCurRootWnd();
else
{
if (wh->getCurRootWnd())
wh->onRemoveWindow();
wnd = wh->onInsertWindow(g, groupid);
}
}
if (!wnd)
{
if (cont)
{
if (!WCSCASEEQLSAFE(cont->getId(), L"main"))
cont->close();
}
return NULL;
}
//int anim = 1;
//if (wh && !whrw->getAnimatedRects()) anim = 0; // FIXME!!
if (lay && r)
{
lay->getWindowRect(&destrect);
}
if (cont /*&& cont->isDynamic()*/)
{
const wchar_t *text = wnd->getRootWndName();
cont->setTranscient(transcient);
if (text != NULL)
if (cont->isDynamic()) cont->setName(text);
if (cont->isDynamic() && !transcient) cont->resetLayouts();
if (newcont) cont->onInit(1);
}
#ifdef WASABI_COMPILE_CONFIG
// {280876CF-48C0-40bc-8E86-73CE6BB462E5}
const GUID options_guid =
{ 0x280876cf, 0x48c0, 0x40bc, { 0x8e, 0x86, 0x73, 0xce, 0x6b, 0xb4, 0x62, 0xe5 } };
CfgItem *cfgitem = WASABI_API_CONFIG->config_getCfgItemByGuid(options_guid);
int findopenrect = _int_getValue(cfgitem, L"Find open rect");
#else
int findopenrect = WASABI_WNDMGR_FINDOPENRECT;
#endif
if (wh && findopenrect)
{
if (lay)
{
RECT rl;
lay->getWindowRect(&rl);
RECT nr = windowTracker->findOpenRect(rl, lay);
destrect = nr; // rewrite destrect
int w = rl.right - rl.left;
int h = rl.bottom - rl.top;
lay->divRatio(&w, &h);
nr.right = nr.left + w;
nr.bottom = nr.top + h;
lay->resizeToRect(&nr);
}
}
if (wh)
{
if (r)
/*if (anim)*/ WASABI_API_WNDMGR->drawAnimatedRects(r, &destrect);
/*else
{
RECT r;
r.left = destrect.left + (destrect.right - destrect.left) / 2 - 1;
r.top = destrect.top + (destrect.bottom - destrect.top) / 2 + 1;
r.right = r.left + 2;
r.bottom = r.top + 2;
if (anim) WASABI_API_WNDMGR->drawAnimatedRects(&r, &destrect);
}*/
}
if (!starthidden)
{
if (cont && cont->isVisible())
{ // we were already shown, duh
// cont->setVisible(0);
}
else
{
if (cont) cont->setVisible(1);
else if (lay) lay->setVisible(1);
}
}
if (wnd && newcont && !transcient)
{
inserted.addItem(new SkinEmbedEntry(wnd->getDependencyPtr(), wnd, g, groupid, prefered_container, container_flag, cont, wh));
viewer_addViewItem(wnd->getDependencyPtr());
}
if (!transcient && wnd)
allofthem.addItem(new SkinEmbedEntry(wnd->getDependencyPtr(), wnd, g, groupid, prefered_container, container_flag, cont, wh));
return wnd;
}
void SkinEmbedder::destroy(ifc_window *w, RECT *r)
{
int donecheck = 0;
SkinEmbedEntry *e = NULL;
for (int i = 0; i < allofthem.getNumItems();i++)
{
e = allofthem.enumItem(i);
if (e->wnd == w)
{
donecheck = 1;
if (SOM::checkAbortShowHideWindow(e->guid, 0))
return ;
break;
}
}
if (WASABI_API_WND->rootwndIsValid(w))
{
if (!donecheck)
{
ifc_window *ww = w->findWindowByInterface(windowHolderGuid);
if (ww)
{
WindowHolder *wh = static_cast<WindowHolder*>(ww->getInterface(windowHolderGuid));
if (wh)
{
GUID g = wh->getCurGuid();
if (g != INVALID_GUID)
{
donecheck = 1;
if (SOM::checkAbortShowHideWindow(g, 0))
return ;
}
}
}
}
}
// checkAbort can render w invalid !!! check again
if (WASABI_API_WND->rootwndIsValid(w))
{
ifc_window *wnd = w->getDesktopParent();
GuiObject *go = static_cast<GuiObject *>(wnd->getInterface(guiObjectGuid));
if (go)
{
Layout *l = go->guiobject_getParentLayout();
if (l)
{
Container *c = l->getParentContainer();
if (c)
{
if (!WCSCASEEQLSAFE(c->getId(), L"main"))
{
c->close(); // deferred if needed
}
else
{
softclose:
ifc_window *wnd = w->findWindowByInterface(windowHolderGuid);
if (wnd != NULL)
{
WindowHolder *wh = static_cast<WindowHolder *>(wnd->getInterface(windowHolderGuid));
if (wh != NULL)
{
wh->onRemoveWindow(1);
}
}
}
}
else goto softclose;
}
}
}
}
int SkinEmbedder::getNumItems(GUID g)
{
int n = 0;
for (int i = 0;i < wndholders.getNumItems();i++)
if (wndholders.enumItem(i)->getRootWndPtr()->isVisible() && wndholders.enumItem(i)->getCurGuid() == g) n++;
return n;
}
int SkinEmbedder::getNumItems(const wchar_t *groupid)
{
int n = 0;
for (int i = 0;i < wndholders.getNumItems();i++)
{
WindowHolder *wh = wndholders.enumItem(i);
if (wh->getRootWndPtr()->isVisible()
&& WCSCASEEQLSAFE(wh->getCurGroupId(), groupid))
n++;
}
return n;
}
ifc_window *SkinEmbedder::enumItem(GUID g, int n)
{
ASSERT(n >= 0);
for (int i = 0;i < wndholders.getNumItems();i++)
{
WindowHolder *wh = wndholders.enumItem(i);
if (wh->getCurGuid() == g)
{
ifc_window *w = wh->getRootWndPtr();
Container *c = NULL;
if (w)
{
w = w->getDesktopParent();
if (w)
{
Layout *l = static_cast<Layout *>(w->getInterface(layoutGuid));
if (l)
{
c = l->getParentContainer();
}
}
}
if (c && c->isVisible() || (!c && wndholders.enumItem(i)->getRootWndPtr()->isVisible()))
{
if (n == 0)
return wndholders.enumItem(i)->getCurRootWnd();
n--;
}
}
}
return NULL;
}
ifc_window *SkinEmbedder::enumItem(const wchar_t *groupid, int n)
{
ASSERT(n >= 0);
for (int i = 0;i < wndholders.getNumItems();i++)
{
WindowHolder *wh = wndholders.enumItem(i);
const wchar_t *curgroupid = wndholders[i]->getCurGroupId();
if (WCSCASEEQLSAFE(curgroupid, groupid))
{
ifc_window *w = wh->getRootWndPtr();
Container *c = NULL;
if (w)
{
w = w->getDesktopParent();
if (w)
{
Layout *l = static_cast<Layout *>(w->getInterface(layoutGuid));
if (l)
{
c = l->getParentContainer();
}
}
}
if (c && c->isVisible() || (!c && wndholders.enumItem(i)->getRootWndPtr()->isVisible()))
{
if (n == 0)
return wndholders.enumItem(i)->getCurRootWnd();
n--;
}
}
}
return NULL;
}
void SkinEmbedder::registerWindowHolder(WindowHolder *wh)
{
if (wndholders.haveItem(wh)) return ;
wndholders.addItem(wh);
}
void SkinEmbedder::unregisterWindowHolder(WindowHolder *wh)
{
if (!wndholders.haveItem(wh)) return ;
wndholders.removeItem(wh);
}
int SkinEmbedder::viewer_onItemDeleted(api_dependent *item)
{
foreach(in_deferred_callback)
if (in_deferred_callback.getfor()->dep == item)
in_deferred_callback.removeByPos(foreach_index);
endfor
foreach(inserted)
SkinEmbedEntry *e = inserted.getfor();
if (e->dep == item)
{
inserted.removeItem(e);
allofthem.removeItem(e);
delete e;
break;
}
endfor;
foreach(allofthem)
SkinEmbedEntry *e = allofthem.getfor();
if (e->dep == item)
{
allofthem.removeItem(e);
delete e;
break;
}
endfor;
return 1;
}
void SkinEmbedder::cancelDestroyContainer(Container *c)
{
if (!cancel_deferred_destroy.haveItem(c)) cancel_deferred_destroy.addItem(c);
}
void SkinEmbedder::destroyContainer(Container *o)
{
ASSERT(o);
//fg>disabled as of 11/4/2003, side effect of cancelling fullscreen video (ie, notifier while playing video fullscreen)
//delt with the problem in basewnd directly
//#ifdef WIN32
//SetFocus(NULL); // FG> this avoids Win32 calling directly WM_KILLFOCUS into a child's wndproc (couldn't they just have posted the damn msg ?), who would then call some of his parent's virtual functions while it is being deleted
// perhaps it would be good to add a generic way to disable most child wnd messages while the parent is being deleted
//#endif
cancel_deferred_destroy.removeItem(o);
foreach(inserted)
SkinEmbedEntry *e = inserted.getfor();
if (e->container == o)
{
if (!in_deferred_callback.haveItem(e))
in_deferred_callback.addItem(e);
break;
}
endfor
deferred_destroy.addItem(o);
timerclient_setTimer(CB_DESTROYCONTAINER, 20);
//o->setVisible(0);
//timerclient_postDeferredCallback(CB_DESTROYCONTAINER, (intptr_t)o);
}
void SkinEmbedder::timerclient_timerCallback(int id)
{
if (id == CB_DESTROYCONTAINER)
{
foreach(deferred_destroy)
Container *c = deferred_destroy.getfor();
foreach(in_deferred_callback)
if (in_deferred_callback.getfor()->container == c)
{
in_deferred_callback.removeByPos(foreach_index);
}
endfor;
if (cancel_deferred_destroy.haveItem(c))
{
continue;
}
if (SkinParser::isContainer(c)) // otherwise i'ts already gone while we were waiting for the callback, duh!
delete c;
endfor
cancel_deferred_destroy.removeAll();
deferred_destroy.removeAll();
timerclient_killTimer(CB_DESTROYCONTAINER);
return ;
}
TimerClientDI::timerclient_timerCallback(id);
}
int SkinEmbedder::timerclient_onDeferredCallback(intptr_t p1, intptr_t p2)
{
return TimerClientDI::timerclient_onDeferredCallback(p1, p2);
}
#ifdef WASABI_COMPILE_CONFIG
void SkinEmbedder::saveState()
{
int i = 0;
wchar_t t[1024] = {0};
foreach(inserted)
SkinEmbedEntry *e = inserted.getfor();
if (e->guid != INVALID_GUID)
{
nsGUID::toCharW(e->guid, t);
}
else
{
WCSCPYN(t, e->groupid, 1024);
}
WASABI_API_CONFIG->setStringPrivate(StringPrintfW(L"wndstatus/id/%d", i), t);
WASABI_API_CONFIG->setStringPrivate(StringPrintfW(L"wndstatus/layout/%d", i), !e->layout.isempty() ? e->layout.getValue() : L"");
WASABI_API_CONFIG->setIntPrivate(StringPrintfW(L"wndstatus/flag/%d", i), e->required);
i++;
endfor;
WASABI_API_CONFIG->setStringPrivate(StringPrintfW(L"wndstatus/id/%d", i), L"");
WASABI_API_CONFIG->setStringPrivate(StringPrintfW(L"wndstatus/layout/%d", i), L"");
WASABI_API_CONFIG->setIntPrivate(StringPrintfW(L"wndstatus/flag/%d", i), 0);
}
void SkinEmbedder::restoreSavedState()
{
int i = 0;
wchar_t t[1024] = {0};
wchar_t l[256] = {0};
while (1)
{
WASABI_API_CONFIG->getStringPrivate(StringPrintfW(L"wndstatus/id/%d", i), t, 1024, L"");
if (!*t) break;
WASABI_API_CONFIG->getStringPrivate(StringPrintfW(L"wndstatus/layout/%d", i), l, 256, L"");
int flag = WASABI_API_CONFIG->getIntPrivate(StringPrintfW(L"wndstatus/flag/%d", i), 0);
GUID g = nsGUID::fromCharW(t);
//ifc_window *created = NULL;
//int tried = 0;
if (g != INVALID_GUID)
{
ifc_window *w = enumItem(g, 0);
if (w == NULL)
{
//tried = 1;
/*created = */create(g, l, flag);
}
}
else
{
ifc_window *w = enumItem(t, 0);
if (w == NULL)
{
//tried = 1;
/*created = */create(t, l, flag);
}
}
/* if (tried && !created) {
for (int j=0;j<inserted.getNumItems();j++) {
SkinEmbedEntry *e = inserted.enumItem(j);
int yes = 0;
if (g != INVALID_GUID) {
if (e->guid == g && e->required == flag && STRCASEEQLSAFE(e->layout, l))
yes = 1;
} else {
if (STRCASEEQLSAFE(e->groupid, t) && e->required == flag && STRCASEEQLSAFE(e->layout, l))
yes = 1;
}
if (yes) {
inserted.removeByPos(j);
j--;
delete e;
}
}
}*/
i++;
}
}
#endif
void SkinEmbedder::attachToSkin(ifc_window *w, int side, int size)
{
RECT r;
if (w == NULL) return ;
ifc_window *_w = w->getDesktopParent();
if (_w == NULL) _w = w;
SkinParser::getSkinRect(&r, _w);
switch (side)
{
case SKINWND_ATTACH_RIGHT:
_w->resize(r.right, r.top, size, r.bottom - r.top);
break;
case SKINWND_ATTACH_TOP:
_w->resize(r.left, r.top - size, r.right - r.left, size);
break;
case SKINWND_ATTACH_LEFT:
_w->resize(r.left - size, r.top, size, r.bottom - r.top);
break;
case SKINWND_ATTACH_BOTTOM:
_w->resize(r.left, r.bottom, r.right - r.left, size);
break;
}
}
PtrList<SkinEmbedEntry> SkinEmbedder::in_deferred_callback;
PtrList<Container> SkinEmbedder::cancel_deferred_destroy;
PtrList<Container> SkinEmbedder::deferred_destroy;

View file

@ -0,0 +1,76 @@
#ifndef __SKIN_EMBEDDER_H
#define __SKIN_EMBEDDER_H
#include <bfc/nsguid.h>
#include <bfc/string/bfcstring.h>
#include <bfc/string/StringW.h>
#include <bfc/ptrlist.h>
#include <bfc/depend.h>
#include <api/timer/timerclient.h>
#define CB_DESTROYCONTAINER 0x887
class ifc_window;
class WindowHolder;
class Container;
class Layout;
class SkinEmbedEntry {
public:
SkinEmbedEntry(api_dependent *d, ifc_window *w, GUID g, const wchar_t *gid, const wchar_t *prefered_container, int container_flag, Container *c, WindowHolder *wh) : groupid(gid), guid(g), dep(d), wnd(w), required(container_flag), layout(prefered_container), container(c), wndholder(wh) { }
virtual ~SkinEmbedEntry() { }
StringW groupid;
GUID guid;
api_dependent *dep;
ifc_window *wnd;
int required;
StringW layout;
Container *container;
WindowHolder *wndholder;
};
class SkinEmbedder : public DependentViewerI, public TimerClientDI {
public:
SkinEmbedder();
virtual ~SkinEmbedder();
int toggle(GUID g, const wchar_t *prefered_container=NULL, int container_flag=0, RECT *r=NULL, int transcient=0);
int toggle(const wchar_t *groupid, const wchar_t *prefered_container=NULL, int container_flag=0, RECT *r=NULL, int transcient=0);
ifc_window *create(GUID g, const wchar_t *prefered_container=NULL, int container_flag=0, RECT *r=NULL, int transcient=0, int starthidden=0, int *isnew=NULL);
ifc_window *create(const wchar_t *groupid, const wchar_t *prefered_container=NULL, int container_flag=0, RECT *r=NULL, int transcient=0, int starthidden=0, int *isnew=NULL);
void destroy(ifc_window *w, RECT *r=NULL);
int getNumItems(GUID g);
int getNumItems(const wchar_t *groupid);
ifc_window *enumItem(GUID g, int n);
ifc_window *enumItem(const wchar_t *groupid, int n);
WindowHolder *getSuitableWindowHolder(GUID g, const wchar_t *group_id, Container *cont, Layout *lay, int visible, int dynamic, int empty, int has_self, int autoavail);
void registerWindowHolder(WindowHolder *w);
void unregisterWindowHolder(WindowHolder *w);
void destroyContainer(Container *o);
virtual int timerclient_onDeferredCallback(intptr_t param1, intptr_t param2);
virtual void timerclient_timerCallback(int id);
#ifdef WASABI_COMPILE_CONFIG
void restoreSavedState();
void saveState();
#endif
void attachToSkin(ifc_window *w, int side, int size);
virtual int viewer_onItemDeleted(api_dependent *item);
static void cancelDestroyContainer(Container *c);
private:
ifc_window *create(GUID g, const wchar_t *groupid, const wchar_t *prefered_container=NULL, int container_flag=0, RECT *r=NULL, int transcient=0, int starthidden=0, int *isnew=NULL);
PtrList<WindowHolder> wndholders;
PtrList<SkinEmbedEntry> inserted;
PtrList<SkinEmbedEntry> allofthem;
static PtrList<SkinEmbedEntry> in_deferred_callback;
static PtrList<Container> cancel_deferred_destroy;
static PtrList<Container> deferred_destroy;
};
extern SkinEmbedder *skinEmbedder;
#endif

View file

@ -0,0 +1,99 @@
#include <precomp.h>
#include "skinwnd.h"
#include <api/wnd/api_window.h>
#include <api/wnd/wndclass/guiobjwnd.h>
#include <api/script/scriptguid.h>
#include <api/script/objects/c_script/c_group.h>
#include <api/script/objects/c_script/c_layout.h>
#include <api/script/objects/c_script/c_container.h>
#include <api/wnd/wndclass/wndholder.h>
SkinWnd::SkinWnd(const wchar_t *group_id, const wchar_t *prefered_container, int container_flag, RECT *animated_rect_source, int transcient, int starthidden)
{
isnew = 0;
wnd = WASABI_API_WNDMGR->skinwnd_createByGroupId(group_id, prefered_container, container_flag, animated_rect_source, transcient, starthidden, &isnew);
notifyMinMaxChanged();
}
SkinWnd::SkinWnd(GUID svc_or_group_guid, const wchar_t *prefered_container, int container_flag, RECT *animated_rect_source, int transcient, int starthidden)
{
isnew = 0;
wnd = WASABI_API_WNDMGR->skinwnd_createByGuid(svc_or_group_guid, prefered_container, container_flag, animated_rect_source, transcient, starthidden, &isnew);
notifyMinMaxChanged();
}
SkinWnd::~SkinWnd()
{}
void SkinWnd::destroy(RECT *animated_rect_dest)
{
if (wnd == NULL) return ;
if (!isnew)
{
ifc_window *w = wnd->findWindowByInterface(windowHolderGuid);
WindowHolder *wh = static_cast<WindowHolder*>(w->getInterface(windowHolderGuid));
if (wh != NULL)
{
wh->onRemoveWindow();
return ;
}
}
WASABI_API_WNDMGR->skinwnd_destroy(wnd, animated_rect_dest);
}
int SkinWnd::runModal(int center)
{
if (wnd == NULL) return 0;
ifc_window *w = wnd->getDesktopParent();
if (center)
{
C_Layout l(getLayout());
l.center();
}
w->setVisible(1);
return w->runModal();
}
void SkinWnd::endModal(int retcode)
{
if (wnd == NULL) return ;
wnd->endModal(retcode);
}
GuiObject *SkinWnd::findObject(const wchar_t *object_id)
{
if (wnd == NULL) return NULL;
GuiObject *obj = NULL;
obj = static_cast<GuiObject *>(wnd->getInterface(guiObjectGuid));
return obj->guiobject_findObject(object_id);
}
ScriptObject *SkinWnd::getContainer()
{
if (wnd == NULL) return NULL;
ifc_window *dw = wnd->getDesktopParent();
if (!dw) return NULL;
ScriptObject *o = static_cast<ScriptObject *>(dw->getInterface(scriptObjectGuid));
if (o != NULL)
{
return C_Layout(o).getContainer();
}
return NULL;
}
ScriptObject *SkinWnd::getLayout()
{
if (wnd == NULL) return NULL;
ifc_window *dw = wnd->getDesktopParent();
if (!dw) return NULL;
ScriptObject *o = static_cast<ScriptObject *>(dw->getInterface(scriptObjectGuid));
return o;
}
void SkinWnd::notifyMinMaxChanged()
{
if (wnd != NULL)
{
wnd->signalMinMaxEnforcerChanged();
}
}

View file

@ -0,0 +1,42 @@
#ifndef __SKINWND_H
#define __SKINWND_H
#include <bfc/common.h>
#include "api.h"
#include <api/script/scriptobj.h>
#define WASABISTDCONTAINER_RESIZABLE_STATUS "resizable_status"
#define WASABISTDCONTAINER_RESIZABLE_NOSTATUS "resizable_nostatus"
#define WASABISTDCONTAINER_STATIC "static"
#define WASABISTDCONTAINER_MODAL "modal"
#define SKINWND_ATTACH_LEFT 1
#define SKINWND_ATTACH_TOP 2
#define SKINWND_ATTACH_RIGHT 3
#define SKINWND_ATTACH_BOTTOM 4
class ifc_window;
class GuiObject;
class SkinWnd
{
public:
SkinWnd(GUID svc_or_group_guid, const wchar_t *prefered_container=NULL, int container_flag=0, RECT *animated_rect_source=NULL, int transcient=0, int starthidden=0);
SkinWnd(const wchar_t *group_id, const wchar_t *prefered_container=NULL, int container_flag=0, RECT *animated_rect_source=NULL, int transcient=0, int starthidden=0);
virtual ~SkinWnd();
void destroy(RECT *animated_rect_dest=NULL);
ifc_window *getWindow() { return wnd; }
ScriptObject *getContainer();
ScriptObject *getLayout();
int runModal(int center=0);
void endModal(int retcode);
GuiObject *findObject(const wchar_t *object_id);
void notifyMinMaxChanged();
int isNewContainer() { return isnew; }
private:
ifc_window *wnd;
int isnew;
};
#endif

View file

@ -0,0 +1,181 @@
#include <precomp.h>
#include "snappnt.h"
#include <api/wndmgr/layout.h>
#include <api/wnd/wndtrack.h>
#include <api/config/items/cfgitem.h>
SnapPoint::SnapPoint(Layout *l, Container *c)
{
points.addItem(this);
setParentLayout(l);
setParentContainer(c);
}
SnapPoint::~SnapPoint()
{
points.removeItem(this);
}
void SnapPoint::removeAll()
{
points.deleteAllSafe();
}
int SnapPoint::setXmlParam(const wchar_t *paramname, const wchar_t *strvalue)
{
if (!WCSICMP(paramname, L"id")) id = strvalue;
else if (!WCSICMP(paramname, L"x")) x = WTOI(strvalue);
else if (!WCSICMP(paramname, L"y")) y = WTOI(strvalue);
else if (!WCSICMP(paramname, L"relatx")) relatx = WTOI(strvalue);
else if (!WCSICMP(paramname, L"relaty")) relaty = WTOI(strvalue);
else return 0;
return 1;
}
void SnapPoint::setParentLayout(Layout *l)
{
playout = l;
}
void SnapPoint::setParentContainer(Container *c)
{
pcontainer = c;
}
Container *SnapPoint::getParentContainer()
{
return pcontainer;
}
Layout *SnapPoint::getParentLayout()
{
return playout;
}
const wchar_t *SnapPoint::getId()
{
return id;
}
int SnapPoint::getX()
{
if (getParentLayout())
return (int)((double)x * getParentLayout()->getRenderRatio());
return x;
}
int SnapPoint::getY()
{
if (getParentLayout())
return (int)((double)y * getParentLayout()->getRenderRatio());
return y;
}
PtrList<SnapPoint> SnapPoint::points;
int SnapPoint::match(ifc_window *master, RECT *z, ifc_window *slave, int flag, int *donex, int *doney, int w, int h)
{
SnapPoint *pmast;
SnapPoint *pslav;
for (int i = 0;i < points.getNumItems();i++)
if (points.enumItem(i)->getParentLayout() == master)
{
pmast = points.enumItem(i);
for (int j = 0;j < points.getNumItems();j++)
if (points.enumItem(j)->getParentLayout() == slave)
{
pslav = points.enumItem(j);
int r = do_match(pmast, pslav, z, flag, donex, doney, w, h);
if (r)
return 1;
}
}
return 0;
}
int SnapPoint::do_match(SnapPoint *pmast, SnapPoint *pslav, RECT *z, int mask, int *donex, int *doney, int w, int h)
{
//#if 0//BU> lone needs to make this work again
//fg> maybe it would have been a good idea to tell me about it... especially since it *works fine*
ASSERT(pmast);
ASSERT(pslav);
int f = 0;
if (((mask & KEEPSIZE) == 0) && !z)
{
ASSERTPR(0, "match resize with no rect");
}
if (!z)
{ // just testing if docked
if (!WCSICMP(pmast->getId(), pslav->getId()))
{
BaseWnd *wm = pmast->getParentLayout();
BaseWnd *ws = pslav->getParentLayout();
if (ws && ws)
{
RECT pmr, psr;
wm->getWindowRect(&pmr);
ws->getWindowRect(&psr);
pmr.left += pmast->relatx ? pmast->getX() : (pmr.right - pmr.left + pmast->getX());
pmr.top += pmast->relaty ? pmast->getY() : (pmr.bottom - pmr.top + pmast->getY());
psr.left += pmast->relatx ? pslav->getX() : (psr.right - psr.left + pslav->getX());
psr.top += pmast->relaty ? pslav->getY() : (psr.bottom - psr.top + pslav->getY());
if (pmr.left == psr.left && pmr.top == psr.top)
{
if (donex) *donex = 1;
if (doney) *doney = 1;
return 1;
}
}
}
}
else
{
ASSERT(donex);
ASSERT(doney);
if (!WCSICMP(pmast->getId(), pslav->getId()))
{
//CUT: BaseWnd *wm = pmast->getParentLayout();
BaseWnd *ws = pslav->getParentLayout();
if (ws && ws)
{
RECT pmr, psr, osr, omr;
pmr = omr = *z;
ws->getWindowRect(&psr);
osr = psr;
pmr.left += pmast->relatx ? pmast->getX() : (pmr.right - pmr.left + pmast->getX());
pmr.top += pmast->relaty ? pmast->getY() : (pmr.bottom - pmr.top + pmast->getY());
psr.left += pmast->relatx ? pslav->getX() : (psr.right - psr.left + pslav->getX());
psr.top += pmast->relaty ? pslav->getY() : (psr.bottom - psr.top + pslav->getY());
if (pmr.left > psr.left - 10 && pmr.left < psr.left + 10 && (mask & LEFT) && ! *donex)
{
*donex = 1;
z->left = omr.left - (pmr.left - psr.left);
if (mask & KEEPSIZE)
z->right = z->left + w;
f++;
}
if (pmr.top > psr.top - 10 && pmr.top < psr.top + 10 && (mask & TOP) && ! *doney)
{
z->top = omr.top - (pmr.top - psr.top);
*doney = 1;
if (mask & KEEPSIZE)
z->bottom = z->top + h;
f++;
}
}
}
return f > 0;
}
return 0;
}

View file

@ -0,0 +1,49 @@
#ifndef __SNAPPOINT_H
#define __SNAPPOINT_H
#include <bfc/ptrlist.h>
#include <bfc/string/StringW.h>
#include <api/skin/xmlobject.h>
#define SNAPPOINT_XMLPARENT XmlObjectI
class Container;
class Layout;
class SnapPoint;
class ifc_window;
class SnapPoint : public SNAPPOINT_XMLPARENT {
public:
SnapPoint(Layout *l, Container *c);
virtual ~SnapPoint();
virtual int setXmlParam(const wchar_t *name, const wchar_t *strvalue);
virtual void setParentContainer(Container *c);
virtual void setParentLayout(Layout *l);
virtual Container *getParentContainer();
virtual Layout *getParentLayout();
virtual const wchar_t *getId();
virtual int getX();
virtual int getY();
static int match(ifc_window *master, RECT *z, ifc_window *slave, int flag, int *donex, int *doney, int w, int h);
static void removeAll();
private:
int x;
int y;
int relatx;
int relaty;
StringW id;
Container *pcontainer;
Layout *playout;
static PtrList<SnapPoint> points;
static int do_match(SnapPoint *pmast, SnapPoint *pslav, RECT *z, int mask, int *donex, int *doney, int w, int h);
};
#endif

View file

@ -0,0 +1,279 @@
#include <precomp.h>
#include "wndmgrapi.h"
#include <api/wndmgr/autopopup.h>
#include <api/wndmgr/skinembed.h>
#include <api/wndmgr/animate.h>
#include <api/wnd/wndtrack.h>
#include <api/skin/skinparse.h>
#include <api/wndmgr/msgbox.h>
#include <api/util/varmgr.h>
wndmgr_api *wndManagerApi = NULL;
WndMgrApi::WndMgrApi()
{
skinEmbedder = new SkinEmbedder();
windowTracker = new WindowTracker();
}
WndMgrApi::~WndMgrApi()
{
delete skinEmbedder;
skinEmbedder = NULL;
delete windowTracker;
windowTracker = NULL;
}
void WndMgrApi::wndTrackAdd(ifc_window *wnd)
{
if (wnd == NULL)
{
DebugString("wndTrackAdd, illegal param : wnd == NULL\n");
return ;
}
windowTracker->addWindow(wnd);
}
void WndMgrApi::wndTrackRemove(ifc_window *wnd)
{
if (wnd == NULL)
{
DebugString("wndTrackAdd, illegal param : wnd == NULL\n");
return ;
}
windowTracker->removeWindow(wnd);
}
bool WndMgrApi::wndTrackDock(ifc_window *wnd, RECT *r, int mask)
{
return windowTracker->autoDock(wnd, r, mask);
}
bool WndMgrApi::wndTrackDock2(ifc_window *wnd, RECT *r, RECT *orig_r, int mask)
{
return windowTracker->autoDock(wnd, r, orig_r, mask);
}
void WndMgrApi::wndTrackStartCooperative(ifc_window *wnd)
{
windowTracker->startCooperativeMove(wnd);
}
void WndMgrApi::wndTrackEndCooperative(void)
{
windowTracker->endCooperativeMove();
}
int WndMgrApi::wndTrackWasCooperative(void)
{
return windowTracker->wasCooperativeMove();
}
void WndMgrApi::wndTrackInvalidateAll()
{
windowTracker->invalidateAllWindows();
}
int WndMgrApi::skinwnd_toggleByGuid(GUID g, const wchar_t *prefered_container, int container_flag, RECT *sourceanimrect, int transcient)
{
return skinEmbedder->toggle(g, prefered_container, container_flag, sourceanimrect, transcient);
}
int WndMgrApi::skinwnd_toggleByGroupId(const wchar_t *groupid, const wchar_t *prefered_container, int container_flag, RECT *sourceanimrect, int transcient)
{
return skinEmbedder->toggle(groupid, prefered_container, container_flag, sourceanimrect, transcient);
}
ifc_window *WndMgrApi::skinwnd_createByGuid(GUID g, const wchar_t *prefered_container, int container_flag, RECT *sourceanimrect, int transcient, int starthidden, int *isnew)
{
return skinEmbedder->create(g, prefered_container, container_flag, sourceanimrect, transcient, starthidden, isnew);
}
ifc_window *WndMgrApi::skinwnd_createByGroupId(const wchar_t *groupid, const wchar_t *prefered_container, int container_flag, RECT *sourceanimrect, int transcient, int starthidden, int *isnew)
{
return skinEmbedder->create(groupid, prefered_container, container_flag, sourceanimrect, transcient, starthidden, isnew);
}
void WndMgrApi::skinwnd_destroy(ifc_window *w, RECT *destanimrect)
{
skinEmbedder->destroy(w, destanimrect);
}
int WndMgrApi::skinwnd_getNumByGuid(GUID g)
{
return skinEmbedder->getNumItems(g);
}
ifc_window *WndMgrApi::skinwnd_enumByGuid(GUID g, int n)
{
return skinEmbedder->enumItem(g, n);
}
int WndMgrApi::skinwnd_getNumByGroupId(const wchar_t *groupid)
{
return skinEmbedder->getNumItems(groupid);
}
ifc_window *WndMgrApi::skinwnd_enumByGroupId(const wchar_t *groupid, int n)
{
return skinEmbedder->enumItem(groupid, n);
}
void WndMgrApi::skinwnd_attachToSkin(ifc_window *w, int side, int size)
{
skinEmbedder->attachToSkin(w, side, size);
}
ScriptObject *WndMgrApi::skin_getContainer(const wchar_t *container_name)
{
Container *c = SkinParser::getContainer(container_name);
if (c != NULL) return c->getScriptObject();
return NULL;
}
ScriptObject *WndMgrApi::skin_getLayout(ScriptObject *container, const wchar_t *layout_name)
{
ASSERT(container != NULL);
Container *c = static_cast<Container *>(container->vcpu_getInterface(containerGuid));
if (c != NULL)
{
Layout *l = c->getLayout(layout_name);
if (l != NULL) return l->getScriptObject();
}
return NULL;
}
void WndMgrApi::wndholder_register(WindowHolder *wh)
{
skinEmbedder->registerWindowHolder(wh);
}
void WndMgrApi::wndholder_unregister(WindowHolder *wh)
{
skinEmbedder->unregisterWindowHolder(wh);
}
int WndMgrApi::messageBox(const wchar_t *txt, const wchar_t *title, int flags, const wchar_t *not_anymore_identifier, ifc_window *parentwnd)
{
#ifdef WASABI_WNDMGR_OSMSGBOX
#ifdef WIN32
int f = 0;
if (flags & MSGBOX_OK) f |= MB_OK;
if (flags & MSGBOX_CANCEL) f |= MB_OKCANCEL;
if (flags & MSGBOX_YES) f |= MB_YESNO;
if ((flags & MSGBOX_YES) && (flags & MSGBOX_CANCEL)) f |= MB_YESNOCANCEL;
int r = MessageBoxW(parentwnd ? parentwnd->gethWnd() : NULL, txt, title, f);
if (r == IDOK) r = MSGBOX_OK;
if (r == IDCANCEL) r = MSGBOX_CANCEL;
if (r == IDYES) r = MSGBOX_YES;
if (r == IDNO) r = MSGBOX_NO;
return r;
#else
// port me!
#endif
#else
MsgBox _mb(txt, title, flags, not_anymore_identifier);
return _mb.run();
#endif
}
void WndMgrApi::drawAnimatedRects(const RECT *r1, const RECT *r2)
{
if (r1 == NULL)
{
DebugString("drawAnimatedRects, illegal param : r1 == NULL\n");
return ;
}
if (r2 == NULL)
{
DebugString("drawAnimatedRects, illegal param : r2 == NULL\n");
return ;
}
AnimatedRects::draw(r1, r2);
}
int WndMgrApi::autopopup_registerGuid(GUID g, const wchar_t *desc, const wchar_t *prefered_container, int container_flag)
{
return AutoPopup::registerGuid(SKINPARTID_NONE, g, desc, prefered_container, container_flag);
}
int WndMgrApi::autopopup_registerGroupId(const wchar_t *groupid, const wchar_t *desc, const wchar_t *prefered_container, int container_flag)
{
return AutoPopup::registerGroupId(SKINPARTID_NONE, groupid, desc, prefered_container, container_flag);
}
void WndMgrApi::autopopup_unregister(int id)
{
AutoPopup::unregister(id);
}
int WndMgrApi::autopopup_getNumGuids()
{
return AutoPopup::getNumGuids();
}
GUID WndMgrApi::autopopup_enumGuid(int n)
{
return AutoPopup::enumGuid(n);
}
int WndMgrApi::autopopup_getNumGroups()
{
return AutoPopup::getNumGroups();
}
const wchar_t *WndMgrApi::autopopup_enumGroup(int n)
{
return AutoPopup::enumGroup(n);
}
const wchar_t *WndMgrApi::autopopup_enumGuidDescription(int n)
{
return AutoPopup::enumGuidDescription(n);
}
const wchar_t *WndMgrApi::autopopup_enumGroupDescription(int n)
{
return AutoPopup::enumGroupDescription(n);
}
const wchar_t *WndMgrApi::varmgr_translate(const wchar_t *str)
{
StringW *s = PublicVarManager::translate_nocontext(str);
if (s)
{
ret.swap(s);
delete s;
return ret.getValueSafe();
}
return str;
}
Stack<ifc_window*> WndMgrApi::modal_wnd_stack;
ifc_window *WndMgrApi::getModalWnd()
{
if (!modal_wnd_stack.peek()) return NULL;
return modal_wnd_stack.top();
}
void WndMgrApi::pushModalWnd(ifc_window *wnd)
{
modal_wnd_stack.push(wnd);
}
void WndMgrApi::popModalWnd(ifc_window *wnd)
{
if (getModalWnd() != wnd) return ;
modal_wnd_stack.pop();
}
Container *WndMgrApi::newDynamicContainer(const wchar_t *name, int transcient)
{
return SkinParser::newDynamicContainer(name, transcient);
}

View file

@ -0,0 +1,59 @@
#ifndef __APIWNDMGR_H
#define __APIWNDMGR_H
#include <api/wndmgr/api_wndmgr.h>
#include <bfc/stack.h>
#include <bfc/string/StringW.h>
class WndMgrApi : public wndmgr_apiI {
public:
WndMgrApi();
virtual ~WndMgrApi();
virtual void wndTrackAdd(ifc_window *wnd);
virtual void wndTrackRemove(ifc_window *wnd);
virtual bool wndTrackDock(ifc_window *wnd, RECT *r, int mask);
virtual bool wndTrackDock2(ifc_window *wnd, RECT *r, RECT *orig_r, int mask);
virtual void wndTrackStartCooperative(ifc_window *wnd);
virtual void wndTrackEndCooperative();
virtual int wndTrackWasCooperative();
virtual void wndTrackInvalidateAll();
virtual int skinwnd_toggleByGuid(GUID g, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0);
virtual int skinwnd_toggleByGroupId(const wchar_t *groupid, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0);
virtual ifc_window *skinwnd_createByGuid(GUID g, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0, int starthidden = 0, int *isnew=NULL);
virtual ifc_window *skinwnd_createByGroupId(const wchar_t *groupid, const wchar_t *prefered_container = NULL, int container_flag = 0, RECT *sourceanimrect = NULL, int transcient = 0, int starthidden = 0, int *isnew=NULL);
virtual void skinwnd_destroy(ifc_window *w, RECT *destanimrect = NULL);
virtual int skinwnd_getNumByGuid(GUID g);
virtual ifc_window *skinwnd_enumByGuid(GUID g, int n);
virtual int skinwnd_getNumByGroupId(const wchar_t *groupid);
virtual ifc_window *skinwnd_enumByGroupId(const wchar_t *groupid, int n);
virtual void skinwnd_attachToSkin(ifc_window *w, int side, int size);
virtual ScriptObject *skin_getContainer(const wchar_t *container_name);
virtual ScriptObject *skin_getLayout(ScriptObject *container, const wchar_t *layout_name);
virtual void wndholder_register(WindowHolder *wh);
virtual void wndholder_unregister(WindowHolder *wh);
virtual int messageBox(const wchar_t *txt, const wchar_t *title, int flags, const wchar_t *not_anymore_identifier, ifc_window *parenwnt);
virtual ifc_window *getModalWnd();
virtual void pushModalWnd(ifc_window *w = MODALWND_NOWND);
virtual void popModalWnd(ifc_window *w = MODALWND_NOWND);
virtual void drawAnimatedRects(const RECT *r1, const RECT *r2);
virtual int autopopup_registerGuid(GUID g, const wchar_t *desc, const wchar_t *prefered_container = NULL, int container_flag = 0);
virtual int autopopup_registerGroupId(const wchar_t *groupid, const wchar_t *desc, const wchar_t *prefered_container = NULL, int container_flag = 0);
virtual void autopopup_unregister(int id);
virtual int autopopup_getNumGuids();
virtual GUID autopopup_enumGuid(int n);
virtual int autopopup_getNumGroups();
virtual const wchar_t *autopopup_enumGroup(int n);
virtual const wchar_t *varmgr_translate(const wchar_t *str);
virtual Container *newDynamicContainer(const wchar_t *name, int transcient);
virtual const wchar_t *autopopup_enumGuidDescription(int n);
virtual const wchar_t *autopopup_enumGroupDescription(int n);
private:
static Stack<ifc_window*> modal_wnd_stack;
StringW ret;
};
#endif // __APIWNDMGR_H