📄 screen_saver.c
字号:
//*****************************************************************************
//
// screen_saver.c - A screen saver for the OSRAM OLED display.
//
// Copyright (c) 2006-2007 Luminary Micro, Inc. All rights reserved.
//
// Software License Agreement
//
// Luminary Micro, Inc. (LMI) is supplying this software for use solely and
// exclusively on LMI's microcontroller products.
//
// The software is owned by LMI and/or its suppliers, and is protected under
// applicable copyright laws. All rights are reserved. You may not combine
// this software with "viral" open-source software in order to form a larger
// program. Any use in violation of the foregoing restrictions may subject
// the user to criminal sanctions under applicable laws, as well as to civil
// liability for the breach of the terms and conditions of this license.
//
// THIS SOFTWARE IS PROVIDED "AS IS". NO WARRANTIES, WHETHER EXPRESS, IMPLIED
// OR STATUTORY, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF
// MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE.
// LMI SHALL NOT, IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL, OR
// CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
//
// This is part of revision 1952 of the Stellaris Peripheral Driver Library.
//
//*****************************************************************************
#include "../../../hw_memmap.h"
#include "../../../hw_types.h"
#include "../../../src/gpio.h"
#include "../../../src/pwm.h"
#include "../../../src/sysctl.h"
#include "../rit128x96x4.h"
#include "audio.h"
#include "globals.h"
#include "random.h"
#include "screen_saver.h"
//*****************************************************************************
//
// These arrays contain the starting and ending points of the lines on the
// display; this history buffer lists the lines from oldest to youngest.
//
//*****************************************************************************
static unsigned char g_pucScreenLinesX1[30];
static unsigned char g_pucScreenLinesY1[30];
static unsigned char g_pucScreenLinesX2[30];
static unsigned char g_pucScreenLinesY2[30];
//*****************************************************************************
//
// These variables contain the direction and rate of movement of the endpoints
// of the lines being drawn on the display.
//
//*****************************************************************************
static char g_cScreenDeltaX1;
static char g_cScreenDeltaY1;
static char g_cScreenDeltaX2;
static char g_cScreenDeltaY2;
//*****************************************************************************
//
// Draws a line in the local frame buffer using Bresneham's line drawing
// algorithm.
//
//*****************************************************************************
static void
ScreenSaverLine(long lX1, long lY1, long lX2, long lY2, unsigned long ulLevel)
{
long lError, lDeltaX, lDeltaY, lYStep;
tBoolean bSteep;
//
// Determine if the line is steep. A steep line has more motion in the Y
// direction than the X direction.
//
if(((lY2 > lY1) ? (lY2 - lY1) : (lY1 - lY2)) >
((lX2 > lX1) ? (lX2 - lX1) : (lX1 - lX2)))
{
bSteep = true;
}
else
{
bSteep = false;
}
//
// If the line is steep, then swap the X and Y coordinates.
//
if(bSteep)
{
lError = lX1;
lX1 = lY1;
lY1 = lError;
lError = lX2;
lX2 = lY2;
lY2 = lError;
}
//
// If the starting X coordinate is larger than the ending X coordinate,
// tehn swap the start and end coordinates.
//
if(lX1 > lX2)
{
lError = lX1;
lX1 = lX2;
lX2 = lError;
lError = lY1;
lY1 = lY2;
lY2 = lError;
}
//
// Compute the difference between the start and end coordinates in each
// axis.
//
lDeltaX = lX2 - lX1;
lDeltaY = (lY2 > lY1) ? (lY2 - lY1) : (lY1 - lY2);
//
// Initialize the error term to negative half the X delta.
//
lError = -lDeltaX / 2;
//
// Determine the direction to step in the Y axis when required.
//
if(lY1 < lY2)
{
lYStep = 1;
}
else
{
lYStep = -1;
}
//
// Loop through all the points along the X axis of the line.
//
for(; lX1 <= lX2; lX1++)
{
//
// See if this is a steep line.
//
if(bSteep)
{
//
// Plot this point of the line, swapping the X and Y coordinates.
//
if(lY1 & 1)
{
g_pucFrame[(lX1 * 64) + (lY1 / 2)] =
((g_pucFrame[(lX1 * 64) + (lY1 / 2)] & 0xf0) |
(ulLevel & 0xf));
}
else
{
g_pucFrame[(lX1 * 64) + (lY1 / 2)] =
((g_pucFrame[(lX1 * 64) + (lY1 / 2)] & 0x0f) |
((ulLevel & 0xf) << 4));
}
}
else
{
//
// Plot this point of the line, using the coordinates as is.
//
if(lX1 & 1)
{
g_pucFrame[(lY1 * 64) + (lX1 / 2)] =
((g_pucFrame[(lY1 * 64) + (lX1 / 2)] & 0xf0) |
(ulLevel & 0xf));
}
else
{
g_pucFrame[(lY1 * 64) + (lX1 / 2)] =
((g_pucFrame[(lY1 * 64) + (lX1 / 2)] & 0x0f) |
((ulLevel & 0xf) << 4));
}
}
//
// Increment the error term by the Y delta.
//
lError += lDeltaY;
//
// See if the error term is now greater than zero.
//
if(lError > 0)
{
//
// Take a step in the Y axis.
//
lY1 += lYStep;
//
// Decrement the error term by the X delta.
//
lError -= lDeltaX;
}
}
}
//*****************************************************************************
//
// A screen saver to avoid damage to the OLED display (it has similar
// characteristics to a CRT with respect to image burn-in). This implements a
// Qix-style chasing line that bounces about the display.
//
//*****************************************************************************
void
ScreenSaver(void)
{
unsigned long ulCount, ulLoop;
//
// Clear out the line history so that any lines from a previous run of the
// screen saver are not used again.
//
for(ulLoop = 0; ulLoop < 29; ulLoop++)
{
g_pucScreenLinesX1[ulLoop] = 0;
g_pucScreenLinesY1[ulLoop] = 0;
g_pucScreenLinesX2[ulLoop] = 0;
g_pucScreenLinesY2[ulLoop] = 0;
}
//
// Choose random starting points for the first line.
//
g_pucScreenLinesX1[29] = RandomNumber() >> 25;
g_pucScreenLinesY1[29] = RandomNumber() >> 26;
g_pucScreenLinesX2[29] = RandomNumber() >> 25;
g_pucScreenLinesY2[29] = RandomNumber() >> 26;
//
// Choose a random direction for each endpoint. Make sure that the
// endpoint does not have a zero direction vector.
//
g_cScreenDeltaX1 = 4 - (RandomNumber() >> 29);
if(g_cScreenDeltaX1 < 1)
{
g_cScreenDeltaX1--;
}
g_cScreenDeltaY1 = 4 - (RandomNumber() >> 29);
if(g_cScreenDeltaY1 < 1)
{
g_cScreenDeltaY1--;
}
g_cScreenDeltaX2 = 4 - (RandomNumber() >> 29);
if(g_cScreenDeltaX2 < 1)
{
g_cScreenDeltaX2--;
}
g_cScreenDeltaY2 = 4 - (RandomNumber() >> 29);
if(g_cScreenDeltaY2 < 1)
{
g_cScreenDeltaY2--;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -