Response.ContentType="image/jpeg"

本文介绍如何使用 ASPCOM.ChartImage 组件创建柱状图。包括设置图表标题、尺寸、背景图片等属性,并演示了如何添加不同数值及标识符到图表中。
导读:
  Set DelphiASPObj = Server.CreateObject("ASPCOM.ChartImage")
  'DelphiASPObj.About
  DelphiASPObj.Clear
  DelphiASPObj.Title="标题" '显示柱状图的标题
  DelphiASPObj.Foot="备注" '备注柱状图是分析啥地
  DelphiASPObj.Width=600 '设备柱状图的宽度
  DelphiASPObj.Height=400 '设备柱状图的长度
  'DelphiASPObj.SetRange 0, 100
  DelphiASPObj.AddValue 200, "达", 123456 '转入值,标识和颜色(这个不敢确定)
  DelphiASPObj.AddValue 40, "#2", 3456677
  ' DelphiASPObj.AddNull "Null" '转入值,标识和颜色(这个不敢确定)
  'DelphiASPObj.AddValue 20, "#5", 1243535
  DelphiASPObj.AddValue 20, "#3", 1243535 '转入值,标识和颜色(这个不敢确定)
  DelphiASPObj.AddValue 50, "#4", 243455 '转入值,标识和颜色(这个不敢确定)
  DelphiASPObj.AddValue 40, "#5", 123535 '转入值,标识和颜色(这个不敢确定)
  DelphiASPObj.AddValue 550, "#6", 123535 '转入值,标识和颜色(这个不敢确定)
  DelphiASPObj.SetChartType 0
  DelphiASPObj.SetMarkFont 8, 0
  DelphiASPObj.SetTitleFont 8, 0
  DelphiASPObj.SetFootFont 8, 0
  'Font Size , Font Color
  '0: Bar 1: HorizBar 2: Line 3: Pie 4: Point 5: Area
  DelphiASPObj.SetMark true,false,true,1
  'Mark Visible , Mark Transparent , Border Visible , Mark Style
  'Style: 0:Value 1:Label 2:LabelValue 3:LabelPercentTotal 4: Percent 5:PercentTotal
  DelphiASPObj.SetAxis true,"x轴",90,"Y轴",0,true '显示x,y轴
  'Axis Visible , Horiz Title , Horiz Angle , Vertical Title , Veritcal Angle , Legend Visible
  'DelphiASPObj.SetPanel 1677215,true,true,9895167,1677215
  'Color , Border Visible , Gradient Visible , Start Color , End Color
  DelphiASPObj.SetBGImage "D:\aliang\chart\TestBG.jpg" '设置图象的背景色
  'BackGround Image File Name
  DelphiASPObj.View3D=true '设置是否显示3d
  Response.BinaryWrite DelphiASPObj.Image(100)
  'Image Quality [Optional] 100 is the best 0 is the worst
  %>

本文转自
http://study.qqcf.com/web/250/31055.htm
(function (global, factory) { typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() : typeof define === 'function' && define.amd ? define(factory) : (global.$fetch = factory()); }(typeof self !== 'undefined' ? self : window, function () { 'use strict'; class fetchFactory { constructor() { this.defaultOptions = { timeout: 10000, retries: 3, retryDelay: 1000 }; } /** * 创建AbortController */ createController() { return new AbortController(); } /** * 检测文件类型 */ detectFileType(contentType, url) { if (!contentType && url) { const ext = url.split('.').pop()?.toLowerCase(); if (['jpg', 'jpeg', 'png', 'gif', 'bmp', 'webp', 'svg'].includes(ext)) { return 'image'; } if (['json'].includes(ext)) { return 'json'; } if (['txt', 'md', 'js', 'css', 'html', 'xml' , 'vue', 'ts', 'jsx', 'scss'].includes(ext)) { return 'text'; } } if (contentType) { if (contentType.startsWith('image/')) return 'image'; if (contentType.includes('json')) return 'json'; if (contentType.startsWith('text/')) return 'text'; } return 'binary'; } /** * 图片专用转换 (FileReader) * @param {Blob} blob * @returns {Promise<string>} Base64字符串 */ toBase64(blob) { let isImage = false; if (!blob.type) return this.txtToBase64(blob) if (blob.type.startsWith('image/')) { console.log(`检测到图片格式: ${blob.type}`); isImage = true; } else { console.log(`其他文件格式: ${blob.type || '未知'}`); return this.txtToBase64(blob) } return new Promise((resolve, reject) => { const reader = new FileReader(); reader.onloadend = () => resolve(reader.result); reader.onerror = (err) => reject(isImage ? '图片转换失败:' + err : err); reader.readAsDataURL(blob); }); } txtToBase64(str = '') { if (!str || typeof str !== 'string') return str // 创建 TextEncoder 实例 const encoder = new TextEncoder(); // 将字符串编码为 Uint8Array const data = encoder.encode(str); // 将字节数组转换为二进制字符串 const binary = Array.from(data, byte => String.fromCharCode(byte)).join(''); // 编码为 Base64 return btoa(binary); } /** * 自动处理响应数据 */ async handleResponse(response, options = {}) { const contentType = response.headers.get('content-type') || ''; const url = response.url; const fileType = this.detectFileType(contentType, url); let data; try { switch (options.readMode || 'auto') { case 'blob': data = await response.blob(); break; case 'text': data = await response.text(); break; case 'json': data = await response.json(); break; case 'arrayBuffer': data = await response.arrayBuffer(); break; case 'auto': default: if (fileType === 'text') { data = await response.text(); } else if (fileType === 'json') { data = await response.json(); } else { data = await response.blob(); } } } catch (error) { // 如果解析失败,返回原始文本 data = await response.text(); } return { data, fileType, contentType, size: response.headers.get('content-length') || 0 }; } /** * 核心请求方法 */ async request(url, options = {}) { const opts = { ...this.defaultOptions, ...options }; const controller = opts.signal || this.createController(); let result = { url, code: null, msg: '', data: null, loaded: 0, total: 0, duration: 0 }; const startTime = Date.now(); let timeoutId = null; try { // 请求前回调 if (opts.before) { await opts.before(url, opts); } if (opts.platform) { result.platform = opts.platform; delete opts.platform; } // 设置超时处理 if (opts.timeout > 0) { timeoutId = setTimeout(() => { controller.abort(); }, opts.timeout); } const response = await fetch(url, { method: 'GET', ...opts, signal: controller.signal }); result.code = response.status; // 处理特殊状态码 switch (response.status) { case 200: case 201: case 204: result.msg = 'ok'; break; case 429: result.msg = '请求频率超限,请稍后重试'; break; case 401: result.msg = '未授权,请检查认证信息'; break; case 403: result.msg = '禁止访问'; break; case 404: result.msg = '资源未找到'; break; case 500: result.msg = '服务器内部错误'; break; default: result.msg = `请求失败: ${response.statusText}`; } // 处理响应数据 const handledData = await this.handleResponse(response, opts); result.data = handledData.data; result.fileType = handledData.fileType; result.contentType = handledData.contentType; result.size = handledData.size; // 流式进度处理 if (opts.progress && response.body && handledData.fileType !== 'text' && handledData.fileType !== 'json') { const reader = response.body.getReader(); const contentLength = response.headers.get('content-length'); result.total = parseInt(contentLength) || 0; const chunks = []; let loaded = 0; while (true) { const { done, value } = await reader.read(); if (done) break; chunks.push(value); loaded += value.length; result.loaded = loaded; opts.progress(url, loaded, result.total); } // 重新组合数据 if (opts.readMode === 'blob' || (opts.readMode === 'auto' && handledData.fileType === 'binary')) { result.data = new Blob(chunks, { type: handledData.contentType }); } } } catch (error) { if (error.name === 'AbortError') { result.code = 0; result.msg = '请求已取消'; } else { result.code = error.code || -1; result.msg = error.message || '网络错误'; } } finally { // 在finally块中清除超时定时器,确保无论如何都会清理 if (timeoutId) { clearTimeout(timeoutId); } result.duration = Date.now() - startTime; // 完成后回调 if (opts.after) { await opts.after(url, result); } } return result; } /** * 带代理支持的请求方法 */ async requestWithProxy(url, options = {}) { const { proxies, ...opts } = options; // 如果没有提供代理,使用普通请求 if (!proxies || !Array.isArray(proxies) || proxies.length === 0) { return await this.request(url, opts); } // 尝试使用代理 let lastError = null; for (const proxy of proxies) { try { // 设置3秒超时 const proxyOptions = { timeout: 5000, ...opts, }; // 构建代理URL let proxyUrl; if (typeof proxy === 'string') { proxyUrl = `${proxy}${url}`; } else { if (proxy.perfix) { // 直接将完整URL拼接到代理URL后面 proxyUrl = `${proxy.url}${url}`; } else { // 只将路径部分拼接到代理URL后面 const urlObj = new URL(url); const path = urlObj.pathname + urlObj.search + urlObj.hash; proxyUrl = `${proxy.url}${path}`; } } const result = await this.request(proxyUrl, proxyOptions); // 如果请求成功,返回结果 if (result.code >= 200 && result.code < 300) { return result; } // 如果请求失败,记录错误并尝试下一个代理 lastError = result; } catch (error) { lastError = { code: -1, msg: error.message, url: proxy.url }; } } // 所有代理都失败,返回最后一个错误 return lastError || { code: -1, msg: '所有代理请求失败', url }; } /** * 并发下载 */ async downloadConcurrent(urls, options = {}) { const maxConcurrency = options.maxConcurrency || 3; const controller = new ConcurrencyController(maxConcurrency); const tasks = urls.map(url => () => this.requestWithProxy(url, options) ); const promises = tasks.map(task => controller.add(task)); return await Promise.allSettled(promises); } /** * 并行上传 */ async uploadParallel(file, platforms, options = {}) { const uploadPromises = platforms.map(async (platform) => { try { // 判断上传类型 if (file && typeof file === 'object') { // 根据平台调整请求体格式 const requestBody = { content: file.content, message: file.message, ...(platform.branch && { branch: platform.branch }) }; options.body = JSON.stringify(requestBody); // 确保Content-Type为application/json options.headers = { 'Content-Type': 'application/json', ...platform.headers }; } else { // 文件上传模式 - 使用原始文件对象 options.body = file; } options.method = options.method || 'POST'; const result = await this.request(platform.url, options); return { platform: platform.name, ...result }; } catch (error) { return { platform: platform.name, code: -1, msg: error.message }; } }); return await Promise.allSettled(uploadPromises); } } /** * 并发控制器 */ class ConcurrencyController { constructor(maxConcurrency = 3) { this.maxConcurrency = maxConcurrency; this.running = 0; this.queue = []; } async add(task) { return new Promise((resolve, reject) => { this.queue.push({ task, resolve, reject }); this.process(); }); } async process() { if (this.running >= this.maxConcurrency || this.queue.length === 0) { return; } this.running++; const { task, resolve, reject } = this.queue.shift(); try { const result = await task(); resolve(result); } catch (error) { reject(error); } finally { this.running--; this.process(); } } } // 创建实例 const instance = new fetchFactory(); // 导出便捷方法 const ketFetch = async (url, options) => { return await instance.request(url, options); }; ketFetch.request = (url, options) => instance.request(url, options); ketFetch.proxy = (url, options) => instance.requestWithProxy(url, options); ketFetch.downloadAll = (urls, options) => instance.downloadConcurrent(urls, options); ketFetch.uploads = (file, platforms, options) => instance.uploadParallel(file, platforms, options); ketFetch.Aborter = () => instance.createController(); ketFetch.fileType = (contentType, url) => instance.detectFileType(contentType, url); ketFetch.toBase64 = (file) => instance.toBase64(file); return ketFetch; })); 结合整个组件权衡一下, 尽量不改动现有逻辑, 不影响现有输出
最新发布
11-23
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值