2 * psychlops_g_canvas_Win32_GL.cpp
3 * Psychlops Standard Library (Universal)
5 * Last Modified 2007/07/07 by Kenchi HOSOKAWA
6 * (C) 2006 Kenchi HOSOKAWA, Kazushi MARUYA and Takao SATO
17 #include "../../core/ApplicationInterfaces/psychlops_app_info.h"
18 #include "../../core/devices/psychlops_io_hid.h"
19 #include "../../core/devices/psychlops_io_file.h"
20 #include "../../core/math/psychlops_math.h"
21 #include "../../core/graphic/psychlops_g_fundamental.h"
22 #include "../../core/graphic/psychlops_g_color.h"
23 #include "../../core/graphic/psychlops_g_shape.h"
24 #include "../../core/graphic/psychlops_g_canvas.h"
25 #include "../../core/graphic/psychlops_g_image.h"
27 #define PSYCHLOPS_WINDOW_API_PLATFORM
28 #include "../psychlops_platform_selector.h"
35 void Canvas::cacheImageBody(Image &img) {
36 APIImageCache *api_ = 0;
37 int tex_width = 0, tex_height = 0;
39 if(img.caches.count(this)==0) {
42 while(pow(2.0,++i)<img.width_) {}
43 tex_width = pow(2.0,i);
45 while(pow(2.0,++i)<img.height_) {}
46 tex_height = pow(2.0,i);
48 api_ = img.caches[this].id;
49 tex_width = api_->tex_width;
50 tex_height = api_->tex_height;
53 Image *tmp = new Image(tex_width, tex_height, img.pixcomp_, img.pixprec_);
54 for(int y=0; y<img.height_; y++) Image::line_direct_copy_(img, *tmp, y);
\r
56 if(img.caches.count(this)!=0) {
\r
57 glEnable(GL_TEXTURE_2D);
58 glBindTexture(GL_TEXTURE_2D, api_->VRAMoffset);
59 glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, api_->tex_width, api_->tex_height, APIImageProperties::PixCompGL_[img.pixcomp_], APIImageProperties::PixPrecGL_[img.pixprec_], tmp->getBitmapPtr());
60 glDisable(GL_TEXTURE_2D);
\r
62 api_ = new APIImageCache;
63 img.caches.insert(std::pair<DrawableWithCache*, ImageCache_>(this, ImageCache_(api_, false)));
64 api_->tex_width = tex_width;
65 api_->tex_height = tex_height;
66 glEnable(GL_TEXTURE_2D);
67 glGenTextures(1, &api_->VRAMoffset);
68 glBindTexture(GL_TEXTURE_2D, api_->VRAMoffset);
69 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
70 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
71 // glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
72 // glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
\r
73 GLenum vramFormat = Image::PixCompSize_[img.pixcomp_];
\r
75 if(img.pixprec_==Image::FLOAT) {
\r
76 switch(img.pixcomp_) {
\r
78 vramFormat = GL_R16UI;
\r
81 vramFormat = GL_RGB16UI;
\r
84 vramFormat = GL_RGBA16UI;
\r
89 glTexImage2D(GL_TEXTURE_2D, 0, vramFormat, api_->tex_width, api_->tex_height, 0, APIImageProperties::PixCompGL_[img.pixcomp_], APIImageProperties::PixPrecGL_[img.pixprec_], tmp->getBitmapPtr());
90 glDisable(GL_TEXTURE_2D);
92 // APIImageProperties::regist((int)Display::getWidth(), (int)Display::getHeight(), width_, height_, VRAMleft_, VRAMtop_);
93 // glDisable(GL_BLEND);
94 // glDrawBuffer(GL_AUX1);
95 // for(int y=0; y<height_; y++) {
96 // for(int x=0; x<width_; x++) {
97 // Display::pix(x+VRAMleft_, y+VRAMtop_, getPix(x, y));
100 // glDrawBuffer(GL_BACK);
101 // glEnable(GL_BLEND);
104 glDrawBuffer(GL_AUX1);
105 glColor4f(1.0,1.0,1.0,1.0);
106 glEnable(GL_TEXTURE_2D);
107 glBindTexture(GL_TEXTURE_2D, api_->getTexIndex());
109 glTexCoord2d(0 , img.height_);
110 glVertex2f(img.targetarea_.getLeft() , img.targetarea_.getTop());
111 glTexCoord2d(img.width_ , img.height_);
112 glVertex2f(img.targetarea_.getRight()+1, img.targetarea_.getTop());
113 glTexCoord2d(img.width_ , 0);
114 glVertex2f(img.targetarea_.getRight()+1, img.targetarea_.getBottom()+1);
116 glVertex2f(img.targetarea_.getLeft() , img.targetarea_.getBottom()+1);
118 glDisable(GL_TEXTURE_2D);
119 glDrawBuffer(GL_BACK);
123 void Canvas::uncacheImageBody(Image &img) {
124 APIImageCache *api_ = 0;
125 if(img.caches.count(this)!=0) {
126 api_ = img.caches[this].id;
127 if(api_->VRAMoffset!=0) glDeleteTextures(1, &(api_->VRAMoffset));
128 api_->VRAMoffset = 0;
129 img.caches.erase(this);
134 void Canvas::drawImage(const Image &img, const double left, const double top) {
135 //int left = Math::round(left__);
136 //int top = Math::round(top__);
138 if(img.caches.count(this)!=0) {
139 APIImageCache *api_ = img.caches[this].id;
140 double tex_top = 1.0;
141 double tex_bottom = ((double)api_->tex_height-img.height_)/api_->tex_height;
143 glColor4f(1.0,1.0,1.0,1.0);
144 glEnable(GL_TEXTURE_2D);
145 glBindTexture(GL_TEXTURE_2D, api_->getTexIndex());
147 /* glTexCoord2d(0 , img.height_/img.api->tex_height);
148 glVertex2f(img.targetarea_.getLeft() , img.targetarea_.getTop());
149 glTexCoord2d(img.width_/img.api->tex_width , img.height_/img.api->tex_height);
150 glVertex2f(img.targetarea_.getRight()+1 , img.targetarea_.getTop());
151 glTexCoord2d(img.width_/img.api->tex_width , 0);
152 glVertex2f(img.targetarea_.getRight()+1, img.targetarea_.getBottom()+1);
154 glVertex2f(img.targetarea_.getLeft() , img.targetarea_.getBottom()+1);
156 glTexCoord2d(0, tex_top);
157 glVertex2f(left, top);
158 glTexCoord2d((double)img.width_/api_->tex_width , tex_top);
159 glVertex2f(left+img.targetarea_.getWidth(), top);
160 glTexCoord2d((double)img.width_/api_->tex_width , tex_bottom);
161 glVertex2f(left+img.targetarea_.getWidth(), top+img.targetarea_.getHeight());
162 glTexCoord2d(0 , tex_bottom);
163 glVertex2f(left, top+img.targetarea_.getHeight());
166 glDisable(GL_TEXTURE_2D);
168 glRasterPos2d(left,img.height_+top);
169 if( img.pixcomp_==Image::RGBA ) {
170 glPushAttrib(GL_ALL_ATTRIB_BITS);
172 glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA);
173 glDrawPixels((GLsizei)img.getWidth(), (GLsizei)img.getHeight(), APIImageProperties::PixCompGL_[img.pixcomp_], APIImageProperties::PixPrecGL_[img.pixprec_], img.getBitmapPtr());
177 glDrawPixels((GLsizei)img.getWidth(), (GLsizei)img.getHeight(), APIImageProperties::PixCompGL_[img.pixcomp_], APIImageProperties::PixPrecGL_[img.pixprec_], img.getBitmapPtr());
182 void Canvas::drawImage(Image &img, const Rectangle &target_area)
\r
184 if(img.caches.count(this)==0) {
\r
187 APIImageCache *api_ = img.caches[this].id;
\r
188 double tex_top = 1.0;
\r
189 double tex_bottom = ((double)api_->tex_height-img.height_)/api_->tex_height;
\r
191 glColor4f(1.0,1.0,1.0,1.0);
\r
192 glEnable(GL_TEXTURE_2D);
\r
193 glBindTexture(GL_TEXTURE_2D, api_->getTexIndex());
\r
195 glTexCoord2d(0, tex_top);
\r
196 glVertex2f(target_area.left, target_area.top);
\r
197 glTexCoord2d((double)img.width_/api_->tex_width , tex_top);
\r
198 glVertex2f(target_area.right, target_area.top);
\r
199 glTexCoord2d((double)img.width_/api_->tex_width , tex_bottom);
\r
200 glVertex2f(target_area.right, target_area.bottom);
\r
201 glTexCoord2d(0 , tex_bottom);
\r
202 glVertex2f(target_area.left, target_area.bottom);
\r
205 glDisable(GL_TEXTURE_2D);
\r
208 Canvas& Canvas::image(Image &img, const Rectangle &target_area, const Rectangle &source_rect)
\r
210 if(img.caches.count(this)==0) {
\r
213 APIImageCache *api_ = img.caches[this].id;
\r
214 // double right = left + source_rect.getWidth();
\r
215 // double bottom = top + source_rect.getHeight();
\r
216 double tex_top = 1.0;
\r
217 double tex_bottom = ((double)api_->tex_height-img.height_)/api_->tex_height;
\r
218 double tex_left = 0.0;
\r
219 double tex_right = (double)img.width_/api_->tex_width;
\r
220 double tex_height = tex_top - tex_bottom;
\r
221 double tex_width = tex_right - tex_left;
\r
222 tex_left = tex_width * source_rect.getLeft() / (img.getWidth()-1.0);
\r
223 tex_top = 1.0 - tex_height * source_rect.getTop() / (img.getHeight()-1.0);
\r
224 tex_right = tex_width * source_rect.getRight() / (img.getWidth()-1.0);
\r
225 tex_bottom = 1.0 - tex_height * source_rect.getBottom() / (img.getHeight()-1.0);
\r
226 //std::cout << "D " << tex_left << " " << tex_top << " " << tex_right << " " << tex_bottom << std::endl;
\r
228 glColor4f(1.0,1.0,1.0,1.0);
\r
229 glEnable(GL_TEXTURE_2D);
\r
230 glBindTexture(GL_TEXTURE_2D, api_->getTexIndex());
\r
233 glTexCoord2d(tex_left, tex_top);
\r
234 // glVertex2f(left, top);
\r
235 glVertex2f(target_area.left, target_area.top);
\r
237 glTexCoord2d(tex_right, tex_top);
\r
238 // glVertex2f(right, top);
\r
239 glVertex2f(target_area.right+1, target_area.top);
\r
241 glTexCoord2d(tex_right , tex_bottom);
\r
242 // glVertex2f(right, bottom);
\r
243 glVertex2f(target_area.right+1, target_area.bottom+1);
\r
245 glTexCoord2d(tex_left , tex_bottom);
\r
246 // glVertex2f(left, bottom);
\r
247 glVertex2f(target_area.left, target_area.bottom+1);
\r
251 glDisable(GL_TEXTURE_2D);
\r
256 int Canvas::msg(Letters &letters, const double x, const double y, const Color &col, const int horiz_align, const int vertical_align, const double max_width) {
257 /* double x_begin_shift;
258 switch(horiz_align) {
259 case Letters::TEXT_ALIGN_RIGHT:
260 x_begin_shift = -letters.width_;
262 case Letters::TEXT_ALIGN_CENTER:
263 x_begin_shift = -letters.width_/2;
265 case Letters::TEXT_ALIGN_LEFT:
270 api->drawLetters(letters, x+x_begin_shift, y, col.Red, col.Green, col.Blue, col.Alpha, horiz_align, vertical_align, max_width);
\r
272 api->draw(letters, x, y, col.Red, col.Green, col.Blue, col.Alpha, horiz_align, vertical_align, max_width);
\r
277 } /* <- namespace Psycholops */