Skip to content

Commit

Permalink
Merge pull request #1664 from GillesDuvert/exact_plot_positioning_in_…
Browse files Browse the repository at this point in the history
…all_cases

Exact plot positioning in all cases
  • Loading branch information
GillesDuvert authored Nov 12, 2023
2 parents eaecbdc + bd58fae commit f3fdb3d
Show file tree
Hide file tree
Showing 22 changed files with 1,189 additions and 987 deletions.
17 changes: 16 additions & 1 deletion src/basic_pro.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2355,7 +2355,12 @@ static DWORD launch_cmd(BOOL hide, BOOL nowait,
SizeT nParam = e->NParam(1);
if (nParam == 1) return;
DDoubleGDL* p0 = e->GetParAs<DDoubleGDL>(0);


static int GDL_DOW = e->KeywordIx("GDL_DOW");
bool hasDow = e->WriteableKeywordPresent(GDL_DOW); //insure the output variable exist and is of 'good' type
static int GDL_ICAP = e->KeywordIx("GDL_ICAP");
bool hasIcap = e->WriteableKeywordPresent(GDL_ICAP); //insure the output variable exist and is of 'good' type

// checking output (if present and global); exiting if nothing to do
bool global[6];
{
Expand All @@ -2374,6 +2379,11 @@ static DWORD launch_cmd(BOOL hide, BOOL nowait,
BaseGDL*** ret;
ret = (BaseGDL***) malloc((nParam - 1) * sizeof (BaseGDL**));
GDLGuard<BaseGDL**, void, void> retGuard(ret, free);

DLongGDL* retdow;
DLongGDL* reticap;
if (hasDow) retdow=new DLongGDL(dimension(nEl));
if (hasIcap) reticap=new DLongGDL(dimension(nEl));

for (int i = nParam - 2; i >= 0; i--) {
if (global[i]) {
Expand Down Expand Up @@ -2416,7 +2426,12 @@ static DWORD launch_cmd(BOOL hide, BOOL nowait,

// seconds
if (global[6 - 1]) (*static_cast<DDoubleGDL*> (*ret[6 - 1]))[i] = Second;

if (hasDow) (*retdow)[i]= dow;
if (hasIcap) (*reticap)[i]= icap;
}
if (hasDow) e->SetKW(GDL_DOW,retdow);
if (hasIcap) e->SetKW(GDL_ICAP,reticap);
// now guarded. s. a.
// free((void *)ret);
}
Expand Down
2 changes: 1 addition & 1 deletion src/calendar.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ using namespace std;
F = JD - Z;
// note that IDL dow is false before Sun dec 31 12:00:00 -4714, (type: a=[-2,-1]& PRINT, FORMAT='(C())',a)
// ...and ... we are not!
if ((DLong)Z > 0) dow = ((DLong)Z) % 7; else dow = ((DLong)Z+1099) % 7; //just translate axis...
if ((DLong)Z+1 > 0) dow = ((DLong)Z+1) % 7; else dow = ((DLong)Z+1099) % 7; //just translate axis...

if (Z < 2299161) A = (DLong)Z;
else {
Expand Down
2 changes: 1 addition & 1 deletion src/deviceps.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -138,11 +138,11 @@ class DevicePS: public GraphicsDevice
actStream->plstream::wind(0, 1, 0, 1);

actStream->ssub(1, 1);
actStream->adv(0); //this is for us (counters)
float fudge=17780./float(XPageSize*scale*PS_RESOL)*12700./float(YPageSize*scale*PS_RESOL);
fudge=1.46*sqrt(fudge); //best value (experimental) to get same results as IDL with varying CHARSIZE
actStream->SetPageDPMM(fudge);
actStream->DefaultCharSize();
actStream->adv(0); //this is for us (counters) //needs DefaultCharSize
// clear();
}

Expand Down
2 changes: 1 addition & 1 deletion src/devicesvg.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -76,9 +76,9 @@ class DeviceSVG : public GraphicsDevice
actStream->plstream::wind(0, 1, 0, 1);

actStream->ssub(1, 1);
actStream->adv(0); //this is for us (counters)
actStream->SetPageDPMM();
actStream->DefaultCharSize();
actStream->adv(0); //this is for us (counters) //needs DefaultCharSize
}

public:
Expand Down
2 changes: 1 addition & 1 deletion src/devicez.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -111,9 +111,9 @@ class DeviceZ: public GraphicsDevice
actStream->plstream::wind(0, 1, 0, 1);

actStream->ssub(1, 1);
actStream->adv(0); //this is for us (counters)
actStream->SetPageDPMM();
actStream->DefaultCharSize();
actStream->adv(0); //this is for us (counters) //needs DefaultCharSize
}

public:
Expand Down
99 changes: 70 additions & 29 deletions src/gdlgstream.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,9 @@
#include "graphicsdevice.hpp"
#include "gdlgstream.hpp"
#include "initsysvar.hpp"
#ifndef MAX
#define MAX(a,b) ((a) < (b) ? (b) : (a))
#endif

using namespace std;

Expand Down Expand Up @@ -380,8 +383,9 @@ void GDLGStream::SetCharSize(DLong ichx, DLong chy) {
gdlDefaultCharInitialized=1;
}

void GDLGStream::NextPlot( bool erase )
{
void GDLGStream::NextPlot( bool erase ) {
// restore charsize to default for newpage at beginning since adv() uses charsize to get box position.
if (!erase) sizeChar(1.0);
DLongGDL* pMulti = SysVar::GetPMulti();

DLong nx = (*pMulti)[ 1];
Expand Down Expand Up @@ -446,8 +450,7 @@ void GDLGStream::NextPlot( bool erase )
--(*pMulti)[0];
}
}
// restore charsize to default for newpage
sizeChar(1.0);

}

void GDLGStream::NoSub()
Expand Down Expand Up @@ -505,7 +508,7 @@ void GDLGStream::GetGeometry( long& xSize, long& ySize)
// - ... a look-up table instead of the long switch/case blocks ...

size_t len = strlen(in);
if (stringLength) *stringLength=0;
if (stringLength!=NULL) *stringLength=0;
// skip conversion if the string is empty
if (len == 0) return "";

Expand Down Expand Up @@ -694,12 +697,12 @@ void GDLGStream::GetGeometry( long& xSize, long& ySize)
}
else
{
if (stringLength) *stringLength+=base*fact[curr_lev%7];
if (stringLength!=NULL) *stringLength+=base*fact[curr_lev%7];
curr_pos++;
// handling IDL exclamation mark escape '!!'
if (in[i] == '!') {
i++;
if (stringLength) *stringLength+=base*fact[curr_lev%7];
if (stringLength!=NULL) *stringLength+=base*fact[curr_lev%7];
}
// handling plplot number sign escape '##'
if
Expand Down Expand Up @@ -1029,12 +1032,12 @@ void GDLGStream::GetGeometry( long& xSize, long& ySize)
activeFontCodeNum = curr_fnt;
//if gdlGetStringLength function is available, use it to give back a better value ("X" and "I" do not have the same width in hershey format!)
#if PLPLOT_PRIVATE_NOT_HIDDEN
if (stringLength) *stringLength=gdlGetStringLength(out)/this->mmCharLength();
if (stringLength!=NULL) *stringLength=gdlGetStringLength(out)/this->mmCharLength();
#endif
return out;
retrn:
activeFontCodeNum = curr_fnt;
if (stringLength) *stringLength=0;
if (stringLength!=NULL) *stringLength=0;
cout << "ERROR: GDLGStream::TranslateFormatCodes(\"" << in << "\") = \"" << out << "\"" << endl;
return "";
}
Expand All @@ -1052,7 +1055,7 @@ void GDLGStream::setLineSpacing(PLFLT newSpacing)
}
PLFLT GDLGStream::getSymbolSize(){return theCurrentSymSize;}
void GDLGStream::mtex( const char *side, PLFLT disp, PLFLT posit, PLFLT just,
const char *text)
const char *text, double *stringCharLength, double *stringCharHeight)
{
//plot does not handle !C
size_t len = strlen(text);
Expand All @@ -1061,15 +1064,17 @@ void GDLGStream::mtex( const char *side, PLFLT disp, PLFLT posit, PLFLT just,
simple=false;
}
if (simple) {
plstream::mtex(side,disp,posit,just,TranslateFormatCodes(text).c_str());
plstream::mtex(side,disp,posit,just,TranslateFormatCodes(text,stringCharLength).c_str());
if (stringCharHeight!=NULL) *stringCharHeight = 1;
return;
}
//complicated:
if (stringCharHeight != NULL) *stringCharHeight = 0;
double d=0;
std::string s(text);
std::string newline="!C";
long pos = 0, oldpos=0;
PLFLT ydisp=(1.0+nLineSpacing()/nCharHeight());
size_t pos = 0, oldpos=0;
PLFLT yadd=nLineSpacing()/nCharHeight();
std::vector<long> positions;
while (pos != string::npos) {
pos = s.find(newline, oldpos);
Expand All @@ -1081,11 +1086,19 @@ void GDLGStream::mtex( const char *side, PLFLT disp, PLFLT posit, PLFLT just,
for (std::vector<long>::iterator it = positions.begin(); it != positions.end();) {
oldpos=(*it++);
pos=(*(it++));
long l=pos-oldpos;
size_t l=pos-oldpos;
if (l<0) l=string::npos;
// std::cerr<<pos<<":"<<l<<" "<<s.substr(oldpos,l)<<std::endl;
plstream::mtex(side,disp,posit,just,TranslateFormatCodes(s.substr(oldpos,l).c_str()).c_str());
disp+=ydisp;
plstream::mtex(side,disp,posit,just,TranslateFormatCodes(s.substr(oldpos,l).c_str(),&d).c_str());
if (strstr(side,"b")!=NULL) { //bottom increments 1 line
disp += yadd;
} else if (strstr(side,"t")!=NULL) {//top decrements 1 line
disp -= yadd;
} else {//left decrements position in Y : change posit not disp unless parallel
if (strstr(side,"v")!=NULL) posit-=nLineSpacing()/boxnYSize() ; else disp -= yadd;
}
if (stringCharLength!=NULL) *stringCharLength = std::max<double>(*stringCharLength, d);
if (stringCharHeight!=NULL) *stringCharHeight += 1;
}
}

Expand All @@ -1106,8 +1119,8 @@ void GDLGStream::ptex( PLFLT x, PLFLT y, PLFLT dx, PLFLT dy, PLFLT just,
double d=0;
std::string s(text);
std::string newline="!C";
long pos = 0, oldpos=0;
PLFLT ydisp=(1.0+nLineSpacing()/nCharHeight())*wCharHeight();
size_t pos = 0, oldpos=0;
PLFLT ydisp=(nLineSpacing()/nCharHeight())*wCharHeight();
std::vector<long> positions;
while (pos != string::npos) {
pos = s.find(newline, oldpos);
Expand All @@ -1119,7 +1132,7 @@ void GDLGStream::ptex( PLFLT x, PLFLT y, PLFLT dx, PLFLT dy, PLFLT just,
for (std::vector<long>::iterator it = positions.begin(); it != positions.end();) {
oldpos=(*it++);
pos=(*(it++));
long l=pos-oldpos;
size_t l=pos-oldpos;
if (l<0) l=string::npos;
// std::cerr<<pos<<":"<<l<<" "<<s.substr(oldpos,l)<<std::endl;
plstream::ptex(x,y,dx,dy,just,TranslateFormatCodes(s.substr(oldpos,l).c_str(),&d).c_str()) ;
Expand Down Expand Up @@ -1326,7 +1339,7 @@ void GDLGStream::adv(PLINT page)
if (thePage.curPage > thePage.nbPages) thePage.curPage=1;
if (GDL_DEBUG_PLSTREAM) fprintf(stderr,"adv() now at page %d\n",thePage.curPage);
PLFLT sxmin,symin,sxmax,symax,szmin,szmax;
getSubpageRegion(sxmin,symin,sxmax,symax,&szmin,&szmax);
getSubpageRegion(&sxmin,&symin,&sxmax,&symax,&szmin,&szmax);
//SET ALL REGION TAGS
unsigned regionTag=SysVar::X()->Desc()->TagIndex("REGION");
(*static_cast<DFloatGDL*>(SysVar::X()->GetTag(regionTag, 0)))[0]=sxmin;
Expand All @@ -1339,19 +1352,47 @@ void GDLGStream::adv(PLINT page)
(*static_cast<DFloatGDL*>(SysVar::Z()->GetTag(regionTag, 0)))[1]=szmax;
}

void GDLGStream::getSubpageRegion(PLFLT &sxmin, PLFLT &symin, PLFLT &sxmax, PLFLT &symax, PLFLT *szmin, PLFLT *szmax){
void GDLGStream::getSubpageRegion(PLFLT *sxmin, PLFLT *symin, PLFLT *sxmax, PLFLT *symax, PLFLT *szmin, PLFLT *szmax) {
//here we must take into account the contents of ![X|Y|Z].OMARGIN
unsigned int omarginTag = SysVar::X()->Desc()->TagIndex("OMARGIN");
DFloat xstart = (*static_cast<DFloatGDL*> (SysVar::X()->GetTag(omarginTag, 0)))[0];
xstart=MAX(xstart,0);
DFloat xend = (*static_cast<DFloatGDL*> (SysVar::X()->GetTag(omarginTag, 0)))[1];
xend=MAX(xend,0);
omarginTag = SysVar::Y()->Desc()->TagIndex("OMARGIN");
DFloat ystart = (*static_cast<DFloatGDL*> (SysVar::Y()->GetTag(omarginTag, 0)))[0];
ystart=MAX(ystart,0);
DFloat yend = (*static_cast<DFloatGDL*> (SysVar::Y()->GetTag(omarginTag, 0)))[1];
yend=MAX(yend,0);
// Z OMARGIN to BE CHECKED and code must be written.
// omarginTag = SysVar::Z()->Desc()->TagIndex("OMARGIN");
// DFloat zstart = (*static_cast<DFloatGDL*> (SysVar::Z()->GetTag(omarginTag, 0)))[0];
// DFloat zend = (*static_cast<DFloatGDL*> (SysVar::Z()->GetTag(omarginTag, 0)))[1];
DFloat xNormedPageSize=1-(xend+xstart)*theCurrentChar.ndsx;
DFloat yNormedPageSize=1-(yend+ystart)*theCurrentChar.nspacing;
if (xNormedPageSize < 0 || xNormedPageSize > 1 || yNormedPageSize < 0 || yNormedPageSize > 1) {
Message("Data coordinate system not established.");
if (xNormedPageSize < 0) xNormedPageSize=0;
if (yNormedPageSize < 0) yNormedPageSize=0;
if (xNormedPageSize > 1) xNormedPageSize=1;
if (yNormedPageSize > 1) yNormedPageSize=1;
}
DFloat zNormedPageSize=1; //zend-zstart??;
DFloat xNormedOffset=xstart*theCurrentChar.ndsx;
DFloat yNormedOffset=yend*theCurrentChar.nspacing;
//check silly values: normed must be >0 and < 1
int p=thePage.curPage-1;
PLFLT width=1.0/thePage.nx;
PLFLT height=1.0/thePage.ny;
PLFLT profund=1.0/thePage.nz;
PLFLT width=xNormedPageSize/thePage.nx;
PLFLT height=yNormedPageSize/thePage.ny;
PLFLT profund=zNormedPageSize/thePage.nz;
int k= p / (thePage.nx*thePage.ny);
int l= p - k*(thePage.nx*thePage.ny);
int j= l /thePage.nx ;
int i= (l - j*thePage.nx);
sxmin=i*width;
sxmax=sxmin+width;
symax=1-(j*height);
symin=symax-height;
int i= (l - j*thePage.nx);
*sxmin=i*width+xNormedOffset;
*sxmax=*sxmin+width;
*symax=1-(j*height+yNormedOffset);
*symin=*symax-height;
if (szmin != NULL) {
*szmin=k*profund;
*szmax=*szmin+profund;
Expand Down
6 changes: 2 additions & 4 deletions src/gdlgstream.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -625,9 +625,7 @@ class GDLGStream: public plstream
void setLineSpacing( PLFLT spacing );
PLFLT getSymbolSize();
void mtex( const char *side, PLFLT disp, PLFLT pos, PLFLT just,
const char *text);
void mtex3( const char *side, PLFLT disp, PLFLT pos, PLFLT just,
const char *text);
const char *text, double *stringCharLength=NULL, double *stringCharHeight=NULL);
void ptex( PLFLT x, PLFLT y, PLFLT dx, PLFLT dy, PLFLT just,
const char *text, double *stringCharLength=NULL );
void setVariableCharacterSize( PLFLT charwidthpixel, PLFLT scale, PLFLT lineSpacingpixel, PLFLT xpxcm, PLFLT ypxcm);
Expand All @@ -641,7 +639,7 @@ class GDLGStream: public plstream
void wind( PLFLT xmin, PLFLT xmax, bool xLog, PLFLT ymin, PLFLT ymax, bool yLog );
void ssub( PLINT nx, PLINT ny, PLINT nz=1);
void adv(PLINT page);
void getSubpageRegion(PLFLT &sxmin, PLFLT &symin, PLFLT &sxmax, PLFLT &symax, PLFLT *zmin=NULL, PLFLT *zmax=NULL);
void getSubpageRegion(PLFLT *sxmin, PLFLT *symin, PLFLT *sxmax, PLFLT *symax, PLFLT *zmin=NULL, PLFLT *zmax=NULL);
void SetPageDPMM(float setPsCharFudge=1.0, float setPsSymFudge=1.0);
void syncPageInfo();
void updateBoxDeviceCoords();
Expand Down
2 changes: 1 addition & 1 deletion src/gdlwxstream.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -93,9 +93,9 @@ GDLWXStream::GDLWXStream( int width, int height )
plstream::wind(0,1,0,1);

ssub(1,1);
adv(0); //this is for us (counters)
SetPageDPMM();
DefaultCharSize();
adv(0); //this is for us (counters) //needs DefaultCharSize
clear();
}

Expand Down
2 changes: 1 addition & 1 deletion src/gdlxstream.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -74,9 +74,9 @@ class GDLXStream: public GDLGStream
plstream::wind(0, 1, 0, 1);

ssub(1, 1);
adv(0); //this is for us (counters)
SetPageDPMM();
DefaultCharSize();
adv(0); //this is for us (counters) //needs DefaultCharSize
clear();
}

Expand Down
3 changes: 2 additions & 1 deletion src/libinit.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -982,7 +982,8 @@ void LibInit()

new DLibFunRetNew(lib::t_pdf,string("T_PDF"),2);

new DLibPro(lib::caldat, string("CALDAT"), 7);
const string caldatKey[]={"GDL_DOW","GDL_ICAP",KLISTEND};
new DLibPro(lib::caldat, string("CALDAT"), 7, caldatKey);
new DLibFunRetNew(lib::julday, string("JULDAY"), 6);

// SA: the HYBRID key is used in imsl_zerosys.pro to switch to the modif. brent algo.
Expand Down
Loading

0 comments on commit f3fdb3d

Please sign in to comment.