/*----------------------------------------------------------------------------*\ | Copyright (C) 2009 - Rafael de O. Lopes Gonçalves and André Shoji Asato | | This program is free software; you can redistribute it and/or | | modify it under the terms of the GNU General Public License | | as published by the Free Software Foundation; either version 3 | | of the License. | | | | This program is distributed in the hope that it will be useful, | | but WITHOUT ANY WARRANTY; without even the implied warranty of | | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | | GNU General Public License for more details. | | | | You should have received a copy of the GNU General Public License | | along with this program; if not, write to the Free Software | | Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.| \*----------------------------------------------------------------------------*/ #include #include #include "visocor.h" static const int LAST_FILTER = N_FILTER_VARIATIONS - 1; static const int FIRST_FILTER = 0; static const int FILTER_STEP = 1; static void recalculateColorFilter(CompScreen * s) { VISOCOR_SCREEN(s); int middle; middle = (LAST_FILTER + FIRST_FILTER) / 2; if (vs->filterIntensity > middle) { vs->ir = ((float) vs->filterIntensity - middle) / (LAST_FILTER - middle); vs->ig = 0; } else { vs->ig = ((float) middle - vs->filterIntensity) / (middle - FIRST_FILTER); vs->ir = 0; } vs->ib = 1.0 - vs->ig - vs->ir; visocorPrintf(CompLogLevelDebug, "ir = %f\tig = %f\tib = %f", vs->ir, vs->ig, vs->ib); } void visocorResetFilter(VISOCORScreen * vs) { int middle; middle = (LAST_FILTER + FIRST_FILTER) / 2; vs->filterIntensity = middle; vs->ig = 0; vs->ir = 0; vs->ib = 1; } Bool visocorToggleFilter(CompDisplay * d, CompAction * action, CompActionState state, CompOption * option, int nOption) { CompWindow *w; w = visocorFindWindow(d, option, nOption); if (w) { VISOCOR_WINDOW(w); if (vw->currentState != FILTER) { visocorToggleWindowToState(w, FILTER); } else { visocorToggleWindowToState(w, vw->lastState); } } return TRUE; } Bool visocorDecreaseFilter(CompDisplay * d, CompAction * action, CompActionState state, CompOption * option, int nOption) { int value; CompScreen *s; s = visocorFindScreen(d, option, nOption); if (s) { VISOCOR_SCREEN(s); value = MAX(FIRST_FILTER, vs->filterIntensity - FILTER_STEP); vs->filterIntensity = value; recalculateColorFilter(s); visocorDamageAllWindows(s); return TRUE; } return FALSE; } Bool visocorIncreaseFilter(CompDisplay * d, CompAction * action, CompActionState state, CompOption * option, int nOption) { CompScreen *s; int value; s = visocorFindScreen(d, option, nOption); if (s) { VISOCOR_SCREEN(s); value = MIN(LAST_FILTER, vs->filterIntensity + FILTER_STEP); vs->filterIntensity = value; recalculateColorFilter(s); visocorDamageAllWindows(s); return TRUE; } return FALSE; } int getVisocorFilterFragmentFunction(CompScreen * s, CompTexture * texture, int param) { VISOCOR_SCREEN(s); if (vs->visocorFunctions[FILTER][param] == 0) { CompFunctionData *data; int target; char filter_operation[1024]; Bool ok = TRUE; visocorPrintf(CompLogLevelDebug, "criando um FILTER com a variavel %d", param); if (texture->target == GL_TEXTURE_2D) target = COMP_FETCH_TARGET_2D; else target = COMP_FETCH_TARGET_RECT; data = createFunctionData(); if (data) { ok &= addTempHeaderOpToFunctionData(data, "tex"); ok &= addTempHeaderOpToFunctionData(data, "temp"); ok &= addFetchOpToFunctionData(data, "tex", NULL, target); char * format = "DP3 temp.r, tex, {1 , 0 , 0 , 0};\n" "DP3 temp.g, tex, {0 , 1 , 0 , 0};\n" "DP3 temp.b, tex, program.env[%d].xyzw;\n" "MOV temp.a, tex.a;"; sprintf(filter_operation, format, param); } ok &= addDataOpToFunctionData(data, filter_operation); ok &= addColorOpToFunctionData(data, "output", "temp"); if (!ok) { destroyFunctionData(data); return 0; } vs->visocorFunctions[FILTER][param] = createFragmentFunction(s, "visocor", data); ; } (*s->programEnvParameter4f)(GL_FRAGMENT_PROGRAM_ARB, param, vs->ir, vs->ig, vs->ib, 1.0f); return vs->visocorFunctions[FILTER][param]; }