Store preferences by model profile
This commit is contained in:
@@ -5,7 +5,7 @@ impl App {
|
||||
pub(super) fn preferences_panel(&self) -> Element<'_, Message> {
|
||||
let legacy_mtp_toggle: Option<fn(bool) -> Message> = self
|
||||
.preference_draft
|
||||
.model
|
||||
.acceleration_model
|
||||
.supports_dspark()
|
||||
.then_some(Message::PreferenceLegacyMtpChanged);
|
||||
let legacy_mtp = hint(
|
||||
@@ -16,7 +16,7 @@ impl App {
|
||||
);
|
||||
let dspark_toggle: Option<fn(bool) -> Message> = self
|
||||
.preference_draft
|
||||
.model
|
||||
.acceleration_model
|
||||
.supports_dspark()
|
||||
.then_some(Message::PreferenceDsparkChanged);
|
||||
let dspark = hint(
|
||||
@@ -25,33 +25,44 @@ impl App {
|
||||
.on_toggle_maybe(dspark_toggle),
|
||||
"Speculative decoding with the managed DSpark draft artifact: a small model proposes tokens that the main model verifies in one pass. Usually a large speedup; the target model may also stream routed experts from SSD.",
|
||||
);
|
||||
let glm_mtp_toggle: Option<fn(bool) -> Message> = (self.preference_draft.model
|
||||
== ModelChoice::Glm52)
|
||||
.then_some(Message::PreferenceGlmMtpChanged);
|
||||
let glm_mtp_timing_toggle: Option<fn(bool) -> Message> = (self.preference_draft.model
|
||||
== ModelChoice::Glm52)
|
||||
.then_some(Message::PreferenceGlmMtpTimingChanged);
|
||||
let glm_mtp_toggle: Option<fn(bool) -> Message> =
|
||||
(self.preference_draft.acceleration_model == ModelChoice::Glm52)
|
||||
.then_some(Message::PreferenceGlmMtpChanged);
|
||||
let glm_mtp_timing_toggle: Option<fn(bool) -> Message> =
|
||||
(self.preference_draft.acceleration_model == ModelChoice::Glm52)
|
||||
.then_some(Message::PreferenceGlmMtpTimingChanged);
|
||||
let dspark_strict_toggle: Option<fn(bool) -> Message> = self
|
||||
.preference_draft
|
||||
.model
|
||||
.acceleration_model
|
||||
.supports_dspark()
|
||||
.then_some(Message::PreferenceDsparkStrictChanged);
|
||||
let effective = self
|
||||
.preference_draft
|
||||
.generation()
|
||||
.and_then(|generation| {
|
||||
self.preference_draft.runtime().and_then(|runtime| {
|
||||
crate::settings::effective_settings(
|
||||
self.preference_draft.model,
|
||||
&generation,
|
||||
&runtime,
|
||||
&models_path(),
|
||||
)
|
||||
})
|
||||
})
|
||||
.effective_for(
|
||||
self.preference_draft.model,
|
||||
self.preference_draft.default_reasoning_mode,
|
||||
)
|
||||
.ok();
|
||||
let generation_effective = self
|
||||
.preference_draft
|
||||
.effective_for(
|
||||
self.preference_draft.generation_model,
|
||||
self.preference_draft.generation_reasoning_mode,
|
||||
)
|
||||
.ok();
|
||||
let acceleration_effective = self
|
||||
.preference_draft
|
||||
.effective_for(
|
||||
self.preference_draft.acceleration_model,
|
||||
self.preference_draft
|
||||
.reasoning_mode_for(self.preference_draft.acceleration_model),
|
||||
)
|
||||
.ok();
|
||||
let engine = effective.as_ref().map(|settings| &settings.engine);
|
||||
let turn = effective.as_ref().map(|settings| &settings.turn);
|
||||
let turn = generation_effective.as_ref().map(|settings| &settings.turn);
|
||||
let acceleration_engine = acceleration_effective
|
||||
.as_ref()
|
||||
.map(|settings| &settings.engine);
|
||||
let mut power = text_input("100", &self.preference_draft.power_percent);
|
||||
let mut prefill = text_input("Automatic", &self.preference_draft.prefill_chunk);
|
||||
let mut ssd_full_layers = text_input("Automatic", &self.preference_draft.ssd_full_layers);
|
||||
@@ -72,10 +83,11 @@ impl App {
|
||||
steering_file = steering_file.on_input(Message::PreferenceSteeringFileChanged);
|
||||
steering_ffn = steering_ffn.on_input(Message::PreferenceSteeringFfnChanged);
|
||||
steering_attn = steering_attn.on_input(Message::PreferenceSteeringAttnChanged);
|
||||
} else {
|
||||
}
|
||||
if self.preference_draft.acceleration_model == ModelChoice::Glm52 {
|
||||
ssd_full_layers = ssd_full_layers.on_input(Message::PreferenceSsdFullLayersChanged);
|
||||
}
|
||||
if self.preference_draft.model.supports_dspark() {
|
||||
if self.preference_draft.acceleration_model.supports_dspark() {
|
||||
dspark_confidence =
|
||||
dspark_confidence.on_input(Message::PreferenceDsparkConfidenceChanged);
|
||||
}
|
||||
@@ -93,6 +105,20 @@ impl App {
|
||||
.width(Length::Fill),
|
||||
"Which local weights the Metal engine loads for chats and for the HTTP endpoint. The choice decides which accelerations below apply, and the matching artifacts must be downloaded in the model manager.",
|
||||
),
|
||||
row![
|
||||
hint(
|
||||
text("Default thinking mode").size(13).width(Length::Fill),
|
||||
"Thinking mode selected when this model becomes active. Chat can switch it for later turns.",
|
||||
),
|
||||
pick_list(
|
||||
&REASONING_MODES[..],
|
||||
Some(self.preference_draft.default_reasoning_mode),
|
||||
Message::PreferenceDefaultReasoningChanged,
|
||||
)
|
||||
.width(240),
|
||||
]
|
||||
.spacing(12)
|
||||
.align_y(Alignment::Center),
|
||||
text(format!(
|
||||
"Main: {}{}",
|
||||
engine.map_or_else(
|
||||
@@ -282,10 +308,49 @@ impl App {
|
||||
]
|
||||
.spacing(10),
|
||||
);
|
||||
let prompt_group = preference_group(
|
||||
PreferenceSection::Prompt,
|
||||
"PROMPT",
|
||||
column![
|
||||
hint(
|
||||
text("System prompt").size(13),
|
||||
"Standing instruction sent before every conversation: persona, tone, house rules. Leave it empty to send no system message at all.",
|
||||
),
|
||||
text_editor(&self.preference_draft.system_prompt)
|
||||
.placeholder("Additional system instructions…")
|
||||
.height(140)
|
||||
.on_action(Message::PreferenceSystemPromptAction)
|
||||
.padding(9),
|
||||
text("The system prompt is shared by every model and thinking mode.").size(12),
|
||||
]
|
||||
.spacing(10),
|
||||
);
|
||||
let generation_group = preference_group(
|
||||
PreferenceSection::Generation,
|
||||
"GENERATION",
|
||||
column![
|
||||
row![
|
||||
text("Model").size(13).width(Length::Fill),
|
||||
pick_list(
|
||||
&MODEL_CHOICES[..],
|
||||
Some(self.preference_draft.generation_model),
|
||||
Message::PreferenceGenerationModelChanged,
|
||||
)
|
||||
.width(400),
|
||||
]
|
||||
.spacing(12)
|
||||
.align_y(Alignment::Center),
|
||||
row![
|
||||
text("Thinking mode").size(13).width(Length::Fill),
|
||||
pick_list(
|
||||
&REASONING_MODES[..],
|
||||
Some(self.preference_draft.generation_reasoning_mode),
|
||||
Message::PreferenceGenerationReasoningChanged,
|
||||
)
|
||||
.width(240),
|
||||
]
|
||||
.spacing(12)
|
||||
.align_y(Alignment::Center),
|
||||
preference_input_row(
|
||||
"Context tokens",
|
||||
"Size of the window the model can see: system prompt, history, the new question and the answer all have to fit. Larger windows allow longer sessions but reserve much more memory for the key-value cache.",
|
||||
@@ -298,17 +363,7 @@ impl App {
|
||||
text_input("50000", &self.preference_draft.max_generated_tokens)
|
||||
.on_input(Message::PreferenceMaxTokensChanged),
|
||||
),
|
||||
hint(
|
||||
text("System prompt").size(13),
|
||||
"Standing instruction sent before every conversation: persona, tone, house rules. Leave it empty to send no system message at all.",
|
||||
),
|
||||
text_editor(&self.preference_draft.system_prompt)
|
||||
.placeholder("Additional system instructions…")
|
||||
.height(140)
|
||||
.on_action(Message::PreferenceSystemPromptAction)
|
||||
.padding(9),
|
||||
Space::new().height(4),
|
||||
text("SAMPLING & REASONING").size(11).color(muted_text()),
|
||||
text("SAMPLING").size(11).color(muted_text()),
|
||||
preference_input_row(
|
||||
"Temperature",
|
||||
"How adventurous token choice is. Near 0 the model repeats the most likely continuation, which suits code and extraction; higher values invent more and drift more.",
|
||||
@@ -333,20 +388,6 @@ impl App {
|
||||
text_input("Random", &self.preference_draft.seed)
|
||||
.on_input(Message::PreferenceSeedChanged),
|
||||
),
|
||||
row![
|
||||
hint(
|
||||
text("Reasoning").size(13).width(Length::Fill),
|
||||
"How much hidden thinking precedes the answer. Direct skips it and replies fastest, Thinking is the balanced default, Think Max reasons longest and needs at least 393216 context tokens.",
|
||||
),
|
||||
pick_list(
|
||||
&REASONING_MODES[..],
|
||||
Some(self.preference_draft.reasoning_mode),
|
||||
Message::PreferenceReasoningChanged,
|
||||
)
|
||||
.width(240),
|
||||
]
|
||||
.spacing(12)
|
||||
.align_y(Alignment::Center),
|
||||
text("Blank sampling values retain DS4's model-family defaults. Think Max needs at least 393216 context tokens.")
|
||||
.size(12),
|
||||
text(turn.map_or_else(
|
||||
@@ -428,6 +469,17 @@ impl App {
|
||||
PreferenceSection::Acceleration,
|
||||
"ACCELERATION & MEMORY",
|
||||
column![
|
||||
row![
|
||||
text("Model").size(13).width(Length::Fill),
|
||||
pick_list(
|
||||
&MODEL_CHOICES[..],
|
||||
Some(self.preference_draft.acceleration_model),
|
||||
Message::PreferenceAccelerationModelChanged,
|
||||
)
|
||||
.width(400),
|
||||
]
|
||||
.spacing(12)
|
||||
.align_y(Alignment::Center),
|
||||
text("SPECULATIVE DECODING").size(11).color(muted_text()),
|
||||
preference_input_row(
|
||||
"MTP draft tokens",
|
||||
@@ -466,15 +518,15 @@ impl App {
|
||||
.on_toggle_maybe(dspark_strict_toggle),
|
||||
"Lets the draft model only propose, never decide: every token is sampled by the full model. Gives up some of the speedup in exchange for output identical to non-speculative decoding.",
|
||||
),
|
||||
text(if self.preference_draft.model.supports_dspark() {
|
||||
text(if self.preference_draft.acceleration_model.supports_dspark() {
|
||||
"Legacy MTP and DSpark use separate managed support artifacts; entering a DSpark threshold or enabling strict mode selects DSpark."
|
||||
} else if self.preference_draft.model == ModelChoice::Glm52 {
|
||||
} else if self.preference_draft.acceleration_model == ModelChoice::Glm52 {
|
||||
"GLM MTP is integrated; DSpark is unavailable for this model."
|
||||
} else {
|
||||
"No managed MTP support artifact is available for this model."
|
||||
})
|
||||
.size(12),
|
||||
text(engine.as_ref().map_or_else(
|
||||
text(acceleration_engine.map_or_else(
|
||||
|| "Effective speculative settings will appear after valid values are entered."
|
||||
.to_owned(),
|
||||
|engine| {
|
||||
@@ -527,7 +579,7 @@ impl App {
|
||||
),
|
||||
text("A blank full-layer value is automatic; an explicit 0 disables fully resident GLM layers. Flash legacy MTP and DSpark support weights remain resident when target experts stream.")
|
||||
.size(12),
|
||||
text(engine.as_ref().map_or_else(
|
||||
text(acceleration_engine.map_or_else(
|
||||
|| "Effective SSD settings will appear after valid values are entered."
|
||||
.to_owned(),
|
||||
|engine| {
|
||||
@@ -680,6 +732,7 @@ impl App {
|
||||
endpoint_group,
|
||||
dev_brain_group,
|
||||
git_group,
|
||||
prompt_group,
|
||||
generation_group,
|
||||
execution_group,
|
||||
acceleration_group,
|
||||
|
||||
Reference in New Issue
Block a user