1848b8605Smrg/* 2848b8605Smrg * Mesa 3-D graphics library 3848b8605Smrg * 4848b8605Smrg * Copyright (C) 1999-2006 Brian Paul All Rights Reserved. 5848b8605Smrg * 6848b8605Smrg * Permission is hereby granted, free of charge, to any person obtaining a 7848b8605Smrg * copy of this software and associated documentation files (the "Software"), 8848b8605Smrg * to deal in the Software without restriction, including without limitation 9848b8605Smrg * the rights to use, copy, modify, merge, publish, distribute, sublicense, 10848b8605Smrg * and/or sell copies of the Software, and to permit persons to whom the 11848b8605Smrg * Software is furnished to do so, subject to the following conditions: 12848b8605Smrg * 13848b8605Smrg * The above copyright notice and this permission notice shall be included 14848b8605Smrg * in all copies or substantial portions of the Software. 15848b8605Smrg * 16848b8605Smrg * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 17848b8605Smrg * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18848b8605Smrg * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 19848b8605Smrg * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR 20848b8605Smrg * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 21848b8605Smrg * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 22848b8605Smrg * OTHER DEALINGS IN THE SOFTWARE. 23848b8605Smrg */ 24848b8605Smrg 25848b8605Smrg 26848b8605Smrg#include "glheader.h" 27848b8605Smrg#include "context.h" 28848b8605Smrg#include "lines.h" 29848b8605Smrg#include "macros.h" 30848b8605Smrg#include "mtypes.h" 31848b8605Smrg 32848b8605Smrg 33848b8605Smrg/** 34848b8605Smrg * Set the line width. 35848b8605Smrg * 36848b8605Smrg * \param width line width in pixels. 37848b8605Smrg * 38848b8605Smrg * \sa glLineWidth(). 39848b8605Smrg */ 40b8e80941Smrgstatic ALWAYS_INLINE void 41b8e80941Smrgline_width(struct gl_context *ctx, GLfloat width, bool no_error) 42848b8605Smrg{ 43b8e80941Smrg /* If width is unchanged, there can't be an error */ 44b8e80941Smrg if (ctx->Line.Width == width) 45b8e80941Smrg return; 46848b8605Smrg 47b8e80941Smrg if (!no_error && width <= 0.0F) { 48848b8605Smrg _mesa_error( ctx, GL_INVALID_VALUE, "glLineWidth" ); 49848b8605Smrg return; 50848b8605Smrg } 51848b8605Smrg 52848b8605Smrg /* Page 407 (page 423 of the PDF) of the OpenGL 3.0 spec says (in the list 53848b8605Smrg * of deprecated functionality): 54848b8605Smrg * 55848b8605Smrg * "Wide lines and line stipple - LineWidth is not deprecated, but 56848b8605Smrg * values greater than 1.0 will generate an INVALID_VALUE error;" 57848b8605Smrg * 58848b8605Smrg * This is one of the very few cases where functionality was deprecated but 59848b8605Smrg * *NOT* removed in a later spec. Therefore, we only disallow this in a 60848b8605Smrg * forward compatible context. 61848b8605Smrg */ 62b8e80941Smrg if (!no_error && ctx->API == API_OPENGL_CORE 63848b8605Smrg && ((ctx->Const.ContextFlags & GL_CONTEXT_FLAG_FORWARD_COMPATIBLE_BIT) 64848b8605Smrg != 0) 65b8e80941Smrg && width > 1.0F) { 66848b8605Smrg _mesa_error( ctx, GL_INVALID_VALUE, "glLineWidth" ); 67848b8605Smrg return; 68848b8605Smrg } 69848b8605Smrg 70b8e80941Smrg FLUSH_VERTICES(ctx, ctx->DriverFlags.NewLineState ? 0 : _NEW_LINE); 71b8e80941Smrg ctx->NewDriverState |= ctx->DriverFlags.NewLineState; 72848b8605Smrg ctx->Line.Width = width; 73848b8605Smrg 74848b8605Smrg if (ctx->Driver.LineWidth) 75848b8605Smrg ctx->Driver.LineWidth(ctx, width); 76848b8605Smrg} 77848b8605Smrg 78848b8605Smrg 79b8e80941Smrgvoid GLAPIENTRY 80b8e80941Smrg_mesa_LineWidth_no_error(GLfloat width) 81b8e80941Smrg{ 82b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 83b8e80941Smrg line_width(ctx, width, true); 84b8e80941Smrg} 85b8e80941Smrg 86b8e80941Smrg 87b8e80941Smrgvoid GLAPIENTRY 88b8e80941Smrg_mesa_LineWidth(GLfloat width) 89b8e80941Smrg{ 90b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 91b8e80941Smrg 92b8e80941Smrg if (MESA_VERBOSE & VERBOSE_API) 93b8e80941Smrg _mesa_debug(ctx, "glLineWidth %f\n", width); 94b8e80941Smrg 95b8e80941Smrg line_width(ctx, width, false); 96b8e80941Smrg} 97b8e80941Smrg 98b8e80941Smrg 99848b8605Smrg/** 100848b8605Smrg * Set the line stipple pattern. 101848b8605Smrg * 102848b8605Smrg * \param factor pattern scale factor. 103848b8605Smrg * \param pattern bit pattern. 104848b8605Smrg * 105848b8605Smrg * \sa glLineStipple(). 106848b8605Smrg * 107848b8605Smrg * Updates gl_line_attrib::StippleFactor and gl_line_attrib::StipplePattern. On 108848b8605Smrg * change flushes the vertices and notifies the driver via 109848b8605Smrg * the dd_function_table::LineStipple callback. 110848b8605Smrg */ 111848b8605Smrgvoid GLAPIENTRY 112848b8605Smrg_mesa_LineStipple( GLint factor, GLushort pattern ) 113848b8605Smrg{ 114848b8605Smrg GET_CURRENT_CONTEXT(ctx); 115848b8605Smrg 116848b8605Smrg if (MESA_VERBOSE & VERBOSE_API) 117848b8605Smrg _mesa_debug(ctx, "glLineStipple %d %u\n", factor, pattern); 118848b8605Smrg 119848b8605Smrg factor = CLAMP( factor, 1, 256 ); 120848b8605Smrg 121848b8605Smrg if (ctx->Line.StippleFactor == factor && 122848b8605Smrg ctx->Line.StipplePattern == pattern) 123848b8605Smrg return; 124848b8605Smrg 125b8e80941Smrg FLUSH_VERTICES(ctx, ctx->DriverFlags.NewLineState ? 0 : _NEW_LINE); 126b8e80941Smrg ctx->NewDriverState |= ctx->DriverFlags.NewLineState; 127848b8605Smrg ctx->Line.StippleFactor = factor; 128848b8605Smrg ctx->Line.StipplePattern = pattern; 129848b8605Smrg 130848b8605Smrg if (ctx->Driver.LineStipple) 131848b8605Smrg ctx->Driver.LineStipple( ctx, factor, pattern ); 132848b8605Smrg} 133848b8605Smrg 134848b8605Smrg 135848b8605Smrg/** 136848b8605Smrg * Initialize the context line state. 137848b8605Smrg * 138848b8605Smrg * \param ctx GL context. 139848b8605Smrg * 140848b8605Smrg * Initializes __struct gl_contextRec::Line and line related constants in 141848b8605Smrg * __struct gl_contextRec::Const. 142848b8605Smrg */ 143b8e80941Smrgvoid 144848b8605Smrg_mesa_init_line( struct gl_context * ctx ) 145848b8605Smrg{ 146848b8605Smrg ctx->Line.SmoothFlag = GL_FALSE; 147848b8605Smrg ctx->Line.StippleFlag = GL_FALSE; 148848b8605Smrg ctx->Line.Width = 1.0; 149848b8605Smrg ctx->Line.StipplePattern = 0xffff; 150848b8605Smrg ctx->Line.StippleFactor = 1; 151848b8605Smrg} 152