WhatsApp Discord
screen.cpp Modificado - LEGENDARY - LastUpdate - Lua ServerSide - S6.E15 GamingM - Source Mu - Mu Server Files
 

screen.cpp Modificado - LEGENDARY - LastUpdate - Lua ServerSide - S6.E15 GamingM

Publicado por Dakosmu, Nov 28, 2025, 05:38 PM

Tema anterior - Siguiente tema

0 Miembros y 1 Visitante están viendo este tema.

Dakosmu

screen.cpp Modificado - LEGENDARY - LastUpdate - Lua ServerSide - S6.E15 GamingMaster

Regístrate para ver el enlace

screen.cpp

#include "stdafx.h"
#include "screen.h"
#include "Interface.h"
#include "Defines.h"
#include "Central.h"
#include "Import.h"
#include "CustomFont.h"
#include "Defines2.h"
#include <vector>
#include <string>
#include <windows.h> 
#include <fstream>
#include <iostream>

// 滑块速度 (每帧像素)
const float sliderSpeed = 10.0f;

// 启动完整文本输入延迟 (毫秒)
const DWORD delayTextoCompleto = 2020; // 2 秒 (2 秒)

Cscreen::Cscreen()
{
// 在构造函数中初始化类成员
this->currentLine = 0;
this->indiceTexto = 0;
this->tempoAnterior = 0;
this->animationFinished = false;
this->animationEndTime = 0;
this->textLoadSuccess = false;

// 初始化标题 (以防加载失败)
this->welcomeTitle = "欢迎来到 Mu Archangel"; // 欢迎标题
this->resumeTitle = "====== 简短摘要 ======"; // 摘要标题
}

Cscreen gscreen;

// 变量用于定义窗口应该打开的次数
int maxDisplays = 7; // <--- 配置为 7 次

// 变量用于跟踪窗口已显示的次数
int displayCount = 0;

// 函数: 从文件中读取计数器
void ReadDisplayCount()
{
std::ifstream infile("Data//display_count.dat");
if (infile.is_open())
{
infile >> displayCount;
infile.close();
}
}

// 函数: 将计数器写入文件
void WriteDisplayCount()
{
std::ofstream outfile("Data//display_count.dat", std::ios::trunc);
if (outfile.is_open())
{
outfile << displayCount;
outfile.close();
}
}

// *** 辅助函数 LoadTitles: 加载标题 1 和标题 2 ***
void Cscreen::LoadTitles(const char* path)
{
// 失败时的调试标题
this->welcomeTitle = "错误: 标题 1 未加载";
this->resumeTitle = "错误: 标题 2 未加载";

std::ifstream file(path);
std::string line;

if (file.is_open())
{
// 第 1 行: 欢迎标题
if (std::getline(file, line))
{
this->welcomeTitle = line;
}

// 第 2 行: 摘要标题
if (std::getline(file, line))
{
this->resumeTitle = line;
}

file.close();
}
}

// *** 主要数据加载函数 (新闻 + 标题) ***
void Cscreen::LoadNewsData(const char* newsPath, const char* titlesPath)
{
// 1. 加载标题
this->LoadTitles(titlesPath);

// 2. 加载新闻
this->textos.clear();
this->textLoadSuccess = false;
std::ifstream file(newsPath);
std::string line;

if (file.is_open())
{
while (std::getline(file, line))
{
if (!line.empty())
{
this->textos.push_back(line);
}
}
file.close();

if (this->textos.empty())
{
this->textos.push_back("错误: 新闻文本文件为空。"); // 错误信息
}
this->textLoadSuccess = true;
}
else
{
this->textos.push_back("错误! 未找到新闻文件或无法访问:"); // 错误信息
this->textos.push_back(newsPath);
this->textLoadSuccess = false;
}
}
// *************************************************************

// 现有全局变量...
bool isDragging = false;
POINT dragStartPoint;
// 初始化位置在屏幕外,以便从左向右滑动。
float windowPosX = -300.0f;
float windowPosY = (MAX_WIN_HEIGHT / 2) - (390.0f / 2);

DWORD intervaloDigitacao = 50; // 每字之间的间隔 (毫秒)
DWORD displayDuration = 6300; // 动画结束后窗口保持可见的时间 (毫秒)

void Cscreen::DrawPanelWindow()
{
// 局部变量,确保滑块只执行一次。
static bool sliderCompleted = false;

// 静态变量,用于控制输入延迟
static bool textDelayComplete = false;
static DWORD panelStartTime = 0;

// 在游戏启动时读取当前计数器并初始化文本。
static bool initialized = false;
if (!initialized)
{
// 1. 从文件读取显示计数器。
ReadDisplayCount();

// 2. 从 .txt 文件加载所有文本
gscreen.LoadNewsData("Data//news_text.txt", "Data//titles.txt");

// 3. 检查窗口是否已达到最大显示次数。
if (displayCount >= maxDisplays)
{
// 不再显示窗口。
gInterface.Data[ePanelWindow].OnShow = false;
return;
}

// 显示窗口。
gInterface.Data[ePanelWindow].OnShow = true;

// 重置输入控制变量 (类成员)
this->currentLine = 0;
this->indiceTexto = 0;
this->tempoAnterior = GetTickCount();
this->animationFinished = false;
this->animationEndTime = 0;

// 启动延迟计时器
panelStartTime = GetTickCount();
textDelayComplete = false;

initialized = true;
}

// 如果窗口不可见,则返回。
if (!gInterface.Data[ePanelWindow].OnShow)
{
return;
}

pSetCursorFocus = true;

// 仅更新一次从左向右滑块的位置。
float destPosX = (MAX_WIN_WIDTH / 2) - (300.0f / 2);
if (!isDragging && !sliderCompleted && windowPosX < destPosX)
{
windowPosX += sliderSpeed;
if (windowPosX >= destPosX)
{
windowPosX = destPosX;
sliderCompleted = true;
}
}

float MainWidth = 300.0f;
float MainHeight = 350.0f;
float StartX = windowPosX;
float StartY = windowPosY;
float StartBody = StartY + 50.0f;

// 在定义的时间后关闭窗口并增加计数器。
if (this->animationFinished)
{
DWORD tempoAtual = GetTickCount();
if (tempoAtual - this->animationEndTime > displayDuration)
{
// 关闭窗口。
gInterface.Data[ePanelWindow].OnShow = false;

// 增加计数器并保存到文件。
displayCount++;
WriteDisplayCount();
}
}

// 拖动窗口的逻辑。 (保持不变)
if (pCheckMouseOver(StartX, StartY, MainWidth, MainHeight) || isDragging)
{
if (GetAsyncKeyState(VK_LBUTTON) & 0x8000)
{
if (!isDragging)
{
isDragging = true;
dragStartPoint.x = pCursorX;
dragStartPoint.y = pCursorY;
}
else
{
float deltaX = pCursorX - dragStartPoint.x;
float deltaY = pCursorY - dragStartPoint.y;

windowPosX += deltaX;
windowPosY += deltaY;

// 限制 X 位置在屏幕范围内。
if (windowPosX < 0)
windowPosX = 0;
else if (windowPosX > MAX_WIN_WIDTH - MainWidth)
windowPosX = MAX_WIN_WIDTH - MainWidth;

// 限制 Y 位置在屏幕范围内。
if (windowPosY < 0)
windowPosY = 0;
else if (windowPosY > MAX_WIN_HEIGHT - MainHeight)
windowPosY = MAX_WIN_HEIGHT - MainHeight;

dragStartPoint.x = pCursorX;
dragStartPoint.y = pCursorY;
}
}
else
{
isDragging = false;
}
}
else
{
isDragging = false;
}

// 绘制主区域。
gCentral.PrintDropBox(StartX, StartY, MainWidth, MainHeight, 0, 0);

// 配置自定义字体... (保持不变)
HFONT hCustomFont = CreateFontA(
-20,                // 字体高度
0,                  // 宽度
0,                  // 倾斜角
0,                  // 方向
FW_BOLD,            // 字体粗细 (粗体)
FALSE,              // 斜体
FALSE,              // 下划线
FALSE,              // 删除线
DEFAULT_CHARSET,
OUT_TT_PRECIS,
CLIP_DEFAULT_PRECIS,
CLEARTYPE_QUALITY,
DEFAULT_PITCH | FF_DONTCARE,
"Segoe UI"
);

if (hCustomFont)
{
// 应用自定义字体。
pSetFont(pTextThis(), (int)hCustomFont);
// 设置文本颜色 (白色)。
pSetTextColor(pTextThis(), 255, 255, 255, 255);

// 文本起始位置。
float posX = StartX + 20.0f;
float posY = StartY + 120.0f;
float linhaAltura = 20.0f;

// 检查是否已达到启动输入的时间
if (!textDelayComplete)
{
if (GetTickCount() - panelStartTime >= delayTextoCompleto)
{
textDelayComplete = true;
// 重启输入计时器
this->tempoAnterior = GetTickCount();
}
}

// 带有输入效果的每行文本循环。
for (size_t i = 0; i < this->textos.size(); ++i)
{
if (i < this->currentLine)
{
// 该行已完全输入: 显示完整的行。
pDrawText(pTextThis(), posX, posY + (i * linhaAltura), (char*)this->textos[i].c_str(), 280, 0, (LPINT)0, 0);
}
else if (i == this->currentLine)
{
// 如果输入延迟尚未完成,则不更新输入。
if (textDelayComplete)
{
DWORD tempoAtual = GetTickCount();
if (tempoAtual - this->tempoAnterior > intervaloDigitacao && this->indiceTexto < this->textos[i].length())
{
this->indiceTexto++;
this->tempoAnterior = tempoAtual;
}
}

// 获取要显示的当前子字符串。
std::string textoParcial = this->textos[i].substr(0, this->indiceTexto);
// 绘制部分文本。
pDrawText(pTextThis(), posX, posY + (i * linhaAltura), (char*)textoParcial.c_str(), 280, 0, (LPINT)0, 0);

// 如果该行已完全输入,则转到下一行。
if (this->indiceTexto >= this->textos[i].length())
{
this->currentLine++;
this->indiceTexto = 0;
this->tempoAnterior = GetTickCount(); // 重置下一行的时间

// 如果所有行都已输入,则标记动画结束。
if (this->currentLine >= this->textos.size())
{
this->animationFinished = true;
this->animationEndTime = GetTickCount();
}
}
}
}

// 使用后释放自定义字体。
DeleteObject(hCustomFont);
}

// *** 使用从 titles.txt 加载的欢迎标题变量 ***
CustomFont.DrawMultipleColor(CustomFont.FontSize20, (int)StartX + 20, (int)StartBody - 20,
0x0, 0, 0, 10, (char*)this->welcomeTitle.c_str());

// *** 使用从 titles.txt 加载的摘要标题变量 ***
pSetFont(pTextThis(), (int)pFontBigBold);
pSetBackgroundTextColor(pTextThis(), 0, 0, 0, 0);
pSetTextColor(pTextThis(), 240, 240, 240, 255);
pDrawText(pTextThis(), StartX + 20, StartY + 90, (char*)this->resumeTitle.c_str(), 260, 0, (LPINT)3, 0);

// 绘制分隔线。
pDrawGUI(71520, StartX + (MainWidth / 2) - 100.0f, StartBody + 35.0f, 200.0f, 1.0f);
pDrawGUI(71520, StartX + (MainWidth / 2) - 100.0f, StartBody + 210.0f, 200.0f, 1.0f);

// 在确定的时间后关闭窗口。
if (this->animationFinished)
{
DWORD tempoAtual = GetTickCount();
if (tempoAtual - this->animationEndTime > displayDuration)
{
// 关闭窗口。
gInterface.Data[ePanelWindow].OnShow = false;
}
}
}


screen.h

#pragma once

#include "Protocol.h"
#include <vector>
#include <string>
#include <windows.h> //  所必需

class Cscreen
{
public:
Cscreen();
void DrawPanelWindow();
// 主要加载函数声明
void LoadNewsData(const char* newsPath, const char* titlesPath);

private:
// 辅助函数声明 (私有)
void LoadTitles(const char* path);

// 新闻和动画变量
std::vector<std::string> textos;
size_t currentLine;
size_t indiceTexto;
DWORD tempoAnterior;
bool animationFinished;
DWORD animationEndTime;
bool textLoadSuccess;

// 从 加载的标题变量
std::string welcomeTitle;
std::string resumeTitle;
};
extern Cscreen gscreen;




Aqui puedes modificar las veces que aparece el anuncio si le colocas 0 . no aparece

int maxDisplays = 7; // <--- 配置为 7 次



en estos TXT puedes modificar el texto y no por source

Regístrate para ver el enlace


Bon Dia

🡱 🡳
Real Time Web Analytics