Fixing our multiple report pixel transfer.
Implementing support for off screen mode which is now the default.
On screen mode is there for debug pruposes.
     1.1 --- a/inc/FutabaVfd.h	Thu May 22 16:46:50 2014 +0200
     1.2 +++ b/inc/FutabaVfd.h	Thu May 22 21:32:45 2014 +0200
     1.3 @@ -30,7 +30,6 @@
     1.4  const unsigned short KFutabaProductIdGP1212A01A = 0x100C;
     1.5  const unsigned short KFutabaProductIdGP1212A02A = 0x1013; //Or is it 0x1015
     1.6  
     1.7 -
     1.8  //typedef struct hid_device_info HidDeviceInfo;
     1.9  
    1.10  /**
    1.11 @@ -44,7 +43,6 @@
    1.12  	};
    1.13  
    1.14  
    1.15 -
    1.16  /**
    1.17  Define a generic Futaba VFD command.
    1.18  */
    1.19 @@ -73,8 +71,8 @@
    1.20  class FutabaVfd : public HidDevice
    1.21  	{
    1.22  public:
    1.23 -	virtual int MinBrightness()=0;
    1.24 -	virtual int MaxBrightness()=0;
    1.25 +	virtual int MinBrightness() const=0;
    1.26 +	virtual int MaxBrightness() const=0;
    1.27  	virtual void SetBrightness(int aBrightness)=0;
    1.28  	virtual void Clear()=0;
    1.29  	};
    1.30 @@ -85,10 +83,11 @@
    1.31  class FutabaGraphicVfd : public FutabaVfd
    1.32  	{
    1.33  public:
    1.34 -	virtual int WidthInPixels()=0;
    1.35 -	virtual int HeightInPixels()=0;
    1.36 -	virtual void SetPixel(int aX, int aY, bool aOn)=0;
    1.37 -	virtual void SetAllPixels(bool aOn)=0;
    1.38 +	virtual int WidthInPixels() const=0;
    1.39 +	virtual int HeightInPixels() const=0;
    1.40 +	virtual void SetPixel(unsigned char aX, unsigned char aY, bool aOn)=0;
    1.41 +	virtual void SetAllPixels(unsigned char aOn)=0;
    1.42 +	virtual int FrameBufferSizeInBytes() const=0;
    1.43  	};
    1.44  
    1.45  /**
    1.46 @@ -98,8 +97,8 @@
    1.47  	{
    1.48  public:
    1.49  	//From FutabaVfd
    1.50 -	virtual int MinBrightness(){return 0;};
    1.51 -	virtual int MaxBrightness(){return 5;};
    1.52 +	virtual int MinBrightness() const {return 0;};
    1.53 +	virtual int MaxBrightness() const {return 5;};
    1.54  	};
    1.55  
    1.56  /**
    1.57 @@ -110,26 +109,33 @@
    1.58  class GP1212A01A : public GP1212XXXX
    1.59  	{
    1.60  public:
    1.61 +	GP1212A01A();
    1.62 +	//
    1.63  	int Open();
    1.64  	//From FutabaGraphicVfd
    1.65 -	virtual int WidthInPixels(){return 256;};
    1.66 -	virtual int HeightInPixels(){return 64;};
    1.67 -	virtual void SetPixel(int aX, int aY, bool aOn);
    1.68 -	virtual void SetAllPixels(bool aOn);
    1.69 +	virtual int WidthInPixels() const {return 256;};
    1.70 +	virtual int HeightInPixels() const {return 64;};
    1.71 +	virtual void SetPixel(unsigned char aX, unsigned char aY, bool aOn);
    1.72 +	virtual void SetAllPixels(unsigned char aPattern);
    1.73 +	virtual int FrameBufferSizeInBytes() const {return 2048;}; //256*64/8
    1.74  	//From FutabaVfd
    1.75  	virtual void SetBrightness(int aBrightness);
    1.76  	virtual void Clear();
    1.77  
    1.78  	//Specific to GP1212A01A
    1.79 -	void SetPixelBlock(int aX, int aY, int aHeight, int aSize, unsigned char aValue);
    1.80 -    void SetPixelBlock(int aX, int aY, int aHeight, int aSize, unsigned char* aPixels);
    1.81 +	void SetPixelBlock(unsigned char aX, unsigned char aY, int aHeight, int aSize, unsigned char aValue);
    1.82 +    void SetPixelBlock(unsigned char aX, unsigned char aY, int aHeight, int aSize, unsigned char* aPixels);
    1.83      //
    1.84 -	void SetDisplayPosition(int aX, int aY);
    1.85 +	void SetDisplayPosition(unsigned char aX, unsigned char aY);
    1.86 +	void SwapBuffers();
    1.87      //
    1.88      void RequestId();
    1.89      void RequestFirmwareRevision();
    1.90      void RequestPowerSupplyStatus();
    1.91 -
    1.92 +	//
    1.93 +	void ToggleOffScreenMode();
    1.94 +	bool OffScreenMode() const {return iOffScreenMode;};
    1.95 +	
    1.96  private:
    1.97  	enum DW
    1.98  		{
    1.99 @@ -137,13 +143,21 @@
   1.100          DW2=0xD0
   1.101  		};
   1.102  
   1.103 -	void SetDisplayPosition(DW aDw,int aX, int aY);
   1.104 +	void SetDisplayPosition(DW aDw,unsigned char aX, unsigned char aY);
   1.105 +	unsigned char OffScreenY() const;
   1.106 +	void SendClearCommand();
   1.107 +	void OffScreenTranslation(unsigned char& aX, unsigned char& aY);
   1.108  
   1.109  private:
   1.110 +	unsigned char iDisplayPositionX;
   1.111 +	unsigned char iDisplayPositionY;
   1.112 +	///Off screen mode is the recommended default settings to avoid tearing.
   1.113 +	///Though turning it off can be useful for debugging
   1.114 +	bool iOffScreenMode;
   1.115  	///
   1.116  	//FutabaVfdReport iReport;
   1.117  	///
   1.118 -	unsigned char iPixelBuffer[256][128];
   1.119 +	//unsigned char iPixelBuffer[256][128];
   1.120  	};
   1.121  
   1.122  
     2.1 --- a/inc/MainWindow.h	Thu May 22 16:46:50 2014 +0200
     2.2 +++ b/inc/MainWindow.h	Thu May 22 21:32:45 2014 +0200
     2.3 @@ -41,6 +41,7 @@
     2.4          ID_FUTABA_RESET_PIXEL,
     2.5          ID_FUTABA_SET_ALL_PIXELS,
     2.6          ID_FUTABA_SET_DISPLAY_POSITION,
     2.7 +		ID_FUTABA_TOGGLE_OFF_SCREEN_MODE,
     2.8          ID_SELECT_FONT,
     2.9          ID_LAST
    2.10      };
    2.11 @@ -73,6 +74,7 @@
    2.12      long onFutabaSetPixel(FXObject *sender, FXSelector sel, void *ptr);
    2.13      long onFutabaResetPixel(FXObject *sender, FXSelector sel, void *ptr);
    2.14      long onFutabaSetDisplayPosition(FXObject *sender, FXSelector sel, void *ptr);
    2.15 +	long onFutabaToggleOffScreenMode(FXObject *sender, FXSelector sel, void *ptr);
    2.16      //
    2.17      long onSelectFont(FXObject *sender, FXSelector sel, void *ptr);
    2.18      //
    2.19 @@ -112,6 +114,7 @@
    2.20      FXButton *iButtonResetPixel;
    2.21      FXButton *iButtonSetAllPixels;
    2.22      FXButton *iButtonSetDisplayPosition;
    2.23 +	FXButton *iButtonToggleOffScreenMode;
    2.24      //Font
    2.25      FXButton *iButtonSelectFont;
    2.26  
     3.1 --- a/src/FutabaVfd.cpp	Thu May 22 16:46:50 2014 +0200
     3.2 +++ b/src/FutabaVfd.cpp	Thu May 22 21:32:45 2014 +0200
     3.3 @@ -71,53 +71,50 @@
     3.4  // class GP1212A01A
     3.5  //
     3.6  
     3.7 +GP1212A01A::GP1212A01A():iDisplayPositionX(0),iDisplayPositionY(0),iOffScreenMode(true)
     3.8 +	{
     3.9 +	}
    3.10 +
    3.11  int GP1212A01A::Open()
    3.12  	{
    3.13  	int success = HidDevice::Open(KFutabaVendorId,KFutabaProductIdGP1212A01A,NULL);
    3.14  	if (success)
    3.15  		{
    3.16  		SetNonBlocking(1);
    3.17 +		//Since we can't get our display position we for it to our default
    3.18 +		//This makes sure frames are in sync from the start
    3.19 +		SetDisplayPosition(iDisplayPositionX,iDisplayPositionY);
    3.20  		}
    3.21  	return success;
    3.22  	}
    3.23  
    3.24  /**
    3.25  */
    3.26 -void GP1212A01A::SetPixel(int aX, int aY, bool aOn)
    3.27 +void GP1212A01A::SetPixel(unsigned char aX, unsigned char aY, bool aOn)
    3.28  	{
    3.29  	//Just specify a one pixel block
    3.30  	SetPixelBlock(aX,aY,0x00,0x01,aOn);
    3.31  	}
    3.32  
    3.33  /**
    3.34 +Set all pixels on our screen to the desired value.
    3.35 +This operation is performed off screen to avoid tearing.
    3.36 +@param 8 pixels pattern
    3.37  */
    3.38 -void GP1212A01A::SetAllPixels(bool aOn)
    3.39 +void GP1212A01A::SetAllPixels(unsigned char aPattern)
    3.40  	{
    3.41 -	//One pixel at a time
    3.42 -	/*
    3.43 -	for (int i=0;i<256;i++)
    3.44 -		{
    3.45 -		for (int j=0;j<64;j++)
    3.46 -			{
    3.47 -			SetPixel(i,j,0x01);
    3.48 -			}
    3.49 -		}
    3.50 -	*/
    3.51 +	//With a single buffer
    3.52 +	//unsigned char screen[2048]; //One screen worth of pixels
    3.53 +	//memset(screen,0xFF,sizeof(screen));
    3.54 +	//SetPixelBlock(0,0,63,sizeof(screen),screen);
    3.55  
    3.56 -	//16x16=256 pixels at a time goes much faster
    3.57 -	//TODO: use even larger blocks
    3.58 -	for (int i=0;i<256;i+=16)
    3.59 -		{
    3.60 -		for (int j=0;j<64;j+=16)
    3.61 -			{
    3.62 -			SetPixelBlock(i,j,15,32,(aOn?0xFF:0x00));
    3.63 -			//FXThread::sleep(1000000000);
    3.64 -			}
    3.65 -		}
    3.66 -
    3.67 +	//Using pattern SetPixelBlock variant.
    3.68 +	SetPixelBlock(0,0,63,FrameBufferSizeInBytes(),aPattern);
    3.69  	}
    3.70  
    3.71  /**
    3.72 +Set our screen brightness.
    3.73 +@param The desired brightness level. Must be between MinBrightness and MaxBrightness.
    3.74  */
    3.75  void GP1212A01A::SetBrightness(int aBrightness)
    3.76      {
    3.77 @@ -149,23 +146,36 @@
    3.78  @param The size of our pixel data. Number of pixels divided by 8.
    3.79  @param The value set to 8 pixels used as a pattern.
    3.80  */
    3.81 -void GP1212A01A::SetPixelBlock(int aX, int aY, int aHeight, int aSize, unsigned char aValue)
    3.82 +void GP1212A01A::SetPixelBlock(unsigned char aX, unsigned char aY, int aHeight, int aSize, unsigned char aValue)
    3.83  	{
    3.84 -	//Size must be 63 or below
    3.85 -	FutabaVfdReport report;
    3.86 -	report[0]=0x00; //Report ID
    3.87 -	report[1]=0x08+aSize; //Report length
    3.88 -	report[2]=0x1B; //
    3.89 -	report[3]=0x5B; //
    3.90 -	report[4]=0xF0; //
    3.91 -	report[5]=aX; //X
    3.92 -	report[6]=aY; //Y
    3.93 -	report[7]=aHeight; //Y length before return. Though outside the specs, setting this to zero apparently allows us to modify a single pixel without touching any other.
    3.94 -	report[8]=0x00; //Size of pixel data in bytes (MSB)
    3.95 -	report[9]=aSize; //Size of pixel data in bytes (LSB)
    3.96 -	memset(report.Buffer()+10, aValue, aSize);
    3.97 -	//iOutputReportBuffer[10]=aValue; //Pixel data
    3.98 -	Write(report);
    3.99 +	OffScreenTranslation(aX,aY);
   3.100 +    FutabaVfdReport report;
   3.101 +    report[0]=0x00; //Report ID
   3.102 +    report[1]=(aSize<=report.Size()-10?aSize+0x08:64); //Report length. -10 is for our header first 10 bytes. +8 is for our Futaba header size
   3.103 +    report[2]=0x1B; //Command ID
   3.104 +    report[3]=0x5B; //Command ID
   3.105 +    report[4]=0xF0; //Command ID
   3.106 +    report[5]=aX;   //X
   3.107 +    report[6]=aY;   //Y
   3.108 +    report[7]=aHeight; //Y length before return. Though outside the specs, setting this to zero apparently allows us to modify a single pixel without touching any other.
   3.109 +	report[8]=aSize>>8; //Size of pixel data in bytes (MSB)
   3.110 +	report[9]=aSize;	//Size of pixel data in bytes (LSB)
   3.111 +    int sizeWritten=MIN(aSize,report.Size()-10);
   3.112 +    memset(report.Buffer()+10, aValue, sizeWritten);
   3.113 +    Write(report);
   3.114 +
   3.115 +    int remainingSize=aSize;
   3.116 +    //We need to keep on sending our pixel data until we are done
   3.117 +    while (report[1]==64)
   3.118 +        {
   3.119 +        report.Reset();
   3.120 +        remainingSize-=sizeWritten;
   3.121 +        report[0]=0x00; //Report ID
   3.122 +        report[1]=(remainingSize<=report.Size()-2?remainingSize:64); //Report length, should be 64 or the remaining size
   3.123 +        sizeWritten=(report[1]==64?63:report[1]);
   3.124 +        memset(report.Buffer()+2, aValue, sizeWritten);
   3.125 +        Write(report);
   3.126 +        }
   3.127  	}
   3.128  
   3.129  /**
   3.130 @@ -176,19 +186,20 @@
   3.131  @param The size of our pixel data. Number of pixels divided by 8.
   3.132  @param Pointer to our pixel data.
   3.133  */
   3.134 -void GP1212A01A::SetPixelBlock(int aX, int aY, int aHeight, int aSize, unsigned char* aPixels)
   3.135 +void GP1212A01A::SetPixelBlock(unsigned char aX, unsigned char aY, int aHeight, int aSize, unsigned char* aPixels)
   3.136      {
   3.137 +	OffScreenTranslation(aX,aY);
   3.138      FutabaVfdReport report;
   3.139      report[0]=0x00; //Report ID
   3.140 -    report[1]=0x08+(aSize<=report.Size()-10?aSize:64); //Report length. -10 is for our header first 10 bytes
   3.141 +    report[1]=(aSize<=report.Size()-10?aSize+0x08:64); //Report length. -10 is for our header first 10 bytes. +8 is for our Futaba header size
   3.142      report[2]=0x1B; //Command ID
   3.143      report[3]=0x5B; //Command ID
   3.144      report[4]=0xF0; //Command ID
   3.145      report[5]=aX;   //X
   3.146      report[6]=aY;   //Y
   3.147      report[7]=aHeight; //Y length before return. Though outside the specs, setting this to zero apparently allows us to modify a single pixel without touching any other.
   3.148 -    unsigned short* sizePtr=(unsigned short*)report.Buffer()+8; //Size of pixel data in bytes (MSB)
   3.149 -    *sizePtr=aSize; //Put our size over 2 bytes
   3.150 +	report[8]=aSize>>8; //Size of pixel data in bytes (MSB)
   3.151 +	report[9]=aSize;	//Size of pixel data in bytes (LSB)
   3.152      int sizeWritten=MIN(aSize,report.Size()-10);
   3.153      memcpy(report.Buffer()+10, aPixels, sizeWritten);
   3.154      Write(report);
   3.155 @@ -200,7 +211,7 @@
   3.156          report.Reset();
   3.157          remainingSize-=sizeWritten;
   3.158          report[0]=0x00; //Report ID
   3.159 -        report[1]=(remainingSize<=report.Size()-2?aSize:64); //Report length, should be 64 or the remaining size
   3.160 +        report[1]=(remainingSize<=report.Size()-2?remainingSize:64); //Report length, should be 64 or the remaining size
   3.161          sizeWritten=(report[1]==64?63:report[1]);
   3.162          memcpy(report.Buffer()+2, aPixels+(aSize-remainingSize), sizeWritten);
   3.163          Write(report);
   3.164 @@ -210,9 +221,21 @@
   3.165  
   3.166  /**
   3.167  Clear our display's screen.
   3.168 +This operation is performed off screen to avoid tearing.
   3.169  */
   3.170  void GP1212A01A::Clear()
   3.171  	{
   3.172 +	//Using pattern SetPixelBlock variant.
   3.173 +	//First fill our off screen buffer with the desired values
   3.174 +	SetPixelBlock(0,0,63,FrameBufferSizeInBytes(),(unsigned char)0x00);
   3.175 +	}
   3.176 +
   3.177 +/**
   3.178 +Using this function is advised against as is causes tearing.
   3.179 +Use Clear instead.
   3.180 +*/
   3.181 +void GP1212A01A::SendClearCommand()
   3.182 +	{
   3.183      //1BH,5BH,32H,4AH
   3.184      //Send Clear Display Command
   3.185  	FutabaVfdReport report;
   3.186 @@ -228,7 +251,7 @@
   3.187  /**
   3.188  Change our display position within our buffer.
   3.189  */
   3.190 -void GP1212A01A::SetDisplayPosition(DW aDw,int aX, int aY)
   3.191 +void GP1212A01A::SetDisplayPosition(DW aDw,unsigned char aX, unsigned char aY)
   3.192      {
   3.193      //1BH,5BH,Dw,Px,Py
   3.194      //Send Display Position Settings Command
   3.195 @@ -246,12 +269,48 @@
   3.196  /**
   3.197  Change our display position within our buffer.
   3.198  */
   3.199 -void GP1212A01A::SetDisplayPosition(int aX, int aY)
   3.200 +void GP1212A01A::SetDisplayPosition(unsigned char aX, unsigned char aY)
   3.201  	{
   3.202  	//Specs apparently says both DW should remain the same
   3.203  	//Just don't ask
   3.204      SetDisplayPosition(GP1212A01A::DW1,aX,aY);
   3.205      SetDisplayPosition(GP1212A01A::DW2,aX,aY);
   3.206 +	iDisplayPositionX=aX;
   3.207 +	iDisplayPositionY=aY;
   3.208 +	}
   3.209 +
   3.210 +/**
   3.211 +Provide Y coordinate of our off screen buffer.
   3.212 +*/
   3.213 +unsigned char GP1212A01A::OffScreenY() const
   3.214 +	{
   3.215 +	//Overflowing is fine this is just what we want
   3.216 +	return iDisplayPositionY+HeightInPixels();
   3.217 +	}
   3.218 +
   3.219 +/**
   3.220 +Put our off screen buffer on screen.
   3.221 +On screen buffer goes off screen.
   3.222 +*/
   3.223 +void GP1212A01A::SwapBuffers()
   3.224 +	{
   3.225 +	//Only perform buffer swapping if off screen mode is enabled
   3.226 +	if (OffScreenMode())
   3.227 +		{
   3.228 +		SetDisplayPosition(iDisplayPositionX,OffScreenY());
   3.229 +		}
   3.230 +	}
   3.231 +
   3.232 +/**
   3.233 +Translate the given pixel coordinate according to our off screen mode.
   3.234 +*/
   3.235 +void GP1212A01A::OffScreenTranslation(unsigned char& aX, unsigned char& aY)
   3.236 +	{
   3.237 +	if (OffScreenMode())
   3.238 +		{
   3.239 +		aX+=WidthInPixels()-iDisplayPositionX;
   3.240 +		aY+=HeightInPixels()-iDisplayPositionY;
   3.241 +		}
   3.242  	}
   3.243  /**
   3.244  */
   3.245 @@ -302,4 +361,19 @@
   3.246      report[5]=0x50; //Command ID
   3.247      report[6]=0x4D; //Command ID
   3.248      Write(report);
   3.249 -    }
   3.250 \ No newline at end of file
   3.251 +    }
   3.252 +
   3.253 +
   3.254 +/**
   3.255 +This is for development purposes only.
   3.256 +Production application should stick to off-screen mode to avoid tearing.
   3.257 +*/
   3.258 +void GP1212A01A::ToggleOffScreenMode()
   3.259 +	{
   3.260 +	iOffScreenMode=!iOffScreenMode;
   3.261 +	//Clean up our buffers upon switching modes	
   3.262 +	SetDisplayPosition(0,0);
   3.263 +	Clear();
   3.264 +	SwapBuffers();
   3.265 +	Clear();
   3.266 +	}
   3.267 \ No newline at end of file
     4.1 --- a/src/test.cpp	Thu May 22 16:46:50 2014 +0200
     4.2 +++ b/src/test.cpp	Thu May 22 21:32:45 2014 +0200
     4.3 @@ -44,6 +44,7 @@
     4.4  	FXMAPFUNC(SEL_COMMAND, MainWindow::ID_FUTABA_RESET_PIXEL, MainWindow::onFutabaResetPixel ),
     4.5      FXMAPFUNC(SEL_COMMAND, MainWindow::ID_FUTABA_SET_ALL_PIXELS, MainWindow::onFutabaSetAllPixels ),
     4.6  	FXMAPFUNC(SEL_COMMAND, MainWindow::ID_FUTABA_SET_DISPLAY_POSITION, MainWindow::onFutabaSetDisplayPosition ),
     4.7 +	FXMAPFUNC(SEL_COMMAND, MainWindow::ID_FUTABA_TOGGLE_OFF_SCREEN_MODE, MainWindow::onFutabaToggleOffScreenMode ),	
     4.8      FXMAPFUNC(SEL_COMMAND, MainWindow::ID_SELECT_FONT, MainWindow::onSelectFont ),
     4.9  	FXMAPFUNC(SEL_TIMEOUT, MainWindow::ID_TIMER, MainWindow::onTimeout ),
    4.10  	FXMAPFUNC(SEL_TIMEOUT, MainWindow::ID_MAC_TIMER, MainWindow::onMacTimeout ),
    4.11 @@ -122,6 +123,7 @@
    4.12      //
    4.13      iButtonSetAllPixels = new FXButton(matrix, "Set All Pixels", NULL, this, ID_FUTABA_SET_ALL_PIXELS, BUTTON_NORMAL|LAYOUT_FILL_X);
    4.14      iButtonSetDisplayPosition = new FXButton(matrix, "Set Display Position", NULL, this, ID_FUTABA_SET_DISPLAY_POSITION, BUTTON_NORMAL|LAYOUT_FILL_X);
    4.15 +	iButtonToggleOffScreenMode = new FXButton(matrix, "Switch to on-screen", NULL, this, ID_FUTABA_TOGGLE_OFF_SCREEN_MODE, BUTTON_NORMAL|LAYOUT_FILL_X);
    4.16      //
    4.17  
    4.18  	// Output Group Box
    4.19 @@ -292,6 +294,7 @@
    4.20              iButtonResetPixel->enable();
    4.21              iButtonSetAllPixels->enable();
    4.22              iButtonSetDisplayPosition->enable();
    4.23 +			iButtonToggleOffScreenMode->enable();
    4.24              }
    4.25          }
    4.26      else
    4.27 @@ -318,6 +321,7 @@
    4.28          iButtonResetPixel->disable();
    4.29          iButtonSetAllPixels->disable();
    4.30          iButtonSetDisplayPosition->disable();
    4.31 +		iButtonToggleOffScreenMode->disable();
    4.32          //
    4.33          }
    4.34  
    4.35 @@ -545,6 +549,7 @@
    4.36  MainWindow::onFutabaClearDisplay(FXObject *sender, FXSelector sel, void *ptr)
    4.37  {
    4.38      iVfd01.Clear();
    4.39 +	iVfd01.SwapBuffers();
    4.40  	return 1;
    4.41  }
    4.42  
    4.43 @@ -589,6 +594,7 @@
    4.44  	iTextFieldY->getText().scan("%d",&y);
    4.45      //SetPixel(x,y,0x01);
    4.46      iVfd01.SetPixel(x,y,true);
    4.47 +	iVfd01.SwapBuffers();
    4.48  	return 1;
    4.49  }
    4.50  
    4.51 @@ -602,12 +608,14 @@
    4.52  	iTextFieldY->getText().scan("%d",&y);
    4.53      //SetPixel(x,y,0x00);
    4.54      iVfd01.SetPixel(x,y,false);
    4.55 +	iVfd01.SwapBuffers();
    4.56      return 1;
    4.57  }
    4.58  
    4.59  long MainWindow::onFutabaSetAllPixels(FXObject *sender, FXSelector sel, void *ptr)
    4.60  	{
    4.61 -    iVfd01.SetAllPixels(true);
    4.62 +    iVfd01.SetAllPixels(0xFF);
    4.63 +	iVfd01.SwapBuffers();
    4.64      return 1;
    4.65  	}
    4.66  
    4.67 @@ -626,6 +634,26 @@
    4.68      }
    4.69  
    4.70  
    4.71 +/**
    4.72 +
    4.73 +*/
    4.74 +long MainWindow::onFutabaToggleOffScreenMode(FXObject *sender, FXSelector sel, void *ptr)
    4.75 +    {
    4.76 +    iVfd01.ToggleOffScreenMode();
    4.77 +	if (iVfd01.OffScreenMode())
    4.78 +		{
    4.79 +		iButtonToggleOffScreenMode->setText("Switch to on-screen");
    4.80 +		}
    4.81 +	else
    4.82 +		{
    4.83 +		iButtonToggleOffScreenMode->setText("Switch to off-screen");
    4.84 +		}
    4.85 +    return 1;
    4.86 +    }
    4.87 +
    4.88 +
    4.89 +
    4.90 +
    4.91  long
    4.92  MainWindow::onFutabaReadId(FXObject *sender, FXSelector sel, void *ptr)
    4.93  {