From cff0a1241ccbdcd930bfc43d7661a14bbc49ba56 Mon Sep 17 00:00:00 2001 From: Jeremy <297323986@qq.com> Date: Wed, 22 Jan 2025 00:23:23 +0800 Subject: [PATCH] overhaul: fix inserting lines and add handling pattern fill --- .../src/calc_engine/calculator/calc_vertex.rs | 5 - crates/controller/src/controller/executor.rs | 6 +- crates/controller/src/controller/style.rs | 42 ++++++++- crates/controller/src/navigator/executor.rs | 34 ++++--- .../src/style_manager/fill_manager.rs | 25 ++++- crates/wasms/server/src/controller.rs | 77 +++++++++++++++- packages/web/src/api/index.ts | 2 +- packages/web/src/api/utils.ts | 6 ++ packages/web/src/api/workbook.ts | 23 +++++ packages/web/src/payloads/index.ts | 6 ++ .../web/src/payloads/set_cell_pattern_fill.ts | 58 ++++++++++++ .../web/src/payloads/set_line_pattern_fill.ts | 68 ++++++++++++++ src/components/canvas/component.tsx | 2 +- src/components/canvas/contextmenu.tsx | 1 + src/components/top-bar/content/index.tsx | 76 +++++++++++++--- src/components/top-bar/content/payload.ts | 91 ++++++++++++++----- src/ui/contextmenu/index.tsx | 3 - 17 files changed, 455 insertions(+), 70 deletions(-) create mode 100644 packages/web/src/payloads/set_cell_pattern_fill.ts create mode 100644 packages/web/src/payloads/set_line_pattern_fill.ts diff --git a/crates/controller/src/calc_engine/calculator/calc_vertex.rs b/crates/controller/src/calc_engine/calculator/calc_vertex.rs index ff02d2a8..5c58cfc7 100644 --- a/crates/controller/src/calc_engine/calculator/calc_vertex.rs +++ b/crates/controller/src/calc_engine/calculator/calc_vertex.rs @@ -134,8 +134,3 @@ pub struct RowRange { pub start: usize, pub end: usize, } -#[derive(Debug, Clone)] -pub struct Range { - pub start: Addr, - pub end: Addr, -} diff --git a/crates/controller/src/controller/executor.rs b/crates/controller/src/controller/executor.rs index a6ac0209..d9b8597b 100644 --- a/crates/controller/src/controller/executor.rs +++ b/crates/controller/src/controller/executor.rs @@ -91,7 +91,7 @@ impl<'a> Executor<'a> { result.status.sheet_pos_manager = sheet_pos_manager; let old_navigator = result.status.navigator.clone(); - let nav_executor = result.execute_navigator(payload.clone())?; + let (nav_executor, nav_updated) = result.execute_navigator(payload.clone())?; let range_executor = result.execute_range(payload.clone())?; let cube_executor = result.execute_cube(payload.clone())?; @@ -115,7 +115,7 @@ impl<'a> Executor<'a> { let formula_executor = result.execute_formula(payload, &old_navigator, dirty_ranges, dirty_cubes)?; - let cell_updated = if updated { + let cell_updated = if updated || nav_updated { true } else { result.updated_cells.len() > 0 @@ -213,7 +213,7 @@ impl<'a> Executor<'a> { executor.execute(&ctx, payload) } - fn execute_navigator(&mut self, payload: EditPayload) -> Result { + fn execute_navigator(&mut self, payload: EditPayload) -> Result<(NavExecutor, bool), Error> { let ctx = NavigatorConnector { sheet_pos_manager: &self.status.sheet_pos_manager, }; diff --git a/crates/controller/src/controller/style.rs b/crates/controller/src/controller/style.rs index 2e143c59..5ccf0b23 100644 --- a/crates/controller/src/controller/style.rs +++ b/crates/controller/src/controller/style.rs @@ -338,7 +338,7 @@ impl<'a> StyleConverter<'a> { } // Convert ARGB hex str and apply the tint to it. -fn from_hex_str(argb: String, tint: f64) -> Color { +pub fn from_hex_str(argb: String, tint: f64) -> Color { use colorsys::{Hsl, Rgb}; if argb.len() < 8 { return Color { @@ -375,9 +375,32 @@ fn from_hex_str(argb: String, tint: f64) -> Color { } } +#[inline] +fn bound(upper: u8, lower: u8, v: f64) -> u8 { + let v = v.round(); + let result = upper.min(v as u8) as u8; + let result = result.max(lower); + result +} + +pub fn color_to_ct_color(c: Color) -> CtColor { + let r = bound(255, 0, c.red.unwrap_or(0.)); + let g = bound(255, 0, c.green.unwrap_or(0.)); + let b = bound(255, 0, c.blue.unwrap_or(0.)); + let a = bound(255, 0, c.alpha.unwrap_or(255.)); + let argb = format!("{:02X}{:02X}{:02X}{:02X}", a, r, g, b); + CtColor { + auto: None, + indexed: None, + rgb: Some(argb), + theme: None, + tint: 0., + } +} + #[cfg(test)] mod tests { - use super::from_hex_str; + use super::{color_to_ct_color, from_hex_str, Color}; #[test] fn test_from_hex_str() { @@ -386,4 +409,19 @@ mod tests { let color = from_hex_str(argb, tint); println!("{:?}", color); } + + #[test] + fn test_color_to_ct_color() { + let color = Color { + red: Some(12.), + green: Some(28.), + blue: Some(100.), + alpha: Some(241.), + }; + let result = color_to_ct_color(color); + if result.rgb.is_none() { + panic!("should not be none") + } + println!("{:?}", result.rgb.unwrap()) + } } diff --git a/crates/controller/src/navigator/executor.rs b/crates/controller/src/navigator/executor.rs index 132bcc36..414ae3a3 100644 --- a/crates/controller/src/navigator/executor.rs +++ b/crates/controller/src/navigator/executor.rs @@ -12,7 +12,11 @@ impl NavExecutor { NavExecutor { nav } } - pub fn execute(mut self, ctx: &C, payload: EditPayload) -> Result { + pub fn execute( + mut self, + ctx: &C, + payload: EditPayload, + ) -> Result<(Self, bool), Error> { match payload { EditPayload::MoveBlock(move_block) => { let sheet_id = ctx @@ -34,14 +38,14 @@ impl NavExecutor { move_block.new_master_row, move_block.new_master_col, ); - Ok(self) + Ok((self, true)) } EditPayload::RemoveBlock(remove_block) => { let sheet_id = ctx .fetch_sheet_id_by_index(remove_block.sheet_idx) .map_err(|l| BasicError::SheetIdxExceed(l))?; self.nav.remove_block(&sheet_id, &remove_block.id); - Ok(self) + Ok((self, true)) } EditPayload::CreateBlock(create_block) => { let sheet_id = ctx @@ -68,21 +72,21 @@ impl NavExecutor { let block_id = create_block.id; sheet_nav.data.blocks.insert(block_id, block_place); sheet_nav.cache = Default::default(); - Ok(self) + Ok((self, true)) } EditPayload::CreateSheet(p) => { let sheet_id = ctx .fetch_sheet_id_by_index(p.idx) .map_err(|l| BasicError::SheetIdxExceed(l))?; self.nav.create_sheet(sheet_id); - Ok(self) + Ok((self, true)) } EditPayload::DeleteSheet(delete_sheet) => { let sheet_id = ctx .fetch_sheet_id_by_index(delete_sheet.idx) .map_err(|l| BasicError::SheetIdxExceed(l))?; self.nav.delete_sheet(&sheet_id); - Ok(self) + Ok((self, true)) } EditPayload::InsertCols(insert_cols) => { let sheet_id = ctx @@ -95,7 +99,7 @@ impl NavExecutor { let res = NavExecutor { nav: Navigator { sheet_navs }, }; - Ok(res) + Ok((res, true)) } EditPayload::DeleteCols(p) => { let sheet_id = ctx @@ -107,7 +111,7 @@ impl NavExecutor { let res = NavExecutor { nav: Navigator { sheet_navs }, }; - Ok(res) + Ok((res, true)) } EditPayload::InsertRows(insert_rows) => { let sheet_id = ctx @@ -120,7 +124,7 @@ impl NavExecutor { let res = NavExecutor { nav: Navigator { sheet_navs }, }; - Ok(res) + Ok((res, true)) } EditPayload::DeleteRows(p) => { let sheet_id = ctx @@ -132,7 +136,7 @@ impl NavExecutor { let res = NavExecutor { nav: Navigator { sheet_navs }, }; - Ok(res) + Ok((res, true)) } EditPayload::InsertColsInBlock(p) => { let sheet_id = ctx @@ -142,7 +146,7 @@ impl NavExecutor { let new_bp = bp.add_new_cols(p.start, p.cnt as u32); let nav = self.nav.add_block_place(sheet_id, p.block_id, new_bp); let result = NavExecutor { nav }; - Ok(result) + Ok((result, true)) } EditPayload::DeleteColsInBlock(p) => { let sheet_id = ctx @@ -152,7 +156,7 @@ impl NavExecutor { let new_bp = bp.delete_cols(p.start, p.cnt as u32); let nav = self.nav.add_block_place(sheet_id, p.block_id, new_bp); let result = NavExecutor { nav }; - Ok(result) + Ok((result, true)) } EditPayload::InsertRowsInBlock(p) => { let sheet_id = ctx @@ -162,7 +166,7 @@ impl NavExecutor { let new_bp = bp.add_new_rows(p.start, p.cnt as u32); let nav = self.nav.add_block_place(sheet_id, p.block_id, new_bp); let result = NavExecutor { nav }; - Ok(result) + Ok((result, true)) } EditPayload::DeleteRowsInBlock(p) => { let sheet_id = ctx @@ -172,9 +176,9 @@ impl NavExecutor { let new_bp = bp.delete_rows(p.start, p.cnt as u32); let nav = self.nav.add_block_place(sheet_id, p.block_id, new_bp); let result = NavExecutor { nav }; - Ok(result) + Ok((result, true)) } - _ => Ok(self), + _ => Ok((self, false)), } } } diff --git a/crates/controller/src/style_manager/fill_manager.rs b/crates/controller/src/style_manager/fill_manager.rs index 5e5a43b0..a2a531c5 100644 --- a/crates/controller/src/style_manager/fill_manager.rs +++ b/crates/controller/src/style_manager/fill_manager.rs @@ -1,3 +1,4 @@ +use crate::controller::style::color_to_ct_color; use crate::edit_action::StyleUpdateType; use super::defaults::get_init_fill; @@ -17,14 +18,32 @@ impl Default for FillManager { } impl FillManager { - pub fn execute(&mut self, id: FillId, _update_type: &StyleUpdateType) -> Option { - let fill = if let Some(fill) = self.get_item(id) { + pub fn execute(&mut self, id: FillId, update_type: &StyleUpdateType) -> Option { + let update = update_type.set_pattern_fill.as_ref()?; + let mut fill = if let Some(fill) = self.get_item(id) { fill.clone() } else { get_init_fill() }; + let new_fill = &mut fill; + match new_fill { + CtFill::PatternFill(ct_pattern_fill) => { + if let Some(p) = &update.pattern_type { + ct_pattern_fill.pattern_type = Some(p.clone()) + } + if let Some(p) = &update.fg_color { + let color = color_to_ct_color(p.clone()); + ct_pattern_fill.fg_color = Some(color); + } + if let Some(p) = &update.bg_color { + let color = color_to_ct_color(p.clone()); + ct_pattern_fill.bg_color = Some(color); + } + } + CtFill::GradientFill(_) => return None, + }; // todo - let new_id = self.get_id(&fill); + let new_id = self.get_id(&new_fill); if id != new_id { Some(new_id) } else { diff --git a/crates/wasms/server/src/controller.rs b/crates/wasms/server/src/controller.rs index ccb13b19..9203faf1 100644 --- a/crates/wasms/server/src/controller.rs +++ b/crates/wasms/server/src/controller.rs @@ -1,4 +1,5 @@ use logisheets_controller::controller::display::{CellPosition, DisplaySheetRequest}; +use logisheets_controller::controller::style::{from_hex_str, PatternFill}; use logisheets_controller::edit_action::{ Alignment, AsyncFuncResult, BlockInput, CellClear, CellInput, CellStyleUpdate, CreateBlock, CreateSheet, DeleteCols, DeleteColsInBlock, DeleteRows, DeleteRowsInBlock, DeleteSheet, @@ -8,7 +9,7 @@ use logisheets_controller::edit_action::{ }; use logisheets_controller::{AsyncCalcResult, AsyncErr, RowInfo, SaveFileResult, Workbook}; use logisheets_controller::{ColInfo, ErrorMessage}; -use logisheets_workbook::prelude::{StBorderStyle, StUnderlineValues}; +use logisheets_workbook::prelude::{StBorderStyle, StPatternType, StUnderlineValues}; use singlyton::{Singleton, SingletonUninit}; use wasm_bindgen::prelude::*; use xmlserde::XmlValue; @@ -629,6 +630,80 @@ pub fn set_border( MANAGER.get_mut().add_payload(id, p); } +#[wasm_bindgen] +pub fn set_line_pattern_fill( + id: usize, + sheet_idx: usize, + row: bool, + from: usize, + to: usize, + fg_color: Option, + bg_color: Option, + pattern: Option, +) { + init(); + let update = build_pattern_fill_style_update(fg_color, bg_color, pattern); + let payload = EditPayload::LineStyleUpdate(LineStyleUpdate { + sheet_idx, + from, + to, + row, + ty: update, + }); + MANAGER.get_mut().add_payload(id, payload); +} + +fn build_pattern_fill_style_update( + fg_color: Option, + bg_color: Option, + pattern: Option, +) -> StyleUpdateType { + let fg = if let Some(f) = fg_color { + Some(from_hex_str(f, 0.)) + } else { + None + }; + let bg = if let Some(b) = bg_color { + Some(from_hex_str(b, 0.)) + } else { + None + }; + let pattern: Option = if let Some(p) = pattern { + serde_json::from_str(&format!("\"{}\"", p)).unwrap() + } else { + None + }; + let pattern_fill = PatternFill { + fg_color: fg, + bg_color: bg, + pattern_type: pattern, + }; + let mut style_update = StyleUpdateType::default(); + style_update.set_pattern_fill = Some(pattern_fill); + style_update +} + +#[wasm_bindgen] +pub fn set_cell_pattern_fill( + id: usize, + sheet_idx: usize, + row: usize, + col: usize, + fg_color: Option, + bg_color: Option, + pattern: Option, +) { + init(); + let style_update = build_pattern_fill_style_update(fg_color, bg_color, pattern); + let payload = EditPayload::CellStyleUpdate(CellStyleUpdate { + sheet_idx, + row, + col, + ty: style_update, + }); + MANAGER.get_mut().add_payload(id, payload); +} + #[wasm_bindgen] pub fn cell_input(id: usize, sheet_idx: usize, row: usize, col: usize, content: String) { init(); diff --git a/packages/web/src/api/index.ts b/packages/web/src/api/index.ts index 0db94027..3771555e 100644 --- a/packages/web/src/api/index.ts +++ b/packages/web/src/api/index.ts @@ -3,5 +3,5 @@ export * from './worksheet' export {CalcException, CustomFunc, Calculator} from './calculator' export type {Executor} from './calculator' export * from './cell' -export {isErrorMessage} from './utils' +export {isErrorMessage, getPatternFill} from './utils' export type {Result} from './utils' diff --git a/packages/web/src/api/utils.ts b/packages/web/src/api/utils.ts index a3fc9e63..d46de552 100644 --- a/packages/web/src/api/utils.ts +++ b/packages/web/src/api/utils.ts @@ -1,3 +1,4 @@ +import {Fill, PatternFill} from '../bindings' import {ErrorMessage} from '../bindings/error_message' // eslint-disable-next-line @typescript-eslint/no-explicit-any @@ -6,3 +7,8 @@ export function isErrorMessage(v: any): v is ErrorMessage { } export type Result = V | ErrorMessage + +export function getPatternFill(v: Fill): PatternFill | null { + if ('patternFill' in v) return v.patternFill + return null +} diff --git a/packages/web/src/api/workbook.ts b/packages/web/src/api/workbook.ts index b5dd0b87..5c876c3a 100644 --- a/packages/web/src/api/workbook.ts +++ b/packages/web/src/api/workbook.ts @@ -22,10 +22,12 @@ import { row_insert, set_border, set_cell_alignment, + set_cell_pattern_fill, set_col_width, set_font, set_line_alignment, set_line_font, + set_line_pattern_fill, set_row_height, sheet_rename_by_idx, sheet_rename_by_name, @@ -305,6 +307,27 @@ export class Workbook { p.alignment.horizontal, p.alignment.vertical ) + if (p.type === 'setCellPatternFill') + return set_cell_pattern_fill( + this._id, + p.sheetIdx, + p.row, + p.col, + p.fgColor, + p.bgColor, + p.pattern + ) + if (p.type === 'setLinePatternFill') + return set_line_pattern_fill( + this._id, + p.sheetIdx, + p.row, + p.from, + p.to, + p.fgColor, + p.bgColor, + p.pattern + ) // eslint-disable-next-line no-console console.log(`Unimplemented!: ${p.type}`) } diff --git a/packages/web/src/payloads/index.ts b/packages/web/src/payloads/index.ts index a0938b9a..7ef1309f 100644 --- a/packages/web/src/payloads/index.ts +++ b/packages/web/src/payloads/index.ts @@ -16,10 +16,12 @@ import {MoveBlock} from './move_block' import {SetBorder} from './set_border' import {SetCellAlignment} from './set_cell_alignment' import {SetCellFont} from './set_cell_font' +import {SetCellPatternFill} from './set_cell_pattern_fill' import {SetColVisible} from './set_col_visible' import {SetColWidth} from './set_col_width' import {SetLineAlignment} from './set_line_alignment' import {SetLineFont} from './set_line_font' +import {SetLinePatternFill} from './set_line_pattern_fill' import {SetRowHeight} from './set_row_height' import {SetRowVisible} from './set_row_visible' import {SheetRename} from './sheet_rename' @@ -42,10 +44,12 @@ export * from './move_block' export * from './set_border' export * from './set_cell_alignment' export * from './set_cell_font' +export * from './set_cell_pattern_fill' export * from './set_col_visible' export * from './set_col_width' export * from './set_line_alignment' export * from './set_line_font' +export * from './set_line_pattern_fill' export * from './set_row_height' export * from './set_row_visible' export * from './sheet_rename' @@ -76,3 +80,5 @@ export type Payload = | SetRowHeight | SetRowVisible | SheetRename + | SetLinePatternFill + | SetCellPatternFill diff --git a/packages/web/src/payloads/set_cell_pattern_fill.ts b/packages/web/src/payloads/set_cell_pattern_fill.ts new file mode 100644 index 00000000..60672e42 --- /dev/null +++ b/packages/web/src/payloads/set_cell_pattern_fill.ts @@ -0,0 +1,58 @@ +import {StPatternType} from '../bindings' + +export interface SetCellPatternFill { + readonly type: 'setCellPatternFill' + readonly sheetIdx: number + readonly row: number + readonly col: number + readonly fgColor?: string + readonly bgColor?: string + readonly pattern?: StPatternType +} + +export class SetCellPatternFillBuilder { + private _sheetIdx?: number + private _row?: number + private _col?: number + private _fgColor?: string + private _bgColor?: string + private _pattern?: StPatternType + public sheetIdx(sheetIdx: number): this { + this._sheetIdx = sheetIdx + return this + } + public row(row: number): this { + this._row = row + return this + } + public col(col: number): this { + this._col = col + return this + } + public fgColor(c: string): this { + this._fgColor = c + return this + } + public bgColor(c: string): this { + this._bgColor = c + return this + } + public pattern(p: StPatternType): this { + this._pattern = p + return this + } + public build(): SetCellPatternFill { + if (this._sheetIdx === undefined) throw Error('sheetIdx is undefined!') + if (this._row === undefined) throw Error('row is undefined!') + if (this._col === undefined) throw Error('col is undefined!') + return { + type: 'setCellPatternFill', + sheetIdx: this._sheetIdx, + row: this._row, + col: this._col, + fgColor: this._fgColor, + bgColor: this._bgColor, + pattern: this._pattern, + } + } +} diff --git a/packages/web/src/payloads/set_line_pattern_fill.ts b/packages/web/src/payloads/set_line_pattern_fill.ts new file mode 100644 index 00000000..db3096fe --- /dev/null +++ b/packages/web/src/payloads/set_line_pattern_fill.ts @@ -0,0 +1,68 @@ +import {StPatternType} from '../bindings' + +export interface SetLinePatternFill { + readonly type: 'setLinePatternFill' + readonly sheetIdx: number + readonly row: boolean + readonly from: number + readonly to: number + readonly fgColor?: string + readonly bgColor?: string + readonly pattern?: StPatternType +} + +export class SetLinePatternFillBuilder { + private _sheetIdx?: number + private _row?: boolean + private _from?: number + private _to?: number + private _fgColor?: string + private _bgColor?: string + private _pattern?: StPatternType + + public sheetIdx(sheetIdx: number): this { + this._sheetIdx = sheetIdx + return this + } + public from(v: number): this { + this._from = v + return this + } + public to(v: number): this { + this._to = v + return this + } + public row(v: boolean): this { + this._row = v + return this + } + public fgColor(v: string): this { + this._fgColor = v + return this + } + public bgColor(v: string): this { + this._bgColor = v + return this + } + public pattern(v: StPatternType): this { + this._pattern = v + return this + } + + public build(): SetLinePatternFill { + if (this._sheetIdx === undefined) throw Error('sheetIdx is undefined!') + if (this._from === undefined) throw Error('from is undefined!') + if (this._to === undefined) throw Error('to is undefined!') + if (this._row === undefined) throw Error('row is undefined!') + return { + type: 'setLinePatternFill', + sheetIdx: this._sheetIdx, + from: this._from, + to: this._to, + row: this._row, + fgColor: this._fgColor, + bgColor: this._bgColor, + pattern: this._pattern, + } + } +} diff --git a/src/components/canvas/component.tsx b/src/components/canvas/component.tsx index f472e7ae..3399558b 100644 --- a/src/components/canvas/component.tsx +++ b/src/components/canvas/component.tsx @@ -297,7 +297,7 @@ const Internal: FC = observer((props: CanvasProps) => { if (!store.selector.startCell) return setContextMenu( { items={items} close$={() => setIsOpen(false)} mouseevent={mouseevent} + ariaHideApp={false} style={{ content: { height: 'fit-content', diff --git a/src/components/top-bar/content/index.tsx b/src/components/top-bar/content/index.tsx index 067005aa..d33b27b2 100644 --- a/src/components/top-bar/content/index.tsx +++ b/src/components/top-bar/content/index.tsx @@ -21,8 +21,12 @@ import FormatAlignJustifyIcon from '@mui/icons-material/FormatAlignJustify' import ToggleButton from '@mui/material/ToggleButton' import ToggleButtonGroup from '@mui/material/ToggleButtonGroup' import Divider from '@mui/material/Divider' -import {generateAlgnmentPayload, generateFontPayload} from './payload' -import {Transaction, Alignment, HorizontalAlignment} from 'logisheets-web' +import { + generateAlgnmentPayload, + generateFontPayload, + generatePatternFillPayload, +} from './payload' +import {Transaction, HorizontalAlignment, getPatternFill} from 'logisheets-web' export * from './font-size' export * from './start-item' @@ -35,8 +39,9 @@ export interface StartProps { export const StartComponent = ({selectedData}: StartProps) => { const DATA_SERVICE = useInjection(TYPES.Data) - const [openSketchPicker, setOpenSketchPicker] = useState(false) const [fontColor, setFontColor] = useState('#000') + const [patternFillColor, setPatternFillColor] = useState('') + const [colorPicking, setColorPicking] = useState('') const [fontBold, setFontBold] = useState(false) const [fontItalic, setFontItalic] = useState(false) @@ -83,6 +88,13 @@ export const StartComponent = ({selectedData}: StartProps) => { } else { setAlignment(null) } + const patternFill = getPatternFill(style.fill) + if (patternFill && patternFill.bgColor) { + const c = StandardColor.fromCtColor(patternFill.bgColor) + setPatternFillColor(c.css()) + } else { + setPatternFillColor('#000') + } const font = StandardFont.from(style.font) setFontColor(font.standardColor.css()) setFontBold(font.bold) @@ -96,6 +108,32 @@ export const StartComponent = ({selectedData}: StartProps) => { } const onColorPick = (result: ColorResult) => { + if (colorPicking === 'font') return onFontColorPick(result) + if (colorPicking === 'fill') return onPatternFillColorPick(result) + } + + const onPatternFillColorPick = (result: ColorResult) => { + if (!selectedData) return + const {r, g, b, a} = result.rgb + const standardColor = StandardColor.from(r, g, b, a) + const payloads = generatePatternFillPayload( + DATA_SERVICE.getCurrentSheetIdx(), + selectedData, + undefined, + standardColor.argb(), + 'solid' + ) + DATA_SERVICE.handleTransaction(new Transaction(payloads, true)).then( + (resp) => { + if (!resp) { + setPatternFillColor(standardColor.css()) + setColorPicking('') + } + } + ) + } + + const onFontColorPick = (result: ColorResult) => { if (!selectedData) return const {r, g, b, a} = result.rgb const standardColor = StandardColor.from(r, g, b, a) @@ -108,7 +146,7 @@ export const StartComponent = ({selectedData}: StartProps) => { (resp) => { if (!resp) { setFontColor(standardColor.css()) - setOpenSketchPicker(false) + setColorPicking('') } } ) @@ -184,7 +222,7 @@ export const StartComponent = ({selectedData}: StartProps) => { value="font-color" size="small" aria-label="font color formatting" - onClick={() => setOpenSketchPicker(true)} + onClick={() => setColorPicking('font')} > @@ -215,10 +253,15 @@ export const StartComponent = ({selectedData}: StartProps) => { > - {/* + + setColorPicking('fill')} + > - - */} + { - + {/* - + */} setOpenSketchPicker(false)} + onRequestClose={() => setColorPicking('')} className={styles['modal-content']} overlayClassName={styles['modal-overlay']} style={{content: {top: '100px', left: '0px'}}} + ariaHideApp={false} > diff --git a/src/components/top-bar/content/payload.ts b/src/components/top-bar/content/payload.ts index 50ca22e1..1fbdafea 100644 --- a/src/components/top-bar/content/payload.ts +++ b/src/components/top-bar/content/payload.ts @@ -4,8 +4,11 @@ import { Payload, SetCellAlignmentBuilder, SetCellFontBuilder, + SetCellPatternFillBuilder, SetLineAlignmentBuilder, SetLineFontBuilder, + SetLinePatternFillBuilder, + StPatternType, } from 'logisheets-web' export interface FontStyle { @@ -39,21 +42,21 @@ export function generateFontPayload( result.push(p) } } - } else { - const d = data.data.d - const builder = new SetLineFontBuilder() - .sheetIdx(sheetIdx) - .row(d.type === 'row') - .from(d.start) - .to(d.end) - if (update.bold !== undefined) builder.bold(update.bold) - if (update.underline !== undefined) - builder.underline(update.underline ? 'single' : 'none') - if (update.italic !== undefined) builder.italic(update.italic) - if (update.color) builder.color(update.color) - const p = builder.build() - result.push(p) + return result } + const d = data.data.d + const builder = new SetLineFontBuilder() + .sheetIdx(sheetIdx) + .row(d.type === 'row') + .from(d.start) + .to(d.end) + if (update.bold !== undefined) builder.bold(update.bold) + if (update.underline !== undefined) + builder.underline(update.underline ? 'single' : 'none') + if (update.italic !== undefined) builder.italic(update.italic) + if (update.color) builder.color(update.color) + const p = builder.build() + result.push(p) return result } @@ -78,16 +81,58 @@ export function generateAlgnmentPayload( result.push(p) } } - } else { + return result + } + const d = data.data.d + const p = new SetLineAlignmentBuilder() + .sheetIdx(sheetIdx) + .row(d.type === 'row') + .from(d.start) + .to(d.end) + .alignment(alignment) + .build() + result.push(p) + + return result +} + +export function generatePatternFillPayload( + sheetIdx: number, + data: SelectedData, + fgColor?: string, + bgColor?: string, + pattern?: StPatternType +): Payload[] { + if (!data.data) return [] + const result: Payload[] = [] + const t = data.data.ty + if (t === 'cellRange') { const d = data.data.d - const p = new SetLineAlignmentBuilder() - .sheetIdx(sheetIdx) - .row(d.type === 'row') - .from(d.start) - .to(d.end) - .alignment(alignment) - .build() - result.push(p) + for (let i = d.startRow; i <= d.endRow; i += 1) { + for (let j = d.startCol; j <= d.endCol; j += 1) { + const builder = new SetCellPatternFillBuilder() + .sheetIdx(sheetIdx) + .row(i) + .col(j) + if (fgColor) builder.fgColor(fgColor) + if (bgColor) builder.bgColor(bgColor) + if (pattern) builder.pattern(pattern) + const p = builder.build() + result.push(p) + } + } + return result } + const d = data.data.d + const builder = new SetLinePatternFillBuilder() + .sheetIdx(sheetIdx) + .from(d.start) + .to(d.end) + .row(d.type === 'row') + if (fgColor) builder.fgColor(fgColor) + if (bgColor) builder.bgColor(bgColor) + if (pattern) builder.pattern(pattern) + const p = builder.build() + result.push(p) return result } diff --git a/src/ui/contextmenu/index.tsx b/src/ui/contextmenu/index.tsx index f38d55a4..b565af0f 100644 --- a/src/ui/contextmenu/index.tsx +++ b/src/ui/contextmenu/index.tsx @@ -3,9 +3,6 @@ import {DialogComponent, DialogProps} from '@/ui/dialog' import './contextmenu.scss' export interface ContextMenuProps extends DialogProps { items: readonly ContextMenuItem[] - /** - * 若需要根据鼠标事件确定contextmenu的位置,则需要传这个域 - */ mouseevent?: MouseEvent }